You are here

function apachesolr_do_query in Apache Solr Search 7

Same name and namespace in other branches
  1. 8 apachesolr.module \apachesolr_do_query()
  2. 5.2 apachesolr.module \apachesolr_do_query()
  3. 6.3 apachesolr.module \apachesolr_do_query()
  4. 6 apachesolr.module \apachesolr_do_query()
  5. 6.2 apachesolr.module \apachesolr_do_query()

Execute a keyword search based on a query object.

Normally this function is used with the default (dismax) handler for keyword searches. The $final_query that's returned will have been modified by both hook_apachesolr_query_prepare() and hook_apachesolr_query_alter().

Parameters

$current_query: A query object from apachesolr_drupal_query(). It will be modified by hook_apachesolr_query_prepare() and then cached in apachesolr_current_query().

$page: For paging into results, using $current_query->params['rows'] results per page.

Return value

array($final_query, $response)

Throws

Exception

2 calls to apachesolr_do_query()
apachesolr_search_run in ./apachesolr_search.module
Execute a search results based on keyword, filter, and sort strings.
apachesolr_search_run_empty in ./apachesolr_search.module
Execute a search with zero results rows so as to populate facets.

File

./apachesolr.module, line 1523
Integration with the Apache Solr search application.

Code

function apachesolr_do_query(DrupalSolrQueryInterface $current_query) {
  if (!is_object($current_query)) {
    throw new Exception(t('NULL query object in function apachesolr_do_query()'));
  }

  // Allow modules to alter the query prior to statically caching it.
  // This can e.g. be used to add available sorts.
  $searcher = $current_query
    ->getSearcher();
  if (module_exists('facetapi')) {

    // Gets enabled facets, adds filter queries to $params.
    $adapter = facetapi_adapter_load($searcher);
    if ($adapter) {

      // Realm could be added but we want all the facets
      $adapter
        ->addActiveFilters($current_query);
    }
  }
  foreach (module_implements('apachesolr_query_prepare') as $module) {
    $function_name = $module . '_apachesolr_query_prepare';
    $function_name($current_query);
  }

  // Cache the original query. Since all the built queries go through
  // this process, all the hook_invocations will happen later
  $env_id = $current_query
    ->solr('getId');

  // Add our defType setting here. Normally this would be dismax or the setting
  // from the solrconfig.xml. This allows the setting to be overridden.
  $defType = apachesolr_environment_variable_get($env_id, 'apachesolr_query_type');
  if (!empty($defType)) {
    $current_query
      ->addParam('defType', $defType);
  }
  $query = apachesolr_current_query($env_id, $current_query);

  // Verify if this query was already executed in the same page load
  if ($response = apachesolr_static_response_cache($searcher)) {

    // Return cached query object
    return array(
      $query,
      $response,
    );
  }
  $query
    ->addParam('start', $query->page * $query
    ->getParam('rows'));

  // This hook allows modules to modify the query and params objects.
  drupal_alter('apachesolr_query', $query);
  if ($query->abort_search) {

    // A module implementing HOOK_apachesolr_query_alter() aborted the search.
    return array(
      NULL,
      array(),
    );
  }
  $keys = $query
    ->getParam('q');
  if (strlen($keys) == 0 && ($filters = $query
    ->getFilters())) {

    // Move the fq params to q.alt for better performance. Only suitable
    // when using dismax or edismax, so we keep this out of the query class itself
    // for now.
    $qalt = array();
    foreach ($filters as $delta => $filter) {

      // Move the fq param if it has no local params and is not negative.
      if (!$filter['#exclude'] && !$filter['#local']) {
        $qalt[] = '(' . $query
          ->makeFilterQuery($filter) . ')';
        $query
          ->removeFilter($filter['#name'], $filter['#value'], $filter['#exclude']);
      }
    }
    if ($qalt) {
      $query
        ->addParam('q.alt', implode(' AND ', $qalt));
    }
  }

  // We must run htmlspecialchars() here since converted entities are in the index.
  // and thus bare entities &, > or < won't match. Single quotes are converted
  // too, but not double quotes since the dismax parser looks at them for
  // phrase queries.
  $keys = htmlspecialchars($keys, ENT_NOQUOTES, 'UTF-8');
  $keys = str_replace("'", '&#039;', $keys);
  $response = $query
    ->search($keys);

  // The response is cached so that it is accessible to the blocks and anything
  // else that needs it beyond the initial search.
  apachesolr_static_response_cache($searcher, $response);
  return array(
    $query,
    $response,
  );
}