使用kibana对类型及映射操作

1,175 阅读7分钟

「这是我参与11月更文挑战的第6天,活动详情查看:2021最后一次更文挑战

有了索引库 ,等于有了数据库中的database 。接下来就需要索引库中的类型了,也就是数据库中的表 。创建数据库表需要设置字段约束,索引库也一样,在创建索引库的类型时,需要知道这个类型下有哪些字段,每个字段有哪些约束信息,这就叫做字段映射(mapping)

注意:Elasticsearch7.x取消了索引type类型的设置,不允许指定类型,默认为_doc,但字段仍然是有的,我们需要设置字段的约束信息,叫做字段映射(mapping)

字段的约束我们在学习Lucene中我们都见到过,包括到不限于:

  • 字段的数据类型
  • 是否要存储
  • 是否要索引
  • 是否分词
  • 分词器是什么

创建字段映射

语法

请求方式依然是PUT

PUT /索引库名/_mapping/typeName
{
    "properties": {
        "字段名": {
            "type": "类型",
            "index": true,
            "store": true,
            "analyzer": "分词器"
        }
    }
}
  • 类型名称:就是前面将的type的概念,类似于数据库中的表字段名:任意填写,下面指定许多属性,例如:
    • type:类型,可以是text、keyword、long、short、date、integer、object等
    • index:是否索引,默认为true
    • store:是否存储,默认为false
    • analyzer:分词器,这里的 ik_max_word 即使用ik分词器

示例

发起请求:

PUT lagou/_mapping/goods
{
    "properties": {
        "title": {
            "type": "text",
            "analyzer": "ik_max_word"
        },
        "images": {
            "type": "keyword",
            "index": "false"
        },
        "price": {
            "type": "float"
        }
    }
}

响应结果:

{
    "acknowledged": true
}

上述案例中,就给lagou这个索引库添加了一个名为 goods 的类型,并且在类型中设置了3个字段:

  • title:商品标题
  • images:商品图片
  • price:商品价格

查看映射关系

语法:

GET /索引库名/_mapping

查看某个索引库中的所有类型的映射。如果要查看某个类型映射,可以再路径后面跟上类型名称。即:

GET /索引库名/_mapping/类型名

示例:

GET /lagou/_mapping/goods

响应:

{
    "lagou": {
        "mappings": {
            "goods": {
                "properties": {
                    "images": {
                        "type": "keyword",
                        "index": false
                    },
                    "price": {
                        "type": "float"
                    },
                    "title": {
                        "type": "text",
                        "analyzer": "ik_max_word"
                    }
                }
            }
        }
    }
}

映射属性详解

type

一级分类二级分类具体类型使用
核心类型字符串类型text,keyword结构化搜索,全文文本搜索、聚合、排序等
整数类型integer,long,short,byte字段的长度越短,索引和搜索的效率越高。
浮点类型double,flfloat,half_flfloat,scaled_flfloat
逻辑类型boolean
日期类型date
范围类型range
二进制类型binary该binary类型接受二进制值作为Base64编码的字符串。该字段默认情况下不存储(store),并且不可搜索
复合类型数组类型array
对象类型object用于单个JSON对象
嵌套类型nested用于JSON对象数组
地理类型地理坐标类型geo_point纬度/经度积分
地理地图geo_shape用于多边形等复杂形状
特殊类型IP类型ip用于IPv4和IPv6地址
范围类型completion提供自动完成建议
令牌计数类型token_count计算字符串中令牌的数量

我们说几个关键的:

  • String类型,又分两种:
    • text:使用文本数据类型的字段,它们会被分词,文本字段不用于排序,很少用于聚合,如文章标题、正文。
    • keyword:关键字数据类型,用于索引结构化内容的字段,不会被分词,必须完整匹配的内容,如邮箱,身份证号。支持聚合

这两种类型都是比较常用的,但有的时候,对于一个字符串字段,我们可能希望他两种都支持,此时,可以利用其多字段特性

"properties": {
    "title":{
        "type": "text",
        "analyzer": "ik_max_word",
        "fields": {
            "sort":{
                "type": "keyword"
            }
        },
        "index": true
    }
}
  • Numerical:数值类型,分两类
    • 基本数据类型:long、interger、short、byte、double、flfloat、half_flfloat
    • double 双精度64位
    • flfloat 单精度32位
    • half_flfloat 半精度16位
    • 浮点数的高精度类型:scaled_flfloat
      • 带有缩放因子的缩放类型浮点数,依靠一个 long 数字类型通过一个固定的( double 类型)缩放因数进行缩放.
      • 需要指定一个精度因子,比如10或100。elasticsearch会把真实值乘以这个因子后存储,取出时再还原。
  • Date:日期类型
    • elasticsearch可以对日期格式化为字符串存储,但是建议我们存储为毫秒值,存储为long,节省空间。
  • Array:数组类型
    • 进行匹配时,任意一个元素满足,都认为满足
    • 排序时,如果升序则用数组中的最小值来排序,如果降序则用数组中的最大值来排序
