diff --git a/core/lib/Drupal/Core/Config/Entity/Query/Query.php b/core/lib/Drupal/Core/Config/Entity/Query/Query.php index b398f83..7f433cb 100644 --- a/core/lib/Drupal/Core/Config/Entity/Query/Query.php +++ b/core/lib/Drupal/Core/Config/Entity/Query/Query.php @@ -84,17 +84,19 @@ public function condition($property, $value = NULL, $operator = NULL, $langcode * Implements \Drupal\Core\Entity\Query\QueryInterface::execute(). */ public function execute() { - // Load all config files. $entity_info = $this->entityManager->getDefinition($this->getEntityType()); $prefix = $entity_info['config_prefix'] . '.'; $prefix_length = strlen($prefix); - $names = $this->configStorage->listAll($prefix); + + // Load the relevant config files. $configs = array(); + $names = $this->findNames($entity_info); $config_objects = $this->configFactory->loadMultiple($names); foreach ($config_objects as $config) { $configs[substr($config->getName(), $prefix_length)] = $config->get(); } + // Apply conditions. $result = $this->condition->compile($configs); // Apply sort settings. @@ -124,4 +126,46 @@ public function execute() { return $result; } + /** + * Determines the names of config records to load for the query. + * + * @param array $entity_info + * The entity info. + * + * @return array + * The list of config record names to load. + */ + protected function findNames(array $entity_info) { + $prefix = $entity_info['config_prefix'] . '.'; + + // If there are conditions on the config id, we can narrow the list of + // config records to load and parse. + $ids = array(); + if ($this->condition->getConjunction() == 'AND') { + foreach ($this->condition->conditions() as $condition) { + if ($condition['field'] == $entity_info['entity_keys']['id']) { + $operator = $condition['operator']; + if (!isset($condition['operator'])) { + $operator = is_array($condition['value']) ? 'IN' : '='; + } + if ($operator == '=' || $operator == 'IN') { + $ids = is_array($condition['value']) ? $condition['value'] : array($condition['value']); + // We can stop at the first condition on ID. In the (weird) case + // where other conditions additionally restrict IDs, results will + // be eliminated when the conditions are checked on the loaded + // records. + break; + } + } + } + } + if ($ids) { + return array_map(function ($id) use ($prefix) { + return $prefix . $id; + }, $ids); + } + + // If no conditions on IDs were found, we need to look at all the records. + return $this->configStorage->listAll($prefix); + } }