isLayeredNavigationEnabled()   B
last analyzed

Complexity

Conditions 8
Paths 7

Size

Total Lines 21
Code Lines 13

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 21
rs 7.1428
c 0
b 0
f 0
cc 8
eloc 13
nc 7
nop 0
1
<?php
2
/*
3
 * WellCommerce Open-Source E-Commerce Platform
4
 * 
5
 * This file is part of the WellCommerce package.
6
 *
7
 * (c) Adam Piotrowski <[email protected]>
8
 * 
9
 * For the full copyright and license information,
10
 * please view the LICENSE file that was distributed with this source code.
11
 */
12
13
namespace WellCommerce\Bundle\CatalogBundle\Helper;
14
15
use WellCommerce\Bundle\CoreBundle\DependencyInjection\AbstractContainerAware;
16
use WellCommerce\Component\DataSet\Conditions\ConditionInterface;
17
use WellCommerce\Component\DataSet\Conditions\ConditionsCollection;
18
19
/**
20
 * Class LayeredNavigationHelper
21
 *
22
 * @author  Adam Piotrowski <[email protected]>
23
 */
24
final class LayeredNavigationHelper extends AbstractContainerAware implements LayeredNavigationHelperInterface
25
{
26
    /**
27
     * @var array
28
     */
29
    private $filters = [];
30
    
31
    /**
32
     * LayeredNavigationHelper constructor.
33
     *
34
     * @param array $filters
35
     */
36
    public function __construct(array $filters = [])
37
    {
38
        $this->setFilters($filters);
39
    }
40
    
41
    public function generateRedirectUrl(): string
42
    {
43
        $formParams              = $this->parseFormParameters($this->getRequestHelper()->getRequestBagParam('form', '', FILTER_DEFAULT));
44
        $route                   = $this->getRequestHelper()->getRequestBagParam('route', 0);
45
        $currentAttributesParams = $this->getRequestHelper()->getRequestBagParam('route_params', []);
46
        $currentQueryParams      = $this->getRequestHelper()->getRequestBagParam('query_params', []);
47
        $currentRouteParams      = array_merge($currentAttributesParams, $currentQueryParams);
48
        $replacements            = [];
49
        
50
        foreach ($this->filters as $parameterName => $configuration) {
51
            if (isset($formParams[$parameterName])) {
52
                $value = $formParams[$parameterName];
53
                if ($configuration['type'] === self::VALUE_TYPE_ARRAY) {
54
                    $replacements[$parameterName] = empty($value) ? 0 : implode(self::MULTI_VALUE_SEPARATOR, $value);
55
                } else {
56
                    $replacements[$parameterName] = $formParams[$parameterName];
57
                }
58
            } else {
59
                $replacements[$parameterName] = 0;
60
            }
61
        }
62
        
63
        $routeParams = array_replace($currentRouteParams, $replacements);
64
        
65
        return $this->getRouterHelper()->generateUrl($route, $routeParams);
66
    }
67
    
68
    public function addLayeredNavigationConditions(ConditionsCollection $collection)
69
    {
70
        if (false === $this->isLayeredNavigationEnabled()) {
71
            return $collection;
72
        }
73
        
74
        foreach ($this->filters as $parameterName => $configuration) {
75
            $currentAttributeValue = $this->getCurrentAttributeValue($parameterName, $configuration['type']);
76
            if (!empty($currentAttributeValue)) {
77
                $collection->add($this->createFilterCondition($currentAttributeValue, $configuration));
78
            }
79
        }
80
        
81
        return $collection;
82
    }
83
    
84
    public function isLayeredNavigationEnabled(): bool
85
    {
86
        $route     = $this->getRouterHelper()->getCurrentRoute();
87
        $keys      = array_keys($this->filters);
88
        $isEnabled = false;
89
        
90
        foreach ($keys as $key) {
91
            $value        = $this->getRequestHelper()->getAttributesBagParam($key);
92
            $defaultValue = null;
93
            if ($route->hasDefault($key)) {
94
                $defaultValue = $route->getDefault($key);
95
            }
96
            if (null !== $value && $value != $defaultValue) {
97
                if ($this->filters[$key]['type'] !== self::VALUE_TYPE_ARRAY || ($this->filters[$key]['type'] === self::VALUE_TYPE_ARRAY && $value != 0)) {
98
                    $isEnabled = true;
99
                }
100
            }
101
        }
102
        
103
        return $isEnabled;
104
    }
105
    
106
    private function createFilterCondition($currentAttributeValue, array $configuration): ConditionInterface
107
    {
108
        return new $configuration['condition']($configuration['column'], $currentAttributeValue);
109
    }
110
    
111
    private function getCurrentAttributeValue(string $parameterName, string $type)
112
    {
113
        if ($type === self::VALUE_TYPE_ARRAY) {
114
            $parameterValue = $this->getRequestHelper()->getAttributesBagParam($parameterName);
115
            $parameterValue = explode(self::MULTI_VALUE_SEPARATOR, $parameterValue);
116
            
117
            return array_filter($parameterValue, function ($v) {
118
                return 0 !== (int)$v;
119
            }, ARRAY_FILTER_USE_BOTH);
120
        }
121
        
122
        return $this->getRequestHelper()->getAttributesBagParam($parameterName);
123
    }
124
    
125
    private function setFilters(array $filters)
126
    {
127
        $this->filters = array_filter($filters, function ($v) {
128
            return (bool)$v['enabled'];
129
        }, ARRAY_FILTER_USE_BOTH);
130
    }
131
    
132
    private function parseFormParameters(string $queryString): array
133
    {
134
        parse_str($queryString, $params);
135
        
136
        return $params;
137
    }
138
}
139