Modify Apache Solr Queries in Drupal

In a recent project I got the opportunity to tweak Drupal’s Apache solr queries.In this blog post I will present to you some of my favourites.

1. Apache Solr MultiCore Join

2. Boost Query

3. Sort Query

Note: To prepare apache solr query use hook_apachesolr_query_prepare($query)

In this hook are available the entire query object. Prepare the query by adding parameters, sorts, etc.

This hook is invoked before the query is cached. The cached query is used after the search such as for building facet and sort blocks, so parameters added during this hook may be visible to end users. This is otherwise the same as HOOK_apachesolr_query_alter(), but runs before it.

1. Apache Solr MultiCore Join

Scenarios where you need to work on documents that have  relationships and the documents have different information that can not be denormalized, scenarios where the search needs to throw results based on this relation is when we use Join. As the documents can not be denormalized, we will need to maintain multiple cores to index them.

In Drupal this could be the case when we are using Node reference or multi valued fields.

Apachesolr Syntax:

http://localhost:3033/solr/QUESTINORE/select?q={!join from=fromFieldname  to=toFieldname fromIndex=fromCoreName} fromQuery

 

Do it in Drupal:

 

$query->addFilter('_query_',  ‘{!join from=fromFieldname  to=toFieldname  fromIndex=fromCoreName} fromQuery’);

 

Note : The join query will executed only in "from" documents. Also in Apache Solr you can not return fields in the "from" documents to the result. The values in the second core are only used to refine the search - but are not available in the results!

2. Boost Query

Drupal ApacheSolr module has interesting options to rank the relevancy of your results based on fields in a particular content type. eg.the field that stores the cost could be ranked higher. This results in a content getting unified ranking for all users.

But increasingly today we want to be able to rank the results not just based on generic parameters but based on profile of the user. What needs to be ranked high for one user is different from that for another user. So what we need is a sort of dynamic ranking, which can be easily achieved using Apache Solr Boost Query.

Boost Query needs dftype edismax

Apachesolr Syntax:   

http://localhost:3033/solr/QUESTINORE/select?defType=edismax&bq =field_name:value^95

 

Do it in Drupal:

 

$query->addParam('defType', 'edismax');  $query->addParam('bq', 'field_name:value^95');

 

3. Sort Order, newest at the top

The Default sorting in Apache Solr is based on relevancy, to sort a result set based on the created date use boost query on the date field.

Apachesolr Syntax:

http://localhost:3033/solr/QUESTINORE/select?defType=edismax&bf=recip(ms(NOW,ds_changed),3.16e-11,1,1)^94

 

Do it in Drupal:

$query->addParam('defType', 'edismax');  $query->addParam('bf','recip(ms(NOW,ds_changed),3.16e-11,1,1)^94');