<?php
namespace App\Http\Controller\User;
use App\Application\CommandBus\Command\ToastSession\ShareToastSessionCommand;
use App\Application\CommandBus\Command\ToastSessionLink\CreateToastSessionLinkCommand;
use App\Database\Domain\Entity\Sessions\Collaborators\CollaboratedSession;
use App\Database\Domain\Entity\Sessions\ToastSession;
use App\Database\Domain\Entity\Sessions\ToastSessionLink;
use App\Database\Domain\Entity\User\User;
use App\Database\Domain\Entity\User\UserStripeMember;
use App\Database\Domain\Repository\CollaboratedSessionRepository;
use App\Database\Domain\Repository\ToastSessionRepository;
use App\Infrastructure\Messenger\CommandBus\CommandBusInterface;
use App\Infrastructure\Security\Voter\ToastSessionLinkVoter;
use App\Infrastructure\Security\Voter\ToastSessionVoter;
use App\Infrastructure\Service\ActionResponseHandler;
use App\Infrastructure\Service\SiteParser;
use App\Infrastructure\Service\StripeHelper;
use App\Infrastructure\Util\ExceptionMessage;
use App\Infrastructure\Util\Identifier;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\Routing\Annotation\Route;
/**
* @Route("/user/sessions", name="user_sessions_")
*/
class SessionsController extends AbstractController
{
/**
* @Route("", name="index")
*/
public function __invoke(Request $request, CollaboratedSessionRepository $collaboratedSessionRepository, ToastSessionRepository $toastSessionRepository, EntityManagerInterface $em, StripeHelper $stripeHelper): Response
{
/** @var User $user */
$user = $this->getUser();
$sessions = $user->getSessions();
/** @var CollaboratedSession[] $collaboratedSessions */
$collaboratedSessions = $collaboratedSessionRepository->findBy(['collaboratedUser' => $user]);
$ids = [];
foreach ($collaboratedSessions as $collaboratedSession) {
$ids[] = $collaboratedSession->getSession()->getId();
}
$notThisOwnerSessions = $toastSessionRepository->findBy(['id' => $ids]);
foreach ($notThisOwnerSessions as $notThisOwnerSession) {
foreach ($collaboratedSessions as $collaboratedSession) {
if ($collaboratedSession->getSession()->getId() === $notThisOwnerSession->getId()) {
$notThisOwnerSession->setOrderIndex($collaboratedSession->getOrderIndex());
$notThisOwnerSession->collaborated = true;
}
}
}
if (!is_array($sessions)) {
$sessions = $sessions->toArray();
}
$sessions = [...$notThisOwnerSessions, ...$sessions];
usort($sessions, function ($a, $b) {
return $a->getOrderIndex() <=> $b->getOrderIndex();
});
$isFirstView = $request->query->get('source');
if ($isFirstView == 'registered') {
$isFirstView = true;
} else {
$isFirstView = false;
}
// Stripe subscription table
if (!$user->getStripeMember()) {
$customer = $stripeHelper->registerMember($user);
$stripeMember = new UserStripeMember(Identifier::generate(), $customer['id']);
$user->setStripeMember($stripeMember);
$em->persist($stripeMember);
$em->flush();
}
$subscriptionSession = $stripeHelper->invokeSubscriptionTableSession($user);
// Stripe subscription table
return $this->render('user/sessions.html.twig', [
'sharing_status_success' => $request->getSession()->get('sharing_status_success', false),
'sharing_errors' => $request->getSession()->get('sharing.errors', null),
'sessions' => $sessions,
'first_view' => $isFirstView,
'appleReviewMode' => true,
'secret' => $subscriptionSession->client_secret,
'table_id' => $user->getMembership()->isAllowedTrial() ? $_ENV['STRIPE_PRICING_TABLE_WITH_TRIAL'] : $_ENV['STRIPE_PRICING_TABLE_WITHOUT_TRIAL'],
'key' => $stripeHelper->publicKey,
]);
}
/**
* @Route("/profile", name="profile")
*/
public function profile(Request $request, EntityManagerInterface $em, StripeHelper $stripeHelper): Response
{
/** @var User $user */
$user = $this->getUser();
// Stripe subscription table
if (!$user->getStripeMember()) {
$customer = $stripeHelper->registerMember($user);
$stripeMember = new UserStripeMember(Identifier::generate(), $customer['id']);
$user->setStripeMember($stripeMember);
$em->persist($stripeMember);
$em->flush();
}
$subscriptionSession = $stripeHelper->invokeSubscriptionTableSession($user);
// Stripe subscription table
return $this->render('user/sessions.html.twig', [
'sharing_status_success' => $request->getSession()->get('sharing_status_success', false),
'sharing_errors' => $request->getSession()->get('sharing.errors', null),
'sessions' => $user->getSessions(),
'first_view' => false,
'appleReviewMode' => true,
'secret' => $subscriptionSession->client_secret,
'table_id' => $user->getMembership()->isAllowedTrial() ? $_ENV['STRIPE_PRICING_TABLE_WITH_TRIAL'] : $_ENV['STRIPE_PRICING_TABLE_WITHOUT_TRIAL'],
'key' => $stripeHelper->publicKey,
]);
}
/**
* @Route("/bonus", name="bonus")
*/
public function getbonus(Request $request, EntityManagerInterface $em, StripeHelper $stripeHelper): Response
{
/** @var User $user */
$user = $this->getUser();
// Stripe subscription table
if (!$user->getStripeMember()) {
$customer = $stripeHelper->registerMember($user);
$stripeMember = new UserStripeMember(Identifier::generate(), $customer['id']);
$user->setStripeMember($stripeMember);
$em->persist($stripeMember);
$em->flush();
}
$subscriptionSession = $stripeHelper->invokeSubscriptionTableSession($user);
// Stripe subscription table
return $this->render('user/sessions.html.twig', [
'sharing_status_success' => $request->getSession()->get('sharing_status_success', false),
'sharing_errors' => $request->getSession()->get('sharing.errors', null),
'sessions' => $user->getSessions(),
'first_view' => false,
'appleReviewMode' => true,
'secret' => $subscriptionSession->client_secret,
'table_id' => $user->getMembership()->isAllowedTrial() ? $_ENV['STRIPE_PRICING_TABLE_WITH_TRIAL'] : $_ENV['STRIPE_PRICING_TABLE_WITHOUT_TRIAL'],
'key' => $stripeHelper->publicKey,
]);
}
/**
* @Route("/upgrade", name="upgrade")
*/
public function upgrade(Request $request, EntityManagerInterface $em, StripeHelper $stripeHelper): Response
{
/** @var User $user */
$user = $this->getUser();
// Stripe subscription table
if (!$user->getStripeMember()) {
$customer = $stripeHelper->registerMember($user);
$stripeMember = new UserStripeMember(Identifier::generate(), $customer['id']);
$user->setStripeMember($stripeMember);
$em->persist($stripeMember);
$em->flush();
}
$subscriptionSession = $stripeHelper->invokeSubscriptionTableSession($user);
// Stripe subscription table
return $this->render('user/sessions.html.twig', [
'sharing_status_success' => $request->getSession()->get('sharing_status_success', false),
'sharing_errors' => $request->getSession()->get('sharing.errors', null),
'sessions' => $user->getSessions(),
'first_view' => false,
'appleReviewMode' => true,
'secret' => $subscriptionSession->client_secret,
'table_id' => $user->getMembership()->isAllowedTrial() ? $_ENV['STRIPE_PRICING_TABLE_WITH_TRIAL'] : $_ENV['STRIPE_PRICING_TABLE_WITHOUT_TRIAL'],
'key' => $stripeHelper->publicKey,
]);
}
/**
* @Route("/synchronization", name="synchronization")
*/
public function synchronization(Request $request): Response
{
/** @var User $user */
$user = $this->getUser();
return $this->render('user/synchronization.html.twig', [
'sharing_status_success' => $request->getSession()->get('sharing_status_success', false),
'sharing_errors' => $request->getSession()->get('sharing.errors', null),
'sessions' => $user->getSessions(),
'first_view' => false,
'appleReviewMode' => true,
'secret' => $subscriptionSession->client_secret,
'table_id' => $user->getMembership()->isAllowedTrial() ? $_ENV['STRIPE_PRICING_TABLE_WITH_TRIAL'] : $_ENV['STRIPE_PRICING_TABLE_WITHOUT_TRIAL'],
'key' => $stripeHelper->publicKey,
]);
}
/**
* @Route("/subscribed", name="subscribed")
*/
public function subscribed(Request $request, EntityManagerInterface $em, StripeHelper $stripeHelper): Response
{
/** @var User $user */
$user = $this->getUser();
// Stripe subscription table
if (!$user->getStripeMember()) {
$customer = $stripeHelper->registerMember($user);
$stripeMember = new UserStripeMember(Identifier::generate(), $customer['id']);
$user->setStripeMember($stripeMember);
$em->persist($stripeMember);
$em->flush();
}
$subscriptionSession = $stripeHelper->invokeSubscriptionTableSession($user);
// Stripe subscription table
return $this->render('user/sessions.html.twig', [
'sharing_status_success' => $request->getSession()->get('sharing_status_success', false),
'sharing_errors' => $request->getSession()->get('sharing.errors', null),
'sessions' => $user->getSessions(),
'first_view' => false,
'appleReviewMode' => true,
'secret' => $subscriptionSession->client_secret,
'table_id' => $user->getMembership()->isAllowedTrial() ? $_ENV['STRIPE_PRICING_TABLE_WITH_TRIAL'] : $_ENV['STRIPE_PRICING_TABLE_WITHOUT_TRIAL'],
'key' => $stripeHelper->publicKey,
]);
}
/**
* @Route("/{id}", name="show")
*/
public function showSession(string $id, Request $request, ToastSessionRepository $toastSessionRepository, EntityManagerInterface $em, StripeHelper $stripeHelper): Response
{
$session = $toastSessionRepository->find($id);
/** @var User $user */
$user = $this->getUser();
// Stripe subscription table
if (!$user->getStripeMember()) {
$customer = $stripeHelper->registerMember($user);
$stripeMember = new UserStripeMember(Identifier::generate(), $customer['id']);
$user->setStripeMember($stripeMember);
$em->persist($stripeMember);
$em->flush();
}
$subscriptionSession = $stripeHelper->invokeSubscriptionTableSession($user);
// Stripe subscription table
return $this->render('user/sessions.html.twig', [
'sharing_status_success' => $request->getSession()->get('sharing_status_success', false),
'sharing_errors' => $request->getSession()->get('sharing.errors', null),
'sessions' => $user->getSessions(),
'session' => $session,
'first_view' => false,
'appleReviewMode' => true,
'secret' => $subscriptionSession->client_secret,
'table_id' => $user->getMembership()->isAllowedTrial() ? $_ENV['STRIPE_PRICING_TABLE_WITH_TRIAL'] : $_ENV['STRIPE_PRICING_TABLE_WITHOUT_TRIAL'],
'key' => $stripeHelper->publicKey,
]);
}
/**
* @Route("/{id}/remove", name="remove", methods={"GET"})
*/
public function removeSession(ToastSession $session, EntityManagerInterface $em): Response
{
$this->denyAccessUnlessGranted(ToastSessionVoter::ACCESS, $session);
$em->remove($session);
$em->flush();
return $this->redirectToRoute('user_sessions_index');
}
/**
* @Route("/links/{id}/remove", name="remove_link")
*/
public function removeLink(ToastSessionLink $link, EntityManagerInterface $em): \Symfony\Component\HttpFoundation\RedirectResponse
{
$this->denyAccessUnlessGranted(ToastSessionLinkVoter::ACCESS, $link);
$em->remove($link);
$em->flush();
return $this->redirectToRoute('user_sessions_index');
}
/**
* @Route("/{id}/invoke-sharing", name="invoke_sharing", methods={"POST"})
*/
public function invokeSessionSharing(
ToastSession $session,
CommandBusInterface $commandBus,
Request $request,
ActionResponseHandler $actionResponseHandler
): Response {
$command = new ShareToastSessionCommand();
$command->session = $session->getId();
$command->recipient = $request->request->get('email');
try {
$commandBus->execute($command);
} catch (\Exception $e) {
return $actionResponseHandler->errorRedirect('user_sessions_index', ExceptionMessage::getMessage($e));
}
return $actionResponseHandler->successRedirect('user_sessions_index', 'Session is successfully shared');
}
/**
* @Route("/{id}/rename", name="rename")
*/
public function renameSession(
Request $request,
ToastSession $session,
EntityManagerInterface $em,
ActionResponseHandler $actionResponseHandler
): Response {
$this->denyAccessUnlessGranted(ToastSessionVoter::ACCESS, $session);
$session->setName($request->request->get('name'));
$em->persist($session);
$em->flush();
return $actionResponseHandler->successRedirect('user_sessions_index', 'Success');
}
/**
* @Route("/{id}/links/add", name="add_link", methods={"POST"})
*/
public function addSessionLink(
Request $request,
CommandBusInterface $commandBus,
ToastSession $session,
ActionResponseHandler $actionResponseHandler
): Response {
$url = $request->request->get('url');
$siteParser = new SiteParser($url);
$command = new CreateToastSessionLinkCommand();
$command->id = Identifier::generate();
$command->name = $siteParser->getPageTitle();
$command->icon = $siteParser->getFavicon();
$command->url = $url;
$command->session = $session->getId();
try {
$commandBus->execute($command);
} catch (\Exception $e) {
return $actionResponseHandler->errorRedirect('user_sessions_index', ExceptionMessage::getMessage($e));
}
return $actionResponseHandler->successRedirect('user_sessions_index', 'Success');
}
}