<?php
namespace B2bSellersCore\Components\B2bPlatform\Subscriber;
use B2bSellersCore\Components\B2bPlatform\Traits\B2bContextTrait;
use B2bSellersCore\Components\Employee\Aggregate\EmployeeCustomer\EmployeeCustomerCollection;
use B2bSellersCore\Storefront\Page\B2bSelectEmployeeAdministrator\B2bSelectEmployeeAdministratorPage;
use LogicException;
use Shopware\Core\Framework\Adapter\Translation\AbstractTranslator;
use Shopware\Core\Framework\DataAbstractionLayer\EntityRepositoryInterface;
use Shopware\Core\Framework\DataAbstractionLayer\Search\Criteria;
use Shopware\Core\Framework\DataAbstractionLayer\Search\Filter\EqualsFilter;
use Shopware\Core\Framework\Struct\ArrayStruct;
use Shopware\Core\System\SystemConfig\SystemConfigService;
use Shopware\Storefront\Event\StorefrontRenderEvent;
use Symfony\Component\DependencyInjection\ContainerInterface;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpFoundation\Exception\SessionNotFoundException;
class StorefrontSubscriber implements EventSubscriberInterface
{
use B2bContextTrait;
private const B2B_PLATFORM_CONFIG_BLACKLIST = ['username', 'password', 'accessKey', 'relativeDocumentPath'];
private SystemConfigService $configService;
private EntityRepositoryInterface $employeeCustomerRepository;
private ContainerInterface $container;
private AbstractTranslator $translator;
public function __construct(
SystemConfigService $configService,
EntityRepositoryInterface $employeeCustomerRepository,
ContainerInterface $container,
AbstractTranslator $translator
)
{
$this->configService = $configService;
$this->employeeCustomerRepository = $employeeCustomerRepository;
$this->container = $container;
$this->translator = $translator;
}
public static function getSubscribedEvents(): array
{
return [
StorefrontRenderEvent::class => [
['addB2bPlatformConfig'],
['checkForEmployeeAdmins']
]
];
}
public function addB2bPlatformConfig(StorefrontRenderEvent $event)
{
$context = $event->getSalesChannelContext();
$config = [];
if (!empty($this->configService->get('B2bSellersCore.config', $context->getSalesChannelId()))) {
$config = array_diff_key(
$this->configService->get('B2bSellersCore.config', $context->getSalesChannelId()),
array_flip(self::B2B_PLATFORM_CONFIG_BLACKLIST)
);
}
$event->setParameter('b2bPlatformConfig', new ArrayStruct($config));
if (!$context->getCustomer()) {
$event->setParameter('isSalesRepresentative', false);
$event->setParameter('loggedInAsCustomer', false);
$event->setParameter('isEmployee', false);
$event->setParameter('employee', null);
$event->setParameter('contactPerson', null);
return;
}
if (!$this->hasB2bPlatformContext($context)) {
return;
}
$b2bPlatformContext = $this->getB2bPlatformContext($context);
$event->setParameter('isSalesRepresentative', $b2bPlatformContext->isSalesRepresentative());
$event->setParameter('loggedInAsCustomer', $this->isSalesRepresentativeLoggedInAsCustomer($context));
$event->setParameter('isEmployee', $b2bPlatformContext->isEmployee());
$event->setParameter('employee', $b2bPlatformContext->getEmployee());
$event->setParameter('contactPerson', $b2bPlatformContext->getContactPerson());
}
public function checkForEmployeeAdmins(StorefrontRenderEvent $event): void
{
$context = $event->getSalesChannelContext();
if (!$this->hasB2bPlatformContext($context)) {
return;
}
if (isset($event->getParameters()['page']) && $event->getParameters()['page'] instanceof B2bSelectEmployeeAdministratorPage) {
return;
}
$criteria = new Criteria();
$criteria->addFilter(new EqualsFilter('customerId', $context->getCustomer()->getId()));
/** @var EmployeeCustomerCollection $employeeCustomers */
$employeeCustomers = $this->employeeCustomerRepository->search($criteria, $context->getContext())->getEntities();
if ($employeeCustomers->count() > 0 && $employeeCustomers->getAdmins()->count() <= 0) {
$this->container->get('session')->getFlashBag()->clear();
if ($this->getEmployee($context) !== null) {
if ($this->getEmployee($context)->getEmail() == $context->getCustomer()->getEmail()) {
$this->addFlash('danger', $this->translator->trans('b2bPlatform.employee.messages.noEmployeeAdminMailSameCustomerError'));
return;
}
}
$this->addFlash('danger', $this->translator->trans('b2bPlatform.employee.messages.noEmployeeAdminError', ['%mail%' => $context->getCustomer()->getEmail()]));
}
}
/**
* Adds a flash message to the current session for type.
*
* @throws LogicException
*/
protected function addFlash(string $type, $message): void
{
try {
$this->container->get('session')->getFlashBag()->add($type, $message);
} catch (SessionNotFoundException $e) {
throw new LogicException('You can not use the addFlash method if sessions are disabled. Enable them in "config/packages/framework.yaml".', 0, $e);
}
}
}