文档章节

Elasticsearch 快速上手

Yeamo
 Yeamo
发布于 2016/12/08 15:28
字数 1498
阅读 74
收藏 3

本文目的是为了让不了解ES的人尽快的上手使用

一、ES的定义

ES(ElasticSearch)是一个基于Lucene的分布式搜索引擎,支持存储,但不是一个可靠的存储引擎,有丢数据风险。

至于为什么会丢数据,此处不作展开,有兴趣的请移步http://www.hansight.com/blog-elasticsearch-data-loss-scenarios.html

二、ES初识

为了方便大家快速理解,这里我们用mysql来跟ES的一些基本概念做下对比。

  • index > 对应一个mysql库
  • type > 对应一个mysql表
  • document > 对应表里的一条
  • mapping > 对应建库建表语句

既然是跟mysql类比,增删改查自然是少不了,首先我们要有个表,下面这个mapping就是我们的建表语句

{
  "pop_ware": {// 索引:数据库
    "settings": {
      "index": {
        "number_of_shards": "32", // 分片:类似数据库分表
        "number_of_replicas": "2" // 副本:类似于从库
      }
    },
    "mappings": {
      "ware": {// 类似于table
        "_all": {
          "enabled": false
        },
        "_source": {
          "enabled": true
        },
        "_routing": {
          "required": true
        },
        "dynamic": false,
        "properties": {
          "wareId": {
            "type": "long"
          }
          "title": {
            "type": "string",
            "analyzer": "ik"
          },
          "shopName": {
            "type": "string",
            "analyzer": "mmseg_maxword"
          },
          "itemNum": {
            "type": "string",
            "index": "not_analyzed"
          },
          "onlineTime": {
            "type": "date"
          }
        }
      }
    }
  }
}

ES中建表不需要考虑字段长度、约束等一些东西,对它来说,只需要知道字段类型就好。
以下是mapping 的Field datatype

注:已经存在的字段不能被更新和删除

Analyzer

解析是搜索类中间件区别于传统关系型数据库的一项重要能力。简单的说,它会对你输入的查询条件进行解析、拆分、转换、等一系列动作后再去查询,在存储的时候也是这样。

举个例子:

我要查名称是“飞利浦的剃须刀”的商品

上图是指定了IK分词器后,查询条件被分解为多组词,然后ES会根据这些解析后的词进行查询匹配,并按找关联度打分,然后返回排序后的匹配结果。

 

增删改查

ES的API支持http和客户端两种形式,这里我们使用http的方式进行演示。

新增

PUT 'http://localhost:9200/popware/ware/123'
{
    "shopCategoryId": [
      3213,
      65465
    ],
    "title": "飞利浦剃须刀",
    "wareId": 123456789
  }

上面代码新增了一条id为123的商品数据,即一个document。

http请求中,popware是index即mysql中数据库,ware是type即mysql中的表,123可以暂时理解为主键,不能重复,但是又和数据库不一样,ES是以id:document的文件形式存储的,所以当key一样的时候,之前的数据会被覆盖。

查询

GET 'http://localhost:9200/twitter/tweet/123'
{
  "found": true,
  "_index": "pop_ware",
  "_type": "ware",
  "_source": {
    "shopCategoryId": [
      3213,
      65465
    ],
    "title": "飞利浦剃须刀",
    "wareId": 123456789
  },
  "_id": "123",
  "_version": 42
}

上面这一段意思是查询ID为123的商品,http请求的格式跟新增一样,区别是吧put换乘了get。

 

修改

POST 'http://localhost:9200/popware/ware/123/_update'
{"doc":{
    "title": "飞利浦剃须刀"
  }
}

上面的请求意思是更为商品的title字段,可以把它看成是先删除再索引的原子操作,只是省略了返回的过程,这样即减少网络成本

 

删除

DELETE 'http://localhost:9200/popware/ware/123'


三、ES查询

既然是一款搜索引擎,必然有很强大查询功能,下面我们就来简单了解下ES查询相关功能

先混个脸熟,看看这些查询中相关的名词

SearchQueryFilterMatch QueryTerm QueryRange QueryBool QueryFiltered Query

  • search
{
    "_source": false,
    "sort" : [
        { "age" : "desc" }
    ],
    "from" : 0, "size" : 10,
    "query" : {
        "term" : { "user" : "kimchy" }
    }
}

搜索相对于query是一个更大的概念,一次搜索主要包含这么几个定义:分页条件、排序、查询。

可以理解为一个select,而query就是where后面那一部分用来筛选的条件。

 

  • query VS filter
{
  "query": { 
    "bool": { 
      "must": [
        { "match": { "title":   "Search"}}, 
      ],
      "filter": [ 
        { "term":  { "status": "published" }}, 
      ]
    }
  }
}

query这个名词在ES中有两层意思:

1、它表示search中的一个查询

2、它表示query上下文,用于区别filter上下文,不在filter内的查询,它就是默认的query上下文。

query默认上下文会对查询的结果进行打分,以影响默认的返回顺序

“这个文档跟查询语句有多匹配?”

filter上下文不会对结果打分

“这个文档跟结果是否匹配?”

谁跑的快?当然filter,并且filter结果会被缓存

  • match VS term

