Compare commits
67 Commits
6.1.x
...
3.0.8.RELEASE
| Author | SHA1 | Date | |
|---|---|---|---|
| a1d508c656 | |||
| 04308394dd | |||
| be80d7eae4 | |||
| de1c28979d | |||
| bd668e6c2a | |||
| ba899a0017 | |||
| 8181c713c7 | |||
| c6419a1f05 | |||
| 09ee8f9026 | |||
| 13cfb039b5 | |||
| 4c9c03ac0b | |||
| cd597f059e | |||
| 7cf251a24e | |||
| fe5426b870 | |||
| 01a37c4fc3 | |||
| 021495580f | |||
| 4970783ca4 | |||
| 5ac31b3d2b | |||
| 71b2ffc128 | |||
| 2642836e4d | |||
| 849d7da652 | |||
| 5e29b958e5 | |||
| 1b1ef4b5f4 | |||
| 79636c2a29 | |||
| 787fc897d3 | |||
| 4bdaf039c2 | |||
| 35003bf942 | |||
| be230f4003 | |||
| 8c1821e7a6 | |||
| 72a2f9f758 | |||
| d9d3521518 | |||
| d50ae96c5e | |||
| 734a28fb03 | |||
| ac403b9198 | |||
| 477c4d1dc3 | |||
| 2b543ff026 | |||
| 02a3e120c2 | |||
| 92286a725d | |||
| 462288be0e | |||
| b844f47795 | |||
| fe488eac32 | |||
| a77b81ecb3 | |||
| 81795f67cd | |||
| 485859ca3d | |||
| 8973d2d7eb | |||
| a525a38825 | |||
| b392090e61 | |||
| ca4a864f9e | |||
| 3a31030f89 | |||
| 34a7900e34 | |||
| 361bc2a333 | |||
| c2c21581d8 | |||
| ecf2efa6e5 | |||
| 418d259fbf | |||
| 737a023b5a | |||
| cc3f578312 | |||
| 81b21f4e6f | |||
| 552cbff6a4 | |||
| 000eb152dc | |||
| ad55402973 | |||
| ef68623d5b | |||
| c075f170c3 | |||
| 02b7dde196 | |||
| 51b7fa2a26 | |||
| 4e5051c57b | |||
| 31d499e6e0 | |||
| 311a06aa67 |
@@ -52,17 +52,12 @@ the appropriate dependency version.
|
|||||||
</repository>
|
</repository>
|
||||||
```
|
```
|
||||||
|
|
||||||
| spring data elasticsearch | elasticsearch |
|
| spring data elasticsearch | elasticsearch |
|
||||||
|:-----------------------------------:|:-------------:|
|
|:-------------------------:|:-------------:|
|
||||||
| 3.0.0.RC2 | 5.5.0 |
|
| 3.0.x | 5.5.0 |
|
||||||
| 3.0.0.M4 | 5.4.0 |
|
| 2.1.x | 2.4.0 |
|
||||||
| 2.0.4.RELEASE | 2.4.0 |
|
| 2.0.x | 2.2.0 |
|
||||||
| 2.0.0.RELEASE | 2.2.0 |
|
| 1.3.x | 1.5.2 |
|
||||||
| 1.4.0.M1 | 1.7.3 |
|
|
||||||
| 1.3.0.RELEASE | 1.5.2 |
|
|
||||||
| 1.2.0.RELEASE | 1.4.4 |
|
|
||||||
| 1.1.0.RELEASE | 1.3.2 |
|
|
||||||
| 1.0.0.RELEASE | 1.1.1 |
|
|
||||||
|
|
||||||
|
|
||||||
### ElasticsearchRepository
|
### ElasticsearchRepository
|
||||||
|
|||||||
@@ -4,12 +4,12 @@
|
|||||||
|
|
||||||
<groupId>org.springframework.data</groupId>
|
<groupId>org.springframework.data</groupId>
|
||||||
<artifactId>spring-data-elasticsearch</artifactId>
|
<artifactId>spring-data-elasticsearch</artifactId>
|
||||||
<version>3.0.0.RELEASE</version>
|
<version>3.0.8.RELEASE</version>
|
||||||
|
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.springframework.data.build</groupId>
|
<groupId>org.springframework.data.build</groupId>
|
||||||
<artifactId>spring-data-parent</artifactId>
|
<artifactId>spring-data-parent</artifactId>
|
||||||
<version>2.0.0.RELEASE</version>
|
<version>2.0.8.RELEASE</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<name>Spring Data Elasticsearch</name>
|
<name>Spring Data Elasticsearch</name>
|
||||||
@@ -20,7 +20,8 @@
|
|||||||
<commonscollections>3.2.1</commonscollections>
|
<commonscollections>3.2.1</commonscollections>
|
||||||
<commonslang>2.6</commonslang>
|
<commonslang>2.6</commonslang>
|
||||||
<elasticsearch>5.5.0</elasticsearch>
|
<elasticsearch>5.5.0</elasticsearch>
|
||||||
<springdata.commons>2.0.0.RELEASE</springdata.commons>
|
<log4j>2.8.2</log4j>
|
||||||
|
<springdata.commons>2.0.8.RELEASE</springdata.commons>
|
||||||
<java-module-name>spring.data.elasticsearch</java-module-name>
|
<java-module-name>spring.data.elasticsearch</java-module-name>
|
||||||
</properties>
|
</properties>
|
||||||
|
|
||||||
@@ -80,31 +81,41 @@
|
|||||||
<groupId>commons-logging</groupId>
|
<groupId>commons-logging</groupId>
|
||||||
<artifactId>commons-logging</artifactId>
|
<artifactId>commons-logging</artifactId>
|
||||||
</exclusion>
|
</exclusion>
|
||||||
|
<exclusion>
|
||||||
|
<groupId>org.elasticsearch.plugin</groupId>
|
||||||
|
<artifactId>transport-netty3-client</artifactId>
|
||||||
|
</exclusion>
|
||||||
</exclusions>
|
</exclusions>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.elasticsearch.plugin</groupId>
|
||||||
|
<artifactId>transport-netty4-client</artifactId>
|
||||||
|
<version>${elasticsearch}</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.slf4j</groupId>
|
<groupId>org.slf4j</groupId>
|
||||||
<artifactId>log4j-over-slf4j</artifactId>
|
<artifactId>log4j-over-slf4j</artifactId>
|
||||||
<version>1.7.22</version>
|
<version>${slf4j}</version>
|
||||||
|
<scope>test</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.apache.logging.log4j</groupId>
|
<groupId>org.apache.logging.log4j</groupId>
|
||||||
<artifactId>log4j-core</artifactId>
|
<artifactId>log4j-core</artifactId>
|
||||||
<version>2.8.2</version>
|
<version>${log4j}</version>
|
||||||
|
<scope>test</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<!-- Jackson JSON Mapper -->
|
<!-- Jackson JSON Mapper -->
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.fasterxml.jackson.core</groupId>
|
<groupId>com.fasterxml.jackson.core</groupId>
|
||||||
<artifactId>jackson-core</artifactId>
|
<artifactId>jackson-core</artifactId>
|
||||||
<version>${jackson}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.fasterxml.jackson.core</groupId>
|
<groupId>com.fasterxml.jackson.core</groupId>
|
||||||
<artifactId>jackson-databind</artifactId>
|
<artifactId>jackson-databind</artifactId>
|
||||||
<version>${jackson}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<!-- CDI -->
|
<!-- CDI -->
|
||||||
@@ -161,14 +172,6 @@
|
|||||||
<scope>test</scope>
|
<scope>test</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
|
||||||
<!-- required by elasticsearch -->
|
|
||||||
<groupId>org.elasticsearch.plugin</groupId>
|
|
||||||
<artifactId>transport-netty4-client</artifactId>
|
|
||||||
<version>${elasticsearch}</version>
|
|
||||||
<!--<scope>test</scope>-->
|
|
||||||
</dependency>
|
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.projectlombok</groupId>
|
<groupId>org.projectlombok</groupId>
|
||||||
<artifactId>lombok</artifactId>
|
<artifactId>lombok</artifactId>
|
||||||
@@ -176,8 +179,6 @@
|
|||||||
<scope>test</scope>
|
<scope>test</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
|
||||||
<build>
|
<build>
|
||||||
|
|||||||
@@ -1,26 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 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.elasticsearch.annotations;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @author Artur Konczak
|
|
||||||
* @author Mohsin Husen
|
|
||||||
* @author Alexander Volz
|
|
||||||
* @author Dennis Maaß
|
|
||||||
*/
|
|
||||||
public enum FieldIndex {
|
|
||||||
not_analyzed, analyzed, no
|
|
||||||
}
|
|
||||||
@@ -21,5 +21,17 @@ package org.springframework.data.elasticsearch.annotations;
|
|||||||
* @author Artur Konczak
|
* @author Artur Konczak
|
||||||
*/
|
*/
|
||||||
public enum FieldType {
|
public enum FieldType {
|
||||||
text, Integer, Long, Date, Float, Double, Boolean, Object, Auto, Nested, Ip, Attachment, keyword
|
Text,
|
||||||
|
Integer,
|
||||||
|
Long,
|
||||||
|
Date,
|
||||||
|
Float,
|
||||||
|
Double,
|
||||||
|
Boolean,
|
||||||
|
Object,
|
||||||
|
Auto,
|
||||||
|
Nested,
|
||||||
|
Ip,
|
||||||
|
Attachment,
|
||||||
|
Keyword
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -33,11 +33,15 @@ public @interface InnerField {
|
|||||||
|
|
||||||
boolean index() default true;
|
boolean index() default true;
|
||||||
|
|
||||||
|
DateFormat format() default DateFormat.none;
|
||||||
|
|
||||||
|
String pattern() default "";
|
||||||
|
|
||||||
boolean store() default false;
|
boolean store() default false;
|
||||||
|
|
||||||
boolean fielddata() default false;
|
boolean fielddata() default false;
|
||||||
|
|
||||||
String searchAnalyzer() default "";
|
String searchAnalyzer() default "";
|
||||||
|
|
||||||
String indexAnalyzer() default "";
|
String analyzer() default "";
|
||||||
}
|
}
|
||||||
|
|||||||
+112
-1
@@ -17,12 +17,29 @@ package org.springframework.data.elasticsearch.client;
|
|||||||
|
|
||||||
import static org.apache.commons.lang.StringUtils.*;
|
import static org.apache.commons.lang.StringUtils.*;
|
||||||
|
|
||||||
|
import io.netty.util.ThreadDeathWatcher;
|
||||||
|
import io.netty.util.concurrent.GlobalEventExecutor;
|
||||||
|
|
||||||
import java.net.InetAddress;
|
import java.net.InetAddress;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.List;
|
||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
import org.elasticsearch.client.transport.TransportClient;
|
import org.elasticsearch.client.transport.TransportClient;
|
||||||
|
import org.elasticsearch.common.SuppressForbidden;
|
||||||
|
import org.elasticsearch.common.network.NetworkModule;
|
||||||
import org.elasticsearch.common.settings.Settings;
|
import org.elasticsearch.common.settings.Settings;
|
||||||
import org.elasticsearch.common.transport.InetSocketTransportAddress;
|
import org.elasticsearch.common.transport.InetSocketTransportAddress;
|
||||||
|
import org.elasticsearch.index.reindex.ReindexPlugin;
|
||||||
|
import org.elasticsearch.join.ParentJoinPlugin;
|
||||||
|
import org.elasticsearch.percolator.PercolatorPlugin;
|
||||||
|
import org.elasticsearch.plugins.Plugin;
|
||||||
|
import org.elasticsearch.script.mustache.MustachePlugin;
|
||||||
|
import org.elasticsearch.transport.Netty4Plugin;
|
||||||
import org.elasticsearch.transport.client.PreBuiltTransportClient;
|
import org.elasticsearch.transport.client.PreBuiltTransportClient;
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
import org.slf4j.LoggerFactory;
|
import org.slf4j.LoggerFactory;
|
||||||
@@ -30,6 +47,7 @@ import org.springframework.beans.factory.DisposableBean;
|
|||||||
import org.springframework.beans.factory.FactoryBean;
|
import org.springframework.beans.factory.FactoryBean;
|
||||||
import org.springframework.beans.factory.InitializingBean;
|
import org.springframework.beans.factory.InitializingBean;
|
||||||
import org.springframework.util.Assert;
|
import org.springframework.util.Assert;
|
||||||
|
import org.springframework.util.ClassUtils;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TransportClientFactoryBean
|
* TransportClientFactoryBean
|
||||||
@@ -88,7 +106,7 @@ public class TransportClientFactoryBean implements FactoryBean<TransportClient>,
|
|||||||
|
|
||||||
protected void buildClient() throws Exception {
|
protected void buildClient() throws Exception {
|
||||||
|
|
||||||
client = new PreBuiltTransportClient(settings());
|
client = new SpringDataTransportClient(settings());
|
||||||
Assert.hasText(clusterNodes, "[Assertion failed] clusterNodes settings missing.");
|
Assert.hasText(clusterNodes, "[Assertion failed] clusterNodes settings missing.");
|
||||||
for (String clusterNode : split(clusterNodes, COMMA)) {
|
for (String clusterNode : split(clusterNodes, COMMA)) {
|
||||||
String hostName = substringBeforeLast(clusterNode, COLON);
|
String hostName = substringBeforeLast(clusterNode, COLON);
|
||||||
@@ -153,4 +171,97 @@ public class TransportClientFactoryBean implements FactoryBean<TransportClient>,
|
|||||||
public void setProperties(Properties properties) {
|
public void setProperties(Properties properties) {
|
||||||
this.properties = properties;
|
this.properties = properties;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pretty exact copy of {@link PreBuiltTransportClient} except that we're inspecting the classpath for Netty
|
||||||
|
* dependencies to only include the ones available. {@link PreBuiltTransportClient} expects both Netty 3 and Netty 4
|
||||||
|
* to be present.
|
||||||
|
*
|
||||||
|
* @author Oliver Gierke
|
||||||
|
* @see https://github.com/elastic/elasticsearch/issues/31240
|
||||||
|
*/
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
private static class SpringDataTransportClient extends TransportClient {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Netty wants to do some unwelcome things like use unsafe and replace a private field, or use a poorly considered
|
||||||
|
* buffer recycler. This method disables these things by default, but can be overridden by setting the corresponding
|
||||||
|
* system properties.
|
||||||
|
*/
|
||||||
|
private static void initializeNetty() {
|
||||||
|
/*
|
||||||
|
* We disable three pieces of Netty functionality here:
|
||||||
|
* - we disable Netty from being unsafe
|
||||||
|
* - we disable Netty from replacing the selector key set
|
||||||
|
* - we disable Netty from using the recycler
|
||||||
|
*
|
||||||
|
* While permissions are needed to read and set these, the permissions needed here are innocuous and thus should simply be granted
|
||||||
|
* rather than us handling a security exception here.
|
||||||
|
*/
|
||||||
|
setSystemPropertyIfUnset("io.netty.noUnsafe", Boolean.toString(true));
|
||||||
|
setSystemPropertyIfUnset("io.netty.noKeySetOptimization", Boolean.toString(true));
|
||||||
|
setSystemPropertyIfUnset("io.netty.recycler.maxCapacityPerThread", Integer.toString(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressForbidden(reason = "set system properties to configure Netty")
|
||||||
|
private static void setSystemPropertyIfUnset(final String key, final String value) {
|
||||||
|
final String currentValue = System.getProperty(key);
|
||||||
|
if (currentValue == null) {
|
||||||
|
System.setProperty(key, value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final List<String> OPTIONAL_DEPENDENCIES = Arrays.asList( //
|
||||||
|
"org.elasticsearch.transport.Netty3Plugin", //
|
||||||
|
"org.elasticsearch.transport.Netty4Plugin");
|
||||||
|
|
||||||
|
private static final Collection<Class<? extends Plugin>> PRE_INSTALLED_PLUGINS;
|
||||||
|
|
||||||
|
static {
|
||||||
|
|
||||||
|
initializeNetty();
|
||||||
|
|
||||||
|
List<Class<? extends Plugin>> plugins = new ArrayList<>();
|
||||||
|
boolean found = false;
|
||||||
|
|
||||||
|
for (String dependency : OPTIONAL_DEPENDENCIES) {
|
||||||
|
try {
|
||||||
|
plugins.add((Class<? extends Plugin>) ClassUtils.forName(dependency,
|
||||||
|
SpringDataTransportClient.class.getClassLoader()));
|
||||||
|
found = true;
|
||||||
|
} catch (ClassNotFoundException | LinkageError e) {}
|
||||||
|
}
|
||||||
|
|
||||||
|
Assert.state(found, "Neither Netty 3 or Netty 4 plugin found on the classpath. One of them is required to run the transport client!");
|
||||||
|
|
||||||
|
plugins.add(ReindexPlugin.class);
|
||||||
|
plugins.add(PercolatorPlugin.class);
|
||||||
|
plugins.add(MustachePlugin.class);
|
||||||
|
plugins.add(ParentJoinPlugin.class);
|
||||||
|
|
||||||
|
PRE_INSTALLED_PLUGINS = Collections.unmodifiableList(plugins);
|
||||||
|
}
|
||||||
|
|
||||||
|
public SpringDataTransportClient(Settings settings) {
|
||||||
|
super(settings, PRE_INSTALLED_PLUGINS);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void close() {
|
||||||
|
super.close();
|
||||||
|
if (NetworkModule.TRANSPORT_TYPE_SETTING.exists(settings) == false
|
||||||
|
|| NetworkModule.TRANSPORT_TYPE_SETTING.get(settings).equals(Netty4Plugin.NETTY_TRANSPORT_NAME)) {
|
||||||
|
try {
|
||||||
|
GlobalEventExecutor.INSTANCE.awaitInactivity(5, TimeUnit.SECONDS);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
Thread.currentThread().interrupt();
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
ThreadDeathWatcher.awaitInactivity(5, TimeUnit.SECONDS);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
Thread.currentThread().interrupt();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -39,6 +39,7 @@ import org.springframework.data.elasticsearch.core.aggregation.impl.AggregatedPa
|
|||||||
import org.springframework.data.elasticsearch.core.mapping.ElasticsearchPersistentEntity;
|
import org.springframework.data.elasticsearch.core.mapping.ElasticsearchPersistentEntity;
|
||||||
import org.springframework.data.elasticsearch.core.mapping.ElasticsearchPersistentProperty;
|
import org.springframework.data.elasticsearch.core.mapping.ElasticsearchPersistentProperty;
|
||||||
import org.springframework.data.mapping.context.MappingContext;
|
import org.springframework.data.mapping.context.MappingContext;
|
||||||
|
import org.springframework.util.Assert;
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonEncoding;
|
import com.fasterxml.jackson.core.JsonEncoding;
|
||||||
import com.fasterxml.jackson.core.JsonFactory;
|
import com.fasterxml.jackson.core.JsonFactory;
|
||||||
@@ -49,6 +50,7 @@ import com.fasterxml.jackson.core.JsonGenerator;
|
|||||||
* @author Petar Tahchiev
|
* @author Petar Tahchiev
|
||||||
* @author Young Gu
|
* @author Young Gu
|
||||||
* @author Oliver Gierke
|
* @author Oliver Gierke
|
||||||
|
* @author Chris White
|
||||||
* @author Mark Paluch
|
* @author Mark Paluch
|
||||||
*/
|
*/
|
||||||
public class DefaultResultMapper extends AbstractResultMapper {
|
public class DefaultResultMapper extends AbstractResultMapper {
|
||||||
@@ -88,6 +90,7 @@ public class DefaultResultMapper extends AbstractResultMapper {
|
|||||||
result = mapEntity(hit.getFields().values(), clazz);
|
result = mapEntity(hit.getFields().values(), clazz);
|
||||||
}
|
}
|
||||||
setPersistentEntityId(result, hit.getId(), clazz);
|
setPersistentEntityId(result, hit.getId(), clazz);
|
||||||
|
setPersistentEntityVersion(result, hit.getVersion(), clazz);
|
||||||
populateScriptFields(result, hit);
|
populateScriptFields(result, hit);
|
||||||
results.add(result);
|
results.add(result);
|
||||||
}
|
}
|
||||||
@@ -153,6 +156,7 @@ public class DefaultResultMapper extends AbstractResultMapper {
|
|||||||
T result = mapEntity(response.getSourceAsString(), clazz);
|
T result = mapEntity(response.getSourceAsString(), clazz);
|
||||||
if (result != null) {
|
if (result != null) {
|
||||||
setPersistentEntityId(result, response.getId(), clazz);
|
setPersistentEntityId(result, response.getId(), clazz);
|
||||||
|
setPersistentEntityVersion(result, response.getVersion(), clazz);
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@@ -164,6 +168,7 @@ public class DefaultResultMapper extends AbstractResultMapper {
|
|||||||
if (!response.isFailed() && response.getResponse().isExists()) {
|
if (!response.isFailed() && response.getResponse().isExists()) {
|
||||||
T result = mapEntity(response.getResponse().getSourceAsString(), clazz);
|
T result = mapEntity(response.getResponse().getSourceAsString(), clazz);
|
||||||
setPersistentEntityId(result, response.getResponse().getId(), clazz);
|
setPersistentEntityId(result, response.getResponse().getId(), clazz);
|
||||||
|
setPersistentEntityVersion(result, response.getResponse().getVersion(), clazz);
|
||||||
list.add(result);
|
list.add(result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -184,4 +189,20 @@ public class DefaultResultMapper extends AbstractResultMapper {
|
|||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private <T> void setPersistentEntityVersion(T result, long version, Class<T> clazz) {
|
||||||
|
if (mappingContext != null && clazz.isAnnotationPresent(Document.class)) {
|
||||||
|
|
||||||
|
ElasticsearchPersistentEntity<?> persistentEntity = mappingContext.getPersistentEntity(clazz);
|
||||||
|
ElasticsearchPersistentProperty versionProperty = persistentEntity.getVersionProperty();
|
||||||
|
|
||||||
|
// Only deal with Long because ES versions are longs !
|
||||||
|
if (versionProperty != null && versionProperty.getType().isAssignableFrom(Long.class)) {
|
||||||
|
// check that a version was actually returned in the response, -1 would indicate that
|
||||||
|
// a search didn't request the version ids in the response, which would be an issue
|
||||||
|
Assert.isTrue(version != -1, "Version in response is -1");
|
||||||
|
persistentEntity.getPropertyAccessor(result).setProperty(versionProperty, version);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+24
-5
@@ -59,7 +59,9 @@ import org.elasticsearch.index.query.QueryBuilders;
|
|||||||
import org.elasticsearch.search.SearchHit;
|
import org.elasticsearch.search.SearchHit;
|
||||||
import org.elasticsearch.search.aggregations.AbstractAggregationBuilder;
|
import org.elasticsearch.search.aggregations.AbstractAggregationBuilder;
|
||||||
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
|
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
|
||||||
|
import org.elasticsearch.search.sort.FieldSortBuilder;
|
||||||
import org.elasticsearch.search.sort.SortBuilder;
|
import org.elasticsearch.search.sort.SortBuilder;
|
||||||
|
import org.elasticsearch.search.sort.SortBuilders;
|
||||||
import org.elasticsearch.search.sort.SortOrder;
|
import org.elasticsearch.search.sort.SortOrder;
|
||||||
import org.elasticsearch.search.suggest.SuggestBuilder;
|
import org.elasticsearch.search.suggest.SuggestBuilder;
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
@@ -105,7 +107,10 @@ import static org.springframework.util.CollectionUtils.isEmpty;
|
|||||||
* @author Young Gu
|
* @author Young Gu
|
||||||
* @author Oliver Gierke
|
* @author Oliver Gierke
|
||||||
* @author Mark Janssen
|
* @author Mark Janssen
|
||||||
|
* @author Chris White
|
||||||
* @author Mark Paluch
|
* @author Mark Paluch
|
||||||
|
* @author Sascha Woo
|
||||||
|
* @author Ted Liang
|
||||||
*/
|
*/
|
||||||
public class ElasticsearchTemplate implements ElasticsearchOperations, ApplicationContextAware {
|
public class ElasticsearchTemplate implements ElasticsearchOperations, ApplicationContextAware {
|
||||||
|
|
||||||
@@ -730,7 +735,10 @@ public class ElasticsearchTemplate implements ElasticsearchOperations, Applicati
|
|||||||
|
|
||||||
private SearchRequestBuilder prepareScroll(Query query, long scrollTimeInMillis) {
|
private SearchRequestBuilder prepareScroll(Query query, long scrollTimeInMillis) {
|
||||||
SearchRequestBuilder requestBuilder = client.prepareSearch(toArray(query.getIndices()))
|
SearchRequestBuilder requestBuilder = client.prepareSearch(toArray(query.getIndices()))
|
||||||
.setTypes(toArray(query.getTypes())).setScroll(TimeValue.timeValueMillis(scrollTimeInMillis)).setFrom(0);
|
.setTypes(toArray(query.getTypes()))
|
||||||
|
.setScroll(TimeValue.timeValueMillis(scrollTimeInMillis))
|
||||||
|
.setFrom(0)
|
||||||
|
.setVersion(true);
|
||||||
|
|
||||||
if(query.getPageable().isPaged()){
|
if(query.getPageable().isPaged()){
|
||||||
requestBuilder.setSize(query.getPageable().getPageSize());
|
requestBuilder.setSize(query.getPageable().getPageSize());
|
||||||
@@ -875,9 +883,11 @@ public class ElasticsearchTemplate implements ElasticsearchOperations, Applicati
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (searchQuery.getHighlightFields() != null) {
|
if (searchQuery.getHighlightFields() != null) {
|
||||||
|
HighlightBuilder highlightBuilder = new HighlightBuilder();
|
||||||
for (HighlightBuilder.Field highlightField : searchQuery.getHighlightFields()) {
|
for (HighlightBuilder.Field highlightField : searchQuery.getHighlightFields()) {
|
||||||
searchRequest.highlighter(new HighlightBuilder().field(highlightField));
|
highlightBuilder.field(highlightField);
|
||||||
}
|
}
|
||||||
|
searchRequest.highlighter(highlightBuilder);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!isEmpty(searchQuery.getIndicesBoost())) {
|
if (!isEmpty(searchQuery.getIndicesBoost())) {
|
||||||
@@ -975,7 +985,9 @@ public class ElasticsearchTemplate implements ElasticsearchOperations, Applicati
|
|||||||
|
|
||||||
int startRecord = 0;
|
int startRecord = 0;
|
||||||
SearchRequestBuilder searchRequestBuilder = client.prepareSearch(toArray(query.getIndices()))
|
SearchRequestBuilder searchRequestBuilder = client.prepareSearch(toArray(query.getIndices()))
|
||||||
.setSearchType(query.getSearchType()).setTypes(toArray(query.getTypes()));
|
.setSearchType(query.getSearchType())
|
||||||
|
.setTypes(toArray(query.getTypes()))
|
||||||
|
.setVersion(true);
|
||||||
|
|
||||||
if (query.getSourceFilter() != null) {
|
if (query.getSourceFilter() != null) {
|
||||||
SourceFilter sourceFilter = query.getSourceFilter();
|
SourceFilter sourceFilter = query.getSourceFilter();
|
||||||
@@ -994,8 +1006,15 @@ public class ElasticsearchTemplate implements ElasticsearchOperations, Applicati
|
|||||||
|
|
||||||
if (query.getSort() != null) {
|
if (query.getSort() != null) {
|
||||||
for (Sort.Order order : query.getSort()) {
|
for (Sort.Order order : query.getSort()) {
|
||||||
searchRequestBuilder.addSort(order.getProperty(),
|
FieldSortBuilder sort = SortBuilders.fieldSort(order.getProperty())
|
||||||
order.getDirection() == Sort.Direction.DESC ? SortOrder.DESC : SortOrder.ASC);
|
.order(order.getDirection().isDescending() ? SortOrder.DESC : SortOrder.ASC);
|
||||||
|
if (order.getNullHandling() == Sort.NullHandling.NULLS_FIRST) {
|
||||||
|
sort.missing("_first");
|
||||||
|
}
|
||||||
|
else if (order.getNullHandling() == Sort.NullHandling.NULLS_LAST) {
|
||||||
|
sort.missing("_last");
|
||||||
|
}
|
||||||
|
searchRequestBuilder.addSort(sort);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -40,6 +40,8 @@ import org.springframework.data.elasticsearch.core.facet.result.StatisticalResul
|
|||||||
import org.springframework.data.elasticsearch.core.facet.result.Term;
|
import org.springframework.data.elasticsearch.core.facet.result.Term;
|
||||||
import org.springframework.data.elasticsearch.core.facet.result.TermResult;
|
import org.springframework.data.elasticsearch.core.facet.result.TermResult;
|
||||||
|
|
||||||
|
import static java.util.Optional.ofNullable;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Container for query result and facet results
|
* Container for query result and facet results
|
||||||
*
|
*
|
||||||
@@ -48,6 +50,7 @@ import org.springframework.data.elasticsearch.core.facet.result.TermResult;
|
|||||||
* @author Artur Konczak
|
* @author Artur Konczak
|
||||||
* @author Jonathan Yan
|
* @author Jonathan Yan
|
||||||
* @author Philipp Kräutli
|
* @author Philipp Kräutli
|
||||||
|
* @author Remco Zigterman
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public abstract class FacetedPageImpl<T> extends PageImpl<T> implements FacetedPage<T>, AggregatedPage<T> {
|
public abstract class FacetedPageImpl<T> extends PageImpl<T> implements FacetedPage<T>, AggregatedPage<T> {
|
||||||
@@ -60,7 +63,7 @@ public abstract class FacetedPageImpl<T> extends PageImpl<T> implements FacetedP
|
|||||||
}
|
}
|
||||||
|
|
||||||
public FacetedPageImpl(List<T> content, Pageable pageable, long total) {
|
public FacetedPageImpl(List<T> content, Pageable pageable, long total) {
|
||||||
super(content, Pageable.unpaged(), total);
|
super(content, ofNullable(pageable).orElse(Pageable.unpaged()), total);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|||||||
@@ -50,6 +50,8 @@ import static org.springframework.util.StringUtils.*;
|
|||||||
* @author Dennis Maaß
|
* @author Dennis Maaß
|
||||||
* @author Pavel Luhin
|
* @author Pavel Luhin
|
||||||
* @author Mark Paluch
|
* @author Mark Paluch
|
||||||
|
* @author Sascha Woo
|
||||||
|
* @author Nordine Bittich
|
||||||
*/
|
*/
|
||||||
class MappingBuilder {
|
class MappingBuilder {
|
||||||
|
|
||||||
@@ -67,8 +69,7 @@ class MappingBuilder {
|
|||||||
public static final String COMPLETION_PRESERVE_POSITION_INCREMENTS = "preserve_position_increments";
|
public static final String COMPLETION_PRESERVE_POSITION_INCREMENTS = "preserve_position_increments";
|
||||||
public static final String COMPLETION_MAX_INPUT_LENGTH = "max_input_length";
|
public static final String COMPLETION_MAX_INPUT_LENGTH = "max_input_length";
|
||||||
|
|
||||||
public static final String INDEX_VALUE_NOT_ANALYZED = "not_analyzed";
|
public static final String TYPE_VALUE_KEYWORD = "keyword";
|
||||||
public static final String TYPE_VALUE_STRING = "text";
|
|
||||||
public static final String TYPE_VALUE_GEO_POINT = "geo_point";
|
public static final String TYPE_VALUE_GEO_POINT = "geo_point";
|
||||||
public static final String TYPE_VALUE_COMPLETION = "completion";
|
public static final String TYPE_VALUE_COMPLETION = "completion";
|
||||||
public static final String TYPE_VALUE_GEO_HASH_PREFIX = "geohash_prefix";
|
public static final String TYPE_VALUE_GEO_HASH_PREFIX = "geohash_prefix";
|
||||||
@@ -215,89 +216,107 @@ class MappingBuilder {
|
|||||||
private static void applyDefaultIdFieldMapping(XContentBuilder xContentBuilder, java.lang.reflect.Field field)
|
private static void applyDefaultIdFieldMapping(XContentBuilder xContentBuilder, java.lang.reflect.Field field)
|
||||||
throws IOException {
|
throws IOException {
|
||||||
xContentBuilder.startObject(field.getName())
|
xContentBuilder.startObject(field.getName())
|
||||||
.field(FIELD_TYPE, TYPE_VALUE_STRING)
|
.field(FIELD_TYPE, TYPE_VALUE_KEYWORD)
|
||||||
.field(FIELD_INDEX, INDEX_VALUE_NOT_ANALYZED);
|
.field(FIELD_INDEX, true);
|
||||||
xContentBuilder.endObject();
|
xContentBuilder.endObject();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Apply mapping for a single @Field annotation
|
* Add mapping for @Field annotation
|
||||||
*
|
*
|
||||||
* @throws IOException
|
* @throws IOException
|
||||||
*/
|
*/
|
||||||
private static void addSingleFieldMapping(XContentBuilder xContentBuilder, java.lang.reflect.Field field,
|
private static void addSingleFieldMapping(XContentBuilder builder, java.lang.reflect.Field field, Field annotation, boolean nestedOrObjectField) throws IOException {
|
||||||
Field fieldAnnotation, boolean nestedOrObjectField) throws IOException {
|
builder.startObject(field.getName());
|
||||||
xContentBuilder.startObject(field.getName());
|
addFieldMappingParameters(builder, annotation, nestedOrObjectField);
|
||||||
if(!nestedOrObjectField) {
|
builder.endObject();
|
||||||
xContentBuilder.field(FIELD_STORE, fieldAnnotation.store());
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add mapping for @MultiField annotation
|
||||||
|
*
|
||||||
|
* @throws IOException
|
||||||
|
*/
|
||||||
|
private static void addMultiFieldMapping(
|
||||||
|
XContentBuilder builder,
|
||||||
|
java.lang.reflect.Field field,
|
||||||
|
MultiField annotation,
|
||||||
|
boolean nestedOrObjectField) throws IOException {
|
||||||
|
|
||||||
|
// main field
|
||||||
|
builder.startObject(field.getName());
|
||||||
|
addFieldMappingParameters(builder, annotation.mainField(), nestedOrObjectField);
|
||||||
|
|
||||||
|
// inner fields
|
||||||
|
builder.startObject("fields");
|
||||||
|
for (InnerField innerField : annotation.otherFields()) {
|
||||||
|
builder.startObject(innerField.suffix());
|
||||||
|
addFieldMappingParameters(builder, innerField, false);
|
||||||
|
builder.endObject();
|
||||||
}
|
}
|
||||||
if(fieldAnnotation.fielddata()) {
|
builder.endObject();
|
||||||
xContentBuilder.field(FIELD_DATA, fieldAnnotation.fielddata());
|
|
||||||
|
builder.endObject();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void addFieldMappingParameters(XContentBuilder builder, Object annotation, boolean nestedOrObjectField) throws IOException {
|
||||||
|
boolean index = true;
|
||||||
|
boolean store = false;
|
||||||
|
boolean fielddata = false;
|
||||||
|
FieldType type = null;
|
||||||
|
DateFormat dateFormat = null;
|
||||||
|
String datePattern = null;
|
||||||
|
String analyzer = null;
|
||||||
|
String searchAnalyzer = null;
|
||||||
|
|
||||||
|
if (annotation instanceof Field) {
|
||||||
|
// @Field
|
||||||
|
Field fieldAnnotation = (Field) annotation;
|
||||||
|
index = fieldAnnotation.index();
|
||||||
|
store = fieldAnnotation.store();
|
||||||
|
fielddata = fieldAnnotation.fielddata();
|
||||||
|
type = fieldAnnotation.type();
|
||||||
|
dateFormat = fieldAnnotation.format();
|
||||||
|
datePattern = fieldAnnotation.pattern();
|
||||||
|
analyzer = fieldAnnotation.analyzer();
|
||||||
|
searchAnalyzer = fieldAnnotation.searchAnalyzer();
|
||||||
|
} else if (annotation instanceof InnerField) {
|
||||||
|
// @InnerField
|
||||||
|
InnerField fieldAnnotation = (InnerField) annotation;
|
||||||
|
index = fieldAnnotation.index();
|
||||||
|
store = fieldAnnotation.store();
|
||||||
|
fielddata = fieldAnnotation.fielddata();
|
||||||
|
type = fieldAnnotation.type();
|
||||||
|
dateFormat = fieldAnnotation.format();
|
||||||
|
datePattern = fieldAnnotation.pattern();
|
||||||
|
analyzer = fieldAnnotation.analyzer();
|
||||||
|
searchAnalyzer = fieldAnnotation.searchAnalyzer();
|
||||||
|
} else {
|
||||||
|
throw new IllegalArgumentException("annotation must be an instance of @Field or @InnerField");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (FieldType.Auto != fieldAnnotation.type()) {
|
if (!nestedOrObjectField) {
|
||||||
xContentBuilder.field(FIELD_TYPE, fieldAnnotation.type().name().toLowerCase());
|
builder.field(FIELD_STORE, store);
|
||||||
if (FieldType.Date == fieldAnnotation.type() && DateFormat.none != fieldAnnotation.format()) {
|
}
|
||||||
xContentBuilder.field(FIELD_FORMAT, DateFormat.custom == fieldAnnotation.format()
|
if (fielddata) {
|
||||||
? fieldAnnotation.pattern() : fieldAnnotation.format());
|
builder.field(FIELD_DATA, fielddata);
|
||||||
|
}
|
||||||
|
if (type != FieldType.Auto) {
|
||||||
|
builder.field(FIELD_TYPE, type.name().toLowerCase());
|
||||||
|
|
||||||
|
if (type == FieldType.Date && dateFormat != DateFormat.none) {
|
||||||
|
builder.field(FIELD_FORMAT, dateFormat == DateFormat.custom ? datePattern : dateFormat.toString());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(!fieldAnnotation.index()) {
|
if (!index) {
|
||||||
xContentBuilder.field(FIELD_INDEX, fieldAnnotation.index());
|
builder.field(FIELD_INDEX, index);
|
||||||
}
|
}
|
||||||
if (isNotBlank(fieldAnnotation.searchAnalyzer())) {
|
if (isNotBlank(analyzer)) {
|
||||||
xContentBuilder.field(FIELD_SEARCH_ANALYZER, fieldAnnotation.searchAnalyzer());
|
builder.field(FIELD_INDEX_ANALYZER, analyzer);
|
||||||
}
|
}
|
||||||
if (isNotBlank(fieldAnnotation.analyzer())) {
|
if (isNotBlank(searchAnalyzer)) {
|
||||||
xContentBuilder.field(FIELD_INDEX_ANALYZER, fieldAnnotation.analyzer());
|
builder.field(FIELD_SEARCH_ANALYZER, searchAnalyzer);
|
||||||
}
|
}
|
||||||
xContentBuilder.endObject();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Apply mapping for a single nested @Field annotation
|
|
||||||
*
|
|
||||||
* @throws IOException
|
|
||||||
*/
|
|
||||||
private static void addNestedFieldMapping(XContentBuilder builder, java.lang.reflect.Field field,
|
|
||||||
InnerField annotation) throws IOException {
|
|
||||||
builder.startObject(annotation.suffix());
|
|
||||||
//builder.field(FIELD_STORE, annotation.store());
|
|
||||||
if (FieldType.Auto != annotation.type()) {
|
|
||||||
builder.field(FIELD_TYPE, annotation.type().name().toLowerCase());
|
|
||||||
}
|
|
||||||
if(!annotation.index()) {
|
|
||||||
builder.field(FIELD_INDEX, annotation.index());
|
|
||||||
}
|
|
||||||
if (isNotBlank(annotation.searchAnalyzer())) {
|
|
||||||
builder.field(FIELD_SEARCH_ANALYZER, annotation.searchAnalyzer());
|
|
||||||
}
|
|
||||||
if (isNotBlank(annotation.indexAnalyzer())) {
|
|
||||||
builder.field(FIELD_INDEX_ANALYZER, annotation.indexAnalyzer());
|
|
||||||
}
|
|
||||||
if (annotation.fielddata()) {
|
|
||||||
builder.field(FIELD_DATA, annotation.fielddata());
|
|
||||||
}
|
|
||||||
builder.endObject();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Multi field mappings for string type fields, support for sorts and facets
|
|
||||||
*
|
|
||||||
* @throws IOException
|
|
||||||
*/
|
|
||||||
private static void addMultiFieldMapping(XContentBuilder builder, java.lang.reflect.Field field,
|
|
||||||
MultiField annotation, boolean nestedOrObjectField) throws IOException {
|
|
||||||
builder.startObject(field.getName());
|
|
||||||
builder.field(FIELD_TYPE, annotation.mainField().type());
|
|
||||||
builder.startObject("fields");
|
|
||||||
//add standard field
|
|
||||||
//addSingleFieldMapping(builder, field, annotation.mainField(), nestedOrObjectField);
|
|
||||||
for (InnerField innerField : annotation.otherFields()) {
|
|
||||||
addNestedFieldMapping(builder, field, innerField);
|
|
||||||
}
|
|
||||||
builder.endObject();
|
|
||||||
builder.endObject();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected static boolean isEntity(java.lang.reflect.Field field) {
|
protected static boolean isEntity(java.lang.reflect.Field field) {
|
||||||
|
|||||||
+2
-1
@@ -55,6 +55,7 @@ import org.springframework.util.Assert;
|
|||||||
* @author Kevin Leturc
|
* @author Kevin Leturc
|
||||||
* @author Mark Paluch
|
* @author Mark Paluch
|
||||||
* @author Christoph Strobl
|
* @author Christoph Strobl
|
||||||
|
* @author Michael Wirth
|
||||||
*/
|
*/
|
||||||
public abstract class AbstractElasticsearchRepository<T, ID extends Serializable>
|
public abstract class AbstractElasticsearchRepository<T, ID extends Serializable>
|
||||||
implements ElasticsearchRepository<T, ID> {
|
implements ElasticsearchRepository<T, ID> {
|
||||||
@@ -188,7 +189,7 @@ public abstract class AbstractElasticsearchRepository<T, ID extends Serializable
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean existsById(ID id) {
|
public boolean existsById(ID id) {
|
||||||
return findById(id) != null;
|
return findById(id).isPresent();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|||||||
@@ -1,6 +1,121 @@
|
|||||||
Spring Data Elasticsearch Changelog
|
Spring Data Elasticsearch Changelog
|
||||||
===================================
|
===================================
|
||||||
|
|
||||||
|
Changes in version 3.0.8.RELEASE (2018-06-13)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-460 - Avoid pulling in Netty 3 as dependency.
|
||||||
|
* DATAES-448 - Release 3.0.8 (Kay SR8).
|
||||||
|
* DATAES-420 - Analyzer of main field ignored when using @MultiField annotation.
|
||||||
|
* DATAES-312 - NullHandling.NULLS_LAST not working in query.sort.
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 2.1.13.RELEASE (2018-06-13)
|
||||||
|
----------------------------------------------
|
||||||
|
* DATAES-447 - Release 2.1.13 (Ingalls SR13).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.1.0.M3 (2018-05-17)
|
||||||
|
----------------------------------------
|
||||||
|
* DATAES-451 - Adapt to SpEL extension API changes in Spring Data Commons.
|
||||||
|
* DATAES-440 - Release 3.1 M3 (Lovelace).
|
||||||
|
* DATAES-422 - Add support for IndicesOptions in search queries.
|
||||||
|
* DATAES-420 - Analyzer of main field ignored when using @MultiField annotation.
|
||||||
|
* DATAES-412 - Highlighted fields is not getting passed to the elastic search query.
|
||||||
|
* DATAES-363 - AbstractElasticsearchRepository.existsById(..) always returns true.
|
||||||
|
* DATAES-312 - NullHandling.NULLS_LAST not working in query.sort.
|
||||||
|
* DATAES-198 - @Version has no effect, so therefore is not useful with spring data elasticsearch.
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.0.7.RELEASE (2018-05-08)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-438 - Expected a boolean [true/false] for property [index] but got [not_analyzed].
|
||||||
|
* DATAES-437 - Release 3.0.7 (Kay SR7).
|
||||||
|
* DATAES-412 - Highlighted fields is not getting passed to the elastic search query.
|
||||||
|
* DATAES-402 - Paging not working correctly.
|
||||||
|
* DATAES-363 - AbstractElasticsearchRepository.existsById(..) always returns true.
|
||||||
|
* DATAES-198 - @Version has no effect, so therefore is not useful with spring data elasticsearch.
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 2.1.12.RELEASE (2018-05-08)
|
||||||
|
----------------------------------------------
|
||||||
|
* DATAES-436 - Release 2.1.12 (Ingalls SR12).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.1.0.M2 (2018-04-13)
|
||||||
|
----------------------------------------
|
||||||
|
* DATAES-439 - Adapt to API changes in Spring Data Commons.
|
||||||
|
* DATAES-434 - Remove explicit declaration of Jackson library versions.
|
||||||
|
* DATAES-432 - Export composable repositories via CDI.
|
||||||
|
* DATAES-427 - Release 3.1 M2 (Lovelace).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.0.6.RELEASE (2018-04-04)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-434 - Remove explicit declaration of Jackson library versions.
|
||||||
|
* DATAES-430 - Release 3.0.6 (Kay SR6).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 2.1.11.RELEASE (2018-04-04)
|
||||||
|
----------------------------------------------
|
||||||
|
* DATAES-434 - Remove explicit declaration of Jackson library versions.
|
||||||
|
* DATAES-424 - Fix line endings.
|
||||||
|
* DATAES-423 - Release 2.1.11 (Ingalls SR11).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.0.5.RELEASE (2018-02-28)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-429 - Release 3.0.5 (Kay SR5).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.0.4.RELEASE (2018-02-19)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-425 - Release 3.0.4 (Kay SR4).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.1.0.M1 (2018-02-06)
|
||||||
|
----------------------------------------
|
||||||
|
* DATAES-424 - Fix line endings.
|
||||||
|
* DATAES-414 - Reduce scope of Lo4j dependencies to test.
|
||||||
|
* DATAES-410 - Adapt API changes in Property in test cases.
|
||||||
|
* DATAES-401 - Release 3.1 M1 (Lovelace).
|
||||||
|
* DATAES-361 - log4j2.xml in classpath root of the library prevents Spring Boot's logging auto-configuration to work.
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.0.3.RELEASE (2018-01-24)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-424 - Fix line endings.
|
||||||
|
* DATAES-417 - Release 3.0.3 (Kay SR3).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 2.1.10.RELEASE (2018-01-24)
|
||||||
|
----------------------------------------------
|
||||||
|
* DATAES-416 - Release 2.1.10 (Ingalls SR10).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.0.2.RELEASE (2017-11-27)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-414 - Reduce scope of Lo4j dependencies to test.
|
||||||
|
* DATAES-411 - Release 3.0.2 (Kay SR2).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 2.1.9.RELEASE (2017-11-27)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-408 - Ensure Spring 5 compatibility in Ingalls.
|
||||||
|
* DATAES-404 - Release 2.1.9 (Ingalls SR9).
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 3.0.1.RELEASE (2017-10-27)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-410 - Adapt API changes in Property in test cases.
|
||||||
|
* DATAES-400 - Release 3.0.1 (Kay SR1).
|
||||||
|
* DATAES-361 - log4j2.xml in classpath root of the library prevents Spring Boot's logging auto-configuration to work.
|
||||||
|
|
||||||
|
|
||||||
|
Changes in version 2.1.8.RELEASE (2017-10-11)
|
||||||
|
---------------------------------------------
|
||||||
|
* DATAES-391 - Release 2.1.8 (Ingalls SR8).
|
||||||
|
|
||||||
|
|
||||||
Changes in version 3.0.0.RELEASE (2017-10-02)
|
Changes in version 3.0.0.RELEASE (2017-10-02)
|
||||||
---------------------------------------------
|
---------------------------------------------
|
||||||
* DATAES-397 - Add explicit automatic module name for Java 9.
|
* DATAES-397 - Add explicit automatic module name for Java 9.
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
Spring Data Elasticsearch 3.0 GA
|
Spring Data Elasticsearch 3.0.8
|
||||||
Copyright (c) [2013-2016] Pivotal Software, Inc.
|
Copyright (c) [2013-2016] Pivotal Software, Inc.
|
||||||
|
|
||||||
This product is licensed to you under the Apache License, Version 2.0 (the "License").
|
This product is licensed to you under the Apache License, Version 2.0 (the "License").
|
||||||
|
|||||||
+68
-2
@@ -16,14 +16,15 @@
|
|||||||
package org.springframework.data.elasticsearch.core;
|
package org.springframework.data.elasticsearch.core;
|
||||||
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collections;
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Iterator;
|
import java.util.LinkedList;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import com.fasterxml.jackson.databind.util.ArrayIterator;
|
import com.fasterxml.jackson.databind.util.ArrayIterator;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.NoArgsConstructor;
|
import lombok.NoArgsConstructor;
|
||||||
import org.elasticsearch.action.get.GetResponse;
|
import org.elasticsearch.action.get.GetResponse;
|
||||||
|
import org.elasticsearch.action.get.MultiGetItemResponse;
|
||||||
|
import org.elasticsearch.action.get.MultiGetResponse;
|
||||||
import org.elasticsearch.action.search.SearchResponse;
|
import org.elasticsearch.action.search.SearchResponse;
|
||||||
import org.elasticsearch.search.SearchHit;
|
import org.elasticsearch.search.SearchHit;
|
||||||
import org.elasticsearch.search.SearchHitField;
|
import org.elasticsearch.search.SearchHitField;
|
||||||
@@ -41,6 +42,7 @@ import org.springframework.data.elasticsearch.annotations.Document;
|
|||||||
import org.springframework.data.elasticsearch.core.aggregation.AggregatedPage;
|
import org.springframework.data.elasticsearch.core.aggregation.AggregatedPage;
|
||||||
import org.springframework.data.elasticsearch.core.mapping.SimpleElasticsearchMappingContext;
|
import org.springframework.data.elasticsearch.core.mapping.SimpleElasticsearchMappingContext;
|
||||||
import org.springframework.data.elasticsearch.entities.Car;
|
import org.springframework.data.elasticsearch.entities.Car;
|
||||||
|
import org.springframework.data.elasticsearch.entities.SampleEntity;
|
||||||
|
|
||||||
import static java.util.Arrays.asList;
|
import static java.util.Arrays.asList;
|
||||||
import static org.hamcrest.Matchers.*;
|
import static org.hamcrest.Matchers.*;
|
||||||
@@ -50,6 +52,7 @@ import static org.mockito.Mockito.*;
|
|||||||
/**
|
/**
|
||||||
* @author Artur Konczak
|
* @author Artur Konczak
|
||||||
* @author Mohsin Husen
|
* @author Mohsin Husen
|
||||||
|
* @author Chris White
|
||||||
* @author Mark Paluch
|
* @author Mark Paluch
|
||||||
*/
|
*/
|
||||||
public class DefaultResultMapperTests {
|
public class DefaultResultMapperTests {
|
||||||
@@ -153,6 +156,69 @@ public class DefaultResultMapperTests {
|
|||||||
assertThat(result.getId(), is("identifier"));
|
assertThat(result.getId(), is("identifier"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-198
|
||||||
|
public void setsVersionFromGetResponse() {
|
||||||
|
GetResponse response = mock(GetResponse.class);
|
||||||
|
when(response.getSourceAsString()).thenReturn("{}");
|
||||||
|
when(response.getVersion()).thenReturn(1234L);
|
||||||
|
|
||||||
|
SampleEntity result = resultMapper.mapResult(response, SampleEntity.class);
|
||||||
|
|
||||||
|
assertThat(result, is(notNullValue()));
|
||||||
|
assertThat(result.getVersion(), is(1234L));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-198
|
||||||
|
public void setsVersionFromMultiGetResponse() {
|
||||||
|
GetResponse response1 = mock(GetResponse.class);
|
||||||
|
when(response1.getSourceAsString()).thenReturn("{}");
|
||||||
|
when(response1.isExists()).thenReturn(true);
|
||||||
|
when(response1.getVersion()).thenReturn(1234L);
|
||||||
|
|
||||||
|
GetResponse response2 = mock(GetResponse.class);
|
||||||
|
when(response2.getSourceAsString()).thenReturn("{}");
|
||||||
|
when(response2.isExists()).thenReturn(true);
|
||||||
|
when(response2.getVersion()).thenReturn(5678L);
|
||||||
|
|
||||||
|
MultiGetResponse multiResponse = mock(MultiGetResponse.class);
|
||||||
|
when(multiResponse.getResponses()).thenReturn(new MultiGetItemResponse[] {
|
||||||
|
new MultiGetItemResponse(response1, null), new MultiGetItemResponse(response2, null) });
|
||||||
|
|
||||||
|
LinkedList<SampleEntity> results = resultMapper.mapResults(multiResponse, SampleEntity.class);
|
||||||
|
|
||||||
|
assertThat(results, is(notNullValue()));
|
||||||
|
assertThat(results, hasSize(2));
|
||||||
|
|
||||||
|
assertThat(results.get(0).getVersion(), is(1234L));
|
||||||
|
assertThat(results.get(1).getVersion(), is(5678L));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-198
|
||||||
|
public void setsVersionFromSearchResponse() {
|
||||||
|
SearchHit hit1 = mock(SearchHit.class);
|
||||||
|
when(hit1.getSourceAsString()).thenReturn("{}");
|
||||||
|
when(hit1.getVersion()).thenReturn(1234L);
|
||||||
|
|
||||||
|
SearchHit hit2 = mock(SearchHit.class);
|
||||||
|
when(hit2.getSourceAsString()).thenReturn("{}");
|
||||||
|
when(hit2.getVersion()).thenReturn(5678L);
|
||||||
|
|
||||||
|
SearchHits searchHits = mock(SearchHits.class);
|
||||||
|
when(searchHits.getTotalHits()).thenReturn(2L);
|
||||||
|
when(searchHits.iterator()).thenReturn(Arrays.asList(hit1, hit2).iterator());
|
||||||
|
|
||||||
|
SearchResponse searchResponse = mock(SearchResponse.class);
|
||||||
|
when(searchResponse.getHits()).thenReturn(searchHits);
|
||||||
|
|
||||||
|
AggregatedPage<SampleEntity> results = resultMapper.mapResults(searchResponse, SampleEntity.class,
|
||||||
|
mock(Pageable.class));
|
||||||
|
|
||||||
|
assertThat(results, is(notNullValue()));
|
||||||
|
|
||||||
|
assertThat(results.getContent().get(0).getVersion(), is(1234L));
|
||||||
|
assertThat(results.getContent().get(1).getVersion(), is(5678L));
|
||||||
|
}
|
||||||
|
|
||||||
private Aggregation createCarAggregation() {
|
private Aggregation createCarAggregation() {
|
||||||
Aggregation aggregation = mock(Terms.class);
|
Aggregation aggregation = mock(Terms.class);
|
||||||
when(aggregation.getName()).thenReturn("Diesel");
|
when(aggregation.getName()).thenReturn("Diesel");
|
||||||
|
|||||||
+161
-2
@@ -33,6 +33,7 @@ import org.elasticsearch.script.Script;
|
|||||||
import org.elasticsearch.script.ScriptType;
|
import org.elasticsearch.script.ScriptType;
|
||||||
import org.elasticsearch.search.SearchHit;
|
import org.elasticsearch.search.SearchHit;
|
||||||
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
|
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
|
||||||
|
import org.elasticsearch.search.fetch.subphase.highlight.HighlightField;
|
||||||
import org.elasticsearch.search.sort.FieldSortBuilder;
|
import org.elasticsearch.search.sort.FieldSortBuilder;
|
||||||
import org.elasticsearch.search.sort.SortOrder;
|
import org.elasticsearch.search.sort.SortOrder;
|
||||||
import org.hamcrest.Matchers;
|
import org.hamcrest.Matchers;
|
||||||
@@ -70,6 +71,8 @@ import static org.springframework.data.elasticsearch.utils.IndexBuilder.*;
|
|||||||
* @author Abdul Mohammed
|
* @author Abdul Mohammed
|
||||||
* @author Kevin Leturc
|
* @author Kevin Leturc
|
||||||
* @author Mason Chan
|
* @author Mason Chan
|
||||||
|
* @author Chris White
|
||||||
|
* @author Sascha Woo
|
||||||
*/
|
*/
|
||||||
@RunWith(SpringJUnit4ClassRunner.class)
|
@RunWith(SpringJUnit4ClassRunner.class)
|
||||||
@ContextConfiguration("classpath:elasticsearch-template-test.xml")
|
@ContextConfiguration("classpath:elasticsearch-template-test.xml")
|
||||||
@@ -461,6 +464,106 @@ public class ElasticsearchTemplateTests {
|
|||||||
assertThat(sampleEntities.getContent().get(1).getMessage(), is(sampleEntity1.getMessage()));
|
assertThat(sampleEntities.getContent().get(1).getMessage(), is(sampleEntity1.getMessage()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-312
|
||||||
|
public void shouldSortResultsGivenNullFirstSortCriteria() {
|
||||||
|
// given
|
||||||
|
List<IndexQuery> indexQueries;
|
||||||
|
|
||||||
|
// first document
|
||||||
|
String documentId = randomNumeric(5);
|
||||||
|
SampleEntity sampleEntity1 = SampleEntity.builder()
|
||||||
|
.id(documentId)
|
||||||
|
.message("abc")
|
||||||
|
.rate(15)
|
||||||
|
.version(System.currentTimeMillis())
|
||||||
|
.build();
|
||||||
|
|
||||||
|
// second document
|
||||||
|
String documentId2 = randomNumeric(5);
|
||||||
|
SampleEntity sampleEntity2 = SampleEntity.builder()
|
||||||
|
.id(documentId2)
|
||||||
|
.message("xyz")
|
||||||
|
.rate(5)
|
||||||
|
.version(System.currentTimeMillis())
|
||||||
|
.build();
|
||||||
|
|
||||||
|
// third document
|
||||||
|
String documentId3 = randomNumeric(5);
|
||||||
|
SampleEntity sampleEntity3 = SampleEntity.builder()
|
||||||
|
.id(documentId3)
|
||||||
|
.rate(10)
|
||||||
|
.version(System.currentTimeMillis())
|
||||||
|
.build();
|
||||||
|
|
||||||
|
indexQueries = getIndexQueries(Arrays.asList(sampleEntity1, sampleEntity2, sampleEntity3));
|
||||||
|
|
||||||
|
elasticsearchTemplate.bulkIndex(indexQueries);
|
||||||
|
elasticsearchTemplate.refresh(SampleEntity.class);
|
||||||
|
|
||||||
|
SearchQuery searchQuery = new NativeSearchQueryBuilder()
|
||||||
|
.withQuery(matchAllQuery())
|
||||||
|
.withPageable(PageRequest.of(0, 10, Sort.by(Sort.Order.asc("message").nullsFirst())))
|
||||||
|
.build();
|
||||||
|
|
||||||
|
// when
|
||||||
|
Page<SampleEntity> sampleEntities = elasticsearchTemplate.queryForPage(searchQuery, SampleEntity.class);
|
||||||
|
|
||||||
|
// then
|
||||||
|
assertThat(sampleEntities.getTotalElements(), equalTo(3L));
|
||||||
|
assertThat(sampleEntities.getContent().get(0).getRate(), is(sampleEntity3.getRate()));
|
||||||
|
assertThat(sampleEntities.getContent().get(1).getMessage(), is(sampleEntity1.getMessage()));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-312
|
||||||
|
public void shouldSortResultsGivenNullLastSortCriteria() {
|
||||||
|
// given
|
||||||
|
List<IndexQuery> indexQueries;
|
||||||
|
|
||||||
|
// first document
|
||||||
|
String documentId = randomNumeric(5);
|
||||||
|
SampleEntity sampleEntity1 = SampleEntity.builder()
|
||||||
|
.id(documentId)
|
||||||
|
.message("abc")
|
||||||
|
.rate(15)
|
||||||
|
.version(System.currentTimeMillis())
|
||||||
|
.build();
|
||||||
|
|
||||||
|
// second document
|
||||||
|
String documentId2 = randomNumeric(5);
|
||||||
|
SampleEntity sampleEntity2 = SampleEntity.builder()
|
||||||
|
.id(documentId2)
|
||||||
|
.message("xyz")
|
||||||
|
.rate(5)
|
||||||
|
.version(System.currentTimeMillis())
|
||||||
|
.build();
|
||||||
|
|
||||||
|
// third document
|
||||||
|
String documentId3 = randomNumeric(5);
|
||||||
|
SampleEntity sampleEntity3 = SampleEntity.builder()
|
||||||
|
.id(documentId3)
|
||||||
|
.rate(10)
|
||||||
|
.version(System.currentTimeMillis())
|
||||||
|
.build();
|
||||||
|
|
||||||
|
indexQueries = getIndexQueries(Arrays.asList(sampleEntity1, sampleEntity2, sampleEntity3));
|
||||||
|
|
||||||
|
elasticsearchTemplate.bulkIndex(indexQueries);
|
||||||
|
elasticsearchTemplate.refresh(SampleEntity.class);
|
||||||
|
|
||||||
|
SearchQuery searchQuery = new NativeSearchQueryBuilder()
|
||||||
|
.withQuery(matchAllQuery())
|
||||||
|
.withPageable(PageRequest.of(0, 10, Sort.by(Sort.Order.asc("message").nullsLast())))
|
||||||
|
.build();
|
||||||
|
|
||||||
|
// when
|
||||||
|
Page<SampleEntity> sampleEntities = elasticsearchTemplate.queryForPage(searchQuery, SampleEntity.class);
|
||||||
|
|
||||||
|
// then
|
||||||
|
assertThat(sampleEntities.getTotalElements(), equalTo(3L));
|
||||||
|
assertThat(sampleEntities.getContent().get(0).getRate(), is(sampleEntity1.getRate()));
|
||||||
|
assertThat(sampleEntities.getContent().get(1).getMessage(), is(sampleEntity2.getMessage()));
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void shouldExecuteStringQuery() {
|
public void shouldExecuteStringQuery() {
|
||||||
// given
|
// given
|
||||||
@@ -1206,6 +1309,58 @@ public class ElasticsearchTemplateTests {
|
|||||||
assertThat(sampleEntities.getContent().get(0).getHighlightedMessage(), is(highlightedMessage));
|
assertThat(sampleEntities.getContent().get(0).getHighlightedMessage(), is(highlightedMessage));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-412
|
||||||
|
public void shouldReturnMultipleHighlightFields() {
|
||||||
|
|
||||||
|
// given
|
||||||
|
String documentId = randomNumeric(5);
|
||||||
|
String actualType = "some test type";
|
||||||
|
String actualMessage = "some test message";
|
||||||
|
String highlightedType = "some <em>test</em> type";
|
||||||
|
String highlightedMessage = "some <em>test</em> message";
|
||||||
|
|
||||||
|
SampleEntity sampleEntity = SampleEntity.builder()
|
||||||
|
.id(documentId)
|
||||||
|
.type(actualType)
|
||||||
|
.message(actualMessage)
|
||||||
|
.version(System.currentTimeMillis())
|
||||||
|
.build();
|
||||||
|
|
||||||
|
IndexQuery indexQuery = getIndexQuery(sampleEntity);
|
||||||
|
|
||||||
|
elasticsearchTemplate.index(indexQuery);
|
||||||
|
elasticsearchTemplate.refresh(SampleEntity.class);
|
||||||
|
|
||||||
|
SearchQuery searchQuery = new NativeSearchQueryBuilder()
|
||||||
|
.withQuery(
|
||||||
|
boolQuery()
|
||||||
|
.must(termQuery("type", "test"))
|
||||||
|
.must(termQuery("message", "test")))
|
||||||
|
.withHighlightFields(
|
||||||
|
new HighlightBuilder.Field("type"),
|
||||||
|
new HighlightBuilder.Field("message"))
|
||||||
|
.build();
|
||||||
|
|
||||||
|
// when
|
||||||
|
elasticsearchTemplate.queryForPage(searchQuery, SampleEntity.class, new SearchResultMapper() {
|
||||||
|
@Override
|
||||||
|
public <T> AggregatedPage<T> mapResults(SearchResponse response, Class<T> clazz, Pageable pageable) {
|
||||||
|
for (SearchHit searchHit : response.getHits()) {
|
||||||
|
Map<String, HighlightField> highlightFields = searchHit.getHighlightFields();
|
||||||
|
HighlightField highlightFieldType = highlightFields.get("type");
|
||||||
|
HighlightField highlightFieldMessage = highlightFields.get("message");
|
||||||
|
|
||||||
|
// then
|
||||||
|
assertNotNull(highlightFieldType);
|
||||||
|
assertNotNull(highlightFieldMessage);
|
||||||
|
assertThat(highlightFieldType.fragments()[0].toString(), is(highlightedType));
|
||||||
|
assertThat(highlightFieldMessage.fragments()[0].toString(), is(highlightedMessage));
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void shouldDeleteDocumentBySpecifiedTypeUsingDeleteQuery() {
|
public void shouldDeleteDocumentBySpecifiedTypeUsingDeleteQuery() {
|
||||||
// given
|
// given
|
||||||
@@ -1987,13 +2142,17 @@ public class ElasticsearchTemplateTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private IndexQuery getIndexQuery(SampleEntity sampleEntity) {
|
private IndexQuery getIndexQuery(SampleEntity sampleEntity) {
|
||||||
return new IndexQueryBuilder().withId(sampleEntity.getId()).withObject(sampleEntity).build();
|
return new IndexQueryBuilder()
|
||||||
|
.withId(sampleEntity.getId())
|
||||||
|
.withObject(sampleEntity)
|
||||||
|
.withVersion(sampleEntity.getVersion())
|
||||||
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
private List<IndexQuery> getIndexQueries(List<SampleEntity> sampleEntities) {
|
private List<IndexQuery> getIndexQueries(List<SampleEntity> sampleEntities) {
|
||||||
List<IndexQuery> indexQueries = new ArrayList<>();
|
List<IndexQuery> indexQueries = new ArrayList<>();
|
||||||
for (SampleEntity sampleEntity : sampleEntities) {
|
for (SampleEntity sampleEntity : sampleEntities) {
|
||||||
indexQueries.add(new IndexQueryBuilder().withId(sampleEntity.getId()).withObject(sampleEntity).build());
|
indexQueries.add(getIndexQuery(sampleEntity));
|
||||||
}
|
}
|
||||||
return indexQueries;
|
return indexQueries;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ import java.io.IOException;
|
|||||||
import java.math.BigDecimal;
|
import java.math.BigDecimal;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
import org.elasticsearch.common.xcontent.XContentBuilder;
|
import org.elasticsearch.common.xcontent.XContentBuilder;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
@@ -43,6 +44,7 @@ import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
|
|||||||
* @author Jakub Vavrik
|
* @author Jakub Vavrik
|
||||||
* @author Mohsin Husen
|
* @author Mohsin Husen
|
||||||
* @author Keivn Leturc
|
* @author Keivn Leturc
|
||||||
|
* @author Nordine Bittich
|
||||||
*/
|
*/
|
||||||
@RunWith(SpringJUnit4ClassRunner.class)
|
@RunWith(SpringJUnit4ClassRunner.class)
|
||||||
@ContextConfiguration("classpath:elasticsearch-template-test.xml")
|
@ContextConfiguration("classpath:elasticsearch-template-test.xml")
|
||||||
@@ -189,8 +191,28 @@ public class MappingBuilderTests {
|
|||||||
elasticsearchTemplate.createIndex(Book.class);
|
elasticsearchTemplate.createIndex(Book.class);
|
||||||
elasticsearchTemplate.putMapping(Book.class);
|
elasticsearchTemplate.putMapping(Book.class);
|
||||||
//when
|
//when
|
||||||
|
|
||||||
//then
|
//then
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-420
|
||||||
|
public void shouldUseBothAnalyzer() {
|
||||||
|
//given
|
||||||
|
elasticsearchTemplate.deleteIndex(Book.class);
|
||||||
|
elasticsearchTemplate.createIndex(Book.class);
|
||||||
|
elasticsearchTemplate.putMapping(Book.class);
|
||||||
|
|
||||||
|
//when
|
||||||
|
Map mapping = elasticsearchTemplate.getMapping(Book.class);
|
||||||
|
Map descriptionMapping = (Map) ((Map) mapping.get("properties")).get("description");
|
||||||
|
Map prefixDescription = (Map) ((Map) descriptionMapping.get("fields")).get("prefix");
|
||||||
|
|
||||||
|
//then
|
||||||
|
assertThat(prefixDescription.size(), is(3));
|
||||||
|
assertThat(prefixDescription.get("type"), equalTo("text"));
|
||||||
|
assertThat(prefixDescription.get("analyzer"), equalTo("stop"));
|
||||||
|
assertThat(prefixDescription.get("search_analyzer"), equalTo("standard"));
|
||||||
|
assertThat(descriptionMapping.get("type"), equalTo("text"));
|
||||||
|
assertThat(descriptionMapping.get("analyzer"), equalTo("whitespace"));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+41
@@ -0,0 +1,41 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2013-2017 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.elasticsearch.core.aggregation;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals;
|
||||||
|
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.springframework.data.domain.Page;
|
||||||
|
import org.springframework.data.domain.PageRequest;
|
||||||
|
import org.springframework.data.elasticsearch.core.aggregation.impl.AggregatedPageImpl;
|
||||||
|
|
||||||
|
import java.util.Arrays;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author Remco Zigterman
|
||||||
|
*/
|
||||||
|
public class AggregatedPageImplTest {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void constructFacetedPageWithPageable() {
|
||||||
|
Page<String> page = new AggregatedPageImpl<>(Arrays.asList("Test", "Test 2"), PageRequest.of(0, 2), 10);
|
||||||
|
|
||||||
|
assertEquals(10, page.getTotalElements());
|
||||||
|
assertEquals(2, page.getNumberOfElements());
|
||||||
|
assertEquals(2, page.getSize());
|
||||||
|
assertEquals(5, page.getTotalPages());
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -16,7 +16,7 @@
|
|||||||
package org.springframework.data.elasticsearch.core.facet;
|
package org.springframework.data.elasticsearch.core.facet;
|
||||||
|
|
||||||
import static org.springframework.data.elasticsearch.annotations.FieldType.Integer;
|
import static org.springframework.data.elasticsearch.annotations.FieldType.Integer;
|
||||||
import static org.springframework.data.elasticsearch.annotations.FieldType.text;
|
import static org.springframework.data.elasticsearch.annotations.FieldType.Text;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@@ -36,14 +36,14 @@ public class ArticleEntity {
|
|||||||
@Id
|
@Id
|
||||||
private String id;
|
private String id;
|
||||||
private String title;
|
private String title;
|
||||||
@Field(type = text, fielddata = true)
|
@Field(type = Text, fielddata = true)
|
||||||
private String subject;
|
private String subject;
|
||||||
|
|
||||||
@MultiField(
|
@MultiField(
|
||||||
mainField = @Field(type = text),
|
mainField = @Field(type = Text),
|
||||||
otherFields = {
|
otherFields = {
|
||||||
@InnerField(suffix = "untouched", type = text, store = true, fielddata = true, indexAnalyzer = "keyword"),
|
@InnerField(suffix = "untouched", type = Text, store = true, fielddata = true, analyzer = "keyword"),
|
||||||
@InnerField(suffix = "sort", type = text, store = true, indexAnalyzer = "keyword")
|
@InnerField(suffix = "sort", type = Text, store = true, analyzer = "keyword")
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
private List<String> authors = new ArrayList<>();
|
private List<String> authors = new ArrayList<>();
|
||||||
|
|||||||
+2
-1
@@ -66,7 +66,8 @@ public class SimpleElasticsearchPersistentEntityTests {
|
|||||||
private static SimpleElasticsearchPersistentProperty createProperty(SimpleElasticsearchPersistentEntity<?> entity,
|
private static SimpleElasticsearchPersistentProperty createProperty(SimpleElasticsearchPersistentEntity<?> entity,
|
||||||
String field) {
|
String field) {
|
||||||
|
|
||||||
Property property = Property.of(ReflectionUtils.findField(entity.getTypeInformation().getType(), field));
|
TypeInformation<?> type = entity.getTypeInformation();
|
||||||
|
Property property = Property.of(type, ReflectionUtils.findField(entity.getType(), field));
|
||||||
return new SimpleElasticsearchPersistentProperty(property, entity, SimpleTypeHolder.DEFAULT);
|
return new SimpleElasticsearchPersistentProperty(property, entity, SimpleTypeHolder.DEFAULT);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,10 +29,13 @@ import org.springframework.data.annotation.Id;
|
|||||||
import org.springframework.data.elasticsearch.annotations.Document;
|
import org.springframework.data.elasticsearch.annotations.Document;
|
||||||
import org.springframework.data.elasticsearch.annotations.Field;
|
import org.springframework.data.elasticsearch.annotations.Field;
|
||||||
import org.springframework.data.elasticsearch.annotations.FieldType;
|
import org.springframework.data.elasticsearch.annotations.FieldType;
|
||||||
|
import org.springframework.data.elasticsearch.annotations.InnerField;
|
||||||
|
import org.springframework.data.elasticsearch.annotations.MultiField;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Rizwan Idrees
|
* @author Rizwan Idrees
|
||||||
* @author Mohsin Husen
|
* @author Mohsin Husen
|
||||||
|
* @author Nordine Bittich
|
||||||
*/
|
*/
|
||||||
@Setter
|
@Setter
|
||||||
@Getter
|
@Getter
|
||||||
@@ -49,4 +52,11 @@ public class Book {
|
|||||||
private Author author;
|
private Author author;
|
||||||
@Field(type = FieldType.Nested)
|
@Field(type = FieldType.Nested)
|
||||||
private Map<Integer, Collection<String>> buckets = new HashMap<>();
|
private Map<Integer, Collection<String>> buckets = new HashMap<>();
|
||||||
|
@MultiField(
|
||||||
|
mainField = @Field(type = FieldType.Text, analyzer = "whitespace"),
|
||||||
|
otherFields = {
|
||||||
|
@InnerField(suffix = "prefix", type = FieldType.Text, analyzer = "stop", searchAnalyzer = "standard")
|
||||||
|
}
|
||||||
|
)
|
||||||
|
private String description;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,7 +19,6 @@ import org.springframework.core.style.ToStringCreator;
|
|||||||
import org.springframework.data.annotation.Id;
|
import org.springframework.data.annotation.Id;
|
||||||
import org.springframework.data.elasticsearch.annotations.Document;
|
import org.springframework.data.elasticsearch.annotations.Document;
|
||||||
import org.springframework.data.elasticsearch.annotations.Field;
|
import org.springframework.data.elasticsearch.annotations.Field;
|
||||||
import org.springframework.data.elasticsearch.annotations.FieldIndex;
|
|
||||||
import org.springframework.data.elasticsearch.annotations.FieldType;
|
import org.springframework.data.elasticsearch.annotations.FieldType;
|
||||||
import org.springframework.data.elasticsearch.annotations.Parent;
|
import org.springframework.data.elasticsearch.annotations.Parent;
|
||||||
|
|
||||||
@@ -38,7 +37,7 @@ public class ParentEntity {
|
|||||||
|
|
||||||
@Id
|
@Id
|
||||||
private String id;
|
private String id;
|
||||||
@Field(type = FieldType.text, store = true)
|
@Field(type = FieldType.Text, store = true)
|
||||||
private String name;
|
private String name;
|
||||||
|
|
||||||
public ParentEntity() {
|
public ParentEntity() {
|
||||||
@@ -67,10 +66,10 @@ public class ParentEntity {
|
|||||||
|
|
||||||
@Id
|
@Id
|
||||||
private String id;
|
private String id;
|
||||||
@Field(type = FieldType.text, store = true)
|
@Field(type = FieldType.Text, store = true)
|
||||||
@Parent(type = PARENT_TYPE)
|
@Parent(type = PARENT_TYPE)
|
||||||
private String parentId;
|
private String parentId;
|
||||||
@Field(type = FieldType.text, store = true)
|
@Field(type = FieldType.Text, store = true)
|
||||||
private String name;
|
private String name;
|
||||||
|
|
||||||
public ChildEntity() {
|
public ChildEntity() {
|
||||||
|
|||||||
+2
-2
@@ -1,7 +1,7 @@
|
|||||||
package org.springframework.data.elasticsearch.entities;
|
package org.springframework.data.elasticsearch.entities;
|
||||||
|
|
||||||
import static org.springframework.data.elasticsearch.annotations.FieldType.*;
|
import static org.springframework.data.elasticsearch.annotations.FieldType.*;
|
||||||
import static org.springframework.data.elasticsearch.annotations.FieldType.text;
|
import static org.springframework.data.elasticsearch.annotations.FieldType.Text;
|
||||||
|
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
|
||||||
@@ -19,7 +19,7 @@ public class SampleDateMappingEntity {
|
|||||||
@Id
|
@Id
|
||||||
private String id;
|
private String id;
|
||||||
|
|
||||||
@Field(type = text, index = false, store = true, analyzer = "standard")
|
@Field(type = Text, index = false, store = true, analyzer = "standard")
|
||||||
private String message;
|
private String message;
|
||||||
|
|
||||||
@Field(type = Date, format = DateFormat.custom, pattern = "dd.MM.yyyy hh:mm")
|
@Field(type = Date, format = DateFormat.custom, pattern = "dd.MM.yyyy hh:mm")
|
||||||
|
|||||||
@@ -23,6 +23,7 @@ import lombok.Builder;
|
|||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.NoArgsConstructor;
|
import lombok.NoArgsConstructor;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
|
import lombok.ToString;
|
||||||
import org.springframework.data.annotation.Id;
|
import org.springframework.data.annotation.Id;
|
||||||
import org.springframework.data.annotation.Version;
|
import org.springframework.data.annotation.Version;
|
||||||
import org.springframework.data.elasticsearch.annotations.Document;
|
import org.springframework.data.elasticsearch.annotations.Document;
|
||||||
@@ -34,21 +35,23 @@ import static org.springframework.data.elasticsearch.annotations.FieldType.*;
|
|||||||
/**
|
/**
|
||||||
* @author Rizwan Idrees
|
* @author Rizwan Idrees
|
||||||
* @author Mohsin Husen
|
* @author Mohsin Husen
|
||||||
|
* @author Chris White
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@Setter
|
@Setter
|
||||||
@Getter
|
@Getter
|
||||||
@NoArgsConstructor
|
@NoArgsConstructor
|
||||||
@AllArgsConstructor
|
@AllArgsConstructor
|
||||||
|
@ToString
|
||||||
@Builder
|
@Builder
|
||||||
@Document(indexName = "test-index-sample", type = "test-type", shards = 1, replicas = 0, refreshInterval = "-1")
|
@Document(indexName = "test-index-sample", type = "test-type", shards = 1, replicas = 0, refreshInterval = "-1")
|
||||||
public class SampleEntity {
|
public class SampleEntity {
|
||||||
|
|
||||||
@Id
|
@Id
|
||||||
private String id;
|
private String id;
|
||||||
@Field(type = text, store = true, fielddata = true)
|
@Field(type = Text, store = true, fielddata = true)
|
||||||
private String type;
|
private String type;
|
||||||
@Field(type = text, store = true, fielddata = true)
|
@Field(type = Text, store = true, fielddata = true)
|
||||||
private String message;
|
private String message;
|
||||||
private int rate;
|
private int rate;
|
||||||
@ScriptedField
|
@ScriptedField
|
||||||
|
|||||||
+1
-1
@@ -48,7 +48,7 @@ public class SampleEntityUUIDKeyed {
|
|||||||
@Id
|
@Id
|
||||||
private UUID id;
|
private UUID id;
|
||||||
private String type;
|
private String type;
|
||||||
@Field(type = FieldType.text, fielddata = true)
|
@Field(type = FieldType.Text, fielddata = true)
|
||||||
private String message;
|
private String message;
|
||||||
private int rate;
|
private int rate;
|
||||||
@ScriptedField
|
@ScriptedField
|
||||||
|
|||||||
+2
-2
@@ -15,7 +15,7 @@
|
|||||||
*/
|
*/
|
||||||
package org.springframework.data.elasticsearch.entities;
|
package org.springframework.data.elasticsearch.entities;
|
||||||
|
|
||||||
import static org.springframework.data.elasticsearch.annotations.FieldType.text;
|
import static org.springframework.data.elasticsearch.annotations.FieldType.Text;
|
||||||
|
|
||||||
import org.springframework.data.elasticsearch.annotations.Document;
|
import org.springframework.data.elasticsearch.annotations.Document;
|
||||||
import org.springframework.data.elasticsearch.annotations.Field;
|
import org.springframework.data.elasticsearch.annotations.Field;
|
||||||
@@ -26,7 +26,7 @@ import org.springframework.data.elasticsearch.annotations.Field;
|
|||||||
@Document(indexName = "test-index-sample-inherited", type = "mapping", shards = 1, replicas = 0, refreshInterval = "-1")
|
@Document(indexName = "test-index-sample-inherited", type = "mapping", shards = 1, replicas = 0, refreshInterval = "-1")
|
||||||
public class SampleInheritedEntity extends AbstractInheritedEntity {
|
public class SampleInheritedEntity extends AbstractInheritedEntity {
|
||||||
|
|
||||||
@Field(type = text, index = false, store = true, analyzer = "standard")
|
@Field(type = Text, index = false, store = true, analyzer = "standard")
|
||||||
private String message;
|
private String message;
|
||||||
|
|
||||||
public String getMessage() {
|
public String getMessage() {
|
||||||
|
|||||||
+3
-3
@@ -15,7 +15,7 @@
|
|||||||
*/
|
*/
|
||||||
package org.springframework.data.elasticsearch.entities;
|
package org.springframework.data.elasticsearch.entities;
|
||||||
|
|
||||||
import static org.springframework.data.elasticsearch.annotations.FieldType.text;
|
import static org.springframework.data.elasticsearch.annotations.FieldType.Text;
|
||||||
|
|
||||||
import org.springframework.data.annotation.Id;
|
import org.springframework.data.annotation.Id;
|
||||||
import org.springframework.data.elasticsearch.annotations.Document;
|
import org.springframework.data.elasticsearch.annotations.Document;
|
||||||
@@ -31,7 +31,7 @@ public class SampleMappingEntity {
|
|||||||
@Id
|
@Id
|
||||||
private String id;
|
private String id;
|
||||||
|
|
||||||
@Field(type = text, index = false, store = true, analyzer = "standard")
|
@Field(type = Text, index = false, store = true, analyzer = "standard")
|
||||||
private String message;
|
private String message;
|
||||||
|
|
||||||
private NestedEntity nested;
|
private NestedEntity nested;
|
||||||
@@ -54,7 +54,7 @@ public class SampleMappingEntity {
|
|||||||
|
|
||||||
static class NestedEntity {
|
static class NestedEntity {
|
||||||
|
|
||||||
@Field(type = text)
|
@Field(type = Text)
|
||||||
private String someField;
|
private String someField;
|
||||||
|
|
||||||
public String getSomeField() {
|
public String getSomeField() {
|
||||||
|
|||||||
+2
-2
@@ -15,7 +15,7 @@
|
|||||||
*/
|
*/
|
||||||
package org.springframework.data.elasticsearch.entities;
|
package org.springframework.data.elasticsearch.entities;
|
||||||
|
|
||||||
import static org.springframework.data.elasticsearch.annotations.FieldType.text;
|
import static org.springframework.data.elasticsearch.annotations.FieldType.Text;
|
||||||
|
|
||||||
import org.springframework.data.annotation.Id;
|
import org.springframework.data.annotation.Id;
|
||||||
import org.springframework.data.annotation.Transient;
|
import org.springframework.data.annotation.Transient;
|
||||||
@@ -31,7 +31,7 @@ public class SampleTransientEntity {
|
|||||||
@Id
|
@Id
|
||||||
private String id;
|
private String id;
|
||||||
|
|
||||||
@Field(type = text, index = false, store = true, analyzer = "standard")
|
@Field(type = Text, index = false, store = true, analyzer = "standard")
|
||||||
private String message;
|
private String message;
|
||||||
|
|
||||||
@Transient
|
@Transient
|
||||||
|
|||||||
+14
@@ -47,6 +47,7 @@ import static org.springframework.data.domain.Sort.Direction.*;
|
|||||||
* @author Mohsin Husen
|
* @author Mohsin Husen
|
||||||
* @author Mark Paluch
|
* @author Mark Paluch
|
||||||
* @author Christoph Strobl
|
* @author Christoph Strobl
|
||||||
|
* @author Michael Wirth
|
||||||
*/
|
*/
|
||||||
@RunWith(SpringJUnit4ClassRunner.class)
|
@RunWith(SpringJUnit4ClassRunner.class)
|
||||||
@ContextConfiguration("classpath:/simple-repository-test.xml")
|
@ContextConfiguration("classpath:/simple-repository-test.xml")
|
||||||
@@ -274,6 +275,19 @@ public class SimpleElasticsearchRepositoryTests {
|
|||||||
assertEquals(exist, true);
|
assertEquals(exist, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-363
|
||||||
|
public void shouldReturnFalseGivenDocumentWithIdDoesNotExist() {
|
||||||
|
|
||||||
|
// given
|
||||||
|
String documentId = randomNumeric(5);
|
||||||
|
|
||||||
|
// when
|
||||||
|
boolean exist = repository.existsById(documentId);
|
||||||
|
|
||||||
|
// then
|
||||||
|
assertThat(exist, is(false));
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void shouldReturnResultsForGivenSearchQuery() {
|
public void shouldReturnResultsForGivenSearchQuery() {
|
||||||
// given
|
// given
|
||||||
|
|||||||
+14
@@ -45,6 +45,7 @@ import static org.junit.Assert.*;
|
|||||||
* @author Mohsin Husen
|
* @author Mohsin Husen
|
||||||
* @author Mark Paluch
|
* @author Mark Paluch
|
||||||
* @author Christoph Strobl
|
* @author Christoph Strobl
|
||||||
|
* @author Michael Wirth
|
||||||
*/
|
*/
|
||||||
@RunWith(SpringJUnit4ClassRunner.class)
|
@RunWith(SpringJUnit4ClassRunner.class)
|
||||||
@ContextConfiguration("classpath:/simple-repository-test.xml")
|
@ContextConfiguration("classpath:/simple-repository-test.xml")
|
||||||
@@ -262,6 +263,19 @@ public class UUIDElasticsearchRepositoryTests {
|
|||||||
assertEquals(exist, true);
|
assertEquals(exist, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // DATAES-363
|
||||||
|
public void shouldReturnFalseGivenDocumentWithIdDoesNotExist() {
|
||||||
|
|
||||||
|
// given
|
||||||
|
UUID documentId = UUID.randomUUID();
|
||||||
|
|
||||||
|
// when
|
||||||
|
boolean exist = repository.existsById(documentId);
|
||||||
|
|
||||||
|
// then
|
||||||
|
assertThat(exist, is(false));
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void shouldDeleteAll() {
|
public void shouldDeleteAll() {
|
||||||
// when
|
// when
|
||||||
|
|||||||
Reference in New Issue
Block a user