elasticsearch安装教程
elasticsearch7.0+基本概念
文档
Elasticsearch是面向文档的,文档是所有可搜索数据的最小单元(json格式)。就拿mysql作为比较,文档就是一条数据。
索引(_index)
索引是具有某种相似特性的文档集合。索引由一个名称(必须全部是小写)标识。在单个集群中,您可以定义任意多个索引。Index体现了逻辑空间的概念,每个索引都有自己的mapping定义,用于定义包含文档的字段名和字段类型。Index体现了物理空间的概念,索引中的数据分散在shard(分片)上。可以将其暂时理解为 MySql中的 database。
1.mapping:定义文档字段的类型
2.setting:定义不同数据的分布
类型
从6.0开始,type已经被逐渐废弃。在7.0之前,一个index可以设置多个types。7.0开始一个索引只能创建一个type(_doc)
节点
节点是一个Elasticsearch实例,本质上就是一个java进程,节点也有一个名称(默认是随机分配的),当然也可以通过配置文件配置,或者在启动的时候,-E node.name=node1指定。此名称对于管理目的很重要,因为您希望确定网络中的哪些服务器对应于ElasticSearch集群中的哪些节点。
在Elasticsearch中,节点的类型主要分为如下几种:
master eligible(主节点):
每个节点启动后,默认就是master eligible节点,可以通过node.master: false 禁止
master eligible可以参加选主流程,成为master节点
当第一个节点启动后,它会将自己选为master节点
每个节点都保存了集群的状态,只有master节点才能修改集群的状态信息
data(数据节点):
可以保存数据的节点。负责保存分片数据,在数据扩展上起到了至关重要的作用
Coordinating (代理节点/客户端节点):
负责接收客户端请求,将请求发送到合适的节点,最终把结果汇集到一起
每个节点默认都起到了Coordinating node的职责
开发环境中一个节点可以承担多个角色,生产环境中,建议设置单一的角色,可以提高性能等
分片(shard)
es默认就是集群,存在多台时,自动分片。
主分片数在索引创建时指定(“number_of_shards”: “a”),后续不允许修改,除非Reindex
分片副本
故障转移机制
“number_of_replicas”: “0”
默认情况下,ElasticSearch中的每个索引都分配一个主分片和一个副本,这意味着如果集群中至少有两个节点,则索引将有一个主分片和另一个副本分片(一个完整副本),每个索引总共有两个分片。
总分片数=主分片数*(副分片数+1)
分配规则:
1.分片与该分片的副分片不在同一个节点
2.相同副本分配不能分配在一个节点
安装教程
es下载地址
bin目录下 ./elasticsearch 启动,会报错
org.elasticsearch.bootstrap.StartupException: java.lang.RuntimeException: can not run elasticsearch as root
在6.xx之前,可以通过root用户启动。但是发现黑客可以透过elasticsearch获取root用户密码,所以为了安全性,在6版本之后就不能通过root启动elasticsearch。当然你页需要修改一些文件的权限,不然无法访问。
创建组员:
groupadd xxx
useradd xxx -g xxx
切换到 xxx上再次启动
如果仅仅是本机测试,则es默认是开发模式,可成功启动。
如果修改配置文件 elasticsearch.yml 的 network.host 可能会报:
max virtual memory areas vm.max_map_count [65530] is too low, increase to at least [262144]
vm最大虚拟内存,max_map_count[65530]太低,至少增加到[262144]
解决方式:
vim /etc/sysctl.conf
vm.max_map_count=262144
sysctl -p 使配置生效
descriptors [4096] for elasticsearch process likely too low, increase to at least [65536]
最大文件描述符[4096]对于elasticsearch进程可能太低,至少增加到[65536]
解决方式:
vim /etc/security/limits.conf
*soft nofile 65536
一般来说不会遇到这些问题,如果是自己装的vm可能会有,用的云服务器一般都设置好了。
访问9200 端口,出现下面说明启动成功了
配置文件
配置说明
cluster.name: 集群名称
node.name:节点名称(命令配置)
node.master: true 是否可以竞选主节点 默认true
node.data: true 是否是数据节点 默认true
network.host: 0.0.0.0 (命令配置)
http.port: 9202 http通讯端口(命令配置)
transport.port: 9302 集群间通信端口(命令配置)
cluster.initial_master_nodes: [“node‐1”] 集群节点名称
discovery.seed_hosts: [“xxx.xxx.xxx.xxx:9300”, “xxx.xxx.xxx.xxx:9301”,“xxx.xxx.xxx.xxx:9302”] 用于集群启动时发现节点
discovery.zen.minimum_master_nodes: 2 防止脑裂 选举
http.cors.enabled: true 解决跨域问题配置
http.cors.allow‐origin: “*” 解决跨域问题配置
集群搭建
跨云集群配置:
network.host: 配置内网ip
network.publish_host: 配置公网ip
discovery.seed_hosts:配置公网ip
插件
Elasticsearch-head
集群信息可视化界面
翻墙,直接谷歌插件下载
cerebro
可是一款可视化界面,比head好用
个人感觉比较好用,阿里云推荐的,解压即用
git下载地址
kibana
vim kibana.yml
将自己es的域名配置上去
elasticsearch.hosts: [“http://xxx.xxx.xxx.xxx:9200”]
如果对英文不习惯的同学可以
i18n.locale: “zh-CN” 变成中文
kibana 不支持后台启动
./kibana --allow-root
nohup ./kibana --allow-root & 后台启动
全文检索
es内置分词器 | |
---|---|
Standard | 默认分词器 按词分类 小写处理 |
Simple | 按照非字母切分,非字母则会被去除 小写处理 |
Stop | 小写处理 停用词过滤(the,a, is) |
Whitespace | 按空格切分 |
Keyword | 不分词,当成一整个 term 输出 |
Patter | 通过正则表达式进行分词 默认是 \W+(非字母进行分隔) |
Language | 提供了 30 多种常见语言的分词器 |
中文分词ik
解压后放在es的plugins 目录下,重启es就可以了,注意点:ik的权限也是root,需要重新分配权限
ElasticStack日志收集
我使用的是filebeat + logstash
filebeat
收集工具,也可以直接存数据到es中
新建xxx.yml
filebeat.inputs:
-type: log
enabled: true
paths:
-/xxx/logs/*.log
output.logstash:
hosts: [“xxx.xxx.xxx.xxx:5044”] 这里配置的是logstash服务地址
启动 ./filebeat -e -c 配置文件名 -e输出到标准输出,默认输出到syslog和logs下 -c 指定配置文件
logstash
可以对filebeat收集的日志进一步优化,添加字段等,在存到es中
新建xxx.yml
input {
beats {
port => “5044”
}
}
filter {
mutate {
split => {“message”=>","}
}
}
output {
elasticsearch {
hosts => [ “xxx.xxx.xxx.xxx:9200”]
}
}
在filter里面也可以添加字段
mutate {
add_field => {
“字段名字” => “%{[message][0]}” ----上面对message进行的了切分
}
}
上面都是一些基本配置,没有过多的深入研究
启动: ./logstash -f 配置文件名
启动方式的话需要先启动logstash 再启动 filebeat
mysql数据导入elasticsearch
logstash
配置文件:
input {
jdbc {
jdbc_driver_library => "/opt/mysql-connector-java-5.1.47.jar"
jdbc_driver_class => "com.mysql.jdbc.Driver"
jdbc_connection_string => "jdbc:mysql://****:3306/****?serverTimezone=UTC&useSSL=false"
jdbc_user => "****"
jdbc_password => "****"
schedule => "* * * * *"
clean_run => true
jdbc_default_timezone => "Asia/Shanghai"
statement =>"select id,content,DATE_FORMAT(update_time,'%Y-%m-%d %T') as update_time,DATE_FORMAT(create_time,'%Y-%m-%d %T') as create_time from goods where create_time>:sql_last_value and create_time<NOW() order by update_time desc"
}
}
#下面filter里面主要是用来解决es@timestamp 时间问题,es默认中时区,中国算是东八区。
filter {
ruby {
code => "event.set('timestamp', event.get('@timestamp').time.localtime + 8*60*60)"
}
ruby {
code => "event.set('@timestamp',event.get('timestamp'))"
}
mutate {
remove_field => ["timestamp"]
}
}
output {
elasticsearch{
hosts => ["es所在服务器地址"]
index => "es上的索引"
document_id => "%{id}"
}
}
然后启动logstash
es中显示如下:
注:可能遇到的问题。
1.mysql连接不上,需要开发mysql权限。
2.javax.net.ssl.SSLException: closing inbound before receiving peer’s close_notify
这个需要在 jdbc_connection_string 配置里面加上 &useSSL=false