Package org.springframework.data.solr.repository.query

Source Code of org.springframework.data.solr.repository.query.SolrQueryTests

/*
* Copyright 2012 - 2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.data.solr.repository.query;

import java.io.Serializable;
import java.lang.reflect.Method;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.List;

import org.apache.solr.common.params.HighlightParams;
import org.hamcrest.collection.IsEmptyIterable;
import org.hamcrest.core.IsEqual;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.ArgumentCaptor;
import org.mockito.Matchers;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.runners.MockitoJUnitRunner;
import org.springframework.dao.InvalidDataAccessApiUsageException;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageImpl;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Slice;
import org.springframework.data.repository.core.RepositoryMetadata;
import org.springframework.data.repository.query.RepositoryQuery;
import org.springframework.data.solr.core.SolrCallback;
import org.springframework.data.solr.core.SolrOperations;
import org.springframework.data.solr.core.convert.MappingSolrConverter;
import org.springframework.data.solr.core.convert.SolrConverter;
import org.springframework.data.solr.core.mapping.SimpleSolrMappingContext;
import org.springframework.data.solr.core.mapping.SolrPersistentEntity;
import org.springframework.data.solr.core.query.Field;
import org.springframework.data.solr.core.query.HighlightOptions;
import org.springframework.data.solr.core.query.HighlightQuery;
import org.springframework.data.solr.core.query.Query;
import org.springframework.data.solr.core.query.SimpleField;
import org.springframework.data.solr.core.query.SimpleQuery;
import org.springframework.data.solr.core.query.SimpleStringCriteria;
import org.springframework.data.solr.core.query.StatsOptions;
import org.springframework.data.solr.repository.Facet;
import org.springframework.data.solr.repository.Highlight;
import org.springframework.data.solr.repository.ProductBean;
import org.springframework.data.solr.repository.SelectiveStats;
import org.springframework.data.solr.repository.SolrCrudRepository;
import org.springframework.data.solr.repository.Stats;
import org.springframework.data.solr.repository.support.MappingSolrEntityInformation;

/**
* @author Christoph Strobl
* @author Francisco Spaeth
*/
@RunWith(MockitoJUnitRunner.class)
public class SolrQueryTests {

  private @Mock RepositoryMetadata metadataMock;

  private @Mock SolrOperations solrOperationsMock;

  private @Mock SolrPersistentEntity<ProductBean> persitentEntityMock;

  private SolrEntityInformationCreator entityInformationCreator;

  private SimpleSolrMappingContext mappingContext;

  private SolrConverter solrConverter;

  @SuppressWarnings("unchecked")
  @Before
  public void setUp() {

    mappingContext = new SimpleSolrMappingContext();
    solrConverter = new MappingSolrConverter(mappingContext);
    entityInformationCreator = new SolrEntityInformationCreatorImpl();
    Mockito.when(persitentEntityMock.getType()).thenReturn(ProductBean.class);
    Mockito.when(solrOperationsMock.execute(Matchers.any(SolrCallback.class))).thenReturn(
        new PageImpl<ProductBean>(Collections.<ProductBean> emptyList()));
    Mockito.when(solrOperationsMock.getConverter()).thenReturn(solrConverter);
  }

  @Test(expected = InvalidDataAccessApiUsageException.class)
  public void testQueryWithHighlightAndFaceting() throws NoSuchMethodException, SecurityException {
    createQueryForMethod("findAndApplyHighlightingAndFaceting", Pageable.class).execute(
        new Object[] { new PageRequest(0, 10) });
  }

