Elasticsearch6.x Mapping详解

1.映射(Mapping)

映射是定义文档及其包含的字段的存储和索引方式的过程。例如,使用映射来定义:

  • 应将哪些字符串字段视为全文字段。
  • 哪些字段包含数字,日期或地理位置。
  • 是否应将文档中所有字段的值索引到catch-all _all字段中。
  • 日期值 的格式
  • 用于控制动态添加字段的映射的自定义规则 

1.1 映射类型(对比于数据库中的一个表)

每个索引都有一种映射类型,用于确定文档的索引方式。 在6.0.0中已弃用映射类型(即只有一个固定的类型名,不能自定义)。

映射类型具有(这个属于内容,还是可以自定义的):

元数据字段
元字段用于自定义文档的元数据关联的处理方式。元数据字段包括
  _index   表示属于哪个索引
_type    类型名
_id     文档的id,唯一标识
_source    文档的原始数据(对比于数据库表中的一条记录)
_routing     文档对应的路由信息(控制文档写到哪一个分片上,默认是使用id进行hash)
字段属性
映射类型包含字段列表或 properties 与文档相关的列表

废弃原因

  传统数据库中同一个数据库下的多个表之间是互相独立的

  es中同一个索引下的不同映射类型底层由ucene实例支持,不同类型下的相同名称的字段需要是相同的类型,因为lucene无法区分来自哪个type。

7.x之后每个索引只有一个type,名字为_doc

1.2 字段数据类型(对比于数据库的列的定义,只是es没有固定的列)

每个字段都有一个数据type,可以是:

  • 常见简单类型
    •  text           用于全文搜索,一般用于存储要搜索的字符串,如微博正文
    •  keyword         用于精确搜索,过滤结果。值可以是字符串或单个单词
    •     date               日期类型
    •     long、integer、shot、byte...      数字类型
  • 一种支持JSON的分层特性的类型,如 objectnested
  • 或一种特殊类型如:geo_point, geo_shapecompletion

为不同目的以不同方式索引相同字段通常很有用。例如,string字段可以索引text用于全文搜索,或者keyword字段用于排序或聚合

1.2.1 设置参数防止映射爆炸(映射字段过多导致问题,对比于数据库的列过多)

在索引中定义太多字段是一种可能导致映射爆炸的情况,这可能导致内存不足错误和难以恢复的情况。

这个问题可能比预期更常见。例如,考虑插入的每个新文档引入新字段的情况。这在动态映射中非常常见。每次文档包含新字段时,这些字段最终都会出现在索引的映射中。

随着映射的增加,可能会成为一个问题。以下设置允许您限制可手动或动态创建的字段映射的数量,以防止错误的文档导致映射爆炸:

index.mapping.total_fields.limit
索引中的最大字段数。字段和对象映射以及字段别名都计入此限制。默认值为 1000
index.mapping.depth.limit
字段的最大深度,以内部对象的数量来衡量。例如,如果所有字段都是在根对象级别定义的,则深度为 1 如果有一个对象映射,则深度为  2 ,等等。默认值为 20
index.mapping.nested_fields.limit
nested 索引中 的最大字段,默认为 50 使用100个嵌套字段索引1个文档实际上索引101个文档,因为每个嵌套文档都被索引为单独的隐藏文档。

1.3 动态映射(根据字段的值自动推断字段的类型)

在使用之前不需要定义字段和映射类型。

由于动态映射,只需索引文档即可自动添加新的字段名称。同一个字段第一次出现的时候就确定了字段类型,后续此字段必须符合这个字段类型。

1.4 显式映射(对比与数据库中的定义表结构)

您对数据的了解比Elasticsearch可以猜到的更多,因此虽然动态映射对于入门很有用,但在某些时候您需要指定自己的显式映射。

您可以在创建索引时创建字段映射 ,也可以使用PUT映射API将字段添加到现有索引

1.5 映射参数

1.5.1 analyzer

作用:

  指定分词器,将对应的text类型数据分割成独立的单词(token或者terms)。

作用时间:

  索引(分词并存储 ,建立倒排索引)和查询(将查询字段分词)

作用范围:

  单词查询,单个字段,单次索引都可以指定分词器。如果没有指定则使用默认的standard分词器。

curl -X PUT "localhost:9200/my_index" -H 'Content-Type: application/json' -d'
{
  "mappings": {
    "_doc": {
      "properties": {
        "text": { 
          "type": "text",    //这里没有指定analyzer,所以使用默认的standard分析器
          "fields": {       //这个字段的作用是,使用同一份数据,进行不同的处理
            "english": {       //定义字段名为english
              "type":     "text",    //字段类型为text
              "analyzer": "english"    //英文分词器,es内置的
            }
          }
        }
      }
    }
  }
}
'
curl -X GET "localhost:9200/my_index/_analyze" -H 'Content-Type: application/json' -d'
{
  "field": "text",
  "text": "The quick Brown Foxes."
}
'
curl -X GET "localhost:9200/my_index/_analyze" -H 'Content-Type: application/json' -d'
{
  "field": "text.english",   //指定这个字段,则会使用其上定义的英文分词器
  "text": "The quick Brown Foxes."
}
'

1.6 更新现有字段映射

已经存在的字段映射无法更新更改映射意味着使已索引的文档无效。

相反,你应该创建正确映射一个新的索引,并调用reindex将数据进行转换到新的索引中如果您只想重命名字段而不更改其映射,则引入alias字段可能是有意义的

1.7 映射示例

创建索引时可以指定映射,如下所示:

curl -X PUT "localhost:9200/my_index" -H 'Content-Type: application/json' -d'
{
  "mappings": {  
    "_doc": {     //映射类型为 _doc
      "properties": {    //定义字段或者properties
        "title":    { "type": "text"  },  //定义字段title的字段类型为text
        "name":     { "type": "text"  }, 
        "age":      { "type": "integer" },  
        "created":  {
          "type":   "date", 
          "format": "strict_date_optional_time||epoch_millis"
        }
      }
    }
  }
}
'

猜你喜欢

转载自www.cnblogs.com/gc65/p/10680418.html