elasticsearch 入门学习

阅读数:87 评论数:0

跳转到新版页面

分类

应用软件

正文

一、基本概念

Elasticsearch是面向文档型数据库,一条数据在这里就是一个文档,比如下面这条用户数据:

{
    "name" :     "John",
    "sex" :      "Male",
    "age" :      25,
    "birthDate": "1990/05/01",
    "about" :    "I love to go rock climbing",
    "interests": [ "sports", "music" ]
}

关系数据库     ⇒ 数据库 ⇒ 表    ⇒ 行    ⇒ 列(Columns)

Elasticsearch  ⇒ 索引(Index)   ⇒ 类型(type)  ⇒ 文档(Docments)  ⇒ 字段(Fields)  

Elasticsearch集群可以包含多个索引(indices)(数据库),每一个索引可以包含多个类型(types)(表),每一个类型包含多个文档(documents)(行),然后每个文档包含多个字段(Fields)(列)。

1、索引

一个索引就像关系数据库中的数据库,它是相关文档存储的地方。

2、倒排索引

传统数据库为特定列增加一个索引,例如B-Tree索引来加速检索。es和lucene使用一种叫做inverted index的数据结构来达到相同目的。

 

Elasticsearch的交互,可以使用Java API,也可以直接使用HTTP的Restful API方式。比如我们打算插入一条记录,可以简单发送一个HTTP的请求:

PUT /megacorp/employee/1  
{
    "name" :     "John",
    "sex" :      "Male",
    "age" :      25,
    "about" :    "I love to go rock climbing",
    "interests": [ "sports", "music" ]
}

一个elasticsearch索引的主要结构如下:

{
    "test_index": {
        "aliases": {},
        "mappings": {
            "my_type": {
                "properties": {
                    "name": {
                        "type": "text",
                        "fields": {
                            "keyword": {
                                "type": "keyword",
                                "ignore_above": 256
                            }
                        }
                    }
                }
            }
        },
        "settings": {
            "index": {
                "creation_date": "1601371474234",
                "number_of_shards": "5",
                "number_of_replicas": "1",
                "uuid": "Xov1AxZ9R5aV2Ji4ZP5YjA",
                "version": {
                    "created": "6020299"
                },
                "provided_name": "test_index"
            }
        }
    }
}

二、数据类型

1、核心类型

(1)字符串类型

text和keyword

text类型用于需要被全文检索的字段,例如新闻正文、邮件内容等比较长的文字,text类型会被Lucenne分词器(Analyzer)处理为一个个词项,并使用Lucene倒排索引存储,不能用于排序。

keyword适合简短、结构化字符串,可以用于过滤、排序、聚合检索,也可以用于精确查询。

(2)数字类型

long、integer、short、byte、double、float、half_float、scaled_float

数字类型的字段在满足需求的前提下应当尽量选择范围较小的数据类型,字段长度越短,搜索效率越高,对于浮点数,可以优先考虑使用 scaled_float 类型,该类型可以通过缩放因子来精确浮点数,例如 12.34 可以转换为 1234 来存储。

(3)日期类型(date、date_nanos)

在 ES 中日期可以为以下形式:

格式化的日期字符串,例如 2020-03-17 00:00、2020/03/17

时间戳(和 1970-01-01 00:00:00 UTC 的差值),单位毫秒或者秒

即使是格式化的日期字符串,ES 底层依然采用的是时间戳的形式存储。

(4)布尔类型(boolean)

JSON 文档中同样存在布尔类型,不过 JSON 字符串类型也可以被 ES 转换为布尔类型存储,前提是字符串的取值为 true 或者 false,布尔类型常用于检索中的过滤条件

(5)二进制类型

二进制类型binary接受base64编码的字符串,默认store属性为false,并且不可以被搜索。

(6)范围类型

integer_range、float_range、long_range、double_range 以及 date_range。

2、复杂类型

(1)对象类型

JSON 字符串允许嵌套对象,一个文档可以嵌套多个、多层对象。可以通过对象类型来存储二级文档,不过由于 Lucene 并没有内部对象的概念,ES 会将原 JSON 文档扁平化,例如文档:

{
  “name”:{
     "first": "cui",
     "last": "hs", 
  }
}

实际上 ES 会将其转换为以下格式,并通过 Lucene 存储,即使 name 是 object 类型:

{
  "name.first": "cui",
  "name.last": "hs",
}

