<?php declare(strict_types=1);
namespace GlobusSW6\Subscriber;
use GlobusSW6\Core\Content\Attributes\Product\Aggregate\ProductReview\ProductReviewAttributesEntity;
use GlobusSW6\Core\Content\ProductRatings\VoteRatingsEntity;
use GlobusSW6\Service\IaneoBusinessExtension;
use GlobusSW6\Service\ProductReviewAndRatingService;
use Shopware\Core\Content\Product\Aggregate\ProductReview\ProductReviewEntity;
use Shopware\Core\Content\Product\ProductCollection;
use Shopware\Core\Framework\Api\Context\AdminApiSource;
use Shopware\Core\Framework\Api\Context\SystemSource;
use Shopware\Core\Framework\DataAbstractionLayer\Event\EntityLoadedEvent;
use Shopware\Core\Framework\DataAbstractionLayer\Event\EntitySearchResultLoadedEvent;
use Shopware\Core\Framework\Struct\ArrayStruct;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
class ProductReviewAndRatingSubscriber implements EventSubscriberInterface
{
/** @var ProductReviewAndRatingService */
private $productReviewAndRatingService;
/** @var IaneoBusinessExtension */
private $ianeoBusinessExtensionService;
public function __construct(ProductReviewAndRatingService $productReviewAndRatingService, IaneoBusinessExtension $ianeoBusinessExtensionService)
{
$this->productReviewAndRatingService = $productReviewAndRatingService;
$this->ianeoBusinessExtensionService = $ianeoBusinessExtensionService;
}
public static function getSubscribedEvents()
{
return [
'product.search.result.loaded' => 'onProductLoaded',
'product_review.loaded' => 'onReviewLoaded'
];
}
public function onProductLoaded(EntitySearchResultLoadedEvent $event)
{
// do not fire event in backend context
if ($event->getContext()->getSource() instanceof AdminApiSource) {
if ($event->getContext()->getSource()->isAdmin()) {
return;
}
}
if ($event->getContext()->getSource() instanceof SystemSource) {
return;
}
$salesChannelId = $event->getContext()->getSource()->getSalesChannelId();
/** @var ProductCollection $products */
$products = $event->getResult()->getEntities();
if ($products === null) {
return;
}
if ($event->getName() !== 'product.search.result.loaded') {
return;
}
$productReviewCount = $this->productReviewAndRatingService->checkProductReviews($products, $salesChannelId);
$averageRatings = $this->productReviewAndRatingService->checkAverageRatings($products);
$productRecommandationCount = $this->productReviewAndRatingService->checkProductRecommandations($products, $salesChannelId);
$this->ianeoBusinessExtensionService->addAttributes($products, $productReviewCount, 'productReviewCount');
$this->ianeoBusinessExtensionService->addAttributes($products, $averageRatings, 'averageProductRating');
$this->ianeoBusinessExtensionService->addAttributes($products, $productRecommandationCount, 'productRecommandationCount');
}
/**
* this method is used to append the customer name and up/down-votes to the ianeoAttributes so that
* this info is available in the routes
* (e.g. in src/Core/Content/Product/SalesChannel/Review/ProductReviewRoute.php
* /store-api/product/{productId}/reviews
* )
*
* @param EntityLoadedEvent $event
* @return void
*/
public function onReviewLoaded(EntityLoadedEvent $event)
{
// do not fire event in backend context
if ($event->getContext()->getSource() instanceof AdminApiSource) {
if ($event->getContext()->getSource()->isAdmin()) {
return;
}
}
$eventEntity = $event->getEntities();
/** @var ProductReviewEntity $entity */
foreach ($eventEntity as $entity) {
$userInfo = new ArrayStruct();
$userInfo->set('firstname', $entity->getExternalUser());
/** @var VoteRatingsEntity $vote */
$vote = $entity->getExtension('vote');
$voteInfo = new ArrayStruct();
if (is_null($vote)) {
$voteInfo->set('vote_info', 'no up- and downvotes available');
} else {
$voteInfo->set('vote_id', $vote->getVoteId());
$voteInfo->set('upvotes', $vote->getUpvotes());
$voteInfo->set('downvotes', $vote->getDownvotes());
}
/** @var ProductReviewAttributesEntity $extension */
$extension = $entity->getExtension('ianeoAttributes');
if (is_null($extension))
{
//Todo SMN Errorhandling
return;
}
$extension->addExtension('author_info', $userInfo);
$extension = $entity->getExtension('ianeoAttributes');
if (is_null($extension))
{
//Todo SMN Errorhandling
return;
}
$extension->addExtension('vote_info', $voteInfo);
}
}
}