src/Repository/CategoryRepository.php line 224

Open in your IDE?
  1. <?php
  2. /**
  3.  * Created by PhpStorm.
  4.  * User: adv
  5.  * Date: 29.11.15
  6.  * Time: 15:30
  7.  */
  8. namespace Slivki\Repository;
  9. use Slivki\Entity\CacheReloadScheduler;
  10. use Slivki\Entity\Category;
  11. use Slivki\Entity\City;
  12. use Slivki\Entity\FavouriteCategory;
  13. use Slivki\Entity\Media;
  14. use Slivki\Entity\PopularCategory;
  15. use Slivki\Entity\Sale;
  16. use Slivki\Entity\Seo;
  17. use Slivki\Entity\User;
  18. use Slivki\Entity\VisitCounter;
  19. use Slivki\Util\SoftCache;
  20. class CategoryRepository extends CategoryRepositoryBase {
  21.     const FAVOURITE_CATEGORIES_COUNT 3;
  22.     const SORTED_SALE_CATEGORIES_CACHE_KEY "sorted_sale_categories";
  23.     public function getSupplierCategories(Category $category) {
  24.         return $this->getActiveCategories($category->getID(), array(Category::SUPPLIER_CATEGORY_TYPE), $category->getDomainObjectID());
  25.     }
  26.     /** @deprecated use CategoryCacheService */
  27.     public function reloadCategoryCache($categoryID) {
  28.         $softCache = new SoftCache(self::CACHE_NAME);
  29.         //$this->reloadEntityList($categoryID);
  30.         $categoryCached $softCache->getWithLock($categoryID);
  31.         $category $this->find($categoryID);
  32.         if (!$category) {
  33.             $softCache->delete($categoryID);
  34.             return false;
  35.         }
  36.         $category->getBanners()->toArray();
  37.         $category->getParentCategories()->toArray();
  38.         $city $category->getCity();
  39.         if ($city) {
  40.             $city->getID();
  41.         } else {
  42.             $city $this->getEntityManager()->find(City::class, City::DEFAULT_CITY_ID);
  43.             $category->setCity($city);
  44.         }
  45.         $category->getMobileMenuIconMedia();
  46.         $category->getAppIconMedia();
  47.         /*if (!isset($categoryCached['entityList']) || !$categoryCached['entityList'] || count($categoryCached['entityList'] == 0)) {
  48.             $this->removeCategoryFromCache($categoryID);
  49.             return false;
  50.         }*/
  51.         if (isset($categoryCached['entityList'])) {
  52.             $category->setEntityCount(count($categoryCached['entityList']));
  53.         } else {
  54.             $this->reloadEntityList($categoryID);
  55.         }
  56.         $this->getEntityManager()->flush($category);
  57.         $mediaRepository $this->getEntityManager()->getRepository(Media::class);
  58.         $category->setHotFeedMedia($mediaRepository->getСategoryHotFeedImageMedia($categoryID));
  59.         $category->setHotFeedIconMedia($mediaRepository->getСategoryHotFeedIconMedia($categoryID));
  60.         $categoryCached['category'] = $category;
  61.         $softCache->set($categoryID$categoryCached0);
  62.         $allCategoriesCached $softCache->getWithLock(self::ALL_CATEGORIES_CACHE_KEY);
  63.         $allCategoriesCached[$categoryID] = $categoryCached;
  64.         $softCache->set(self::ALL_CATEGORIES_CACHE_KEY$allCategoriesCached0);
  65.         $softCache->set($categoryID$categoryCached0);
  66.         switch ($category->getDomainObjectID()) {
  67.             case Category::OFFER_CATEGORY_ID:
  68.                 $this->getEntityManager()->getRepository(Seo::class)->reloadCacheForEntity(SeoRepository::RESOURCE_URL_OFFER_CATEGORY$categoryID);
  69.                 break;
  70.             case Category::SALE_CATEGORY_ID:
  71.                 $this->getEntityManager()->getRepository(Seo::class)->reloadCacheForEntity(SeoRepository::RESOURCE_URL_SALE_CATEGORY$categoryID);
  72.                 break;
  73.         }
  74.         return $categoryCached;
  75.     }
  76.     public function scheduleCategoryReload($categoryID) {
  77.         $scheduler = new CacheReloadScheduler();
  78.         $scheduler->setType(CacheReloadScheduler::TYPE_CATEGORY);
  79.         $scheduler->setEntityID($categoryID);
  80.         $entityManager $this->getEntityManager();
  81.         $entityManager->persist($scheduler);
  82.         $entityManager->flush($scheduler);
  83.     }
  84.     //TODO: Store entityList in class field
  85.     public function putCategoryToCache($category) {
  86.         if (!$category['category']->isActive() || $category['category']->isPast()) {
  87.             return;
  88.         }
  89.         $entityCount count($category['entityList']);
  90.         $category['category']->setEntityCount($entityCount);
  91.         $category['category']->getParentCategories()->toArray();
  92.         $category['category']->getCity()->getID();
  93.         $softCache = new SoftCache(self::CACHE_NAME);
  94.         $categoryList $softCache->get(self::ALL_CATEGORIES_CACHE_KEY);
  95.         $categoryList[$category['category']->getID()] = $category;
  96.         $softCache->set(self::ALL_CATEGORIES_CACHE_KEY$categoryList0);
  97.         $softCache->set($category['category']->getID(), $category0);
  98.         $category $this->find($category['category']->getID());
  99.         if (!$category) {
  100.             return;
  101.         }
  102.         $category->setEntityCount($entityCount);
  103.         $this->getEntityManager()->flush($category);
  104.         $this->scheduleCategoryReload($category->getID());//Workaround for tarantool. TODO: remove
  105.     }
  106.     public function removeCategoryFromCache($categoryID) {
  107.         $softCache = new SoftCache(self::CACHE_NAME);
  108.         $categoryList $softCache->get(self::ALL_CATEGORIES_CACHE_KEY);
  109.         unset($categoryList[$categoryID]);
  110.         $softCache->set(self::ALL_CATEGORIES_CACHE_KEY$categoryList0);
  111.         $softCache->delete($categoryID);
  112.     }
  113.     public function getPayedOffersByCategoryID($categoryID$sales false) {
  114.         if ($sales) {
  115.             $dql "select sale.ID, offerPayedCategory.position from Slivki:Sale sale index by sale.ID
  116.             join sale.categories category
  117.             join Slivki:OfferPayedCategory offerPayedCategory
  118.               with offerPayedCategory.entityID = sale.ID and offerPayedCategory.categoryID = :categoryID
  119.             where category.ID = :categoryID
  120.             order by offerPayedCategory.position";
  121.         } else {
  122.             $dql "select offer.ID, offerPayedCategory.position from Slivki:Offer offer index by offer.ID
  123.             join offer.categories category
  124.             join Slivki:OfferPayedCategory offerPayedCategory 
  125.               with offerPayedCategory.entityID = offer.ID and offerPayedCategory.categoryID = :categoryID
  126.             where category.ID = :categoryID
  127.             order by offerPayedCategory.position";
  128.         }
  129.         return $this->getEntityManager()->createQuery($dql)->setParameter('categoryID'$categoryID)->getResult();
  130.     }
  131.     /**
  132.      * @deprecated use CategoryService -> getCategoryNameWithBreadcrumbs
  133.      */
  134.     public function getCategoryBreadcrumbs(Category $category) {
  135.         $breadcrumbs '';
  136.         foreach ($this->getCategoryParentList($category) as $category) {
  137.             $breadcrumbs .= $category->getName() . ' > ';
  138.         }
  139.         return $breadcrumbs;
  140.     }
  141.     public function reloadEntityList($categoryID) {
  142.         $category $this->findCached($categoryID);
  143.         if (!$category) {
  144.             $this->reloadCategoryCache($categoryID);//TODO: move to service
  145.             $category $this->findCached($categoryID);
  146.         }
  147.         if (!$category || !isset($category['category'])) {
  148.             return;
  149.         }
  150.         if ($category['category']->getDomainObjectID() == Category::OFFER_CATEGORY_ID) {
  151.             $sql "select distinct(offer.id) from category2entity 
  152.                 inner join offer on offer.id = category2entity.entity_id
  153.                 where category2entity.category_id = $categoryID and offer.active
  154.                 and now() between offer.active_since and offer.active_till and not offer.hidden;";
  155.             $category['entityList'] = $this->getEntityManager()->getConnection()->executeQuery($sql)->fetchAll(\PDO::FETCH_COLUMN);
  156.             $this->putCategoryToCache($category);
  157.         } else if ($category['category']->getDomainObjectID() == Category::SALE_CATEGORY_ID) {
  158.             $sql 'select sale.id from sale inner join category2entity on sale.id = category2entity.entity_id 
  159.               where category2entity.category_id = ' . (int)$categoryID ' and now() between sale.since and sale.till and sale.active';
  160.             $category['entityList'] = $this->getEntityManager()->getConnection()->executeQuery($sql)->fetchAll(\PDO::FETCH_COLUMN);
  161.             $this->putCategoryToCache($category);
  162.         }
  163.     }
  164.     public function getActiveEntityListByCategory($categoryID) {
  165.         $softCache = new SoftCache(self::CACHE_NAME);
  166.         $category $softCache->get($categoryID);
  167.         if (!$category) {
  168.             return [];
  169.         }
  170.         $cacheName false;
  171.         switch ($category['category']->getDomainObjectID()) {
  172.             case 1:
  173.                 $cacheName OfferRepository::CACHE_NAME;
  174.                 break;
  175.             case Category::SALE_CATEGORY_ID:
  176.                 $cacheName SaleRepository::CACHE_NAME;
  177.                 break;
  178.             case 4:
  179.                 $cacheName PartnerOfferRepository::CACHE_NAME;
  180.                 break;
  181.             case Category::INSTALLMENT_CATEGORY_ID:
  182.                 $cacheName InstallmentRepository::CACHE_NAME;
  183.                 break;
  184.         }
  185.         if (!$cacheName) {
  186.             return [];
  187.         }
  188.         $softCache = new SoftCache($cacheName);
  189.         $entityList $softCache->getMulti($category['entityList']);
  190.         return $entityList $entityList : [];
  191.     }
  192.     public function getRootCategoryList($domainObjectID$cityID null) {
  193.         $cityCondition '';
  194.         if ($cityID) {
  195.             $cityCondition ' and city.ID = :cityID ';
  196.         }
  197.         $dql 'select category from Slivki:Category category join category.city city where category.active = true and category.past = false and category.domainObjectID = :domainObjectID ' $cityCondition ' and category.parents is empty order by category.sortOrder';
  198.         $query $this->getEntityManager()->createQuery($dql);
  199.         $query->setParameter('domainObjectID'$domainObjectID);
  200.         if ($cityID) {
  201.             $query->setParameter('cityID'$cityID);
  202.         }
  203.         return $query->getResult();
  204.     }
  205.     public function getUserFavouriteCategories(User $user null) {
  206.         $favouriteCategoryList $this->getEntityManager()->getRepository(PopularCategory::class)->findBy([], ['sortOrder' => 'asc'], self::FAVOURITE_CATEGORIES_COUNT);
  207.         $mediaRepository $this->getEntityManager()->getRepository(Media::class);
  208.         foreach ($favouriteCategoryList as $key => $category) {
  209.             $favouriteCategoryList[$key] = [
  210.                 'category' => $category->getCategory(),
  211.                 'media' => $mediaRepository->getLandingCategoryMedia($category->getCategory())
  212.             ];
  213.         }
  214.         return $favouriteCategoryList;
  215.     }
  216.     public function getCategoriesCached(array $categoryIDList) {
  217.         $softCache = new SoftCache(self::CACHE_NAME);
  218.         return $softCache->getMulti($categoryIDList);
  219.     }
  220.     public function getSaleCategoriesSortedBySaleVisits() {
  221.         $softCache = new SoftCache(self::CACHE_NAME);
  222.         $saleCategoriesSortedBySaleVisits $softCache->get(self::SORTED_SALE_CATEGORIES_CACHE_KEY);
  223.         return $saleCategoriesSortedBySaleVisits $saleCategoriesSortedBySaleVisits : [];
  224.     }
  225.     public function reloadSaleCategoriesSortedBySaleVisitsCache() {
  226.         $sql "select category.id, coalesce(max(v.visit), 0) as cnt from category 
  227.           inner join category2entity on category.id = category2entity.category_id
  228.           left join (select entity_id, count(*) as visit from visit 
  229.             where visit.entity_type_id = " Category::SALE_CATEGORY_ID " and visit.created_on > now() - interval '1 day' 
  230.             group by 1) as v on category2entity.entity_id = v.entity_id
  231.           where category.active and category.domain_object_id = " Category::SALE_CATEGORY_ID " and category.id not in (select child_id from category_child_relation) group by 1 order by 2 desc;";
  232.         $sortedSaleCategoryIDList $this->getEntityManager()->getConnection()->executeQuery($sql)->fetchAll(\PDO::FETCH_COLUMN);
  233.         $sortedSaleCategoryList self::getCategoriesCached($sortedSaleCategoryIDList);
  234.         $result = [];
  235.         $resultWithPosition = [];
  236.         foreach ($sortedSaleCategoryList as $key => $sortedSaleCategoryItem) {
  237.             if ($sortedSaleCategoryItem) {
  238.                 $category $sortedSaleCategoryItem['category'];
  239.                 $categoryPosition $category->getSortOrder();
  240.                 if ($categoryPosition 0) {
  241.                     while (isset($resultWithPosition[$categoryPosition])) {
  242.                         $categoryPosition++;
  243.                     }
  244.                     $resultWithPosition[$categoryPosition] = $category;
  245.                 } else {
  246.                     $result[] = $category;
  247.                 }
  248.             }
  249.         }
  250.         ksort($resultWithPosition);
  251.         foreach ($resultWithPosition as $key => $item) {
  252.             array_splice($result$key 10, [$item]);
  253.         }
  254.         $softCache = new SoftCache(self::CACHE_NAME);
  255.         $softCache->set(self::SORTED_SALE_CATEGORIES_CACHE_KEY$result0);
  256.     }
  257.     public function getSaleVideoguideCategoryMenu() {
  258.         $saleVideoguideCategory $this->getEntityManager()->getRepository(Category::class)->findCached(Category::SALE_VIDEO_GUIDE_CATEGORY_ID);
  259.         return $this->getSubCategories($saleVideoguideCategory['category']);
  260.     }
  261.     public function getSaleVideoguideAutorsCategoryMenu() {
  262.         $entityManager $this->getEntityManager();
  263.         $saleVideoguideAutorsCategory $entityManager->getRepository(Category::class)->findCached(Category::SALE_VIDEO_GUIDE_AUTORS_CATEGORY_ID);
  264.         $autorsMenu = [];
  265.         $saleRepository $entityManager->getRepository(Sale::class);
  266.         $visitCounterRepository $entityManager->getRepository(VisitCounter::class);
  267.         /** @var Category $category */
  268.         foreach ($this->getSubCategories($saleVideoguideAutorsCategory['category']) as $category) {
  269.             $visitCount 0;
  270.             /** @var Sale $sale */
  271.             foreach ($saleRepository->getActiveSalesByCategoryID($category->getID()) as $sale) {
  272.                 $visitCount += $visitCounterRepository->getVisitCount($sale->getID(), VisitCounter::TYPE_SALEfalse);
  273.             }
  274.             $autorsMenu[] = [
  275.                 'category' => $category,
  276.                 'visitCount' => $visitCount
  277.             ];
  278.         }
  279.         return $autorsMenu;
  280.     }
  281.     public function getParentCategoryIDsByOfferID($offerID) {
  282.         $sql 'select category_id from category2entity left join category_child_relation on category2entity.category_id = category_child_relation.child_id where child_id is null and entity_id = ' $offerID;
  283.         return $this->getEntityManager()->getConnection()->executeQuery($sql)->fetchAll(\PDO::FETCH_COLUMN);
  284.     }
  285.     public function scheduleCategoryBannerReload($categoryID) {
  286.         $scheduler = new CacheReloadScheduler();
  287.         $scheduler->setType(CacheReloadScheduler::TYPE_CATEGORY_BANNER);
  288.         $scheduler->setEntityID($categoryID);
  289.         $entityManager $this->getEntityManager();
  290.         $entityManager->persist($scheduler);
  291.         $entityManager->flush($scheduler);
  292.     }
  293.     public function getCategoryForMobileApi($categoryID) {
  294.         $dql 'select category, appIconMedia from Slivki:Category category left join category.appIconMedias appIconMedia where category.ID = :categoryID';
  295.         $query $this->getEntityManager()->createQuery($dql);
  296.         $query->setParameter('categoryID'$categoryID);
  297.         $result $query->getResult();
  298.         if ($result && count($result) > 0) {
  299.             return $result[0];
  300.         }
  301.     }
  302. }