Passed
Push — feature/909_Ampache_API_improv... ( f93b1c...7380bc )
by Pauli
02:41
created

BaseMapper::advFormatSqlOperator()   C

Complexity

Conditions 13
Paths 13

Size

Total Lines 15
Code Lines 14

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 13
eloc 14
c 0
b 0
f 0
nc 13
nop 2
dl 0
loc 15
rs 6.6166

How to fix   Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php declare(strict_types=1);
2
3
/**
4
 * ownCloud - Music app
5
 *
6
 * This file is licensed under the Affero General Public License version 3 or
7
 * later. See the COPYING file.
8
 *
9
 * @author Pauli Järvinen <[email protected]>
10
 * @copyright Pauli Järvinen 2016 - 2023
11
 */
12
13
namespace OCA\Music\Db;
14
15
use OCP\AppFramework\Db\DoesNotExistException;
16
use OCP\AppFramework\Db\MultipleObjectsReturnedException;
17
use OCP\IDBConnection;
18
19
use OCA\Music\AppFramework\Db\CompatibleMapper;
20
use OCA\Music\AppFramework\Db\UniqueConstraintViolationException;
21
use OCA\Music\Utility\Util;
22
23
/**
24
 * Common base class for data access classes of the Music app
25
 * @phpstan-template EntityType of Entity
26
 * @phpstan-method EntityType findEntity(string $sql, array $params)
27
 * @phpstan-method EntityType[] findEntities(string $sql, array $params, ?int $limit=null, ?int $offset=null)
28
 */
