<?php
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
namespace App\Controller;
use App\Model\DefaultMarca;
use App\Service\CartService;
use App\Service\ProductService;
use App\Service\ShopService;
use Symfony\Component\HttpFoundation\Cookie;
use App\Twig\Extension\ProductExtension;
use Pimcore\Model\DataObject;
use Pimcore\Controller\FrontendController;
use Pimcore\Model\DataObject\Folder;
use Pimcore\Model\Document;
use Pimcore\Twig\Extension\Templating\HeadTitle;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\Session\SessionInterface;
use Symfony\Component\Routing\Annotation\Route;
use App\Model\DefaultProduct;
use Pimcore\Config;
use App\Model\ShopCategory;
use App\Service\HelperService;
use Pimcore\Bundle\EcommerceFrameworkBundle\Factory;
use Pimcore\Bundle\EcommerceFrameworkBundle\FilterService\Helper;
use Pimcore\Bundle\EcommerceFrameworkBundle\FilterService\ListHelper;
use Pimcore\Bundle\EcommerceFrameworkBundle\IndexService\ProductList\ProductListInterface;
use Pimcore\Model\DataObject\FilterDefinition;
use Symfony\Component\HttpKernel\Event\FilterControllerEvent;
use Knp\Component\Pager\Pagination\SlidingPagination;
use Knp\Component\Pager\PaginatorInterface;
use App\Templating\Helper\BreadcrumbHelperService;
use Symfony\Component\Security\Core\User\UserInterface;
use App\Model\Customer;
/**
* ShopController
*/
class ShopController extends FrontendController
{
/**
* onKernelController
*/
public function onKernelController(FilterControllerEvent $event)
{
parent::onKernelController($event);
//$this->view->category = ShopCategory::getById($event->getRequest()->get('category'));
}
/**
* defaultAction
*/
public function defaultAction(
Request $request,
HelperService $helperService
)
{
$params = array_merge($request->query->all(), $request->attributes->all(), $request->request->all());
// $this->checkAccess($request);
// $this->setCookieTemplate();
$params['unique'] = $helperService->generateUniqueCode();
}
#[Route('/categories-filter',name: 'categoriesFilter')]
public function categoriesFilter(
UserInterface $user = null,
Request $request,
HeadTitle $headTitleHelper,
BreadcrumbHelperService $breadcrumbHelperService,
Factory $ecommerceFactory,
HelperService $helperService,
ListHelper $listHelper,
PaginatorInterface $paginator,
){
$params = array_merge($request->query->all(), $request->attributes->all(), $request->request->all());
//needed to make sure category filter filters for active category
$params['parentCategoryIds'] = $params['currentCategory'] ?? null;
$category = ShopCategory::getById($params['currentCategory']);
$params['category'] = $category;
if($category){
$headTitleHelper($category->getTitle());
$breadcrumbHelperService->enrichCategoryPage($category);
}
// create product list
$indexService = $ecommerceFactory->getIndexService();
$products = $indexService->getProductListForCurrentTenant();
$products->setVariantMode(ProductListInterface::VARIANT_MODE_HIDE);
$products->addCondition("productstatus NOT IN ('new','decatelogized','for_delete') OR productstatus IS NULL", 'productstatus');
$params["products"] = $products;
// load current filter
if ($category) {
$filterDefinition = $category->getFilterdefinition();
$trackingManager = Factory::getInstance()->getTrackingManager();
$trackingManager->trackCategoryPageView($category->getTitle(), null);
}
if ($request->get('filterdefinition') instanceof FilterDefinition) {
$filterDefinition = $request->get('filterdefinition');
}
if (empty($filterDefinition)) {
$filterDefinition = Config::getWebsiteConfig()->get('fallbackFilterdefinition');
}
$environment = $ecommerceFactory->getEnvironment();
$environment->setCurrentAssortmentTenant('OptimizedMysql');
// create and init filter service
$filterService = $ecommerceFactory->getFilterService();
$listHelper->setupProductList($filterDefinition, $products, $params, $filterService, true);
$params["filterService"] = $filterService;
$params["filterDefinition"] = $filterDefinition;
//init pagination
$paginator = $paginator->paginate(
$products,
$request->get('page', 1),
$filterDefinition->getPageLimit()
);
$params["paginator"] = $paginator;
$params['paginationVariables'] = $paginator->getPaginationData();
//check if layout should not be included
$params["showLayout"] = ($request->get('noLayout')) ? false : true;
$params["listViewStyle"] = (array_key_exists('listViewStyle', $params)) ? $params['listViewStyle'] : 'grid';
$params["unique"] = $helperService->generateUniqueCode();
// track product impressions
$trackingManager = $ecommerceFactory->getTrackingManager();
foreach ($paginator as $product) {
$trackingManager->trackProductImpression($product);
}
$params['categories'] = $this->getCategories();
$params['brands'] = $this->getMarcas();
return $this->render('Shop/filters/productSubCategories.html.twig',$params);
}
public function listAction(
UserInterface $user = null,
Request $request,
HeadTitle $headTitleHelper,
BreadcrumbHelperService $breadcrumbHelperService,
Factory $ecommerceFactory,
HelperService $helperService,
ListHelper $listHelper,
PaginatorInterface $paginator,
):Response
{
$params = array_merge($request->query->all(), $request->attributes->all(), $request->request->all());
$brandName = $request->get('brandname');
$brandId = $request->get('brand');
$isSeoFriendlyUrl = preg_match('/productos\/marcas/', $brandName);
if ($isSeoFriendlyUrl) {
$params["marca"] = $params["brand"];
}
//needed to make sure category filter filters for active category
$params['parentCategoryIds'] = $params['category'] ?? null;
//current Category for subFilter Proposes
$params['currentCategory'] = $params['category'] ?? null;
$category = ShopCategory::getById($params['category'] ?? null);
$params['category'] = $category;
if($category){
$headTitleHelper($category->getTitle());
$breadcrumbHelperService->enrichCategoryPage($category);
}
// create product list
$indexService = $ecommerceFactory->getIndexService();
$products = $indexService->getProductListForCurrentTenant();
$products->setVariantMode(ProductListInterface::VARIANT_MODE_HIDE);
$products->addCondition("productstatus NOT IN ('new','decatelogized','for_delete') OR productstatus IS NULL", 'productstatus');
$params["products"] = $products;
// load current filter
if ($category) {
$filterDefinition = $category->getFilterdefinition();
$trackingManager = Factory::getInstance()->getTrackingManager();
$trackingManager->trackCategoryPageView($category->getTitle(), null);
}
if ($request->get('filterdefinition') instanceof FilterDefinition) {
$filterDefinition = $request->get('filterdefinition');
}
if (empty($filterDefinition)) {
$filterDefinition = Config::getWebsiteConfig()->get('fallbackFilterdefinition');
}
$environment = $ecommerceFactory->getEnvironment();
$environment->setCurrentAssortmentTenant('OptimizedMysql');
// create and init filter service
$filterService = $ecommerceFactory->getFilterService();
$listHelper->setupProductList($filterDefinition, $products, $params, $filterService, true);
$params["filterService"] = $filterService;
$params["filterDefinition"] = $filterDefinition;
//init pagination
$paginator = $paginator->paginate(
$products,
$request->get('page', 1),
$filterDefinition->getPageLimit()
);
$params["paginator"] = $paginator;
$params['paginationVariables'] = $paginator->getPaginationData();
//check if layout should not be included
$params["showLayout"] = ($request->get('noLayout')) ? false : true;
$params["listViewStyle"] = (array_key_exists('listViewStyle', $params)) ? $params['listViewStyle'] : 'grid';
$params["unique"] = $helperService->generateUniqueCode();
// track product impressions
$trackingManager = $ecommerceFactory->getTrackingManager();
foreach ($paginator as $product) {
$trackingManager->trackProductImpression($product);
}
//subCategories Logic
if ($params['currentCategory']){
if ($params['currentCategory'] == 21822){//Awlcraft G-H LINE
return $this->redirect('/es/Pinturas/Acabados/Awlgrip-GH-Line/GH-Line-Solidos_c21836/awlgrip-top-coat-g-h-line_p2580');
}
elseif ($params['currentCategory'] == 21828){//Alcraft Se E Line metalizados
return $this->redirect('/es/Pinturas/Acabados/Awlcraft-Se/Awlcraft-Se-E-Line-Metalizados_c21828/awlcraft-se-e-line_p2336');
}
elseif ($params['currentCategory'] == 21829){//Alcraft Se L Line metalizados
return $this->redirect('/es/Pinturas/Acabados/Awlcraft-Se/Awlcraft-Se-l-Line-Solidos_c21829/awlcralf-se-l-line_p21578');
}
elseif ($params['currentCategory'] == 21825){//Alcraft 2000 Metalizados
return $this->redirect('/es/Pinturas/Acabados/Awlcraft-2000/Awlcraft-2000-Metalizados_c21825/awlcraft-2000-metallics_p21474');
}
elseif ($params['currentCategory'] == 21824){//Alcraft 2000 Solidos
return $this->redirect('/es/Pinturas/Acabados/Awlcraft-2000/Awlcraft-2000-solidos_c21824/awlcraft-2000-topcoat_p21665');
}
elseif ($params['currentCategory'] == 21832){//International Perfection
return $this->redirect('/es/Pinturas/Acabados/Perfection-Topcoat/Perfection_c21832/perfection_p898');
}
return $this->render('Shop/listing.html.twig', $params);
}
//end subCategories Logic
return $this->render('Shop/listing.html.twig', $params);
}
public function detailAction(
Request $request,
ProductService $productService
): Response
{
$user = $this->getUser();
$params = array_merge($request->query->all(), $request->attributes->all(), $request->request->all());
$product = DefaultProduct::getById($params['product']);
if ($user) {
//User ID to get product discount
$params['userIdSage'] = $user->getIdSage();
}
if ($product) {
if ($product->getType() == DataObject\AbstractObject::OBJECT_TYPE_VARIANT) {
$parentObj = DefaultProduct::getById($product->getParentId());
if ($product->getClassId() == $parentObj->getClassId()) {
$product = $parentObj;
}
}
$marca = $product->getMarcaObject();
if ($marca) {
$params['marca'] = array($marca->getId());
}
$params['product'] = $product;
}
$params['filterBtnActive'] = true;
$params['company'] = DataObject\Company::getById(415);
$lastVisitedProductsIds = json_decode($request->cookies->get('last_visited_products', '[]'), true);
$productID = $params['product']->getId();
if (!in_array($productID, $lastVisitedProductsIds)) {
// Add the ID of the currently visited product to the beginning of the array
array_unshift($lastVisitedProductsIds, $productID);
}
$lastVisitedProductsIds = array_slice($lastVisitedProductsIds, 0, 11);
$lastVisitedProducts = [];
foreach ($lastVisitedProductsIds as $productID) {
$lastVisitedProducts[] = DefaultProduct::getById($productID);
}
$params['lastVisitedProducts'] = $lastVisitedProducts;
// Get Related Product for product bundle
$relatedProducts = $productService->getRelatedProducts($product);
$params['relatedProducts'] = $relatedProducts;
$response = $this->render('Shop/ProductDetails/productDetail.html.twig', $params);
$cookie = new Cookie('last_visited_products', json_encode($lastVisitedProductsIds), time() + 86400); // 86400 segundos = 1 dÃa
$response->headers->setCookie($cookie);
return $response;
}
/**
* searchAction
* @Route("/search")
*/
public function searchAction(
Request $request,
ProductExtension $productExtension
)
{
$products = [];
$productList = Factory::getInstance()->getIndexService()->getProductListForTenant('OptimizedMysql');
$productList->addCondition("productstatus NOT IN ('new','decatelogized','for_delete') OR productstatus IS NULL ", 'productstatus');
//Remove extra spaces between words to avoid affecting matches.
$params['keyword'] = trim(preg_replace('/\s+/', ' ', $request->get('input')));
$params['isEmpty'] = false;
if (key_exists('keyword', $params)) {
$productList->addQueryCondition($params['keyword'], 'search');
if ($productList->count() === 0){
$productList->resetConditions();
$query = "bsncode LIKE '%" . $params['keyword'] . "%'";
$productList->addCondition($query, 'bsncode');
}
}
$language = $request->query->get('lang');
$count = 0;
$maxProducts = 75; // Maximum number of products allowed in $products
foreach ($productList as $product) {
$auxParent = $product->getParent();
if (!$auxParent instanceof Folder){
$product = $product->getParent();
}
$auxParent = new \stdClass();
$auxParent->id = $product->getId();
$auxParent->name = $product->getName();
$auxParent->bsnCode = $product->getBsncode();
$found = false;
foreach ($products as $existingProduct) {
if ($existingProduct['id'] == $auxParent->id) {
$found = true;
break;
}
}
if (!$found) {
// Convert both the product name and the search term to their form without accents using iconv()
$productNameWithoutAccents = iconv('UTF-8', 'ASCII//TRANSLIT//IGNORE', $auxParent->name);
$searchTermWithoutAccents = iconv('UTF-8', 'ASCII//TRANSLIT//IGNORE', $params['keyword']);
if (strcasecmp(trim($productNameWithoutAccents), $searchTermWithoutAccents) == 0) { // Check if product name matches search term exactly
unset($products);
$products[] = [
'id' => $product->getId(),
'name' => $product->getName(),
'brand' => $product->getMarca(),
'item' => DefaultProduct::getById($product->getId())
];
break; // Stop iterating if exact match is found
}
else if ($count < $maxProducts) { // Check if the maximum limit has been reached
$products[] = [
'id' => $product->getId(),
'name' => $product->getName(),
'brand' => $product->getMarca(),
'item' => DefaultProduct::getById($product->getId()),
];
$count++;
} else {
break; // Stop iterating if maximum limit has been reached
}
}
}
foreach ($products as &$product) {
$productName = strtolower($product['name']);
$distance = levenshtein($params['keyword'], $productName);
$score = 100 - $distance; // Asigna un puntaje inversamente proporcional a la distancia
$product['score'] = $score;
}
// Paso 3: Ordenar los productos según el puntaje
usort($products, function($a, $b) {
return $b['score'] - $a['score'];
});
$params['products'] = $products;
$params['lang'] = $language;
return $this->render('layout/includes/navbar-serach-suggestion-items.html.twig', $params);
}
/**
* searchdocumentAction
*
* @param Request $request
* @param Factory $ecommerceFactory
* @param HelperService $helperService,
* @param ListHelper $listHelper
* @param PaginatorInterface $paginator
* @return void
*/
public function searchdocumentAction(
Request $request,
Factory $ecommerceFactory,
HelperService $helperService,
ListHelper $listHelper,
PaginatorInterface $paginator
)
{
// $this->checkAccess($request);
// $this->setCookieTemplate();
$params = array_merge($request->query->all(), $request->attributes->all(), $request->request->all());
$limit = $params['limit'];
$params["orderBy"] = "name#ASC";
$actPage = $params['page'];
if (empty($actPage)) {
$actPage = 1;
}
if ($request->get('filterdefinition') instanceof \Pimcore\Model\DataObject\FilterDefinition) {
$filterDefinition = $request->get('filterdefinition');
}
if (empty($filterDefinition)) {
$filterDefinition = \Pimcore\Config::getWebsiteConfig()->fallbackFilterdefinition;
}
$this->view->filterDefinitionObject = $filterDefinition;
if (empty($limit)) {
$limit = $filterDefinition->getPageLimit();
}
$productList = Factory::getInstance()->getIndexService()->getProductListForCurrentTenant();
$productList->addCondition("productstatus NOT IN ('new','decatelogized','for_delete') OR productstatus IS NULL", 'productstatus');
if (empty($params['keyword'])) {
$params['keyword'] = $params['searchwords'];
}
if (key_exists('keyword', $params)) {
// foreach (explode(' ', $params['keyword']) as $term) {
$productList->addQueryCondition($params['keyword'], 'search');
// }
}
$filterService = Factory::getInstance()->getFilterService();
$params['filterService'] = $filterService;
$params['products'] = $productList;
$params['searchwords'] = $params['keyword'];
/** @var SlidingPagination $paginator */
$paginator = $paginator->paginate(
$productList,
$request->get('page', 1),
$limit
);
$params["paginator"] = $paginator;
$params['paginationVariables'] = $paginator->getPaginationData();
$params['actPage'] = $actPage;
$params['limit'] = $limit;
$params['unique'] = $helperService->generateUniqueCode();
}
/**
* cuantapinturanecesarioresultAction
*
* @param Request $request
* @param Factory $ecommerceFactory
* @param HelperService $helperService,
* @param ListHelper $listHelper
* @param PaginatorInterface $paginator
*
* @return void
*/
public function cuantapinturanecesarioresultAction(
Request $request,
Factory $ecommerceFactory,
HelperService $helperService,
ListHelper $listHelper,
PaginatorInterface $paginator
)
{
//$this->checkAccess($request);
//$this->setCookieTemplate();
$params = array_merge($request->query->all(), $request->attributes->all(), $request->request->all());
$limit = $params['limit'];
$params["orderBy"] = "name#ASC";
$actPage = $params['page'];
if (empty($actPage)) {
$actPage = 1;
}
$resultado = array();
$resultado["tipo-embarcacion"] = $params["radio_1"];
if (preg_match("/^mo/i", $params["radio_1"], $params["radio_1"])) {
$resultado["tipo-embarcacion"] = $resultado["tipo-embarcacion"] . $params["radio_2"];
}
$resultado["base-embarcacion"] = $params["radio_3"];
$resultado["dimension-eslora"] = $params["value1"];
$resultado["dimension-calado"] = $params["value2"];
$resultado["dimension-manga"] = $params["value3"];
$resultado["resultado-litre"] = round($params["value_1"], 2);
$this->view->resultado = $resultado;
if (!key_exists("calculvariant", $params)) {
if (empty($params["calculvariant"])) {
$params["calculvariant"] = $params["value_hidden"];
}
}
if ($request->get('filterdefinition') instanceof \Pimcore\Model\DataObject\FilterDefinition) {
$filterDefinition = $request->get('filterdefinition');
}
if (empty($filterDefinition)) {
$filterDefinition = \Pimcore\Config::getWebsiteConfig()->resultcuantapinturaFilterdefinition;
}
$params['filterDefinition'] = $filterDefinition;
if (empty($limit)) {
$limit = $filterDefinition->getPageLimit();
}
// create product list
$products = Factory::getInstance()->getIndexService()->getProductListForCurrentTenant();
$products->setVariantMode(ProductListInterface::VARIANT_MODE_INCLUDE_PARENT_OBJECT);
$products->addCondition("productstatus NOT IN ('new','decatelogized','for_delete') OR productstatus IS NULL", 'productstatus');
$products->addCondition("calculvariant LIKE '%#" . $params["value_hidden"] . "#%'", 'calculvariant');
$params['products'] = $products;
// create and init filter service
$filterService = Factory::getInstance()->getFilterService();
Helper::setupProductList($filterDefinition, $products, $params, $this->view, $filterService, true);
$params['filterService'] = $filterService;
/** @var SlidingPagination $paginator */
$paginator = $paginator->paginate(
$products,
$request->get('page', 1),
$limit
);
$params["paginator"] = $paginator;
$params['paginationVariables'] = $paginator->getPaginationData();
$params['actPage'] = $actPage;
$params['limit'] = $limit;
$params['unique'] = $helperService->generateUniqueCode();
}
/**
* setCookieTemplate
*
* @return void
*/
public function setCookieTemplate()
{
$cookieListener = $this->get(\Pimcore\Bundle\CoreBundle\EventListener\Frontend\CookiePolicyNoticeListener::class);
$cookieListener->loadTemplateFromResource("@App/Resources/views/Misc/cookie-policy-bsn-template.html");
}
/**
* checkAccess
*
* @param Request $request
* @return void
*/
private function checkAccess(Request $request)
{
if (!(($request->query->get('pimcore_preview') == "true") || ($request->query->get('pimcore_editmode') == "true"))) {
// $this->denyAccessUnlessGranted('IS_AUTHENTICATED_FULLY');
}
}
/**
* @Route("/ajax_productDetail_getStock", name="ajax_productDetail_getStock")
*/
public function productDetailGetStockAjaxAction(
Request $request,
ShopService $shopService,
): JsonResponse
{
$product = DefaultProduct::getById($request->get('id'));
$params = [];
if (!is_null($product)) {
$params['deliveryTime'] = $product->getPlazoentregaprovedor();
$params['stock']['total'] = $shopService->getStock($product->getBsncode());
$params['stock']['warehouse'] = $shopService->getStockByWarehouse($product->getBsncode());
}
return new JsonResponse($params);
}
/**
* @Route("/ajax_productDetail_new_asset", name="ajax_productDetail_new_asset")
*/
public function productDetailnewAsset(
Request $request,
){
$idProduct = $request->get('id');
$product = DefaultProduct::getById($idProduct);
$param['product'] = $product;
$param['test'] = $idProduct;
return $this->render('Shop/includes/newAsset.html.twig',$param);
}
/**
* @Route("/ajax_productDetail_info", name="ajax_productDetail_info")
*/
public function productDetailInfo(
Request $request,
){
$idProduct = $request->get('newId');
$product = DefaultProduct::getById($idProduct);
$param['deliveryTime'] = $product->getPlazoentregaprovedor();
return new JsonResponse($param);
}
/**
* @Route("/ajax_variant_info", name="ajax_variant_info")
*/
public function variantInfo(
Request $request,
ShopService $shopService,
UserInterface $user= null
){
/** @var \Pimcore\Model\DataObject\Customer $user */
$variant = DefaultProduct::getById($request->get('id'));
$priceWithDiscount = $shopService->getProductDiscount($variant->getBsncode(),$user->getIdSage());
$params['price'] = $variant->getPrice();
$params['bsnCode'] = $variant->getBsncode();
$params['stock']['total'] = $shopService->getStock($params['bsnCode']);
$params['stock']['warehouse'] = $shopService->getStockByWarehouse($params['bsnCode']);
$params['deliveryTime'] = $variant->getPlazoentregaprovedor();
$params['priceWithDiscount'] = $priceWithDiscount;
return new JsonResponse($params);
}
protected function getCategories(): DataObject\ProductCategory\Listing
{
$categories = new DataObject\ProductCategory\Listing();
$categories->setUnpublished(false);
$categories->setOrderKey("order");
$categories->setCondition('o_parentId = ?', [10]);
$categories->load();
return $categories;
}
protected function getMarcas(): DataObject\ProductMarca\Listing
{
$marcas = new DataObject\ProductMarca\Listing();
$marcas->setUnpublished(false);
$marcas->setOrderKey("order");
$marcas->load();
return $marcas;
}
#[Route('/ajax_productDetail_getBrandName',name:'ajax-productDetail-getBrandName')]
public function ajax_productDetail_getBrandName(Request $request): Response
{
$product = DefaultProduct::getById($request->get('id'));
return $this->json($product->getMarcaObject()->getName());
}
}