1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
/** |
4
|
|
|
* TechDivision\Import\Utils\UrlKeyUtil |
5
|
|
|
* |
6
|
|
|
* NOTICE OF LICENSE |
7
|
|
|
* |
8
|
|
|
* This source file is subject to the Open Software License (OSL 3.0) |
9
|
|
|
* that is available through the world-wide-web at this URL: |
10
|
|
|
* http://opensource.org/licenses/osl-3.0.php |
11
|
|
|
* |
12
|
|
|
* PHP version 5 |
13
|
|
|
* |
14
|
|
|
* @author Tim Wagner <[email protected]> |
15
|
|
|
* @copyright 2019 TechDivision GmbH <[email protected]> |
16
|
|
|
* @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0) |
17
|
|
|
* @link https://github.com/techdivision/import |
18
|
|
|
* @link http://www.techdivision.com |
19
|
|
|
*/ |
20
|
|
|
|
21
|
|
|
namespace TechDivision\Import\Utils; |
22
|
|
|
|
23
|
|
|
use TechDivision\Import\Configuration\ConfigurationInterface; |
24
|
|
|
use TechDivision\Import\Subjects\UrlKeyAwareSubjectInterface; |
25
|
|
|
use TechDivision\Import\Services\UrlKeyAwareProcessorInterface; |
26
|
|
|
|
27
|
|
|
/** |
28
|
|
|
* Utility class that provides functionality to make URL keys unique. |
29
|
|
|
* |
30
|
|
|
* @author Tim Wagner <[email protected]> |
31
|
|
|
* @copyright 2019 TechDivision GmbH <[email protected]> |
32
|
|
|
* @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0) |
33
|
|
|
* @link https://github.com/techdivision/import |
34
|
|
|
* @link http://www.techdivision.com |
35
|
|
|
*/ |
36
|
|
|
class UrlKeyUtil implements UrlKeyUtilInterface |
37
|
|
|
{ |
38
|
|
|
|
39
|
|
|
/** |
40
|
|
|
* The configuration instance. |
41
|
|
|
* |
42
|
|
|
* @var \TechDivision\Import\Configuration\ConfigurationInterface |
43
|
|
|
*/ |
44
|
|
|
protected $configuration; |
45
|
|
|
|
46
|
|
|
/** |
47
|
|
|
* The URL key aware processor instance. |
48
|
|
|
* |
49
|
|
|
* \TechDivision\Import\Services\UrlKeyAwareProcessorInterface |
50
|
|
|
*/ |
51
|
|
|
protected $urlKeyAwareProcessor; |
52
|
|
|
|
53
|
|
|
/** |
54
|
|
|
* Construct a new instance. |
55
|
|
|
* |
56
|
|
|
* @param \TechDivision\Import\Configuration\ConfigurationInterface $configuration The configuration instance |
57
|
|
|
* @param \TechDivision\Import\Services\UrlKeyAwareProcessorInterface $urlKeyAwareProcessor The URL key aware processor instance |
58
|
|
|
*/ |
59
|
|
|
public function __construct( |
60
|
|
|
ConfigurationInterface $configuration, |
61
|
|
|
UrlKeyAwareProcessorInterface $urlKeyAwareProcessor |
62
|
|
|
) { |
63
|
|
|
$this->configuration = $configuration; |
64
|
|
|
$this->urlKeyAwareProcessor = $urlKeyAwareProcessor; |
65
|
|
|
} |
66
|
|
|
|
67
|
|
|
/** |
68
|
|
|
* Returns the URL key aware processor instance. |
69
|
|
|
* |
70
|
|
|
* @return \TechDivision\Import\Services\UrlKeyAwareProcessorInterface The processor instance |
71
|
|
|
*/ |
72
|
|
|
protected function getUrlKeyAwareProcessor() |
73
|
|
|
{ |
74
|
|
|
return $this->urlKeyAwareProcessor; |
75
|
|
|
} |
76
|
|
|
|
77
|
|
|
/** |
78
|
|
|
* Load's and return's the varchar attribute with the passed params. |
79
|
|
|
* |
80
|
|
|
* @param integer $attributeCode The attribute code of the varchar attribute |
81
|
|
|
* @param integer $entityTypeId The entity type ID of the varchar attribute |
82
|
|
|
* @param integer $storeId The store ID of the varchar attribute |
83
|
|
|
* @param string $value The value of the varchar attribute |
84
|
|
|
* |
85
|
|
|
* @return array|null The varchar attribute |
86
|
|
|
*/ |
87
|
|
|
protected function loadVarcharAttributeByAttributeCodeAndEntityTypeIdAndStoreIdAndValue($attributeCode, $entityTypeId, $storeId, $value) |
88
|
|
|
{ |
89
|
|
|
return $this->getUrlKeyAwareProcessor() |
90
|
|
|
->loadVarcharAttributeByAttributeCodeAndEntityTypeIdAndStoreIdAndValue( |
91
|
|
|
$attributeCode, |
92
|
|
|
$entityTypeId, |
93
|
|
|
$storeId, |
94
|
|
|
$value |
95
|
|
|
); |
96
|
|
|
} |
97
|
|
|
|
98
|
|
|
/** |
99
|
|
|
* Make's the passed URL key unique by adding the next number to the end. |
100
|
|
|
* |
101
|
|
|
* @param \TechDivision\Import\Subjects\UrlKeyAwareSubjectInterface $subject The subject to make the URL key unique for |
102
|
|
|
* @param string $urlKey The URL key to make unique |
103
|
|
|
* |
104
|
|
|
* @return string The unique URL key |
105
|
|
|
*/ |
106
|
|
|
public function makeUnique(UrlKeyAwareSubjectInterface $subject, $urlKey) |
107
|
|
|
{ |
108
|
|
|
|
109
|
|
|
// initialize the entity type ID |
110
|
|
|
$entityType = $subject->getEntityType(); |
111
|
|
|
$entityTypeId = (integer) $entityType[MemberNames::ENTITY_TYPE_ID]; |
112
|
|
|
|
113
|
|
|
// initialize the store view ID, use the admin store view if no store view has |
114
|
|
|
// been set, because the default url_key value has been set in admin store view |
115
|
|
|
$storeId = $subject->getRowStoreId(StoreViewCodes::ADMIN); |
116
|
|
|
|
117
|
|
|
// initialize the counter |
118
|
|
|
$counter = 0; |
119
|
|
|
|
120
|
|
|
// initialize the counters |
121
|
|
|
$matchingCounters = array(); |
122
|
|
|
$notMatchingCounters = array(); |
123
|
|
|
|
124
|
|
|
// pre-initialze the URL key to query for |
125
|
|
|
$value = $urlKey; |
126
|
|
|
|
127
|
|
|
do { |
128
|
|
|
// try to load the attribute |
129
|
|
|
$attribute = |
130
|
|
|
$this->loadVarcharAttributeByAttributeCodeAndEntityTypeIdAndStoreIdAndValue( |
131
|
|
|
MemberNames::URL_KEY, |
132
|
|
|
$entityTypeId, |
133
|
|
|
$storeId, |
134
|
|
|
$value |
135
|
|
|
); |
136
|
|
|
|
137
|
|
|
// try to load the entity's URL key |
138
|
|
|
if ($attribute) { |
|
|
|
|
139
|
|
|
// this IS the URL key of the passed entity |
140
|
|
|
if ($subject->isUrlKeyOf($attribute)) { |
141
|
|
|
$matchingCounters[] = $counter; |
142
|
|
|
} else { |
143
|
|
|
$notMatchingCounters[] = $counter; |
144
|
|
|
} |
145
|
|
|
|
146
|
|
|
// prepare the next URL key to query for |
147
|
|
|
$value = sprintf('%s-%d', $urlKey, ++$counter); |
148
|
|
|
} |
149
|
|
|
} while ($attribute); |
|
|
|
|
150
|
|
|
|
151
|
|
|
// sort the array ascending according to the counter |
152
|
|
|
asort($matchingCounters); |
153
|
|
|
asort($notMatchingCounters); |
154
|
|
|
|
155
|
|
|
// this IS the URL key of the passed entity => we've an UPDATE |
156
|
|
|
if (sizeof($matchingCounters) > 0) { |
157
|
|
|
// load highest counter |
158
|
|
|
$counter = end($matchingCounters); |
159
|
|
|
// if the counter is > 0, we've to append it to the new URL key |
160
|
|
|
if ($counter > 0) { |
161
|
|
|
$urlKey = sprintf('%s-%d', $urlKey, $counter); |
162
|
|
|
} |
163
|
|
|
} elseif (sizeof($notMatchingCounters) > 0) { |
164
|
|
|
// create a new URL key by raising the counter |
165
|
|
|
$newCounter = end($notMatchingCounters); |
166
|
|
|
$urlKey = sprintf('%s-%d', $urlKey, ++$newCounter); |
167
|
|
|
} |
168
|
|
|
|
169
|
|
|
// return the passed URL key, if NOT |
170
|
|
|
return $urlKey; |
171
|
|
|
} |
172
|
|
|
} |
173
|
|
|
|
This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.
Consider making the comparison explicit by using
empty(..)
or! empty(...)
instead.