(2)嵌套类型

嵌套类型可以看成是一个特殊的对象类型,可以让对象数组独立检索,例如文档:

{
  “group”: "users",
  "username": [
     {"first":"cui"},
     {"first":"li"},
  ]
}

嵌套类型将数组中的每个 JSON 对象作为独立的隐藏文档来存储,每个嵌套的对象都能够独立地被搜索,所以上述案例中虽然表面上只有 1 个文档,但实际上是存储了 3个文档。

3、地理类型

(1)经纬度类型

经纬度类型字段(geo_point)可以存储经纬度相关信息,通过地理类型的字段,可以用来实现诸如查找在指定地理区域内相关的文档、根据距离排序、根据地理位置修改评分规则等需求。

(2)地理区域类型

经纬度类型可以表达一个点,而 geo_shape 类型可以表达一块地理区域,区域的形状可以是任意多边形,也可以是点、线、面、多点、多线、多面等几何类型。

4、特殊类型

(1)IP类型

IP 类型的字段可以用来存储 IPv4 或者 IPv6 地址,如果需要存储 IP 类型的字段,需要手动定义映射.

(2)Join类型

用来实现文档的一对一、一对多的关系,主要用来做父子查询。

PUT my_index 
{
  "mappings": {
    "properties": {
       "my_join_field": {
          "type": "join"
          "relations": {
            "question": "answer"
          }
        }
     }
   }
}

relations指定关系:question是answer的父类。

 

三、Mapping

Mapping类似关系数据库的schema,主要包括以下内容:

1、定义索引中字段的名称

2、定义字段的数据类型,如:字符串、数字、boolean等

3、可以对字段设置倒排索引的相关配置,如是否需要分词,使用什么分词器。

  "mappings": {       #mappings关键字
            "my_type": {     #类型名称
                "properties": {   #字段名称和类型的定义
                    "name": {  #字段名
                        "type": "text",   #字段类型
                        "fields": {
                            "keyword": {
                                "type": "keyword",
                                "ignore_above": 256
                            }
                        }
                    }
                }
            }
        }

一个Mapping只属于一个索引的type,默认type为_doc。

因为动态映射的类型和分词器不一定符合你的要求,有时仍需要指定自己的显示映射。

4、在创建索引时可以指定一个mapping映射。

{
  "mappings": {
    "_doc": {          #添加名为_doc的映射类型
      "properties": {       #指定字段或属性
        "title":    { "type": "text"  },      #指定title字段的类型为text
        "name":     { "type": "text"  }, 
        "age":      { "type": "integer" },  
        "created":  {
          "type":   "date", 
          "format": "strict_date_optional_time||epoch_millis"
        }
      }
    }
  }
}

5、也可以使用put mapping api将字段添加到现有索引中

PUT /my_index/_mapping/my_type
{
        "properties": {
            "english_title": {
                "type":     "text",
                "analyzer": "english"
            }
        }    
}

注:已存在的字段,一旦数据被写入,就不再支持修改字段定义,我们修改已存在的字段属性,是通过Reindex api,即重建索引来实现的,在数据较多的时候,开销较大

6、映射参数

