Question

I've a field defined in my model as :

@Column(name = "name")
@Field(index = Index.YES, analyze = Analyze.YES, store = Store.NO)
private String name;

and my query is

public Result search(String term, int offset, int limit) {
    WildcardQuery regexQuery = new WildcardQuery(new org.apache.lucene.index.Term("name", "*" + term + "*"));

    QueryBuilder qb = getFullTextSession().getSearchFactory().buildQueryBuilder().forEntity(Company.class).get();
    org.apache.lucene.search.Query query =
            qb.bool().should(qb.phrase().onField("address.street").sentence(term).createQuery())
            .should(regexQuery)
            .createQuery();

    FullTextQuery hibQuery = getFullTextSession().createFullTextQuery(query, Company.class);

    hibQuery.setFirstResult(offset);
    hibQuery.setMaxResults(limit);

    Result result = new Result();
    result.total = hibQuery.getResultSize();
    result.items = hibQuery.list();

    return result;
}

I've a value in database (also indexed) 'Intersprint GmbH.'. If i call the method :

search("Interspr");

i expect to get this entity but result was empty. Any suggestion how can i build a "contains" query?

Was it helpful?

Solution

My guess is capitalization. I assume that "Intersprint GmbH" is indexed as two tokens - "intersprint" and "gmbh" (all lowercase, because an analyzer got applied. At query time you use a WildcardQuery with a given term "Interspr". There is no analyzer applied in this case, meaning you have no match between the lower cased "intersprint" and the wildcard query "Inter". You can confirm this by checking the index with Luke.

As a solution you can either use a QueryParser (which also uses the analyzer) or you use QueryBuilder#keyword#wildcard() which also will apply the analyzer. In the latter case the right analyzer should even be picked transparently for you.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top