  @SuppressWarnings("unchecked")
  @Test
  public void testQueryWithHighlight() {
    ArgumentCaptor<HighlightQuery> captor = ArgumentCaptor.forClass(HighlightQuery.class);

    createQueryForMethod("findAndApplyHighlighting", Pageable.class).execute(new Object[] { new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForHighlightPage(captor.capture(),
        (Class<ProductBean>) Matchers.any());

    HighlightOptions capturedOptions = captor.getValue().getHighlightOptions();
    Assert.assertNotNull(capturedOptions);
  }

  @SuppressWarnings("unchecked")
  @Test
  public void testQueryWithHighlightParameters() {
    ArgumentCaptor<HighlightQuery> captor = ArgumentCaptor.forClass(HighlightQuery.class);

    createQueryForMethod("findAndApplyHighlightingAllParameters", Pageable.class).execute(
        new Object[] { new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForHighlightPage(captor.capture(),
        (Class<ProductBean>) Matchers.any());

    HighlightOptions capturedOptions = captor.getValue().getHighlightOptions();
    Assert.assertNotNull(capturedOptions);
    Assert.assertEquals("<b>", capturedOptions.getSimplePrefix());
    Assert.assertEquals("</b>", capturedOptions.getSimplePostfix());
    Assert.assertEquals("name", capturedOptions.getFields().get(0).getName());
    Assert.assertEquals("description", capturedOptions.getFields().get(1).getName());
    Assert.assertEquals("simple", capturedOptions.getFormatter());
    Assert.assertEquals(Integer.valueOf(10), capturedOptions.getFragsize());
    Assert.assertEquals(Integer.valueOf(20), capturedOptions.getNrSnipplets());
    Assert
        .assertEquals("name:with", ((SimpleStringCriteria) capturedOptions.getQuery().getCriteria()).getQueryString());
  }

  @SuppressWarnings("unchecked")
  @Test
  public void testQueryWithParametrizedHighlightQuery() {
    ArgumentCaptor<HighlightQuery> captor = ArgumentCaptor.forClass(HighlightQuery.class);

    createQueryForMethod("findAndApplyHighlightingWithParametrizedHighlightQuery", String.class, Pageable.class)
        .execute(new Object[] { "spring", new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForHighlightPage(captor.capture(),
        (Class<ProductBean>) Matchers.any());

    HighlightOptions capturedOptions = captor.getValue().getHighlightOptions();
    Assert.assertEquals("name:*spring*",
        ((SimpleStringCriteria) capturedOptions.getQuery().getCriteria()).getQueryString());
  }

  @SuppressWarnings("unchecked")
  @Test
  public void testQueryWithNonDefaultHighlightFormatter() {
    ArgumentCaptor<HighlightQuery> captor = ArgumentCaptor.forClass(HighlightQuery.class);

    createQueryForMethod("findAndApplyHighlightingWithNonDefaultFormatter", Pageable.class).execute(
        new Object[] { new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForHighlightPage(captor.capture(),
        (Class<ProductBean>) Matchers.any());

    HighlightOptions capturedOptions = captor.getValue().getHighlightOptions();
    Assert.assertNotNull(capturedOptions);
    Assert.assertNull(capturedOptions.getSimplePrefix());
    Assert.assertNull(capturedOptions.getSimplePrefix());
    Assert.assertNull(capturedOptions.getSimplePostfix());
    Assert.assertEquals("postingshighlighter", capturedOptions.getFormatter());
    Assert.assertEquals("{pre}", capturedOptions.getHighlightParameterValue(HighlightParams.TAG_PRE));
    Assert.assertEquals("{post}", capturedOptions.getHighlightParameterValue(HighlightParams.TAG_POST));
  }

  /**
   * @see DATASOLR-170
   */
  @SuppressWarnings({ "rawtypes", "unchecked" })
  @Test
  public void shouldApplyLimitCorrectlyWhenPageSizeToBig() throws NoSuchMethodException, SecurityException {

    Mockito.when(metadataMock.getDomainType()).thenReturn((Class) ProductBean.class);
    Mockito.when(metadataMock.getReturnedDomainClass(Matchers.any(Method.class))).thenReturn((Class) ProductBean.class);

    Method method = Repo1.class.getMethod("findTop5ByName", String.class, Pageable.class);
    SolrQueryMethod sqm = createSolrQueryMethodFrom(method);

    PartTreeSolrQuery ptsq = new PartTreeSolrQuery(sqm, this.solrOperationsMock);

    ptsq.execute(new Object[] { "foo", new PageRequest(0, 10) });

    ArgumentCaptor<Query> captor = ArgumentCaptor.forClass(Query.class);

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForPage(captor.capture(), (Class<?>) Matchers.any());

    Assert.assertThat(captor.getValue().getPageRequest().getPageNumber(), IsEqual.equalTo(0));
    Assert.assertThat(captor.getValue().getPageRequest().getPageSize(), IsEqual.equalTo(5));
  }

  /**
   * @see DATASOLR-170
   */
  @SuppressWarnings({ "rawtypes", "unchecked" })
  @Test
  public void shouldApplyLimitCorrectlyToPageWhenPageInsideLimit() throws NoSuchMethodException, SecurityException {

    Mockito.when(metadataMock.getDomainType()).thenReturn((Class) ProductBean.class);
    Mockito.when(metadataMock.getReturnedDomainClass(Matchers.any(Method.class))).thenReturn((Class) ProductBean.class);

    Method method = Repo1.class.getMethod("findTop5ByName", String.class, Pageable.class);
    SolrQueryMethod sqm = createSolrQueryMethodFrom(method);

    PartTreeSolrQuery ptsq = new PartTreeSolrQuery(sqm, this.solrOperationsMock);

    ptsq.execute(new Object[] { "foo", new PageRequest(1, 2) });

    ArgumentCaptor<Query> captor = ArgumentCaptor.forClass(Query.class);

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForPage(captor.capture(), (Class<?>) Matchers.any());

    Assert.assertThat(captor.getValue().getPageRequest().getPageNumber(), IsEqual.equalTo(1));
    Assert.assertThat(captor.getValue().getPageRequest().getPageSize(), IsEqual.equalTo(2));
  }

  /**
   * @see DATASOLR-170
   */
  @SuppressWarnings({ "rawtypes", "unchecked" })
  @Test
  public void shouldNotCallServerIfPageOutsideLimit() throws NoSuchMethodException, SecurityException {

    Mockito.when(metadataMock.getDomainType()).thenReturn((Class) ProductBean.class);
    Mockito.when(metadataMock.getReturnedDomainClass(Matchers.any(Method.class))).thenReturn((Class) ProductBean.class);

    Method method = Repo1.class.getMethod("findTop5ByName", String.class, Pageable.class);
    SolrQueryMethod sqm = createSolrQueryMethodFrom(method);

    PartTreeSolrQuery ptsq = new PartTreeSolrQuery(sqm, this.solrOperationsMock);

    ptsq.execute(new Object[] { "foo", new PageRequest(2, 5) });

    Mockito.verify(solrOperationsMock, Mockito.never()).queryForPage(Matchers.any(Query.class),
        (Class<?>) Matchers.any());
  }

  /**
   * @see DATASOLR-186
   */
  @Test
  public void sliceShouldTriggerPagedExecution() {

    createQueryForMethod("findByName", String.class, Pageable.class).execute(
        new Object[] { "sliceme", new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForPage(Matchers.any(Query.class),
        Matchers.<Class<ProductBean>> any());
  }

  /**
   * @see DATASOLR-160
   */
  @SuppressWarnings("unchecked")
  @Test
  public void testQueryWithStats() {
    ArgumentCaptor<Query> captor = ArgumentCaptor.forClass(Query.class);

    createQueryForMethod("findAndApplyStats", Pageable.class).execute(new Object[] { new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForPage(captor.capture(),
        (Class<ProductBean>) Matchers.any());

    StatsOptions capturedOptions = captor.getValue().getStatsOptions();

    Assert.assertEquals(2, capturedOptions.getFields().size());
    Assert.assertTrue(capturedOptions.getFields().containsAll(
        Arrays.asList(new SimpleField("field1"), new SimpleField("field4"))));

    Assert.assertEquals(2, capturedOptions.getFacets().size());
    Assert.assertTrue(capturedOptions.getFacets().containsAll(
        Arrays.asList(new SimpleField("field2"), new SimpleField("field3"))));

    Collection<Field> selectiveFacetsField = capturedOptions.getSelectiveFacets().get(new SimpleField("field4"));
    List<SimpleField> selectiveFacetsFields = Arrays.asList(new SimpleField("field4_1"), new SimpleField("field4_2"));
    Assert.assertEquals(1, capturedOptions.getSelectiveFacets().size());
    Assert.assertTrue(selectiveFacetsField.containsAll(selectiveFacetsFields));
  }

  /**
   * @see DATASOLR-160
   */
  @SuppressWarnings("unchecked")
  @Test
  public void testQueryWithStatsNonSelective() {
    ArgumentCaptor<Query> captor = ArgumentCaptor.forClass(Query.class);

    createQueryForMethod("findAndApplyStatsNonSelective", Pageable.class).execute(
        new Object[] { new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForPage(captor.capture(),
        (Class<ProductBean>) Matchers.any());

    StatsOptions capturedOptions = captor.getValue().getStatsOptions();

    Assert.assertEquals(1, capturedOptions.getFields().size());
    Assert.assertTrue(capturedOptions.getFields().containsAll(Arrays.asList(new SimpleField("field1"))));

    Assert.assertEquals(2, capturedOptions.getFacets().size());
    Assert.assertTrue(capturedOptions.getFacets().containsAll(
        Arrays.asList(new SimpleField("field2"), new SimpleField("field3"))));

    Assert.assertThat(capturedOptions.getSelectiveFacets().entrySet(), IsEmptyIterable.emptyIterable());
  }

  /**
   * @see DATASOLR-160
   */
  @SuppressWarnings("unchecked")
  @Test
  public void testQueryWithStatsNoFacets() {
    ArgumentCaptor<Query> captor = ArgumentCaptor.forClass(Query.class);

    createQueryForMethod("findAndApplyStatsNoFacets", Pageable.class).execute(new Object[] { new PageRequest(0, 10) });

    Mockito.verify(solrOperationsMock, Mockito.times(1)).queryForPage(captor.capture(),
        (Class<ProductBean>) Matchers.any());

    StatsOptions capturedOptions = captor.getValue().getStatsOptions();

    Assert.assertEquals(1, capturedOptions.getFields().size());
    Assert.assertTrue(capturedOptions.getFields().containsAll(Arrays.asList(new SimpleField("field1"))));

    Assert.assertThat(capturedOptions.getFacets(), IsEmptyIterable.emptyIterable());
    Assert.assertThat(capturedOptions.getSelectiveFacets().entrySet(), IsEmptyIterable.emptyIterable());
  }

  private RepositoryQuery createQueryForMethod(String methodName, Class<?>... paramTypes) {
    try {
      return this.createQueryForMethod(Repo1.class.getMethod(methodName, paramTypes));
    } catch (NoSuchMethodException e) {
      throw new IllegalArgumentException(e.getMessage(), e);
    } catch (SecurityException e) {
      throw new IllegalArgumentException(e.getMessage(), e);
    }
  }

  private RepositoryQuery createQueryForMethod(Method method) {
    return new SolrQueryImpl(this.solrOperationsMock, createSolrQueryMethodFrom(method));
  }

  private SolrQueryMethod createSolrQueryMethodFrom(Method method) {
    return new SolrQueryMethod(method, metadataMock, entityInformationCreator);
  }

  private interface Repo1 extends SolrCrudRepository<ProductBean, String> {

    @Facet(fields = { "name" })
    @Highlight
    Page<ProductBean> findAndApplyHighlightingAndFaceting(Pageable page);

    @Highlight
    Page<ProductBean> findAndApplyHighlighting(Pageable page);

    @Highlight(fields = { "name", "description" }, fragsize = 10, snipplets = 20, prefix = "<b>", postfix = "</b>",
        query = "name:with", formatter = "simple")
    Page<ProductBean> findAndApplyHighlightingAllParameters(Pageable page);

    @Highlight(query = "name:*?0*")
    Page<ProductBean> findAndApplyHighlightingWithParametrizedHighlightQuery(String name, Pageable page);

    @Highlight(formatter = "postingshighlighter", prefix = "{pre}", postfix = "{post}")
    Page<ProductBean> findAndApplyHighlightingWithNonDefaultFormatter(Pageable page);

    Page<ProductBean> findTop5ByName(String name, Pageable page);

    Slice<ProductBean> findByName(String name, Pageable page);

    @Stats(value = "field1", facets = { "field2", "field3" }, //
        selective = @SelectiveStats(field = "field4", facets = { "field4_1", "field4_2" }))
    Page<ProductBean> findAndApplyStats(Pageable page);

    @Stats(value = "field1", facets = { "field2", "field3" })
    Page<ProductBean> findAndApplyStatsNonSelective(Pageable page);

    @Stats(value = "field1")
    Page<ProductBean> findAndApplyStatsNoFacets(Pageable page);

  }

  private class SolrEntityInformationCreatorImpl implements SolrEntityInformationCreator {

    @SuppressWarnings("unchecked")
    @Override
    public <T, ID extends Serializable> SolrEntityInformation<T, ID> getEntityInformation(Class<T> domainClass) {
      return (SolrEntityInformation<T, ID>) new SolrEntityInformationImpl(persitentEntityMock);
    }
  }

  private class SolrEntityInformationImpl extends MappingSolrEntityInformation<ProductBean, String> {

    public SolrEntityInformationImpl(SolrPersistentEntity<ProductBean> entity) {
      super(entity);
    }

    @Override
    public Class<String> getIdType() {
      return String.class;
    }

    @Override
    public Class<ProductBean> getJavaType() {
      return ProductBean.class;
    }

  }

  private class SolrQueryImpl extends AbstractSolrQuery {

    public SolrQueryImpl(SolrOperations solrOperations, SolrQueryMethod solrQueryMethod) {
      super(solrOperations, solrQueryMethod);
    }

    @Override
    protected Query createQuery(SolrParameterAccessor parameterAccessor) {
      return new SimpleQuery(new SimpleStringCriteria("fake:query"));
    }

  }

}
TOP

Related Classes of org.springframework.data.solr.repository.query.SolrQueryTests

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.