You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

284 lines
9.8KB

  1. <?php
  2. namespace Lc\CaracoleBundle\Repository\Product;
  3. use Lc\CaracoleBundle\Model\Product\ProductCategoryInterface;
  4. use Lc\CaracoleBundle\Model\Product\ProductFamilyInterface;
  5. use Lc\CaracoleBundle\Model\Reduction\ReductionCatalogInterface;
  6. use Lc\CaracoleBundle\Repository\SectionStoreTrait;
  7. use Lc\CaracoleBundle\Solver\Price\PriceSolver;
  8. use Lc\SovBundle\Model\User\UserInterface;
  9. use Lc\SovBundle\Repository\AbstractStore;
  10. use Lc\SovBundle\Repository\RepositoryQueryInterface;
  11. class ProductFamilyStore extends AbstractStore
  12. {
  13. use SectionStoreTrait;
  14. protected ProductFamilyRepositoryQuery $query;
  15. protected PriceSolver $priceSolver;
  16. public function __construct(ProductFamilyRepositoryQuery $query, PriceSolver $priceSolver)
  17. {
  18. $this->query = $query;
  19. $this->priceSolver = $priceSolver;
  20. }
  21. public function orderByDefault(RepositoryQueryInterface $query): RepositoryQueryInterface
  22. {
  23. $query->orderBy('position');
  24. return $query;
  25. }
  26. public function filtersDefault(RepositoryQueryInterface $query): RepositoryQueryInterface
  27. {
  28. if($this->section) {
  29. $query->filterBySection($this->section);
  30. }
  31. return $query;
  32. }
  33. public function relationsDefault($query): RepositoryQueryInterface
  34. {
  35. $query->joinProductCategories();
  36. $query->joinProducts();
  37. return $query;
  38. }
  39. public function getByParentCategory(
  40. ProductCategoryInterface $parentCategory,
  41. $user = null,
  42. $query = null
  43. ) {
  44. $productFamiliesArray = [];
  45. foreach ($parentCategory->getChildrens() as $i => $category) {
  46. $productFamiliesCategory = $this->getByCategory($category, $query);
  47. foreach ($productFamiliesCategory as $productFamily) {
  48. $productFamiliesArray[$productFamily->getId()] = $productFamily;
  49. }
  50. }
  51. return $this->getWithReductions($productFamiliesArray, $user, true);
  52. }
  53. // getProductFamiliesByCategory
  54. public function getByCategory(
  55. ProductCategoryInterface $productCategory,
  56. $query = null
  57. ) {
  58. $query = $this->createDefaultQuery($query);
  59. $query
  60. ->filterIsOnline()
  61. ->filterByProductCategory($productCategory);
  62. return $query->find();
  63. }
  64. // getProductFamiliesNovelties
  65. public function getNovelty($user = null, $organizeByParentCategory = true, $query = null)
  66. {
  67. $query = $this->createDefaultQuery($query);
  68. $query
  69. ->filterByPropertyNoveltyExpirationDate()
  70. ->filterIsOnline();
  71. $results = $query->find();
  72. return $this->getWithReductions($results, $user, false, $organizeByParentCategory);
  73. }
  74. // getProductFamiliesOrganics
  75. public function getOrganic($user = null, $organizeByParentCategory = true, $query = null)
  76. {
  77. $query = $this->createDefaultQuery($query);
  78. $query
  79. ->filterIsOrganicLabel()
  80. ->filterIsOnline();
  81. $results = $query->find();
  82. return $this->getWithReductions($results, $user, false, $organizeByParentCategory);
  83. }
  84. // getProductFamiliesOnDiscount
  85. public function getDiscount($user = null, $organizeByParentCategory = true, $query = null)
  86. {
  87. return $this->getWithReductions($this->getOnline($query), $user, false, $organizeByParentCategory, true);
  88. }
  89. // getProductFamiliesFavorites
  90. public function getFavorite($user = null, $organizeByParentCategory = true, $query = null)
  91. {
  92. if ($user) {
  93. return $this->getWithReductions(
  94. $user->getFavoriteProductFamilies(),
  95. $user,
  96. false,
  97. $organizeByParentCategory
  98. );
  99. }
  100. return [];
  101. }
  102. // findByTerms
  103. public function getByTerms(
  104. $terms,
  105. $maxResults = false,
  106. $organizeByParentCategory = false,
  107. $user = null,
  108. $query = null
  109. ) {
  110. $query = $this->createDefaultQuery($query);
  111. $query->filterIsOnline();
  112. $query->filterByTerms($terms);
  113. $query->groupBy('id');
  114. if ($maxResults) {
  115. $query->limit($maxResults);
  116. }
  117. $results = $query->find();
  118. return $this->getWithReductions($results, $user, false, $organizeByParentCategory);
  119. }
  120. public function getBestReductionCatalog(
  121. ProductFamilyInterface $productFamily,
  122. ReductionCatalogInterface $reductionCatalog1,
  123. ReductionCatalogInterface $reductionCatalog2
  124. ) {
  125. $price1 = $this->priceSolver->applyReductionCatalog(
  126. $productFamily,
  127. $this->priceSolver->getPrice($productFamily),
  128. $this->priceSolver->getPriceWithTax($productFamily),
  129. 1,
  130. $reductionCatalog1
  131. );
  132. $price2 = $this->priceSolver->applyReductionCatalog(
  133. $productFamily,
  134. $this->priceSolver->getPrice($productFamily),
  135. $this->priceSolver->getPriceWithTax($productFamily),
  136. 1,
  137. $reductionCatalog2
  138. );
  139. if ($price1 > $price2) {
  140. return $reductionCatalog2;
  141. } else {
  142. return $reductionCatalog1;
  143. }
  144. }
  145. // setReductionForProductFamilies
  146. public function getWithReductions(
  147. $productFamilies,
  148. UserInterface $user = null,
  149. $organizeByCategory = false,
  150. $organizeByParentCategory = false,
  151. $onlyOnDiscount = false
  152. ) {
  153. $conditions = [
  154. 'ids' => [],
  155. 'categories' => [],
  156. ];
  157. foreach ($productFamilies as $productFamily) {
  158. $conditions['ids'][] = $productFamily->getId();
  159. $conditions['categories'] = array_merge(
  160. $conditions['categories'],
  161. $productFamily->getProductCategories()->toArray()
  162. );
  163. }
  164. if ($productFamilies) {
  165. $reductionCatalogs = $this->reductionCatalogStore->getByProductFamiliesConditions(
  166. $conditions,
  167. $user
  168. );
  169. }
  170. $productFamiliesToReturn = array();
  171. foreach ($productFamilies as $productFamily) {
  172. foreach ($reductionCatalogs as $reductionCatalog) {
  173. $conditionProductFamilies = $conditionProductFamily = $conditionProductCategory = false;
  174. if ($reductionCatalog->getProductFamilies()->contains(
  175. $productFamily
  176. ) || $reductionCatalog->getProductFamilies()->isEmpty()) {
  177. $conditionProductFamilies = true;
  178. }
  179. if ($reductionCatalog->getProductFamily() == $productFamily || $reductionCatalog->getProductFamily(
  180. ) === null) {
  181. $conditionProductFamily = true;
  182. }
  183. foreach ($productFamily->getProductCategories() as $productCategory) {
  184. if ($reductionCatalog->getProductCategories()->contains(
  185. $productCategory
  186. ) || $reductionCatalog->getProductCategories()->isEmpty()) {
  187. $conditionProductCategory = true;
  188. }
  189. }
  190. if ($conditionProductFamilies && $conditionProductFamily && $conditionProductCategory) {
  191. if ($productFamily->getReductionCatalog()) {
  192. $productFamily->setReductionCatalog(
  193. $this->getBestReductionCatalog(
  194. $productFamily,
  195. $reductionCatalog,
  196. $productFamily->getReductionCatalog()
  197. )
  198. );
  199. } else {
  200. $productFamily->setReductionCatalog($reductionCatalog);
  201. }
  202. }
  203. }
  204. if (($onlyOnDiscount && $productFamily->getReductionCatalog()) || !$onlyOnDiscount) {
  205. if ($organizeByParentCategory) {
  206. $productCategories = $productFamily->getProductCategories();
  207. if ($productCategories && count($productCategories) > 0) {
  208. $parentCategory = $productCategories[0]->getParentCategory();
  209. if ($this->productCategorySolver->isDisplay($parentCategory, $user)) {
  210. if (!isset($productFamiliesToReturn[$parentCategory->getId()])) {
  211. $productFamiliesToReturn[$parentCategory->getId()] = [
  212. 'category' => $parentCategory,
  213. 'products' => []
  214. ];
  215. }
  216. $productFamiliesToReturn[$parentCategory->getId()]['products'][] = $productFamily;
  217. }
  218. }
  219. } elseif ($organizeByCategory) {
  220. foreach ($productFamily->getProductCategories() as $productCategory) {
  221. if ($this->isDisplay($productFamily)) {
  222. $productFamiliesToReturn[$productCategory->getId()][] = $productFamily;
  223. }
  224. }
  225. } else {
  226. if ($this->isDisplay($productFamily)) {
  227. $productFamiliesToReturn[] = $productFamily;
  228. }
  229. }
  230. }
  231. }
  232. if ($organizeByParentCategory) {
  233. uasort($productFamiliesToReturn, array($this, 'compMethodSortProductFamiliesByParentCategory'));
  234. }
  235. return $productFamiliesToReturn;
  236. }
  237. }