Passed
Push — master ( c46287...9f1c00 )
by Aimeos
05:19
created

Base::delete()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 1
dl 0
loc 3
rs 10
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * @license LGPLv3, https://opensource.org/licenses/LGPL-3.0
5
 * @copyright Aimeos (aimeos.org), 2014-2024
6
 * @package MShop
7
 * @subpackage Common
8
 */
9
10
11
namespace Aimeos\MShop\Common\Manager\Property;
12
13
14
/**
15
 * Abstract property manager implementation.
16
 *
17
 * @package MShop
18
 * @subpackage Common
19
 */
20
abstract class Base
21
	extends \Aimeos\MShop\Common\Manager\Base
22
{
23
	private array $searchConfig;
24
	private ?string $languageId;
25
	private string $prefix;
26
27
28
	/**
29
	 * Initializes the object.
30
	 *
31
	 * @param \Aimeos\MShop\ContextIface $context Context object
32
	 */
33
	public function __construct( \Aimeos\MShop\ContextIface $context )
34
	{
35
		parent::__construct( $context );
36
37
		$this->languageId = $context->locale()->getLanguageId();
38
		$this->searchConfig = $this->getSearchConfig();
39
40
		if( ( $entry = reset( $this->searchConfig ) ) === false )
41
		{
42
			$msg = $this->context()->translate( 'mshop', 'Search configuration not available' );
43
			throw new \Aimeos\MShop\Exception( $msg );
44
		}
45
46
		if( ( $pos = strrpos( $entry['code'], '.' ) ) === false )
47
		{
48
			$msg = $this->context()->translate( 'mshop', 'Search configuration for "%1$s" not available' );
49
			throw new \Aimeos\MShop\Exception( sprintf( $msg, $entry['code'] ) );
50
		}
51
52
		if( empty( $this->prefix = substr( $entry['code'], 0, $pos + 1 ) ) )
53
		{
54
			$msg = $this->context()->translate( 'mshop', 'Search configuration for "%1$s" not available' );
55
			throw new \Aimeos\MShop\Exception( sprintf( $msg, $entry['code'] ) );
56
		}
57
	}
58
59
60
	/**
61
	 * Creates a new empty item instance
62
	 *
63
	 * @param array $values Values the item should be initialized with
64
	 * @return \Aimeos\MShop\Common\Item\Property\Iface New property item object
65
	 */
66
	public function create( array $values = [] ) : \Aimeos\MShop\Common\Item\Iface
67
	{
68
		$values[$this->prefix . 'siteid'] = $values[$this->prefix . 'siteid'] ?? $this->context()->locale()->getSiteId();
69
		return $this->createItemBase( $values );
70
	}
71
72
73
	/**
74
	 * Creates a filter object.
75
	 *
76
	 * @param bool|null $default Add default criteria or NULL for relaxed default criteria
77
	 * @param bool $site TRUE for adding site criteria to limit items by the site of related items
78
	 * @return \Aimeos\Base\Criteria\Iface Returns the filter object
79
	 */
80
	public function filter( ?bool $default = false, bool $site = false ) : \Aimeos\Base\Criteria\Iface
81
	{
82
		$object = parent::filter();
83
84
		if( $default !== false )
85
		{
86
			$langid = $this->context()->locale()->getLanguageId();
87
88
			$expr = array(
89
				$object->compare( '==', $this->prefix . 'languageid', null ),
90
				$object->compare( '==', $this->prefix . 'languageid', $langid ),
91
			);
92
93
			$object->setConditions( $object->or( $expr ) );
94
		}
95
96
		return $object;
97
	}
98
99
100
	/**
101
	 * Inserts the new property items for product item
102
	 *
103
	 * @param \Aimeos\MShop\Common\Item\Property\Iface $item Property item which should be saved
104
	 * @param bool $fetch True if the new ID should be returned in the item
105
	 * @return \Aimeos\MShop\Common\Item\Property\Iface $item Updated item including the generated ID
106
	 */
107
	protected function saveItem( \Aimeos\MShop\Common\Item\Property\Iface $item, bool $fetch = true ) : \Aimeos\MShop\Common\Item\Property\Iface
108
	{
109
		if( !$item->isModified() ) {
110
			return $item;
111
		}
112
113
		$context = $this->context();
114
		$conn = $context->db( $this->getResourceName() );
115
116
		$id = $item->getId();
117
		$path = $this->getConfigPath();
118
		$columns = $this->object()->getSaveAttributes();
119
120
		if( $id === null ) {
121
			$sql = $this->addSqlColumns( array_keys( $columns ), $this->getSqlConfig( $path .= 'insert' ) );
0 ignored issues
show
Bug introduced by
It seems like $this->getSqlConfig(AssignConcatNode) can also be of type array; however, parameter $sql of Aimeos\MShop\Common\Manager\Base::addSqlColumns() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

121
			$sql = $this->addSqlColumns( array_keys( $columns ), /** @scrutinizer ignore-type */ $this->getSqlConfig( $path .= 'insert' ) );
Loading history...
122
		} else {
123
			$sql = $this->addSqlColumns( array_keys( $columns ), $this->getSqlConfig( $path .= 'update' ), false );
124
		}
125
126
		$idx = 1;
127
		$stmt = $this->getCachedStatement( $conn, $path, $sql );
128
129
		foreach( $columns as $name => $entry ) {
130
			$stmt->bind( $idx++, $item->get( $name ), \Aimeos\Base\Criteria\SQL::type( $entry->getType() ) );
131
		}
132
133
		$stmt->bind( $idx++, $item->getParentId(), \Aimeos\Base\DB\Statement\Base::PARAM_INT );
134
		$stmt->bind( $idx++, $item->getKey() );
135
		$stmt->bind( $idx++, $item->getType() );
136
		$stmt->bind( $idx++, $item->getLanguageId() );
137
		$stmt->bind( $idx++, $item->getValue() );
138
		$stmt->bind( $idx++, $context->datetime() ); //mtime
139
		$stmt->bind( $idx++, $context->editor() );
140
141
		if( $id !== null ) {
142
			$stmt->bind( $idx++, $context->locale()->getSiteId() . '%' );
143
			$stmt->bind( $idx++, $id, \Aimeos\Base\DB\Statement\Base::PARAM_INT );
144
		} else {
145
			$stmt->bind( $idx++, $this->siteId( $item->getSiteId(), \Aimeos\MShop\Locale\Manager\Base::SITE_SUBTREE ) );
146
			$stmt->bind( $idx++, $context->datetime() ); //ctime
147
		}
148
149
		$stmt->execute()->finish();
150
151
		if( $id === null && $fetch === true ) {
152
			$id = $this->newId( $conn, $this->getConfigPath() . 'newid' );
153
		}
154
155
		$item->setId( $id );
156
157
		return $item;
158
	}
159
160
161
	/**
162
	 * Removes multiple items.
163
	 *
164
	 * @param \Aimeos\MShop\Common\Item\Iface[]|string[] $itemIds List of item objects or IDs of the items
165
	 * @return \Aimeos\MShop\Common\Manager\Property\Iface Manager object for chaining method calls
166
	 */
167
	public function delete( $itemIds ) : \Aimeos\MShop\Common\Manager\Iface
168
	{
169
		return $this->deleteItemsBase( $itemIds, $this->getConfigPath() . 'delete' );
170
	}
171
172
173
	/**
174
	 * Returns product property item with given Id.
175
	 *
176
	 * @param string $id Id of the product property item
177
	 * @param string[] $ref List of domains to fetch list items and referenced items for
178
	 * @param bool|null $default Add default criteria or NULL for relaxed default criteria
179
	 * @return \Aimeos\MShop\Common\Item\Property\Iface Returns the product property item of the given id
180
	 * @throws \Aimeos\MShop\Exception If item couldn't be found
181
	 */
182
	public function get( string $id, array $ref = [], ?bool $default = false ) : \Aimeos\MShop\Common\Item\Iface
183
	{
184
		return $this->getItemBase( $this->prefix . 'id', $id, $ref, $default );
185
	}
186
187
188
	/**
189
	 * Search for all property items based on the given critera.
190
	 *
191
	 * @param \Aimeos\Base\Criteria\Iface $search Search criteria object
192
	 * @param string[] $ref List of domains to fetch list items and referenced items for
193
	 * @param int|null &$total Number of items that are available in total
194
	 * @return \Aimeos\Map List of items implementing \Aimeos\MShop\Common\Item\Property\Iface with ids as keys
195
	 */
196
	public function search( \Aimeos\Base\Criteria\Iface $search, array $ref = [], int &$total = null ) : \Aimeos\Map
197
	{
198
		$items = [];
199
		$context = $this->context();
200
		$conn = $context->db( $this->getResourceName() );
201
202
		$level = \Aimeos\MShop\Locale\Manager\Base::SITE_ALL;
203
		$cfgPathSearch = $this->getConfigPath() . 'search';
204
		$cfgPathCount = $this->getConfigPath() . 'count';
205
		$required = array( trim( $this->prefix, '.' ) );
206
207
		$results = $this->searchItemsBase( $conn, $search, $cfgPathSearch, $cfgPathCount, $required, $total, $level );
208
209
		while( $row = $results->fetch() )
210
		{
211
			if( $item = $this->applyFilter( $this->createItemBase( $row ) ) ) {
212
				$items[$row[$this->prefix . 'id']] = $item;
213
			}
214
		}
215
216
		return map( $items );
217
	}
218
219
220
	/**
221
	 * Returns a new manager for product extensions
222
	 *
223
	 * @param string $manager Name of the sub manager type in lower case
224
	 * @param string|null $name Name of the implementation, will be from configuration (or "Standard") if null
225
	 * @return \Aimeos\MShop\Common\Manager\Iface Manager for different extensions, e.g property types, property lists etc.
226
	 */
227
	public function getSubManager( string $manager, string $name = null ) : \Aimeos\MShop\Common\Manager\Iface
228
	{
229
		return $this->getSubManagerBase( 'common', 'property/' . $manager, $name );
230
	}
231
232
233
	/**
234
	 * Returns the config path for retrieving the configuration values.
235
	 *
236
	 * @return string Configuration path
237
	 */
238
	abstract protected function getConfigPath() : string;
239
240
241
	/**
242
	 * Returns the search configuration for searching items.
243
	 *
244
	 * @return array Associative list of search keys and search definitions
245
	 */
246
	abstract protected function getSearchConfig() : array;
247
248
249
	/**
250
	 * Creates new property item object.
251
	 *
252
	 * @param array $values Associative list of key/value pairs
253
	 * @return \Aimeos\MShop\Common\Item\Property\Iface New property item object
254
	 */
255
	protected function createItemBase( array $values = [] ) : \Aimeos\MShop\Common\Item\Property\Iface
256
	{
257
		$values['.languageid'] = $this->languageId;
258
		return new \Aimeos\MShop\Common\Item\Property\Standard( $this->prefix, $values );
259
	}
260
261
262
	/**
263
	 * Returns the prefix used for the item keys.
264
	 *
265
	 * @return string Item key prefix
266
	 */
267
	protected function prefix() : string
268
	{
269
		return $this->prefix;
270
	}
271
}
272