搭建ElasticSearch + Canal同步MySQL以及Java实现搜索功能

一、安装Elastic Search 6.8

1.下载

链接: https://pan.baidu.com/s/1tKtt_XeQ9IRAJdKUAqM1Yg 提取码: 7iyx

2.部署环境配置

1)创建用户

adduser elastic

2)修改服务器配置

vi /etc/sysctl.conf

添加

vm.max_map_count = 262144

vi /etc/security/limits.conf

添加

*                soft    nofile          65536
*                hard    nofile          65536

3)查看配置

sysctl -p

在这里插入图片描述
3.安装

1)上传压缩包

2)解压

tar -zxvf elasticsearch-6.8.4.tar.gz

3)修改 config/elasticsearch.yml 配置文件

vim elasticsearch.yml

需要修改的配置

cluster.name: mpx  				#集群名称
node.name: node-1				#节点名称
network.host: 192.168.100.46	#配置访问地址
http.port: 9200					#访问端口
bootstrap.system_call_filter: false
transport.tcp.port: 9300		##集群通讯端口
transport.tcp.compress: true
http.cors.enabled: true
http.cors.allow-origin: "*"

4)修改权限给elastic用户赋权

cd 到解压的es同级目录

chown -R elastic:elastic elasticsearch

4.启动

su - elastic
cd /home/elasticSearch/elasticsearch-6.8.4/
./bin/elasticsearch -d

5.查看日志

tail -f logs/mpx.log	(日志名称为集群名称)

二.安装kibana

1.下载

链接: https://pan.baidu.com/s/1bC22pUOo3sh9syCoz9F0Gg 提取码: n7y5

2.安装

1)上传压缩包

2)解压

tar -zxvf kibana-6.2.4-linux-x86_64.tar.gz

3)修改 config 文件夹中 kibana.yml

vim kibana.yml

需要修改的配置

server.port: 5601
server.host: "192.168.100.46"
elasticsearch.url: "http://192.168.100.46:9200"

3.启动

./bin/kibana &

4.查看

浏览器访问:http://192.168.100.46:5601

三.安装canal 1.1.4

1.下载

链接: https://pan.baidu.com/s/1yrB24aHeWksznthejATRGQ 提取码: xwaf

2.安装

1)上传压缩包

2)解压canal

tar -zxvf canal.deployer-1.1.4.tar.gz

3.配置

1)配置MySQL的binlog写入功能

vim /etc/my.cnf

添加配置

server-id=1
expire-logs-days=15
log-bin=/data/mysql/mysql-bin
binlog-format=ROW

2)授权canal链接MySQL账号

登录要连接的MySQL,执行下面命令

CREATE USER canal IDENTIFIED BY 'canal';
GRANT SELECT, REPLICATION SLAVE, REPLICATION CLIENT ON *.* TO 'canal'@'%';
GRANT ALL PRIVILEGES ON *.* TO 'canal'@'%';
FLUSH PRIVILEGES;

3.配置 example/instance.properties

canal.instance.master.address=192.168.100.46:3306

4.启动

./bin/startup.sh

四.安装canal adapter 1.1.4

1.下载

链接: https://pan.baidu.com/s/1Vaq4unEAwUNkHOJ0CWCGng 提取码: 4fqc

2.安装

1)上传压缩包

2)解压canal

tar -zxvf canal.adapter-1.1.4.tar.gz

3.配置

1)配置 conf/application.yml

server:
  port: 8081
spring:
  jackson:
    date-format: yyyy-MM-dd HH:mm:ss
    time-zone: GMT+8
    default-property-inclusion: non_null
canal.conf:
  mode: tcp
  canalServerHost: 127.0.0.1:11111
  batchSize: 500
  syncBatchSize: 1000
  retries: 0
  timeout:
  accessKey:
  secretKey:
  srcDataSources:
    defaultDS:
      url: 此处配置连接数据库的地址
      username: 用户名
      password: 密码
  canalAdapters:
  - instance: example
    groups:
    - groupId: g1
      outerAdapters:
      - name: logger
      - name: es
        hosts: 192.168.100.46:9200
        properties:
          mode: rest
          cluster.name: mpx  #节点名称

