Skip to content

Commit

Permalink
Merge pull request #87 from zuliaio/query_builder
Browse files Browse the repository at this point in the history
Query Values Builder
  • Loading branch information
payammeyer authored Jan 3, 2023
2 parents 7efabd3 + 1ed9254 commit 5796cc0
Show file tree
Hide file tree
Showing 7 changed files with 328 additions and 74 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -2,32 +2,37 @@

import io.zulia.message.ZuliaQuery;

public class FilterQuery extends StandardQuery {

private boolean exclude = false;

public FilterQuery(String query) {
super(query);
}

public FilterQuery include() {
exclude = false;
return this;
}

public FilterQuery exclude() {
exclude = true;
return this;
}

@Override
protected void completeQuery(ZuliaQuery.Query.Builder queryBuilder) {
if (exclude) {
queryBuilder.setQueryType(ZuliaQuery.Query.QueryType.FILTER_NOT);
}
else {
queryBuilder.setQueryType(ZuliaQuery.Query.QueryType.FILTER);
}
}
public class FilterQuery extends StandardQuery<FilterQuery> {

private boolean exclude = false;

public FilterQuery(String query) {
super(query);
}

@Override
protected FilterQuery getSelf() {
return this;
}

public FilterQuery include() {
exclude = false;
return this;
}

public FilterQuery exclude() {
exclude = true;
return this;
}

@Override
protected void completeQuery(ZuliaQuery.Query.Builder queryBuilder) {
if (exclude) {
queryBuilder.setQueryType(ZuliaQuery.Query.QueryType.FILTER_NOT);
} else {
queryBuilder.setQueryType(ZuliaQuery.Query.QueryType.FILTER);
}
}


}
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,22 @@
import io.zulia.message.ZuliaQuery;
import io.zulia.message.ZuliaQuery.Query.QueryType;

public class ScoredQuery extends StandardQuery {
public class ScoredQuery extends StandardQuery<ScoredQuery> {
private boolean must;
private String scoreFunction;

public ScoredQuery(String query) {
this(query, true);
}

@Override
protected ScoredQuery getSelf() {
return this;
}

/**
*
* @param query
* @param must - if must is true than query will be required, otherwise it will be used to as an optional (should clause) to help scoring
* @param must - if must is true then query will be required, otherwise it will be used to as an optional (should clause) to help scoring
*/
public ScoredQuery(String query, boolean must) {
super(query);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

import java.util.List;

public abstract class StandardQuery implements QueryBuilder {
public abstract class StandardQuery<T extends StandardQuery> implements QueryBuilder {

private final ZuliaQuery.Query.Builder queryBuilder;

Expand All @@ -18,60 +18,62 @@ public StandardQuery(String query) {
}
}

public StandardQuery setQuery(String query) {
public T setQuery(String query) {
queryBuilder.setQ(query);
return this;
return getSelf();
}

protected abstract T getSelf();

public List<String> getQueryFields() {
return queryBuilder.getQfList();
}

public StandardQuery addQueryField(String queryField) {
public T addQueryField(String queryField) {
queryBuilder.addQf(queryField);
return this;
return getSelf();
}

public StandardQuery addQueryFields(String... queryFields) {
public T addQueryFields(String... queryFields) {
queryBuilder.addAllQf(List.of(queryFields));
return this;
return getSelf();
}

public StandardQuery addQueryFields(Iterable<String> queryFields) {
public T addQueryFields(Iterable<String> queryFields) {
queryBuilder.addAllQf(queryFields);
return this;
return getSelf();
}

public StandardQuery clearQueryField() {
public T clearQueryField() {
queryBuilder.clearQf();
return this;
return getSelf();
}

public StandardQuery setQueryFields(@NotNull List<String> queryFields) {
public T setQueryFields(@NotNull List<String> queryFields) {
if (queryFields == null) {
throw new IllegalArgumentException("Query Fields cannot be null");
}
queryBuilder.clearQf();
queryBuilder.addAllQf(queryFields);
return this;
return getSelf();
}

public ZuliaQuery.Query.Operator getDefaultOperator() {
return queryBuilder.getDefaultOp();
}

public StandardQuery setDefaultOperator(ZuliaQuery.Query.Operator defaultOperator) {
public T setDefaultOperator(ZuliaQuery.Query.Operator defaultOperator) {
queryBuilder.setDefaultOp(defaultOperator);
return this;
return getSelf();
}

public int getMinShouldMatch() {
return queryBuilder.getMm();
}

public StandardQuery setMinShouldMatch(int minShouldMatch) {
public T setMinShouldMatch(int minShouldMatch) {
queryBuilder.setMm(minShouldMatch);
return this;
return getSelf();
}

@Override
Expand Down
164 changes: 164 additions & 0 deletions zulia-client/src/main/java/io/zulia/client/command/factory/Values.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,164 @@
package io.zulia.client.command.factory;

import com.google.common.base.Joiner;
import io.zulia.client.command.builder.FilterQuery;
import io.zulia.client.command.builder.ScoredQuery;
import io.zulia.client.command.builder.StandardQuery;
import io.zulia.message.ZuliaQuery.Query.Operator;

import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.function.Function;

public class Values {
public static final Joiner COMMA_JOINER = Joiner.on(",");
public static final Joiner SPACE_JOINER = Joiner.on(" ");
public static final Joiner OR_JOINER = Joiner.on(" OR ");

public static final Joiner AND_JOINER = Joiner.on(" AND ");

public static Function<String, String> VALUE_QUOTER = s -> {
s = s.trim();
if (s.startsWith("\"") && s.endsWith("\"")) {
return s;
}
if (s.contains(" ") || s.contains("-")) {
return "\"" + s + "\"";
}
return s;
};


private final Type type;

private final Integer minimumShouldMatch;

private Collection<String> values;

private Collection<String> fields;
private boolean exclude;

private Function<String, String> valueHandler = VALUE_QUOTER;


private enum Type {
ANY, ALL, AT_LEAST
}

public static Values any() {
return new Values(Type.ANY, null);
}

public static Values all() {
return new Values(Type.ALL, null);
}

public static Values atLeast(int minimumShouldMatch) {
return new Values(Type.AT_LEAST, minimumShouldMatch);
}

private Values(Type type, Integer minimumShouldMatch) {
this.type = type;
this.minimumShouldMatch = minimumShouldMatch;
}

public Values of(String... values) {
this.values = Arrays.stream(values).toList();
return this;
}

public Values of(Collection<String> values) {
this.values = values;
return this;
}


public Values exclude() {
this.exclude = true;
return this;
}

public Values include() {
this.exclude = false;
return this;
}


public Values withFields(String... fields) {
this.fields = List.of(fields);
return this;
}

public Values withFields(Collection<String> fields) {
this.fields = fields;
return this;
}


public void setValueHandler(Function<String, String> valueHandler) {
this.valueHandler = valueHandler;
}

public String asString() {

StringBuilder sb = new StringBuilder();

if (exclude) {
sb.append("-");
}

if (fields != null && !fields.isEmpty()) {
COMMA_JOINER.appendTo(sb, fields);
sb.append(":");
}
sb.append("(");

List<String> valuesHandled = values.stream().map(valueHandler).toList();
if (type.equals(Type.ALL)) {
AND_JOINER.appendTo(sb, valuesHandled);
} else {
OR_JOINER.appendTo(sb, valuesHandled);
}
sb.append(")");
if (type.equals(Type.AT_LEAST)) {
sb.append("~");
sb.append(minimumShouldMatch);
}
return sb.toString();
}


public FilterQuery asFilterQuery() {
return asQuery(FilterQuery::new);
}

public ScoredQuery asScoredQuery() {
return asQuery(ScoredQuery::new);
}


public <T extends StandardQuery<T>> T asQuery(Function<String, T> constructor) {
List<String> valuesHandled = values.stream().map(valueHandler).toList();
String query = SPACE_JOINER.join(valuesHandled);
T tQuery = constructor.apply(query);
tQuery.setDefaultOperator(type.equals(Type.ALL) ? Operator.AND : Operator.OR);
fields.forEach(tQuery::addQueryField);

if (exclude) {
if (tQuery instanceof FilterQuery fq) {
fq.exclude();
} else if (tQuery instanceof ScoredQuery sq) {
throw new IllegalStateException("Exclude cannot be used with ScoredQuery");
}
}
if (minimumShouldMatch != null) {
tQuery.setMinShouldMatch(minimumShouldMatch);
}
return tQuery;
}




}
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
import io.zulia.client.config.ClientIndexConfig;
import io.zulia.client.config.ZuliaPoolConfig;
import io.zulia.client.result.*;
import io.zulia.fields.Mapper;
import io.zulia.fields.GsonDocumentMapper;
import io.zulia.message.ZuliaIndex.IndexAlias;
import io.zulia.message.ZuliaQuery.ScoredResult;
import io.zulia.util.ResultHelper;
Expand Down Expand Up @@ -215,12 +215,11 @@ public SearchResult search(Search search) throws Exception {
return execute(search);
}

public <T> void searchAllAsMappedDocument(Search search, Mapper<T> mapper, Consumer<T> mappedDocumentHandler) throws Exception {
public <T> void searchAllAsMappedDocument(Search search, GsonDocumentMapper<T> mapper, Consumer<T> mappedDocumentHandler) throws Exception {
searchAllAsScoredResult(search, scoredResult -> {
try {
mappedDocumentHandler.accept(mapper.fromScoredResult(scoredResult));
}
catch (Exception e) {
} catch (Exception e) {
throw new RuntimeException(e);
}
});
Expand Down
Loading

0 comments on commit 5796cc0

Please sign in to comment.