字符串数组:["one", "two"]
整数数组:[1,2]
数组的数组:[1, [2, 3]],等价于[1,2,3]
对象数组:[ { "name": "Mary", "age": 12 }, { "name": "John", "age": 10 }]
  • Object:对象
    • JSON文档本质上是分层的:文档包含内部对象,内部对象本身还包含内部对象。
{
    "region": "US",
    "manager.age": 30,
    "manager.name ": "John Smith"
}

索引方法如下:

{
"mappings": {
    "properties": {
        "region": { "type": "keyword" },
        "manager": {
            "properties": {
                    "age": { "type": "integer" },
                    "name": { "type": "text" }
                }
            }
        }
    }
}

如果存储到索引库的是对象类型,例如上面的girl,会把girl编程两个字段:girl.name和girl.age

  • ip地址
PUT my_index
{
    "mappings": {
        "_doc": {
            "properties": {
                "ip_addr": {
                    "type": "ip"
                }
            }
        }
    }
}

PUT my_index/_doc/1
{
    "ip_addr": "192.168.1.1"
}

GET my_index/_search
{
    "query": {
        "term": {
            "ip_addr": "192.168.0.0/16"
        }
    }
}

index

index影响字段的索引情况。

  • true:字段会被索引,则可以用来进行搜索过滤。默认值就是true,只有当某一个字段的index值设置为true时,检索ES才可以作为条件去检索。
  • false:字段不会被索引,不能用来搜索

index的默认值就是true,也就是说你不进行任何配置,所有字段都会被索引。

但是有些字段是我们不希望被索引的,比如商品的图片信息(URL),就需要手动设置index为false。

store

是否将数据进行额外存储。

在学习lucene时,我们知道如果一个字段的store设置为false,那么在文档列表中就不会有这个字段的值,用户的搜索结果中不会显示出来。

但是在Elasticsearch中,即便store设置为false,也可以搜索到结果。

原因是Elasticsearch在创建文档索引时,会将文档中的原始数据备份,保存到一个叫做 _source 的属性中。而且我们可以通过过滤 _source 来选择哪些要显示,哪些不显示。

而如果设置store为true,就会在 _source 以外额外存储一份数据,多余,因此一般我们都会将store设置为false,事实上,store的默认值就是false。

在某些情况下,这对 store 某个领域可能是有意义的。例如,如果您的文档包含一个 title ,一个date 和一个非常大的 content 字段,则可能只想检索the title 和the date 而不必从一个大 _source

字段中提取这些字段:

PUT my_index
{
    "mappings": {
        "_doc": {
            "properties": {
                "title": {
                    "type": "text",
                    "store": true
                },
                "date": {
                    "type": "date",
                    "store": true
                },
                "content": {
                    "type": "text"
                }
            }
        }
    }
}

boost

网站权重:网站权重是指搜索引擎给网站(包括网页)赋予一定的权威值,对网站(含网页)权威的评估评价。一个网站权重越高,在搜索引擎所占的份量越大,在搜索引擎排名就越好。提高网站权重,不但利于网站(包括网页)在搜索引擎的排名更靠前,还能提高整站的流量,提高网站信任度。所以提高网站的权重具有相当重要的意义。 权重即网站在SEO中的重要性,权威性。英文:Page Strength。1、权重不等于排名 2、权重对排名有着非常大的影响 3、整站权重的提高有利于内页的排名。

权重,新增数据时,可以指定该数据的权重,权重越高,得分越高,排名越靠前。

PUT my_index
{
    "mappings": {
        "_doc": {
            "properties": {
                "title": {
                    "type": "text",
                    "boost": 2
                },
                "content": {
                    "type": "text"
                }
            }
        }
    }
}

title字段上的匹配项的权重是字段上的匹配项的权重的两倍content,默认boost值为1.0 。

提升仅适用于Term查询(不提升prefifix,range和模糊查询)。

一次创建索引库和类型

第一步:
PUT /lagou

第二步:
PUT lagou/_mapping/goods
{
    "properties": {
        "title": {
            "type": "text",
            "analyzer": "ik_max_word"
        },
        "images": {
            "type": "keyword",
            "index": "false"
        },
        "price": {
            "type": "float"
        }
    }
}

刚才的案例中我们是把创建索引库和类型分开来做,其实也可以在创建索引库的同时,直接制定索引库中的类型,基本语法:

put /索引库名
{
    "settings":{
        "索引库属性名":"索引库属性值"
    },
    "mappings":{
        "类型名":{
            "properties":{
                "字段名":{
                    "映射属性名":"映射属性值"
                }
            }
        }
    }
}

来试一下吧:

PUT /lagou2
{
    "settings": {},
    "mappings": {
        "goods": {
            "properties": {
                "title": {
                    "type": "text",
                    "analyzer": "ik_max_word"
                }
            }
        }
    }
}

结果:

{
    "acknowledged": true,
    "shards_acknowledged": true,
    "index": "lagou2"
}