<?php
declare(strict_types=1);
namespace App\EventListener;
use App\Repository\Blog\ArticleCategoryRepository;
use App\Repository\Blog\ArticleRepository;
use App\Repository\Cms\PageRepository;
use App\Repository\Product\ProductRepository;
use App\Repository\Taxon\TaxonRepository;
use Sylius\Component\Channel\Context\ChannelContextInterface;
use Sylius\Component\Locale\Context\LocaleContextInterface;
use Symfony\Component\HttpFoundation\RequestStack;
use Symfony\Component\HttpFoundation\Session\Flash\FlashBag;
use Symfony\Component\HttpKernel\Event\RequestEvent;
use Symfony\Component\Security\Core\Authorization\AuthorizationCheckerInterface;
use Xynnn\GoogleTagManagerBundle\Service\GoogleTagManagerInterface;
final class GtmRouteListener
{
private GoogleTagManagerInterface $googleTagManager;
private PageRepository $pageRepo;
private ChannelContextInterface $channelContext;
private LocaleContextInterface $localeContext;
private TaxonRepository $taxonRepo;
private FlashBag $flashBag;
private ProductRepository $productRepo;
private AuthorizationCheckerInterface $authorizationCheckerInterface;
private RequestStack $requestStack;
public function __construct(ChannelContextInterface $channelContext, LocaleContextInterface $localeContext, GoogleTagManagerInterface $googleTagManager, PageRepository $pageRepo, TaxonRepository $taxonRepo, ProductRepository $productRepo, /* ArticleRepository $articleBlogRepo, ArticleCategoryRepository $articleCatBlogRepo, */ FlashBag $flashBag, AuthorizationCheckerInterface $authorizationCheckerInterface, RequestStack $requestStack)
{
$this->googleTagManager = $googleTagManager;
$this->pageRepo = $pageRepo;
$this->channelContext = $channelContext;
$this->localeContext = $localeContext;
$this->taxonRepo = $taxonRepo;
$this->flashBag = $flashBag;
$this->productRepo = $productRepo;
$this->authorizationCheckerInterface = $authorizationCheckerInterface;
$this->requestStack = $requestStack;
}
public function onKernelRequest(RequestEvent $event): void
{
if (!$event->isMasterRequest())
{
return;
}
// Pas de suite si le code de GoogleTagManager n'est pas ajouté en BO
if ($this->channelContext->getChannel()->getGoogleTagManagerId() === null)
{
return;
}
// Par défaut
$sPageCategory1 = '';
$sPageCategory2 = '';
$sPageCategory3 = '';
$sPageName = $event->getRequest()->getPathInfo();
$sLoginStatus = ($this->authorizationCheckerInterface->isGranted('IS_AUTHENTICATED_FULLY')) ? 'true' : 'false';
switch ($event->getRequest()->get('_route'))
{
case 'sylius_shop_homepage':
// Succès de la page contact
$flashSuccess = $this->flashBag->peekAll();
if (!empty($flashSuccess))
{
foreach ($flashSuccess as $key => $val)
{
if ($key == 'success')
{
foreach ($val as $flash)
{
if ($flash == 'sylius.contact.request_success')
{
$sPageCategory1 = 'contact';
$sPageCategory2 = 'form';
$sPageCategory3 = 'form completed';
$sPageName = '/contact/form/completed';
break;
}
}
}
}
}
if ($sPageCategory1 == '')
{
// Homepage
$sPageCategory1 = 'homepage';
$sPageCategory2 = '';
$sPageCategory3 = '';
$sPageName = '/homepage';
}
break;
case 'monsieurbiz_sylius_search_taxon':
// Catégorie
$sSlug = str_replace('/categorie/', '', $sPageName);
$sSlug = str_replace('/taxons/', '', $sPageName);
$taxon = $this->taxonRepo->findOneBySlug($sSlug, $this->localeContext->getLocaleCode());
if (!empty($taxon))
{
$sPageCategory1 = ($taxon->getParent()) ? $taxon->getParent()->getName() : '';
$sPageCategory2 = 'categorie';
$sPageCategory3 = $taxon->getName();
if ($sPageCategory1 == 'Categories')
{
$sPageCategory1 = $sPageCategory3;
$sPageCategory3 = '';
}
}
break;
case 'sylius_shop_product_show':
// Produit
$sSlug = str_replace('/produit/', '', $sPageName);
$sSlug = str_replace('/products/', '', $sPageName);
$product = $this->productRepo->findOneBySlug($this->localeContext->getLocaleCode(), $this->channelContext->getChannel(), $sSlug);
if (!empty($product))
{
$taxon = $product->getMainTaxon();
if ($taxon) {
$sPageCategory1 = ($product && $taxon->getParent()) ? $taxon->getParent()->getName() : '';
$sPageCategory2 = 'produit';
$sPageCategory3 = $taxon->getName();
}
}
break;
case 'bitbag_sylius_cms_plugin_shop_page_show':
// Pages
$sSlug = str_replace('/page/', '', $sPageName);
$page = $this->pageRepo->findOneBySectionCodeAndChannelCodeAndSlug('', $this->localeContext->getLocaleCode(), $this->channelContext->getChannel()->getCode(), $sSlug);
if (!empty($page))
{
$sections = reset($page)->getSections()->toArray();
if (!empty($sections))
{
$sPageCategory1 = reset($sections)->getName();
}
else
{
$sPageCategory1 = reset($page)->getName();
}
$sPageCategory2 = 'content page';
$sPageCategory3 = reset($page)->getName();
}
break;
case 'sylius_shop_contact_request':
// Page contact
$sPageCategory1 = 'contact';
$sPageCategory2 = 'form';
$sPageCategory3 = 'form started';
$sPageName = '/contact/form/started';
break;
case 'sylius_shop_login':
// Page login
$sPageCategory1 = 'login';
$sPageCategory2 = '';
$sPageCategory3 = '';
$sPageName = '/contact/form/started';
break;
case 'sylius_shop_register':
// Page inscription
$sPageCategory1 = 'register';
$sPageCategory2 = 'account-creation';
$sPageCategory3 = 'step0';
break;
case 'app_shop_register_from_cart':
// Page inscription depuis le panier
$sPageCategory1 = 'register';
$sPageCategory2 = 'account-creation';
$sPageCategory3 = 'step1';
$sPageName = '/register/account-creation/step1';
break;
case 'app_shop_choice_login':
// Page inscription succès depuis le panier
$flashSuccess = $this->flashBag->peekAll();
if (!empty($flashSuccess))
{
foreach ($flashSuccess as $key => $val)
{
if ($key == 'success')
{
foreach ($val as $flash)
{
if ($flash == 'sylius.customer.register')
{
$sPageCategory1 = 'register';
$sPageCategory2 = 'account-creation';
$sPageCategory3 = 'step2';
$sPageName = '/register/account-creation/step2';
}
}
}
}
}
break;
case 'monsieurbiz_sylius_search_search':
case 'monsieurbiz_sylius_search_post':
// Page recherche
$sRecherche = htmlspecialchars(urldecode(str_replace('/search/', '', $sPageName)));
$sPageCategory1 = 'search';
$sPageCategory2 = $sRecherche;
$sPageCategory3 = '';
break;
/*
case 'odiseo_sylius_blog_plugin_shop_article_index':
// Blog index
$sPageCategory1 = 'blog';
$sPageCategory2 = 'index';
break;
case 'odiseo_sylius_blog_plugin_shop_article_index_by_category':
// Blog categ
$sPageCategory1 = 'blog';
$sPageCategory2 = 'categorie';
$sSlug = str_replace('/blog/articles/category/', '', $sPageName);
$category = $this->articleCatBlogRepo->findOneByCategorySlug($this->localeContext->getLocaleCode(), $sSlug);
if (!empty($category))
{
$sPageCategory3 = $category->getTitle();
}
break;
case 'odiseo_sylius_blog_plugin_shop_article_show':
// Blog article
$sPageCategory1 = 'blog';
$sPageCategory2 = 'article';
$sSlug = str_replace('/blog/articles/', '', $sPageName);
$article = $this->articleBlogRepo->findOneBySlugAndChannel($sSlug, $this->localeContext->getLocaleCode(), $this->channelContext->getChannel()->getCode());
if (!empty($article))
{
$sPageCategory3 = $article->getTitle();
}
break;
*/
default:
// dump($event->getRequest()->get('_route'));
// exit;
}
$this->googleTagManager->setData('pageCategory1', $this->replace_accents($sPageCategory1));
$this->googleTagManager->setData('pageCategory2', $this->replace_accents($sPageCategory2));
$this->googleTagManager->setData('pageCategory3', $this->replace_accents($sPageCategory3));
$this->googleTagManager->setData('pageName', $sPageName);
// Utilise session pour être affiché qu'une fois
if ($sLoginStatus == 'true')
{
$session = $this->requestStack->getSession();
if ($session->get('loginStatus') === null)
{
$this->googleTagManager->setData('login_status', $sLoginStatus);
$session->set('loginStatus', true);
}
}
}
private function replace_accents($str)
{
$str = htmlentities($str, ENT_COMPAT, 'UTF-8');
$str = preg_replace('/&([a-zA-Z])(uml|acute|grave|circ|tilde|ring);/', '$1', $str);
return html_entity_decode($str);
}
}