Abstract
This chapter covers additional support for Solr operations (such as faceting) that cannot be directly accessed via the repository interface. It is recommended to add those operations as custom implementation as described in Section 1.3, “Custom implementations for Spring Data repositories” .
PartialUpdates can be done using
PartialUpdate
which implements
Update
.
Note | |
---|---|
Partial updates require Solr 4.x. With Solr 4.0.0 it is not possible to update mulitvalue fields. |
Note | |
---|---|
With Solr 4.1.0 you have to take care on parameter order when setting null values. Order parameters with nulls last. |
Example 3.1.
PartialUpdate update = new PartialUpdate("id", "123"); update.add("name", "updated-name"); solrTemplate.saveBean(update);
Projections can be applied via
@Query
using the fields value.
Example 3.2.
@Query(fields = { "name", "id" })
List<ProductBean> findByNameStartingWith(String name);
Faceting cannot be directly applied using the
SolrRepository
but the
SolrTemplate
holds support for this feature.
Example 3.3.
FacetQuery query = new SimpleFacetQuery(new Criteria(Criteria.WILDCARD).expression(Criteria.WILDCARD)) .setFacetOptions(new FacetOptions().addFacetOnField("name").setFacetLimit(5)); FacetPage<Product> page = solrTemplate.queryForFacetPage(query, Product.class);
Facets on fields and/or queries can also be defined using
@Facet
. Please mind that the result will be a
FacetPage
.
Note | |
---|---|
Using
@Facet
allows you to define place holders which will use your input
parameter as value.
|
Example 3.4.
@Query(value = "*:*") @Facet(fields = { "name" }, limit = 5) FacetPage<Product> findAllFacetOnName(Pageable page);
Example 3.5.
@Query(value = "popularity:?0") @Facet(fields = { "name" }, limit = 5, prefix="?1") FacetPage<Product> findByPopularityFacetOnName(int popularity, String prefix, Pageable page);
Solr allows definition of facet parameters on a per field basis. In order to add special facet options to defined fields use FieldWithFacetParameters
.
Example 3.6.
// produces: f.name.facet.prefix=spring FacetOptions options = new FacetOptions(); options.addFacetOnField(new FieldWithFacetParameters("name").setPrefix("spring"));
Terms Vector cannot directly be used within SolrRepository
but can be applied via SolrTemplate
.
Please mind, that the result will be a TermsPage
.
Example 3.7.
TermsQuery query = SimpleTermsQuery.queryBuilder().fields("name").build();
TermsPage page = solrTemplate.queryForTermsPage(query);
Filter Queries improve query speed and do not influence document score. It is recommended to implement geospatial search as filter query.
Note | |
---|---|
Please note that in solr, unless otherwise specified, all units of distance are kilometers and points are in degrees of latitude,longitude. |
Example 3.8.
Query query = new SimpleQuery(new Criteria("category").is("supercalifragilisticexpialidocious")); FilterQuery fq = new SimpleFilterQuery(new Criteria("store") .near(new GeoLocation(48.305478, 14.286699), new Distance(5))); query.addFilterQuery(fq);
Simple filter queries can also be defined using
@Query
.
Note | |
---|---|
Using
@Query
allows you to define place holders which will use your input
parameter as value.
|
@Query(value = "*:*", filters = { "inStock:true", "popularity:[* TO 3]" })
List<Product> findAllFilterAvailableTrueAndPopularityLessThanEqual3();
It it possible to set the time allowed for a search to finish. This value only applies to the search and not to requests in general. Time is in milliseconds. Values less than or equal to zero implies no time restriction. Partial results may be returned, if there are any.
Example 3.9.
Query query = new SimpleQuery(new SimpleStringCriteria("field_1:value_1")); // Allowing maximum of 100ms for this search query.setTimeAllowed(100);
Boost document score in case of matching criteria to influence result order. This can be done by either
setting boost on Criteria
or using @Boost
for derived queries.
Boosting documents score can be done on index time by using @SolrDocument
annotation on
classes (for Solr documents) and/or @Indexed
on fields (for Solr fields).
Example 3.11.
import org.apache.solr.client.solrj.beans.Field; import org.springframework.data.solr.repository.Boost; @SolrDocument(boost = 0.8f) public class MyEntity { @Id @Indexed private String id; @Indexed(boost = 1.0f) private String name; // setters and getters ... }
Select the request handler via qt
Parameter directly in
Query
or add @Query
to your method signature.
Example 3.12.
@Query(requestHandler = "/instock")
Page<Product> findByNameOrDescription(String name, String description);
Join attributes within one solr core by defining Join
attribute of Query
.
Note | |
---|---|
Join is not available prior to solr 4.x. |
Example 3.13.
SimpleQuery query = new SimpleQuery(new SimpleStringCriteria("text:ipod")); query.setJoin(Join.from("manu_id_s").to("id"));
To highlight matches in search result add HighlightOptions
to the SimpleHighlightQuery
.
Providing HighlightOptions
without any further attributes will highlight apply highlighting on all fields within a SolrDocument
.
Note | |
---|---|
Field specific highlight parameters can be set by adding FieldWithHighlightParameters to HighlightOptions .
|
Example 3.14.
SimpleHighlightQuery query = new SimpleHighlightQuery(new SimpleStringCriteria("name:with")); query.setHighlightOptions(new HighlightOptions()); HighlightPage<Product> page = solrTemplate.queryForHighlightPage(query, Product.class);
Not all parameters are available via setters/getters but can be added directly.
Example 3.15.
SimpleHighlightQuery query = new SimpleHighlightQuery(new SimpleStringCriteria("name:with")); query.setHighlightOptions(new HighlightOptions().addHighlightParameter("hl.bs.country", "at"));
In order to apply Highlighting to derived queries use @Highlight
. If no fields
are defined highlighting will be aplied on all fields.
Example 3.16.
@Highlight(prefix = "<b>", postfix = "</b>")
HighlightPage<Product> findByName(String name, Pageable page);
Solr supports several functional expressions within queries. Followig functions are supported out of the box. Custom functions can be added by implementing Function
Table 3.1. Functions
Class | Solr Function |
---|---|
CurrencyFunction
|
currency(field_name,[CODE])
|
DefaultValueFunction
|
def(field|function,defaultValue)
|
DistanceFunction
|
dist(power, pointA, pointB)
|
DivideFunction
|
div(x,y)
|
ExistsFunction
|
exists(field|function)
|
GeoDistanceFunction
|
geodist(sfield, latitude, longitude)
|
GeoHashFunction
|
geohash(latitude, longitude)
|
IfFunction
|
if(value|field|function,trueValue,falseValue)
|
MaxFunction
|
max(field|function,value)
|
NotFunction
|
not(field|function)
|
ProductFunction
|
product(x,y,...)
|
QueryFunction
|
query(x)
|
TermFrequencyFunction
|
termfreq(field,term)
|
Example 3.17.
SimpleQuery query = new SimpleQuery(new SimpleStringCriteria("text:ipod")); query.addFilterQuery(new FilterQuery(Criteria.where(QueryFunction.query("name:sol*"))));