29
abstract class BaseMapper extends CompatibleMapper {
0 ignored issues
show
Deprecated Code introduced by
The class OCA\Music\AppFramework\Db\OldNextcloudMapper has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

29
abstract class BaseMapper extends /** @scrutinizer ignore-deprecated */ CompatibleMapper {
Loading history...
30
	const SQL_DATE_FORMAT = 'Y-m-d H:i:s.v';
31
32
	protected $nameColumn;
33
	/** @phpstan-var class-string<EntityType> $entityClass */
34
	protected $entityClass;
35
36
	/**
37
	 * @phpstan-param class-string<EntityType> $entityClass
38
	 */
39
	public function __construct(IDBConnection $db, string $tableName, string $entityClass, string $nameColumn) {
40
		parent::__construct($db, $tableName, $entityClass);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...udMapper::__construct() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

40
		/** @scrutinizer ignore-deprecated */ parent::__construct($db, $tableName, $entityClass);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
41
		$this->nameColumn = $nameColumn;
42
		// eclipse the base class property to help phpstan
43
		$this->entityClass = $entityClass;
44
	}
45
46
	/**
47
	 * Create an empty object of the entity class bound to this mapper
48
	 * @phpstan-return EntityType
49
	 */
50
	public function createEntity() : Entity {
51
		return new $this->entityClass();
52
	}
53
54
	/**
55
	 * Find a single entity by id and user_id
56
	 * @throws DoesNotExistException if the entity does not exist
57
	 * @throws MultipleObjectsReturnedException if more than one entity exists
58
	 * @phpstan-return EntityType
59
	 */
60
	public function find(int $id, string $userId) : Entity {
61
		$sql = $this->selectUserEntities("`{$this->getTableName()}`.`id` = ?");
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

61
		$sql = $this->selectUserEntities("`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`id` = ?");

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
62
		return $this->findEntity($sql, [$userId, $id]);
0 ignored issues
show
Bug Best Practice introduced by
The expression return $this->findEntity...l, array($userId, $id)) returns the type OCP\AppFramework\Db\Entity which includes types incompatible with the type-hinted return OCA\Music\Db\Entity.
Loading history...
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...oudMapper::findEntity() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

62
		return /** @scrutinizer ignore-deprecated */ $this->findEntity($sql, [$userId, $id]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
63
	}
64
65
	/**
66
	 * Find all entities matching the given IDs. Specifying the owning user is optional.
67
	 * @param integer[] $ids  IDs of the entities to be found
68
	 * @param string|null $userId
69
	 * @return Entity[]
70
	 * @phpstan-return EntityType[]
71
	 */
72
	public function findById(array $ids, string $userId=null) : array {
73
		$count = \count($ids);
74
		$condition = "`{$this->getTableName()}`.`id` IN ". $this->questionMarks($count);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

74
		$condition = "`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`id` IN ". $this->questionMarks($count);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
75
76
		if (empty($userId)) {
77
			$sql = $this->selectEntities($condition);
78
		} else {
79
			$sql = $this->selectUserEntities($condition);
80
			$ids = \array_merge([$userId], $ids);
81
		}
82
83
		return $this->findEntities($sql, $ids);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::findEntities() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

83
		return /** @scrutinizer ignore-deprecated */ $this->findEntities($sql, $ids);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
84
	}
85
86
	/**
87
	 * Find all user's entities
88
	 * @param string|null $createdMin Optional minimum `created` timestamp.
89
	 * @param string|null $createdMax Optional maximum `created` timestamp.
90
	 * @param string|null $updatedMin Optional minimum `updated` timestamp.
91
	 * @param string|null $updatedMax Optional maximum `updated` timestamp.
92
	 * @return Entity[]
93
	 * @phpstan-return EntityType[]
94
	 */
95
	public function findAll(string $userId, int $sortBy=SortBy::None, int $limit=null, int $offset=null,
96
							?string $createdMin=null, ?string $createdMax=null, ?string $updatedMin=null, ?string $updatedMax=null) : array {
97
		$sorting = $this->formatSortingClause($sortBy);
98
		[$condition, $params] = $this->formatTimestampConditions($createdMin, $createdMax, $updatedMin, $updatedMax);
99
		$sql = $this->selectUserEntities($condition, $sorting);
100
		\array_unshift($params, $userId);
101
		return $this->findEntities($sql, $params, $limit, $offset);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::findEntities() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

101
		return /** @scrutinizer ignore-deprecated */ $this->findEntities($sql, $params, $limit, $offset);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
102
	}
103
104
	/**
105
	 * Find all user's entities matching the given name
106
	 * @param string|null $createdMin Optional minimum `created` timestamp.
107
	 * @param string|null $createdMax Optional maximum `created` timestamp.
108
	 * @param string|null $updatedMin Optional minimum `updated` timestamp.
109
	 * @param string|null $updatedMax Optional maximum `updated` timestamp.
110
	 * @return Entity[]
111
	 * @phpstan-return EntityType[]
112
	 */
113
	public function findAllByName(
114
		?string $name, string $userId, int $matchMode=MatchMode::Exact, int $limit=null, int $offset=null,
115
		?string $createdMin=null, ?string $createdMax=null, ?string $updatedMin=null, ?string $updatedMax=null) : array {
116
117
		$params = [$userId];
118
		$nameCol = "`{$this->getTableName()}`.`{$this->nameColumn}`";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

118
		$nameCol = "`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`{$this->nameColumn}`";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
119
		if ($name === null) {
120
			$condition = "$nameCol IS NULL";
121
		} else {
122
			if ($matchMode === MatchMode::Exact) {
123
				$condition = "LOWER($nameCol) = LOWER(?)";
124
			} else {
125
				$condition = "LOWER($nameCol) LIKE LOWER(?)";
126
			}
127
			if ($matchMode === MatchMode::Substring) {
128
				$params[] = self::prepareSubstringSearchPattern($name);
129
			} else {
130
				$params[] = $name;
131
			}
132
		}
133
134
		[$timestampConds, $timestampParams] = $this->formatTimestampConditions($createdMin, $createdMax, $updatedMin, $updatedMax);
135
		if (!empty($timestampConds)) {
136
			$condition .= ' AND ' . $timestampConds;
137
			$params = \array_merge($params, $timestampParams);
138
		}
139
140
		$sql = $this->selectUserEntities($condition, "ORDER BY LOWER($nameCol)");
141
142
		return $this->findEntities($sql, $params, $limit, $offset);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::findEntities() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

142
		return /** @scrutinizer ignore-deprecated */ $this->findEntities($sql, $params, $limit, $offset);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
143
	}
144
145
	/**
146
	 * Find all user's starred entities. It is safe to call this also on entity types
147
	 * not supporting starring in which case an empty array will be returned.
148
	 * @return Entity[]
149
	 * @phpstan-return EntityType[]
150
	 */
151
	public function findAllStarred(string $userId, int $limit=null, int $offset=null) : array {
152
		if (\property_exists($this->entityClass, 'starred')) {
153
			$sql = $this->selectUserEntities(
154
				"`{$this->getTableName()}`.`starred` IS NOT NULL",
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

154
				"`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`starred` IS NOT NULL",

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
155
				"ORDER BY LOWER(`{$this->getTableName()}`.`{$this->nameColumn}`)");
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

155
				"ORDER BY LOWER(`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`{$this->nameColumn}`)");

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
156
			return $this->findEntities($sql, [$userId], $limit, $offset);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::findEntities() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

156
			return /** @scrutinizer ignore-deprecated */ $this->findEntities($sql, [$userId], $limit, $offset);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
157
		} else {
158
			return [];
159
		}
160
	}
161
162
	/**
163
	 * Find all entities matching multiple criteria, as needed for the Ampache API method `advanced_search`
164
	 * @param string $conjunction Operator to use between the rules, either 'and' or 'or'
165
	 * @param array $rules Array of arrays: [['rule' => string, 'operator' => string, 'input' => string], ...]
166
	 * 				Here, 'rule' has dozens of possible values depending on the business layer in question
167
	 * 				(see https://ampache.org/api/api-advanced-search#available-search-rules, alias names not supported here),
168
	 * 				'operator' is one of ['contain', 'notcontain', 'start', 'end', 'is', 'isnot', '>=', '<=', '=', '!=', '>', '<', 'true', 'false'],
169
	 * 				'input' is the right side value of the 'operator' (disregarded for the operators 'true' and 'false')
170
	 * @return Entity[]
171
	 * @phpstan-return EntityType[]
172
	 */
173
	public function findAllAdvanced(string $conjunction, array $rules, string $userId, ?int $limit=null, ?int $offset=null) : array {
174
		$sqlConditions = [];
175
		$sqlParams = [$userId];
176
177
		foreach ($rules as $rule) {
178
			list('op' => $sqlOp, 'param' => $param) = $this->advFormatSqlOperator($rule['operator'], $rule['input']);
179
			$sqlConditions[] = $this->advFormatSqlCondition($rule['rule'], $sqlOp);
180
			if ($param !== null) {
181
				$sqlParams[] = $param;
182
			}
183
		}
184
		$sqlConditions = \implode(" $conjunction ", $sqlConditions);
185
186
		$sql = $this->selectUserEntities($sqlConditions, "ORDER BY LOWER(`{$this->getTableName()}`.`{$this->nameColumn}`)");
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

186
		$sql = $this->selectUserEntities($sqlConditions, "ORDER BY LOWER(`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`{$this->nameColumn}`)");

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
187
		return $this->findEntities($sql, $sqlParams, $limit, $offset);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::findEntities() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

187
		return /** @scrutinizer ignore-deprecated */ $this->findEntities($sql, $sqlParams, $limit, $offset);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
188
	}
189
190
	/**
191
	 * Find IDs of all user's entities of this kind
192
	 * @return int[]
193
	 */
194
	public function findAllIds(string $userId) : array {
195
		$sql = "SELECT `id` FROM `{$this->getTableName()}` WHERE `user_id` = ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

195
		$sql = "SELECT `id` FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE `user_id` = ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
196
		$result = $this->execute($sql, [$userId]);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

196
		$result = /** @scrutinizer ignore-deprecated */ $this->execute($sql, [$userId]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
197
198
		return \array_map('intval', $result->fetchAll(\PDO::FETCH_COLUMN));
199
	}
200
201
	/**
202
	 * Find IDs of all users owning any entities of this mapper
203
	 * @return string[]
204
	 */
205
	public function findAllUsers() : array {
206
		$sql = "SELECT DISTINCT(`user_id`) FROM `{$this->getTableName()}`";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

206
		$sql = "SELECT DISTINCT(`user_id`) FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
207
		$result = $this->execute($sql);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

207
		$result = /** @scrutinizer ignore-deprecated */ $this->execute($sql);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
208
209
		return $result->fetchAll(\PDO::FETCH_COLUMN);
210
	}
211
212
	/**
213
	 * Delete all entities with given IDs without specifying the user
214
	 * @param integer[] $ids  IDs of the entities to be deleted
215
	 */
216
	public function deleteById(array $ids) : void {
217
		$count = \count($ids);
218
		if ($count === 0) {
219
			return;
220
		}
221
		$this->deleteByCond('`id` IN ' . $this->questionMarks($count), $ids);
222
	}
223
224
	/**
225
	 * Delete all entities matching the given SQL condition
226
	 * @param string $condition SQL 'WHERE' condition (without the keyword 'WHERE')
227
	 * @param array $params SQL parameters for the condition
228
	 */
229
	protected function deleteByCond(string $condition, array $params) : void {
230
		$sql = "DELETE FROM `{$this->getTableName()}` WHERE ". $condition;
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

230
		$sql = "DELETE FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE ". $condition;

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
231
		$this->execute($sql, $params);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

231
		/** @scrutinizer ignore-deprecated */ $this->execute($sql, $params);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
232
	}
233
234
	/**
235
	 * Delete all entities of the given user
236
	 */
237
	public function deleteAll(string $userId) : void {
238
		$sql = "DELETE FROM `{$this->getTableName()}` WHERE `user_id` = ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

238
		$sql = "DELETE FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE `user_id` = ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
239
		$this->execute($sql, [$userId]);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

239
		/** @scrutinizer ignore-deprecated */ $this->execute($sql, [$userId]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
240
	}
241
242
	/**
243
	 * Tests if entity with given ID and user ID exists in the database
244
	 */
245
	public function exists(int $id, string $userId) : bool {
246
		$sql = "SELECT 1 FROM `{$this->getTableName()}` WHERE `id` = ? AND `user_id` = ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

246
		$sql = "SELECT 1 FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE `id` = ? AND `user_id` = ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
247
		$result = $this->execute($sql, [$id, $userId]);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

247
		$result = /** @scrutinizer ignore-deprecated */ $this->execute($sql, [$id, $userId]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
248
		return $result->rowCount() > 0;
249
	}
250
251
	/**
252
	 * Count all entities of a user
253
	 */
254
	public function count(string $userId) : int {
255
		$sql = "SELECT COUNT(*) AS count FROM `{$this->getTableName()}` WHERE `user_id` = ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

255
		$sql = "SELECT COUNT(*) AS count FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE `user_id` = ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
256
		$result = $this->execute($sql, [$userId]);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

256
		$result = /** @scrutinizer ignore-deprecated */ $this->execute($sql, [$userId]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
257
		$row = $result->fetch();
258
		return \intval($row['count']);
259
	}
260
261
	/**
262
	 * {@inheritDoc}
263
	 * @see CompatibleMapper::insert()
264
	 * @phpstan-param EntityType $entity
265
	 * @phpstan-return EntityType
266
	 */
267
	public function insert(\OCP\AppFramework\Db\Entity $entity) : \OCP\AppFramework\Db\Entity {
268
		$now = new \DateTime();
269
		$nowStr = $now->format(self::SQL_DATE_FORMAT);
270
		$entity->setCreated($nowStr);
271
		$entity->setUpdated($nowStr);
272
273
		try {
274
			return parent::insert($entity); // @phpstan-ignore-line: no way to tell phpstan that the parent uses the template type
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...xtcloudMapper::insert() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

274
			return /** @scrutinizer ignore-deprecated */ parent::insert($entity); // @phpstan-ignore-line: no way to tell phpstan that the parent uses the template type

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
275
		} catch (\Doctrine\DBAL\Exception\UniqueConstraintViolationException $e) {
276
			throw new UniqueConstraintViolationException($e->getMessage(), $e->getCode(), $e);
277
		} catch (\OCP\DB\Exception $e) {
278
			// Nextcloud 21+
279
			if ($e->getReason() == \OCP\DB\Exception::REASON_UNIQUE_CONSTRAINT_VIOLATION) {
280
				throw new UniqueConstraintViolationException($e->getMessage(), $e->getCode(), $e);
281
			} else {
282
				throw $e;
283
			}
284
		}
285
	}
286
287
	/**
288
	 * {@inheritDoc}
289
	 * @see CompatibleMapper::update()
290
	 * @phpstan-param EntityType $entity
291
	 * @phpstan-return EntityType
292
	 */
293
	public function update(\OCP\AppFramework\Db\Entity $entity) : \OCP\AppFramework\Db\Entity {
294
		$now = new \DateTime();
295
		$entity->setUpdated($now->format(self::SQL_DATE_FORMAT));
296
		return parent::update($entity); // @phpstan-ignore-line: no way to tell phpstan that the parent uses the template type
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...xtcloudMapper::update() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

296
		return /** @scrutinizer ignore-deprecated */ parent::update($entity); // @phpstan-ignore-line: no way to tell phpstan that the parent uses the template type

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
297
	}
298
299
	/**
300
	 * Insert an entity, or if an entity with the same identity already exists,
301
	 * update the existing entity.
302
	 * Note: The functions insertOrUpate and updateOrInsert get the exactly same thing done. The only difference is
303
	 * that the former is optimized for cases where the entity doens't exist and the latter for cases where it does exist.
304
	 * @return Entity The inserted or updated entity, containing also the id field
305
	 * @phpstan-param EntityType $entity
306
	 * @phpstan-return EntityType
307
	 */
308
	public function insertOrUpdate(Entity $entity) : Entity {
309
		try {
310
			return $this->insert($entity);
311
		} catch (UniqueConstraintViolationException $ex) {
312
			$existingEntity = $this->findUniqueEntity($entity);
313
			$entity->setId($existingEntity->getId());
314
			$entity->setCreated($existingEntity->getCreated());
315
			return $this->update($entity);
316
		}
317
	}
318
319
	/**
320
	 * Update an entity whose unique constraint fields match the given entity. If such entity is not found,
321
	 * a new entity is inserted.
322
	 * Note: The functions insertOrUpate and updateOrInsert get the exactly same thing done. The only difference is
323
	 * that the former is optimized for cases where the entity doens't exist and the latter for cases where it does exist.
324
	 * @return Entity The inserted or updated entity, containing also the id field
325
	 * @phpstan-param EntityType $entity
326
	 * @phpstan-return EntityType
327
	 */
328
	public function updateOrInsert(Entity $entity) : Entity {
329
		try {
330
			$existingEntity = $this->findUniqueEntity($entity);
331
			$entity->setId($existingEntity->getId());
332
			return $this->update($entity);
333
		} catch (DoesNotExistException $ex) {
334
			try {
335
				return $this->insert($entity);
336
			} catch (UniqueConstraintViolationException $ex) {
337
				// the conflicting entry didn't exist an eyeblink ago but now it does
338
				// => this is essentially a concurrent update and it is anyway non-deterministic, which
339
				//    update happens last; cancel this update
340
				return $this->findUniqueEntity($entity);
341
			}
342
		}
343
	}
344
345
	/**
346
	 * Set the "starred" column of the given entities
347
	 * @param \DateTime|null $date
348
	 * @param integer[] $ids
349
	 * @param string $userId
350
	 * @return int number of modified entities
351
	 */
352
	public function setStarredDate(?\DateTime $date, array $ids, string $userId) : int {
353
		$count = \count($ids);
354
		if (!empty($date)) {
355
			$date = $date->format(self::SQL_DATE_FORMAT);
356
		}
357
358
		$sql = "UPDATE `{$this->getTableName()}` SET `starred` = ?
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

358
		$sql = "UPDATE `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` SET `starred` = ?

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
359
				WHERE `id` IN {$this->questionMarks($count)} AND `user_id` = ?";
360
		$params = \array_merge([$date], $ids, [$userId]);
361
		return $this->execute($sql, $params)->rowCount();
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

361
		return /** @scrutinizer ignore-deprecated */ $this->execute($sql, $params)->rowCount();

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
362
	}
363
364
	public function latestInsertTime(string $userId) : ?\DateTime {
365
		$sql = "SELECT MAX(`{$this->getTableName()}`.`created`) FROM `{$this->getTableName()}` WHERE `user_id` = ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

365
		$sql = "SELECT MAX(`{$this->getTableName()}`.`created`) FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE `user_id` = ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
366
		$result = $this->execute($sql, [$userId]);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

366
		$result = /** @scrutinizer ignore-deprecated */ $this->execute($sql, [$userId]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
367
		$createdTime = $result->fetch(\PDO::FETCH_COLUMN);
368
369
		return ($createdTime === null) ? null : new \DateTime($createdTime);
370
	}
371
372
	public function latestUpdateTime(string $userId) : ?\DateTime {
373
		$sql = "SELECT MAX(`{$this->getTableName()}`.`updated`) FROM `{$this->getTableName()}` WHERE `user_id` = ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

373
		$sql = "SELECT MAX(`{$this->getTableName()}`.`updated`) FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE `user_id` = ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
374
		$result = $this->execute($sql, [$userId]);
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...tcloudMapper::execute() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

374
		$result = /** @scrutinizer ignore-deprecated */ $this->execute($sql, [$userId]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
375
		$createdTime = $result->fetch(\PDO::FETCH_COLUMN);
376
377
		return ($createdTime === null) ? null : new \DateTime($createdTime);
378
	}
379
380
	/**
381
	 * helper creating a string like '(?,?,?)' with the specified number of elements
382
	 */
383
	protected function questionMarks(int $count) : string {
384
		$questionMarks = [];
385
		for ($i = 0; $i < $count; $i++) {
386
			$questionMarks[] = '?';
387
		}
388
		return '(' . \implode(',', $questionMarks) . ')';
389
	}
390
391
	/**
392
	 * Build a SQL SELECT statement which selects all entities of the given user,
393
	 * and optionally applies other conditions, too.
394
	 * This is built upon `selectEntities` which may be overridden by the derived class.
395
	 * @param string|null $condition Optional extra condition. This will get automatically
396
	 *                               prefixed with ' AND ', so don't include that.
397
	 * @param string|null $extension Any extension (e.g. ORDER BY, LIMIT) to be added after
398
	 *                               the conditions in the SQL statement
399
	 */
400
	protected function selectUserEntities(string $condition=null, string $extension=null) : string {
401
		$allConditions = "`{$this->getTableName()}`.`user_id` = ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

401
		$allConditions = "`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`user_id` = ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
402
403
		if (!empty($condition)) {
404
			$allConditions .= " AND $condition";
405
		}
406
407
		return $this->selectEntities($allConditions, $extension);
408
	}
409
410
	/**
411
	 * Build a SQL SELECT statement which selects all entities matching the given condition.
412
	 * The derived class may override this if necessary.
413
	 * @param string $condition This will get automatically prefixed with ' WHERE '
414
	 * @param string|null $extension Any extension (e.g. ORDER BY, LIMIT) to be added after
415
	 *                               the conditions in the SQL statement
416
	 */
417
	protected function selectEntities(string $condition, string $extension=null) : string {
418
		return "SELECT * FROM `{$this->getTableName()}` WHERE $condition $extension ";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

418
		return "SELECT * FROM `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}` WHERE $condition $extension ";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
419
	}
420
421
	/**
422
	 * @return array with two values: The SQL condition as string and the SQL parameters as string[]
423
	 */
424
	protected function formatTimestampConditions(?string $createdMin, ?string $createdMax, ?string $updatedMin, ?string $updatedMax) : array {
425
		$conditions = [];
426
		$params = [];
427
428
		if (!empty($createdMin)) {
429
			$conditions[] = "`{$this->getTableName()}`.`created` >= ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

429
			$conditions[] = "`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`created` >= ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
430
			$params[] = $createdMin;
431
		}
432
433
		if (!empty($createdMax)) {
434
			$conditions[] = "`{$this->getTableName()}`.`created` <= ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

434
			$conditions[] = "`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`created` <= ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
435
			$params[] = $createdMax;
436
		}
437
438
		if (!empty($updatedMin)) {
439
			$conditions[] = "`{$this->getTableName()}`.`updated` >= ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

439
			$conditions[] = "`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`updated` >= ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
440
			$params[] = $updatedMin;
441
		}
442
443
		if (!empty($updatedMax)) {
444
			$conditions[] = "`{$this->getTableName()}`.`updated` <= ?";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

444
			$conditions[] = "`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`updated` <= ?";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
445
			$params[] = $updatedMax;
446
		}
447
448
		return [\implode(' AND ', $conditions), $params];
449
	}
450
451
	/**
452
	 * Convert given sorting condition to an SQL clause. Derived class may overide this if necessary.
453
	 * @param int $sortBy One of the constants defined in the class SortBy
454
	 */
455
	protected function formatSortingClause(int $sortBy, bool $invertSort = false) : ?string {
456
		if ($sortBy == SortBy::Name) {
457
			$dir = $invertSort ? 'DESC' : 'ASC';
458
			return "ORDER BY LOWER(`{$this->getTableName()}`.`{$this->nameColumn}`) $dir";
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

458
			return "ORDER BY LOWER(`{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`{$this->nameColumn}`) $dir";

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
459
		} elseif ($sortBy == SortBy::Newest) {
460
			$dir = $invertSort ? 'ASC' : 'DESC';
461
			return "ORDER BY `{$this->getTableName()}`.`id` $dir"; // abuse the fact that IDs are ever-incrementing values
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

461
			return "ORDER BY `{/** @scrutinizer ignore-deprecated */ $this->getTableName()}`.`id` $dir"; // abuse the fact that IDs are ever-incrementing values

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
462
		} else {
463
			return null;
464
		}
465
	}
466
467
	protected static function prepareSubstringSearchPattern(string $input) : string {
468
		// possibly multiparted query enclosed in quotation marks is handled as a single substring,
469
		// while the default interpretation of multipart string is that each of the parts can be found
470
		// separately as substring in the given order
471
		if (Util::startsWith($input, '"') && Util::endsWith($input, '"')) {
472
			// remove the quotation
473
			$pattern = \substr($input, 1, -1);
474
		} else {
475
			// split to parts by whitespace
476
			$parts = \preg_split('/\s+/', $input, -1, PREG_SPLIT_NO_EMPTY);
477
			// glue the parts back together with a wildcard charater
478
			$pattern = \implode('%', $parts);
479
		}
480
		return "%$pattern%";
481
	}
482
483
	/**
484
	 * Format SQL operator and parameter matching the given advanced search operator.
485
	 * @return array like ['op' => string, 'param' => string]
486
	 */
487
	protected function advFormatSqlOperator(string $ruleOperator, string $ruleInput) {
488
		switch ($ruleOperator) {
489
			case 'contain':		return ['op' => 'LIKE',				'param' => "%$ruleInput%"];
490
			case 'notcontain':	return ['op' => 'NOT LIKE',			'param' => "%$ruleInput%"];
491
			case 'start':		return ['op' => 'LIKE',				'param' => "$ruleInput%"];
492
			case 'end':			return ['op' => 'LIKE',				'param' => "%$ruleInput"];
493
			case 'is':			return ['op' => '=',				'param' => "$ruleInput"];
494
			case 'isnot':		return ['op' => '!=',				'param' => "$ruleInput"];
495
			case 'sounds':		return ['op' => 'SOUNDS LIKE',		'param' => $ruleInput]; // MySQL-specific syntax
496
			case 'notsounds':	return ['op' => 'NOT SOUNDS LIKE',	'param' => $ruleInput]; // MySQL-specific syntax
497
			case 'regexp':		return ['op' => 'REGEXP',			'param' => $ruleInput]; // MySQL-specific syntax
498
			case 'notregexp':	return ['op' => 'NOT REGEXP',		'param' => $ruleInput]; // MySQL-specific syntax
499
			case 'true':		return ['op' => 'IS NOT NULL',		'param' => null];
500
			case 'false':		return ['op' => 'IS NULL',			'param' => null];
501
			default:			return ['op' => $ruleOperator,		'param' => $ruleInput]; // all numerical operators fall here
502
		}
503
	}
504
505
	/**
506
	 * Format SQL condition matching the given advanced search rule and SQL operator.
507
	 * Derived classes should override this to provide support for table-specific rules.
508
	 */
509
	protected function advFormatSqlCondition(string $rule, string $sqlOp) : string {
510
		$table = $this->getTableName();
0 ignored issues
show
Deprecated Code introduced by
The function OCA\Music\AppFramework\D...dMapper::getTableName() has been deprecated: 14.0.0 Move over to QBMapper ( Ignorable by Annotation )

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

510
		$table = /** @scrutinizer ignore-deprecated */ $this->getTableName();

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
511
		$nameCol = $this->nameColumn;
512
513
		switch ($rule) {
514
			case 'title':		return "LOWER(`$table`.`$nameCol`) $sqlOp LOWER(?)";
515
			case 'my_flagged':	return "`$table`.`starred` $sqlOp";
516
			case 'favorite':	return "(LOWER(`$table`.`$nameCol`) $sqlOp LOWER(?) AND `$table`.`starred` IS NOT NULL)"; // title search among flagged
517
			case 'added':		return "`$table`.`created` $sqlOp ?";
518
			case 'updated':		return "`$table`.`updated` $sqlOp ?";
519
			case 'mbid':		return "`$table`.`mbid` $sqlOp ?";
520
			default:			throw new \DomainException("Rule '$rule' not supported on this entity type");
521
		}
522
	}
523
524
	/**
525
	 * Find an entity which has the same identity as the supplied entity.
526
	 * How the identity of the entity is defined, depends on the derived concrete class.
527
	 * @phpstan-param EntityType $entity
528
	 * @phpstan-return EntityType
529
	 */
530
	abstract protected function findUniqueEntity(Entity $entity) : Entity;
531
}
532