"field": {  
         "type":  "text", //文本类型  ,指定类型
       
         "index": "false"// ,设置成false,字段将不会被索引  
         
         "analyzer":"ik"//指定分词器  
         
         "boost":1.23//字段级别的分数加权  
         
         "doc_values":false//对not_analyzed字段,默认都是开启,analyzed字段不能使用,对排序和聚合能提升较大性能,节约内存,如果您确定不需要对字段进行排序或聚合,或者从script访问字段值,则可以禁用doc值以节省磁盘空间:
         
         "fielddata":{"loading" : "eager" }//Elasticsearch 加载内存 fielddata 的默认行为是 延迟 加载 。 当 Elasticsearch 第一次查询某个字段时,它将会完整加载这个字段所有 Segment 中的倒排索引到内存中,以便于以后的查询能够获取更好的性能。
         
         "fields":{"keyword": {"type": "keyword","ignore_above": 256}} //可以对一个字段提供多种索引模式,同一个字段的值,一个分词,一个不分词  
         
         "ignore_above":100 //超过100个字符的文本,将会被忽略,不被索引
           
         "include_in_all":ture//设置是否此字段包含在_all字段中,默认是true,除非index设置成no选项  
         
         "index_options":"docs"//4个可选参数docs(索引文档号) ,freqs(文档号+词频),positions(文档号+词频+位置,通常用来距离查询),offsets(文档号+词频+位置+偏移量,通常被使用在高亮字段)分词字段默认是position,其他的默认是docs  
         
         "norms":{"enable":true,"loading":"lazy"}//分词字段默认配置,不分词字段:默认{"enable":false},存储长度因子和索引时boost,建议对需要参与评分字段使用 ,会额外增加内存消耗量  
         
         "null_value":"NULL"//设置一些缺失字段的初始化值,只有string可以使用,分词字段的null值也会被分词  
         
         "position_increament_gap":0//影响距离查询或近似查询,可以设置在多值字段的数据上火分词字段上,查询时可指定slop间隔,默认值是100  
         
         "store":false//是否单独设置此字段的是否存储而从_source字段中分离,默认是false,只能搜索,不能获取值  
         
         "search_analyzer":"ik"//设置搜索时的分词器,默认跟ananlyzer是一致的,比如index时用standard+ngram,搜索时用standard用来完成自动提示功能  
         
         "similarity":"BM25"//默认是TF/IDF算法,指定一个字段评分策略,仅仅对字符串型和分词类型有效  
         
         "term_vector":"no"//默认不存储向量信息,支持参数yes(term存储),with_positions(term+位置),with_offsets(term+偏移量),with_positions_offsets(term+位置+偏移量) 对快速高亮fast vector highlighter能提升性能,但开启又会加大索引体积,不适合大数据量用  
       }  

 

四、Setting

setting为ES索引的配置属性,索引的配置项按是否可以更改分为静态(static)属性与动态配置,所谓的静态配置即索引创建后不能修改,静态配置只能在创建索引时或者在状态为 closed index的索引(闭合的索引)上设置

1、索引静态配置

index.number_of_shards :主分片数,默认为5.只能在创建索引时设置,不能修改

index.shard.check_on_startup :是否在索引打开前检查分片是否损坏,当检查到分片损坏将禁止分片被打开
可选值:false:不检测;checksum:只检查物理结构;true:检查物理和逻辑损坏,相对比较耗CPU;fix:类同与false,7.0版本后将废弃。默认值:false。

index.codec:数据存储的压缩算法,默认算法为LZ4,也可以设置成best_compression,best_compression压缩比较好,但存储性能比LZ4差

index.routing_partition_size :路由分区数,默认为 1,只能在索引创建时设置。此值必须小于index.number_of_shards,如果设置了该参数,其路由算法为: (hash(_routing) + hash(_id) % index.routing_parttion_size ) % number_of_shards。如果该值不设置,则路由算法为 hash(_routing) % number_of_shardings,_routing默认值为_id。

2、索引动态配置

index.number_of_replicas :每个主分片的副本数,默认为 1,该值必须大于等于0

index.auto_expand_replicas :基于可用节点的数量自动分配副本数量,默认为 false(即禁用此功能)

index.refresh_interval :执行刷新操作的频率,这使得索引的最近更改可以被搜索。默认为 1s。可以设置为 -1 以禁用刷新。
 
index.max_result_window :用于索引搜索的 from+size 的最大值。默认为 10000
 
index.max_rescore_window : 在搜索此索引中 rescore 的 window_size 的最大值
 
index.blocks.read_only :设置为 true 使索引和索引元数据为只读,false 为允许写入和元数据更改。

index.blocks.read_only_allow_delete:与index.blocks.read_only基本类似,唯一的区别是允许删除动作。
 
index.blocks.read :设置为 true 可禁用对索引的读取操作
 
index.blocks.write :设置为 true 可禁用对索引的写入操作。
 
index.blocks.metadata :设置为 true 可禁用索引元数据的读取和写入。
 
index.max_refresh_listeners :索引的每个分片上可用的最大刷新侦听器数

index.max_docvalue_fields_search:一次查询最多包含开启doc_values字段的个数,默认为100。

3、配置

(1)可以在创建索引时就进行settings配置

PUT /test_setting

{
  
    "settings": {
        "number_of_shards": "3",
        "number_of_replicas": "1"     
    }
    
    
}

对于已存在的索引,我们想要修改它的动态配置,可以使用_settings方法

PUT  /test_setting/_settings

{
    
    "number_of_replicas": "0"           
    
}

 




相关推荐