2)配置 conf/es/***.yml

根据需要同步的数据库表进行配置,索引名称需要与文件名一致
以下为open_user表的同步配置

表结构:
在这里插入图片描述

配置 open_user.yml

dataSourceKey: defaultDS  #此配置为application.yml 的key
destination: example      #此配置为canal的name
groupId: g1
esMapping:
  _index: open_user
  _type: _doc
  _id: _id
  sql: "SELECT u.id AS _id,u.user_name AS userName,u.sex,u.portrait,u.create_time as createTime FROM open_user u"
  commitBatch: 3000

是可以有多个DS或者多个**.yml的

4.启动

./bin/startup.sh

五.全量同步

1.添加索引

打开 kibana

地址:http://192.168.100.46:5601
在这里插入图片描述

2.导入数据

curl -X POST http://127.0.0.1:8081/etl/es/*.yml (*为索引和es下的文件夹的名称)

在这里插入图片描述

3.测试同步MySQL

1)查看 adapter.log 日志

 cd /home/canaladapter/logs/adapter/
 tail -200f adapter.log

2)修改数据库 open_user 表中的数据

update open_user set user_name = 'abc' where id = 4
2020-09-24 10:12:01.663 [pool-3-thread-1] INFO  c.a.o.canal.client.adapter.logger.LoggerAdapterExample - DML: {"data":[{"id":4,"user_name":"abc","sex":1,"portrait":"","create_time":1600307267000}],"database":"test","destination":"example","es":1600913520000,"groupId":null,"isDdl":false,"old":[{"user_name":"abcd"}],"pkNames":["id"],"sql":"","table":"open_user","ts":1600913521501,"type":"UPDATE"}
2020-09-24 10:12:01.667 [pool-3-thread-1] DEBUG c.a.otter.canal.client.adapter.es.service.ESSyncService - DML: {"data":[{"id":4,"user_name":"abc","sex":1,"portrait":"","create_time":1600307267000}],"database":"test","destination":"example","es":1600913520000,"groupId":null,"isDdl":false,"old":[{"user_name":"abcd"}],"pkNames":["id"],"sql":"","table":"open_user","ts":1600913521663,"type":"UPDATE"} 
Affected indexes: open_user

说明修改的值已经同步到Es库中

六.注意事项

1.使用canal-adapter 需要查看版本对应,es6 与es7 相差较大。

2.使用canal-adapter 需要在es中提前使用mappings建立索引结构,否则无法同步


以上是搭建了Es,下面简单介绍代码如何实现搜索Es索引库

一.代码

1.引入依赖

注意spring boot版本,我使用的是2.1.4.RELEASE

		<dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
            <version>2.1.8.RELEASE</version>
        </dependency>

2.application.yml 添加配置

spring:
  jackson:
    date-format: yyyy-MM-dd HH:mm:ss
  data:
    elasticsearch:
      cluster-name: mpx
      cluster-nodes: 192.168.100.46:9300
      repositories:
        enabled: true
  elasticsearch:
    rest:
      uris: ["http://192.168.100.46:9200"]

3.创建索引实体类

package com.dcm4che.findscu.entity;

import org.springframework.data.annotation.Id;
import org.springframework.data.elasticsearch.annotations.Document;
import org.springframework.data.elasticsearch.annotations.Field;
import org.springframework.data.elasticsearch.annotations.FieldType;

import java.io.Serializable;
import java.util.Calendar;
import java.util.Date;

@Document(indexName = "open_user", type = "_doc")
public class OpenUser implements Serializable {

	@Id
	private String id;

	@Field(type = FieldType.Text)
	private String userName;

	@Field(type = FieldType.Text)
	private String sex;

	@Field(type = FieldType.Text)
	private String portrait;

	@Field(type = FieldType.Date)
	private Date createTime;

	public String getId() {
		return id;
	}

	public void setId(String id) {
		this.id = id;
	}

	public String getUserName() {
		return userName;
	}

	public void setUserName(String userName) {
		this.userName = userName;
	}

	public String getSex() {
		return sex;
	}

	public void setSex(String sex) {
		this.sex = sex;
	}

	public String getPortrait() {
		return portrait;
	}

	public void setPortrait(String portrait) {
		this.portrait = portrait;
	}

	public Date getCreateTime() {
		return createTime;
	}

	public void setCreateTime(Date createTime) {
		// 时间改为东八区
		Calendar cal = Calendar.getInstance();
		cal.setTime(createTime);
		cal.add(Calendar.HOUR, +8);
		this.createTime = cal.getTime();
	}

	@Override
	public String toString() {
		return "OpenUser{" + "id='" + id + '\'' + ", userName='" + userName + '\'' + ", sex='" + sex + '\''
				+ ", portrait='" + portrait + '\'' + ", createTime=" + createTime + '}';
	}
}

4.查询 userName 接口

中英文搜索是需要处理的,这里用了原生的写法处理。

package com.dcm4che.findscu.controller;

import com.dcm4che.findscu.entity.OpenUser;
import org.apache.commons.lang3.StringUtils;
import org.elasticsearch.index.query.QueryBuilder;
import org.elasticsearch.index.query.QueryBuilders;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.data.elasticsearch.core.ElasticsearchTemplate;
import org.springframework.data.elasticsearch.core.query.NativeSearchQueryBuilder;
import org.springframework.data.elasticsearch.core.query.SearchQuery;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class SearchController {

	@Autowired
	private ElasticsearchTemplate elasticsearchTemplate;

	@PostMapping("/findOpenUserByUserName")
	public Page<OpenUser> findOpenUserByUserName(@RequestParam(value = "userName") String userName,
			@RequestParam(value = "pageNum", required = false) Integer pageNum,
			@RequestParam(value = "pageSize", required = false) Integer pageSize) {
		if (StringUtils.isBlank(userName)) {
			return null;
		}
		if (pageNum == null || pageNum < 0) {
			pageNum = 0; // if page is null, page = 0 size default 1
		}
		if (pageSize == null || pageSize < 0) {
			pageSize = 10; // if size is null, size default 10
		}
		// 分页,根据时间倒序
		Pageable pageable = PageRequest.of(pageNum, pageSize, Sort.Direction.DESC, "createTime");
		// 查询姓名
		QueryBuilder builder = null;
		if (userName.matches("^[A-Za-z0-9]+$")) {
			builder = QueryBuilders.boolQuery()
					.must(QueryBuilders.wildcardQuery("userName", ("*" + userName + "*").toLowerCase()));
		} else {
			builder = QueryBuilders.boolQuery()
					.must(QueryBuilders.matchPhraseQuery("userName", userName.toLowerCase()));
		}
		SearchQuery searchQuery = new NativeSearchQueryBuilder().withQuery(builder).withPageable(pageable).build();
		return elasticsearchTemplate.queryForPage(searchQuery, OpenUser.class);
	}
}

5.测试

用了postman测试,搜索userName=abc
在这里插入图片描述在这里插入图片描述

与数据库信息一致,到此结束。

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
实现MySQL数据实时同步Elasticsearch可以使用Canal工具。 Canal是阿里巴巴开源的一套基于数据库增量日志解析的数据同步和逆向解析工具,可以实时获取数据库的变更日志,然后将这些变更日志解析成数据并发送到指定的目的地。在实现MySQL数据实时同步Elasticsearch中,可以使用Canal实现以下步骤: 1. 安装配置Canal:首先,需要下载并安装Canal,并配置Canal的参数,如MySQL的地址、端口、用户名、密码等。 2. 创建Canal实例:根据实际需求,可以创建一个或多个Canal实例来监控和同步MySQL的变更日志。 3. 配置Elasticsearch目的地:配置Canal将变更日志发送到Elasticsearch作为同步的目的地。 4. 启动Canal实例:通过命令行或脚本启动Canal实例,让Canal开始监控MySQL的变更日志。 5. 解析并同步数据:Canal会实时监控MySQL的变更日志,一旦有变更,就会解析并发送到Elasticsearch。在Elasticsearch中,可以根据业务需求进行相应的处理,比如数据转换、数据筛选、数据拆分等,并将处理后的数据存储到Elasticsearch中。 通过以上步骤,就可以实现MySQL数据的实时同步Elasticsearch中。Canal工具可以很好地解析MySQL的增量日志并将数据发送到Elasticsearch,保证数据的实时性和一致性。同时,Canal还支持分布式部署和高可用性,可以满足大规模数据同步的需求。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值