chg: [internal] Optimise Tag::findTagIdsByTagNames

pull/7908/head
Jakub Onderka 2021-10-30 19:13:17 +02:00
parent ab432a02d6
commit 9ae7d88f23
3 changed files with 30 additions and 30 deletions

View File

@ -2554,9 +2554,8 @@ class AppModel extends Model
} }
// generate a generic subquery - options needs to include conditions // generate a generic subquery - options needs to include conditions
public function subQueryGenerator($model, $options, $lookupKey, $negation = false) protected function subQueryGenerator(AppModel $model, array $options, $lookupKey, $negation = false)
{ {
$db = $model->getDataSource();
$defaults = array( $defaults = array(
'fields' => array('*'), 'fields' => array('*'),
'table' => $model->table, 'table' => $model->table,
@ -2569,17 +2568,15 @@ class AppModel extends Model
'recursive' => -1 'recursive' => -1
); );
$params = array(); $params = array();
foreach (array_keys($defaults) as $key) { foreach ($defaults as $key => $defaultValue) {
if (isset($options[$key])) { if (isset($options[$key])) {
$params[$key] = $options[$key]; $params[$key] = $options[$key];
} else { } else {
$params[$key] = $defaults[$key]; $params[$key] = $defaultValue;
} }
} }
$subQuery = $db->buildStatement( $db = $model->getDataSource();
$params, $subQuery = $db->buildStatement($params, $model);
$model
);
if ($negation) { if ($negation) {
$subQuery = $lookupKey . ' NOT IN (' . $subQuery . ') '; $subQuery = $lookupKey . ' NOT IN (' . $subQuery . ') ';
} else { } else {

View File

@ -1229,6 +1229,7 @@ class Attribute extends AppModel
if (empty($params['tags'])) { if (empty($params['tags'])) {
return $conditions; return $conditions;
} }
/** @var Tag $tag */
$tag = ClassRegistry::init('Tag'); $tag = ClassRegistry::init('Tag');
$params['tags'] = $this->dissectArgs($params['tags']); $params['tags'] = $this->dissectArgs($params['tags']);
foreach (array(0, 1, 2) as $tag_operator) { foreach (array(0, 1, 2) as $tag_operator) {
@ -1683,13 +1684,13 @@ class Attribute extends AppModel
// array 1 will have all of the non negated terms and array 2 all the negated terms // array 1 will have all of the non negated terms and array 2 all the negated terms
public function dissectArgs($args) public function dissectArgs($args)
{ {
$result = array(0 => array(), 1 => array(), 2 => array());
if (empty($args)) { if (empty($args)) {
return array(0 => array(), 1 => array(), 2 => array()); return $result;
} }
if (!is_array($args)) { if (!is_array($args)) {
$args = explode('&&', $args); $args = explode('&&', $args);
} }
$result = array(0 => array(), 1 => array(), 2 => array());
if (isset($args['OR']) || isset($args['NOT']) || isset($args['AND'])) { if (isset($args['OR']) || isset($args['NOT']) || isset($args['AND'])) {
if (!empty($args['OR'])) { if (!empty($args['OR'])) {
$result[0] = $args['OR']; $result[0] = $args['OR'];

View File

@ -277,38 +277,40 @@ class Tag extends AppModel
return array($acceptIds, $rejectIds); return array($acceptIds, $rejectIds);
} }
// pass a list of tag names to receive a list of matched tag IDs /**
* pass a list of tag names to receive a list of matched tag IDs
* @param string|array $array
* @return array|int|null
*/
public function findTagIdsByTagNames($array) public function findTagIdsByTagNames($array)
{ {
$ids = array();
$tag_ids = array();
if (!is_array($array)) { if (!is_array($array)) {
$array = array($array); $array = array($array);
} }
foreach ($array as $k => $tag) { $tagIds = [];
$tagNames = [];
foreach ($array as $tag) {
if (is_numeric($tag)) { if (is_numeric($tag)) {
$tag_ids[] = $tag; $tagIds[] = $tag;
unset($array[$k]); } else {
$tagNames[] = $tag;
} }
} }
$array = array_values($array); if (!empty($tagNames)) {
if (!empty($array)) { $conditions = [];
foreach ($array as $a) { foreach ($tagNames as $tagName) {
$conditions['OR'][] = array('Tag.name like' => $a); $conditions[] = array('Tag.name LIKE' => $tagName);
} }
$params = array( $result = $this->find('column', array(
'recursive' => 1, 'recursive' => 1,
'conditions' => $conditions, 'conditions' => ['OR' => $conditions],
'fields' => array('Tag.id', 'Tag.id') 'fields' => array('Tag.id')
); ));
$result = $this->find('list', $params); $tagIds = array_merge($result, $tagIds);
$tag_ids = array_merge($result, $tag_ids);
} }
return array_values($tag_ids); return $tagIds;
} }
/** /**
* @param array $tag * @param array $tag
* @param array $user * @param array $user