DATAES-106 - Add support for countBy projection
This commit is contained in:
committed by
Mohsin Husen
parent
c866664acc
commit
1ea9920a0d
@@ -30,6 +30,7 @@ import org.springframework.data.elasticsearch.core.query.*;
|
||||
*
|
||||
* @author Rizwan Idrees
|
||||
* @author Mohsin Husen
|
||||
* @author Kevin Leturc
|
||||
*/
|
||||
public interface ElasticsearchOperations {
|
||||
|
||||
@@ -246,6 +247,23 @@ public interface ElasticsearchOperations {
|
||||
*/
|
||||
<T> List<String> queryForIds(SearchQuery query);
|
||||
|
||||
/**
|
||||
* return number of elements found by given query
|
||||
*
|
||||
* @param query
|
||||
* @param clazz
|
||||
* @return
|
||||
*/
|
||||
<T> long count(CriteriaQuery query, Class<T> clazz);
|
||||
|
||||
/**
|
||||
* return number of elements found by given query
|
||||
*
|
||||
* @param query
|
||||
* @return
|
||||
*/
|
||||
<T> long count(CriteriaQuery query);
|
||||
|
||||
/**
|
||||
* return number of elements found by given query
|
||||
*
|
||||
|
||||
@@ -50,6 +50,7 @@ import org.elasticsearch.action.index.IndexRequestBuilder;
|
||||
import org.elasticsearch.action.mlt.MoreLikeThisRequestBuilder;
|
||||
import org.elasticsearch.action.search.SearchRequestBuilder;
|
||||
import org.elasticsearch.action.search.SearchResponse;
|
||||
import org.elasticsearch.action.search.SearchType;
|
||||
import org.elasticsearch.action.update.UpdateRequestBuilder;
|
||||
import org.elasticsearch.action.update.UpdateResponse;
|
||||
import org.elasticsearch.client.Client;
|
||||
@@ -96,6 +97,7 @@ import org.springframework.util.Assert;
|
||||
* @author Rizwan Idrees
|
||||
* @author Mohsin Husen
|
||||
* @author Artur Konczak
|
||||
* @author Kevin Leturc
|
||||
*/
|
||||
|
||||
public class ElasticsearchTemplate implements ElasticsearchOperations, ApplicationContextAware {
|
||||
@@ -317,10 +319,65 @@ public class ElasticsearchTemplate implements ElasticsearchOperations, Applicati
|
||||
return mapper.mapResults(response, clazz, query.getPageable());
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> long count(CriteriaQuery criteriaQuery, Class<T> clazz) {
|
||||
QueryBuilder elasticsearchQuery = new CriteriaQueryProcessor().createQueryFromCriteria(criteriaQuery.getCriteria());
|
||||
FilterBuilder elasticsearchFilter = new CriteriaFilterProcessor().createFilterFromCriteria(criteriaQuery.getCriteria());
|
||||
|
||||
if (elasticsearchFilter == null) {
|
||||
return doCount(prepareCount(criteriaQuery, clazz), elasticsearchQuery);
|
||||
} else {
|
||||
// filter could not be set into CountRequestBuilder, convert request into search request
|
||||
return doCount(prepareSearch(criteriaQuery, clazz), elasticsearchQuery, elasticsearchFilter);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> long count(SearchQuery searchQuery, Class<T> clazz) {
|
||||
String indexName[] = isNotEmpty(searchQuery.getIndices()) ? searchQuery.getIndices().toArray(new String[searchQuery.getIndices().size()]) : retrieveIndexNameFromPersistentEntity(clazz);
|
||||
String types[] = isNotEmpty(searchQuery.getTypes()) ? searchQuery.getTypes().toArray(new String[searchQuery.getTypes().size()]) : retrieveTypeFromPersistentEntity(clazz);
|
||||
QueryBuilder elasticsearchQuery = searchQuery.getQuery();
|
||||
FilterBuilder elasticsearchFilter = searchQuery.getFilter();
|
||||
|
||||
if (elasticsearchFilter == null) {
|
||||
return doCount(prepareCount(searchQuery, clazz), elasticsearchQuery);
|
||||
} else {
|
||||
// filter could not be set into CountRequestBuilder, convert request into search request
|
||||
return doCount(prepareSearch(searchQuery, clazz), elasticsearchQuery, elasticsearchFilter);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> long count(CriteriaQuery query) {
|
||||
return count(query, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> long count(SearchQuery query) {
|
||||
return count(query, null);
|
||||
}
|
||||
|
||||
private long doCount(CountRequestBuilder countRequestBuilder, QueryBuilder elasticsearchQuery) {
|
||||
if (elasticsearchQuery != null) {
|
||||
countRequestBuilder.setQuery(elasticsearchQuery);
|
||||
}
|
||||
return countRequestBuilder.execute().actionGet().getCount();
|
||||
}
|
||||
|
||||
private long doCount(SearchRequestBuilder searchRequestBuilder, QueryBuilder elasticsearchQuery, FilterBuilder elasticsearchFilter) {
|
||||
if (elasticsearchQuery != null) {
|
||||
searchRequestBuilder.setQuery(elasticsearchQuery);
|
||||
} else {
|
||||
searchRequestBuilder.setQuery(QueryBuilders.matchAllQuery());
|
||||
}
|
||||
if (elasticsearchFilter != null) {
|
||||
searchRequestBuilder.setPostFilter(elasticsearchFilter);
|
||||
}
|
||||
searchRequestBuilder.setSearchType(SearchType.COUNT);
|
||||
return searchRequestBuilder.execute().actionGet().getHits().getTotalHits();
|
||||
}
|
||||
|
||||
private <T> CountRequestBuilder prepareCount(Query query, Class<T> clazz) {
|
||||
String indexName[] = isNotEmpty(query.getIndices()) ? query.getIndices().toArray(new String[query.getIndices().size()]) : retrieveIndexNameFromPersistentEntity(clazz);
|
||||
String types[] = isNotEmpty(query.getTypes()) ? query.getTypes().toArray(new String[query.getTypes().size()]) : retrieveTypeFromPersistentEntity(clazz);
|
||||
|
||||
Assert.notNull(indexName, "No index defined for Query");
|
||||
|
||||
@@ -329,15 +386,7 @@ public class ElasticsearchTemplate implements ElasticsearchOperations, Applicati
|
||||
if (types != null) {
|
||||
countRequestBuilder.setTypes(types);
|
||||
}
|
||||
if (searchQuery.getQuery() != null) {
|
||||
countRequestBuilder.setQuery(searchQuery.getQuery());
|
||||
}
|
||||
return countRequestBuilder.execute().actionGet().getCount();
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> long count(SearchQuery query) {
|
||||
return count(query, null);
|
||||
return countRequestBuilder;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -28,6 +28,7 @@ import org.springframework.data.repository.query.parser.PartTree;
|
||||
*
|
||||
* @author Rizwan Idrees
|
||||
* @author Mohsin Husen
|
||||
* @author Kevin Leturc
|
||||
*/
|
||||
public class ElasticsearchPartQuery extends AbstractElasticsearchRepositoryQuery {
|
||||
|
||||
@@ -52,6 +53,8 @@ public class ElasticsearchPartQuery extends AbstractElasticsearchRepositoryQuery
|
||||
query.setPageable(accessor.getPageable());
|
||||
}
|
||||
return elasticsearchOperations.queryForList(query, queryMethod.getEntityInformation().getJavaType());
|
||||
} else if (tree.isCountProjection()) {
|
||||
return elasticsearchOperations.count(query, queryMethod.getEntityInformation().getJavaType());
|
||||
}
|
||||
return elasticsearchOperations.queryForObject(query, queryMethod.getEntityInformation().getJavaType());
|
||||
}
|
||||
|
||||
@@ -19,8 +19,6 @@ import java.lang.reflect.Method;
|
||||
|
||||
import org.springframework.core.annotation.AnnotationUtils;
|
||||
import org.springframework.data.elasticsearch.annotations.Query;
|
||||
import org.springframework.data.elasticsearch.repository.support.ElasticsearchEntityInformation;
|
||||
import org.springframework.data.elasticsearch.repository.support.ElasticsearchEntityInformationCreator;
|
||||
import org.springframework.data.repository.core.RepositoryMetadata;
|
||||
import org.springframework.data.repository.query.QueryMethod;
|
||||
import org.springframework.util.StringUtils;
|
||||
@@ -33,14 +31,10 @@ import org.springframework.util.StringUtils;
|
||||
*/
|
||||
public class ElasticsearchQueryMethod extends QueryMethod {
|
||||
|
||||
private final ElasticsearchEntityInformation<?, ?> entityInformation;
|
||||
private Method method;
|
||||
|
||||
public ElasticsearchQueryMethod(Method method, RepositoryMetadata metadata,
|
||||
ElasticsearchEntityInformationCreator elasticsearchEntityInformationCreator) {
|
||||
public ElasticsearchQueryMethod(Method method, RepositoryMetadata metadata) {
|
||||
super(method, metadata);
|
||||
this.entityInformation = elasticsearchEntityInformationCreator.getEntityInformation(metadata
|
||||
.getReturnedDomainClass(method));
|
||||
this.method = method;
|
||||
}
|
||||
|
||||
|
||||
@@ -105,7 +105,7 @@ public class ElasticsearchRepositoryFactory extends RepositoryFactorySupport {
|
||||
@Override
|
||||
public RepositoryQuery resolveQuery(Method method, RepositoryMetadata metadata, NamedQueries namedQueries) {
|
||||
|
||||
ElasticsearchQueryMethod queryMethod = new ElasticsearchQueryMethod(method, metadata, entityInformationCreator);
|
||||
ElasticsearchQueryMethod queryMethod = new ElasticsearchQueryMethod(method, metadata);
|
||||
String namedQueryName = queryMethod.getNamedQueryName();
|
||||
|
||||
if (namedQueries.hasQuery(namedQueryName)) {
|
||||
|
||||
Reference in New Issue
Block a user