You are here

protected function SearchApiMultiQuery::ensureSortFields in Search API Multi-Index Searches 7

Ensure that all results have all fields needed for sorting.

Parameters

array $results: The results array, as in the 'results' key of the return value of SearchApiMultiQueryInterface::execute().

1 call to SearchApiMultiQuery::ensureSortFields()
SearchApiMultiQuery::searchMultiple in ./search_api_multi.query.inc
Searches multiple indexes with this query.

File

./search_api_multi.query.inc, line 906

Class

SearchApiMultiQuery
Standard implementation of SearchApiMultiQueryInterface.

Code

protected function ensureSortFields(array &$results) {
  $sort = array_keys($this->sort);

  // Eliminate special fields which are always included.
  foreach ($sort as $i => $key) {
    if ($key == 'search_api_id' || $key == 'search_api_relevance') {
      unset($sort[$i]);
    }
  }
  if (!$sort) {
    return;
  }

  // Determine what fields we need from items of each index.
  $fields = array();
  foreach ($sort as $key) {
    list($index_id, $field) = explode(':', $key, 2);
    if (!empty($this->indexes[$index_id])) {
      $fields[$index_id][$field] = $this->indexes[$index_id]->options['fields'][$field];
    }
  }
  if (!$fields) {
    return;
  }

  // Determine for which items we need the entity.
  $to_load = array();
  foreach ($results as $i => $result) {
    $results[$i] = $result += array(
      'fields' => array(),
      'entity' => NULL,
    );
    if (empty($fields[$result['index_id']]) || $result['entity']) {
      continue;
    }
    foreach ($fields[$result['index_id']] as $field => $info) {
      if (!array_key_exists($field, $result['fields'])) {
        $to_load[$this->indexes[$result['index_id']]->item_type][$i] = $result['id'];
        break;
      }
    }
  }

  // Load items, as necessary.
  foreach ($to_load as $type => $ids) {
    $type_items = search_api_get_datasource_controller($type)
      ->loadItems($ids);
    foreach ($ids as $i => $id) {
      if (isset($type_items[$id])) {
        $results[$i]['entity'] = $type_items[$id];
      }
    }
  }

  // Now extract the fields for each item.
  foreach ($results as $i => $result) {
    if (empty($fields[$result['index_id']])) {
      continue;
    }
    $item_fields = $fields[$result['index_id']];
    if (empty($result['entity'])) {
      $results[$i]['fields'] += array_fill_keys(array_keys($item_fields), NULL);
      continue;
    }
    $item_fields = array_diff_key($item_fields, $result['fields']);
    if ($item_fields) {
      $wrapper = $this->indexes[$result['index_id']]
        ->entityWrapper($result['entity']);
      $item_fields = search_api_extract_fields($wrapper, $item_fields);
      foreach ($item_fields as $field => $info) {
        $results[$i]['fields'][$field] = $info['value'];
      }
    }
  }
}