本文主要介绍logstash工具,将Mysql数据同步到Elasticsearch。
1、下载地址:
https://artifacts.elastic.co/downloads/logstash/logstash-6.0.0.zip
2、在logstash目录下创建config-mysql
3、先上配置文件内容
input {
jdbc {
#jdbc_driver_library => "./config/mysql-connector-java-8.0.29.jar"
jdbc_driver_library => "D:/logstash-6.0.0/config/mysql-connector-java-8.0.29.jar"
jdbc_driver_class => "com.mysql.jdbc.Driver"
# 数据库相关配置
jdbc_connection_string => "jdbc:mysql://IP:3306/order?characterEncoding=UTF-8&useSSL=false"
jdbc_user => "root"
jdbc_password => "******"
# 定时执行的SQL语句,Logstash会根据schedule配置,定时执行这里的SQL语句
# 将SQL语句查询的结果,传给output插件
statement => "SELECT * FROM TEMP_MAIN limit 0,1000"
jdbc_paging_enabled => "true"
jdbc_page_size => "1000"
# 定时任务配置,下面表示每分钟执行一次SQL
# 具体语法请参考下一个章节内容
schedule => "* * * * *"
type => "TEMP_MAIN"
}
}
filter {
json {
source => "message"
remove_field => ["message"]
}
}
output {
stdout {
codec => json_lines
}
#读取input里的type
if[type] == "TEMP_MAIN"{
elasticsearch {
hosts => ["IP:9200"]
user => elastic
password => "test123"
#将mysql数据加入myindex索引(数据库)下,会自动创建
index => "order"
document_type => "TEMP_MAIN"
#需写入唯一ID,对应表的字段m_id
document_id => "%{m_id}"
}
}
}
定时任务配置
jdbc schedule的配置规则,类似linux的crontab的写法,具体语法规则如下:
语法格式,总共由5个字段组成,含义如下:
* * * * * 分 时 天 月 星期
各个字段取值范围:
-
分 - 0-59
-
时 - 0-23
-
天 - 1-31
-
月 - 1-12
-
星期 - 0-7
特殊字符含义:
-
星号() :代表所有值,例如:第一个字段是星号(),则代表每分钟。
-
逗号(,):指定一个数值范围,例如:1,2,3,4
-
横杠(-):另外一种表示一个整数范围的方法,例如:1-4 表示1,2,3,4
-
斜线(/):可以用斜线指定时间的间隔频率,例如:*/5,如果用在分钟字段,表示每5分钟执行一次。
例子:
# 每分钟执行一次 * * * * * # 每10分钟执行一次 */10 * * * * # 每小时执行一次 * */1 * * * # 每天0点执行一次 0 0 * * * # 每天凌晨2点1分执行一次 1 2 * * *
4、window下,在logstash目录下,cmd运行
D:\logstash\logstash.bat -f ../config/logstash-mysql.conf
如果要停止该文件运行,可以直接kill掉进程,进程号会在执行上面的命令时打印出来
可以看到logs目录下生成logstash.out
打开logstash.out会看到同步到es的相关数据
打开http://localhost:9200/_plugin/head/,可以看到数据已经同步到es中了
5、增量同步配置:
同步数据的SQL语句,直接扫描全表的数据,如果数据量比较小,问题不大,如果数据量比较大,会直接卡死,logstash OOM挂了,因此需要实现增量同步,每次仅同步新增的数据。
Logstash提供了sql_last_value字段值,帮助我们实现增量同步;增量同步的核心思路就是,logstash每次执行SQL的时候,会将SQL查询结果的最后一条记录的某个值保存到sql_last_value字段中,下一次执行SQL的时候,以sql_last_value值作为参考,从这个值往后查询新数据。
例子:
input {
jdbc {
# 注意where条件id > :sql_last_value
# 每次执行SQL的时候,id大于sql_last_value的值
statement => "SELECT id, mycolumn1, mycolumn2 FROM my_table WHERE id > :sql_last_value"
# 允许sql_last_value的值来自查询结果的某个字段值。
use_column_value => true
# sql_last_value的值来自查询结果中的最后一个id值
tracking_column => "id"
# ... 忽略其他配置
}
}
说明:
sql_last_value的默认值是0或者1970-01-01,具体是什么值跟数据类型有关,上面的例子,定时任务执行SQL如下
# 第一次执行,sql_last_value=0 SELECT id, mycolumn1, mycolumn2 FROM my_table WHERE id > 0 # 第二次执行,sql_last_value=100,假设上面的SQL最后的id值是100 SELECT id, mycolumn1, mycolumn2 FROM my_table WHERE id > 100 # 第三次执行,sql_last_value=200,,假设上面的SQL最后的id值是200 SELECT id, mycolumn1, mycolumn2 FROM my_table WHERE id > 200
提示:
上面的例子,使用id作为增量同步数据的依据,不一定适合所有的业务场景,例如:同步文章数据,文章更新了,但是文章的id没有更新,这个时候使用id作为增量同步的依据,会导致更新的文章没有同步到ES,这种场景适合使用更新时间作为增量同步的依据,用法一样,sql_last_value换一个字段值即可。
6、番外话:
一次要将excel的数据,更新至elastic数据库,由于我只用elasticsearch-head的谷歌插件,无法直接导入,只能将excel表导入mysql,再使用logstash同步至elastic。在导入mysql时,遇到文件编码问题,记录下解决办法,以备忘。
1、将excel数据转换为csv,wps默认的编码是antis,导入mysql默认使用utf-8,会出现中文乱码情况。需要使用txt记事本打开csv文件,另存为时,设置编码格式。
2、我使用dbeaver导入数据。此处显示utf-8编码,与文件编码一致,就不会出现中文乱码情况。
相关链接如下: