Spring Data Elasticsearch对象映射是将Java对象(域实体)映射到存储在Elasticsearch中的JSON表示中并返回的过程。内部用于此映射的类是MappingElasticsearchConverter。
一、元模型对象映射
基于元模型的方法使用域类型信息来读取/写入Elasticsearch。这允许为特定的域类型映射注册Converter实例。
1、映射注释概述
MappingElasticsearchConverter使用元数据来驱动对象到文档的映射。元数据取自可以注释的实体属性。
以下注释可用:
-
@Document
: 应用于类级别,以指示该类是映射到数据库的候选类。最重要的属性是(有关属性的完整列表,请查看API文档):-
indexName:
存储该实体的索引的名称。它可以包含类似于以下内容的SpEL模板表达式:"log-#{T(java.time.LocalDate).now().toString()}"
-
createIndex:
标记是否在存储库引导上创建索引。默认值为true。请参见使用相应的映射自动创建索引
-
-
@Id
: 应用于字段级别,以标记用于标识的字段。 -
@Transient
,@ReadOnlyProperty
,@WriteOnlyProperty
: 有关详细信息,请参阅下面的控制向Elasticsearch写入和从中读取哪些属性一节。 -
@PersistenceConstructor
: 标记给定的构造函数(即使是受包保护的构造函数)以在从数据库中实例化对象时使用。构造函数参数按名称映射到检索到的文档中的键值。 -
@Field
: 应用于字段级别并定义字段的属性,大多数属性映射到各自的Elasticsearch Mapping定义(下表不完整,请检查注释Javadoc以获得完整的参考):-
name
: 字段的名称将在Elasticsearch文档中表示,如果未设置,则使用Java字段名。 -
type
: 字段类型,可以是Text、Keyword、Long、Integer、Short、Byte、Double、Float、Half_Float、Scaled_Float,Date、Date_Nanos、Boolean、Binary、Integer_Range、Float_Range,Long_Range和Double_Range中的一种,Date_Range。Ip_Range;Object,Nested,Ip,TokenCount,Percolator,Flattened,Search_As_You_type。请参见Elasticsearch映射类型。如果未指定字段类型,则默认为FieldType。自动。这意味着没有为属性写入映射条目,并且当存储该属性的第一个数据时,Elasticsearch将动态添加映射条目(有关动态映射规则,请查看Elasticsearch文档)。 -
format
: 一个或多个内置日期格式,请参阅下一节日期格式映射。 -
pattern
: 一个或多个自定义日期格式,请参阅下一节日期格式映射。 -
store
: 标记原始字段值是否应存储在Elasticsearch中,默认值为false。 -
analyzer
,searchAnalyzer
,normalizer
用于指定自定义分析器和规范化器。
-
-
@GeoPoint
: 将字段标记为geo_point数据类型。如果字段是GeoPoint类的实例,则可以省略。 -
@ValueConverter
:定义用于转换给定属性的类。与注册的Spring Converter不同,这仅转换带注释的属性,而不是给定类型的每个属性。
映射元数据基础架构在单独的spring数据公共项目中定义,该项目与技术无关。
2、控制向Elasticsearch写入和从中读取的属性
本节详细介绍了定义属性的值是写入还是从Elasticsearch读取的注释。
@Transient :用该注释注释的属性不会写入映射,其值不会发送到Elasticsearch,并且当文档从Elasticsearch返回时,不会在结果实体中设置该属性。
@ReadOnlyProperty:具有此注释的属性不会将其值写入Elasticsearch,但当返回数据时,该属性将用Elasticsearch在文档中返回的值填充。这方面的一个用例是在索引映射中定义的运行时字段。
@WriteOnlyProperty:具有此注释的属性的值将存储在Elasticsearch中,但在读取文档时不会设置任何值。例如,这可以用于应进入Elasticsearch索引但不在其他地方使用的合成字段。
3、日期格式映射
派生自TemporalAccessor或类型为java.util的属性。日期必须具有类型为FieldType的@Field批注。必须为此类型注册日期或自定义转换器。本段描述FieldType的使用。日期。
@Field注释有两个属性,定义将哪个日期格式信息写入映射(另请参阅Elasticsearch内置格式和Elasticsearch自定义日期格式)
format属性用于定义至少一种预定义格式。如果未定义,则使用默认值_date_optional_time和epoch_millis。
模式属性可用于添加其他自定义格式字符串。如果只想使用自定义日期格式,则必须将format属性设置为空{}。
下表显示了不同的属性以及根据其值创建的映射:
注解 | format string in Elasticsearch mapping |
---|---|
@Field(type=FieldType.Date) | "date_optional_time||epoch_millis", |
@Field(type=FieldType.Date, format=DateFormat.basic_date) | "basic_date" |
@Field(type=FieldType.Date, format={DateFormat.basic_date, DateFormat.basic_time}) | "basic_date||basic_time" |
@Field(type=FieldType.Date, pattern="dd.MM.uuuu") | "date_optional_time||epoch_millis||dd.MM.uuuu", |
@Field(type=FieldType.Date, format={}, pattern="dd.MM.uuuu") | "dd.MM.uuuu" |
检查org.springframework.data.elasticsearch.annotations的代码。用于预定义值及其模式的完整列表的DateFormat枚举。
4、范围类型
当用Integer_Range、Float_Range或Long_Range之一的类型注释字段时,字段必须是将映射到Elasticsearch范围的类的实例,例如:
class SomePersonData {
@Field(type = FieldType.Integer_Range)
private ValidAge validAge;
// getter and setter
}
class ValidAge {
@Field(name="gte")
private Integer from;
@Field(name="lte")
private Integer to;
// getter and setter
}
作为另一种选择,Spring Data Elasticsearch提供了Range<T>类,因此前面的示例可以编写为:
class SomePersonData {
@Field(type = FieldType.Integer_Range)
private Range<Integer> validAge;
// getter and setter
}
类型<T>支持的类包括Integer、Long、Float、Double、Date和实现TemporalAccessor接口的类。
5、映射的字段名
在没有进一步配置的情况下,Spring Data Elasticsearch将使用对象的属性名作为Elasticsearch中的字段名。通过使用该属性上的@field注释,可以为单个字段更改此设置。
也可以在客户端(Elasticsearch客户端)的配置中定义FieldNamingStrategy。例如,如果配置了SnakeCaseFieldNamingStrategy,则对象的属性sampleProperty将映射到Elasticsearch中的sample_property。FieldNamingStrategy适用于所有实体;可以通过在属性上使用@Field设置特定名称来覆盖它。
6、非字段支持的属性
通常,实体中使用的属性是实体类的字段。在某些情况下,在实体中计算属性值并应存储在Elasticsearch中。在这种情况下,除了必须用@AccessType(AccessType.Type.PROPERTY)注释方法外,还可以用@Field注释注释getter方法(getProperty())。在这种情况下需要的第三个注释是@WriteOnlyProperty,因为这样的值仅写入Elasticsearch。完整示例:
@Field(type = Keyword)
@WriteOnlyProperty
@AccessType(AccessType.Type.PROPERTY)
public String getProperty() {
return "some value that is calculated here";
}
7、其他特性注释
@IndexedIndexName
可以在实体的String属性上设置此注释。该属性不会写入映射,它不会存储在Elasticsearch中,并且不会从Elasticsearch文档中读取其值。在持久化实体后,例如通过调用ElasticsearchOperations.save(T实体),从该调用返回的实体将包含实体保存到该属性中的索引的名称。当bean动态设置索引名时,或者在写入写入别名时,这很有用。
将一些值放入这样的属性中不会设置实体存储到的索引!
二、映射规则
1、键入提示
映射使用嵌入在发送到服务器的文档中的类型提示来允许泛型类型映射。这些类型提示在文档中表示为_class属性,并为每个聚合根编写。
{
"_class" : "com.example.Person",
"id" : "cb7bef",
"firstname" : "Sarah",
"lastname" : "Connor"
}
可以将类型提示配置为保存自定义信息。使用@TypeAlias注释来执行此操作。
{
"_class" : "human",
"id" : ...
}