match 一般应用于 query 上下文中,查询的字段一般都是指定分析器(IK,MSEG)的string 类型,

term  精准匹配,适用于除指定了分析器之外的类型

{    
    "term": {
        "status": {
            "value": "A",
            "boost": 2.0 
        }
    }
}

上面这句话的意思是:如果status等于A,权重翻倍

下面是一个terms查询,可以传一个集合,上面说了,ES中每一个字段都可以作为数组来使用,设置多个值,查询也是一样,可以传递多个值

{    
    "terms": {
        "status": [2,3,520]
    }
}
  • range
{
    "range" : {
        "born" : {
            "gte": "01/01/2012",
            "lte": "2013",
            "format": "dd/MM/yyyy||yyyy"
        }
    }
}
  • boolquery  VS filteredquery

    boolquery

组合查询的一种,关键字包含以下四种:

  1. must:必须有  and
  2. filter:必须有  and  不打分   性能好
  3. should:应该有 or
  4. must_not:必须没有  not in  <>

 

    filterdquery

在2.0之前  boolquery是不支持filter的,想用filter只能是以下这种方式:

{
  "filtered": {
    "query": {
      "match": { "tweet": "full text search" }
    },
    "filter": {
      "range": { "created": { "gte": "now-1d/d" }}
    }
  }
}

 


以上就是常用的一些查询功能的用法,公司有ES云服务提供,不需要我们自己搭建,大家可以拿公司的测试环境练练手。

在使用的时候,需要注意查询条件的顺序,尽可能的将匹配结果集少的条件前置,以获取更好的性能。

ES FAQ上有很多干货,建议大家使用前可以通读一遍。

 

 

© 著作权归作者所有

共有 人打赏支持
上一篇: 关系型redis应用
下一篇: 关系型redis应用
Yeamo
粉丝 0
博文 2
码字总数 6132
作品 0
东城
程序员
私信 提问
快速上手 Elasticsearch 的几个建议

相信不少同学都听说过 Elasticsearch,作为目前最流行的搜索引擎实现方案,越来越多的公司在自己的架构中引入,而其应用场景也从搜索引擎扩展到了日志存储分析、大数据分析领域,本文尝试给初...

rockybean
05/21
0
0
CentOS7 上搭建多节点 Elasticsearch集群

本文内容脑图如下: 文章共 747字,阅读大约需要 2分钟 ! --- 概 述 最近学 Elasticsearch,既然学之,怎么能没有实际的集群来把玩呢,因此自己必须动手搭一个! 注: 本文首发于 My Perso...

CodeSheep
11/06
0
0
渣渣菜鸡为什么要看 ElasticSearch 源码?

前提 人工智能、大数据快速发展的今天,对于 TB 甚至 PB 级大数据的快速检索已然成为刚需,大型企业早已淹没在系统生成的浩瀚数据流当中。大数据技术业已集中在如何存储和处理这些海量的数据...

Java小铺
08/10
0
0
分布式作业 Elastic Job 如何动态调整?

前面分享了两篇分布式作业调度框架 Elastic Job 的介绍及应用实战。 ElasticJob-分布式作业调度神器 分布式作业 Elastic Job 快速上手指南! Elastic Job 提供了简单易用的运维平台,方便用...

Java技术栈
08/24
0
0
当Elasticsearch遇见Kafka

欢迎大家前往腾讯云+社区,获取更多腾讯海量技术实践干货哦~ 本文由michelmu发表于云+社区专栏 Elasticsearch作为当前主流的全文检索引擎,除了强大的全文检索能力和高扩展性之外,对多种数据...

腾讯云加社区
11/12
0
0

没有更多内容

加载失败,请刷新页面

加载更多

apache顶级项目(二) - B~C

apache顶级项目(二) - B~C https://www.apache.org/ Bahir Apache Bahir provides extensions to multiple distributed analytic platforms, extending their reach with a diversity of s......

晨猫
今天
3
0
day152-2018-11-19-英语流利阅读

“超级食物”竟然是营销噱头? Daniel 2018-11-19 1.今日导读 近几年来,超级食物 superfoods 开始逐渐走红。不难发现,越来越多的轻食餐厅也在不断推出以超级食物为主打食材的健康料理,像是...

飞鱼说编程
今天
9
0
SpringBoot源码:启动过程分析(二)

接着上篇继续分析 SpringBoot 的启动过程。 SpringBoot的版本为:2.1.0 release,最新版本。 一.时序图 一样的,我们先把时序图贴上来,方便理解: 二.源码分析 回顾一下,前面我们分析到了下...

Jacktanger
昨天
3
0
Apache防盗链配置,Directory访问控制,FilesMatch进行访问控制

防盗链配置 通过限制referer来实现防盗链的功能 配置前,使用curl -e 指定referer [root@test-a test-webroot]# curl -e "http://www.test.com/1.html" -x127.0.0.1:80 "www.test.com/1.jpg......

野雪球
昨天
6
0
RxJava threading

因为Rx针对异步系统设计,并且Rx也自然支持多线程,所以新的Rx开发人员有时会假设Rx默认是多线程的。在其他任何事情之前,重要的是澄清Rx默认是单线程的。 除非另有说明,否则每次调用onNex...

woshixin
昨天
2
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部