使用Canal实现MySQL主从同步

说明:本文介绍如何使用Canal实现MySQL主从同步的效果,关于Canal入门使用参考:Canal入门使用

启动Canal

首先,设置Canal服务器里,目标节点(即监测的MySQL节点)的配置,启动Canal服务;

在这里插入图片描述

启动Canal服务器,Windows操作系统下,直接双击startup.bat文件即可;

在这里插入图片描述

具体操作参考:Canal入门使用

创建项目

创建一个Spring Boot项目,pom.xml文件如下:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"><modelVersion>4.0.0</modelVersion><parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>2.7.12</version><relativePath/></parent><groupId>com.hezy</groupId><artifactId>canal_demo</artifactId><version>1.0-SNAPSHOT</version><properties><maven.compiler.source>11</maven.compiler.source><maven.compiler.target>11</maven.compiler.target><project.build.sourceEncoding>UTF-8</project.build.sourceEncoding></properties><dependencies><!--lombok--><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId></dependency><!--druid--><dependency><groupId>com.alibaba</groupId><artifactId>druid-spring-boot-starter</artifactId><version>1.2.8</version></dependency><!--mybatis--><dependency><groupId>org.mybatis.spring.boot</groupId><artifactId>mybatis-spring-boot-starter</artifactId><version>2.2.2</version></dependency><!--mysql驱动--><dependency><groupId>com.mysql</groupId><artifactId>mysql-connector-j</artifactId><scope>runtime</scope></dependency><!--canal客户端--><dependency><groupId>top.javatool</groupId><artifactId>canal-spring-boot-starter</artifactId><version>1.2.1-RELEASE</version></dependency></dependencies></project>

application.yml文件如下,这里的数据库配置写从节点的,且账户应该有数据读写权限;

server:port: 8080# 1.数据源的配置
spring:# 数据库配置datasource:driver-class-name: com.mysql.cj.jdbc.Driverurl: jdbc:mysql://从节点MySQLIP:3306/test?useUnicode=true&characterEncoding=utf-8&useSSL=falseusername: rootpassword: 123456# 2.mybatis配置
mybatis:configuration:# 显示SQL日志配置log-impl: org.apache.ibatis.logging.stdout.StdOutImpl# 驼峰命名配置map-underscore-to-camel-case: true# 3.canal配置
canal:# canal服务端的ipserver: 127.0.0.1:11111destination: example

实体类对象

import lombok.Data;import java.io.Serializable;@Data
public class User implements Serializable {private String id;private String username;private String password;
}

canal处理类

import com.hezy.mapper.UserMapper;
import com.hezy.pojo.User;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import top.javatool.canal.client.annotation.CanalTable;
import top.javatool.canal.client.handler.EntryHandler;@Component
@CanalTable("i_user")
public class UserHandler implements EntryHandler<User> {@Autowiredprivate UserMapper userMapper;@Overridepublic void insert(User user) {System.out.println("新增用户:" + user);userMapper.insertUser(user);}@Overridepublic void update(User before, User after) {System.out.println("更新用户:" + before + " -> " + after);userMapper.updateUserById(after);}@Overridepublic void delete(User user) {System.out.println("删除用户:" + user);userMapper.deleteUserById(user.getId());}
}

对应写三个针对User表(User实体类对应的表,即i_user表)操作的Mapper方法;

import com.hezy.pojo.User;
import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Insert;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Update;@Mapper
public interface UserMapper {@Insert("insert into i_user values (#{id}, #{username}, #{password})")void insertUser(User uesr);@Delete("delete from i_user where id = #{id}")void deleteUserById(String id);@Update("update i_user set username=#{username}, password=#{password} where id=#{id}")void updateUserById(User user);}

启动程序前,看下两个数据库的表内容,目前是一致的,即使不一致,在你想要进行同步前,也应该手动导出/导入数据,使其初始状态数据保持一致。

在这里插入图片描述

启动程序,数据库开始同步,查看控制台,在实时打印检测的信息;

在这里插入图片描述

此时,在主节点i_user表内修改一条数据,查看控制台,从数据库内容;

在这里插入图片描述

可以看到这次操作被canal监测到了,并通过代码更新到了从库,即代码中配置的数据库;

在这里插入图片描述

查看从库i_user表内容,从库数据成功同步;

在这里插入图片描述

到这里,使用Canal实现MySQL主从同步已完成;

另外

另外,我有个想法,能不能把这个项目package,打成一个jar包,当遇到短期的数据库同步场景时,直接运行这个jar包就可以了。

比如日常开发时,我们想让自己的本地库与测试环境的库保持同步,直接去修改测试库配置,搭建主从可能比较麻烦,就可以用这种方式。甚至可以写个bat脚本,配个环境变量,直接敲CMD命令就能实现两个数据库之间的同步了,非常方便。

总结

本文介绍了如何使用Canal实现MySQL主从同步,参考B站视频:

  • Canal极简入门:一小时让你快速上手Canal数据同步神技~

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/4484.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Scala 03 —— Scala OOP Extension

Scala 2.1 —— Scala OOP Extension 一、正则 文章目录 Scala 2.1 —— Scala OOP Extension一、正则1.1 Java正则和Scala正则的区别1.2 Java正则和Scala正则的的基本知识点Java正则Scala正则 1.3 练习练习一&#xff1a;使用正则表达式解析日志方法一&#xff1a;使用findAl…

心理学上有个概念叫:习惯性反驳(附上解决办法)

在心理学上&#xff0c;有一个词&#xff0c;叫做习惯性反驳。 什么意思呢&#xff1f; 就是不管你说什么&#xff0c;他都要反驳你&#xff0c;最后把你带入负面的情绪黑洞&#xff0c;搞得你非常崩溃。 一个总是习惯性反驳的人&#xff0c;其实是非常可怕的。 习惯性反驳的3个…

【LeetCode题库】1148. 文章浏览 I

文章目录 原题题解解题笔记——相关知识点拓展 我是一名立志把细节都说清楚的博主&#xff0c;欢迎【关注】&#x1f389; ~ 原创不易&#xff0c; 如果有帮助 &#xff0c;记得【点赞】【收藏】 哦~ ❥(^_-)~ 如有错误、疑惑&#xff0c;欢迎【评论】指正探讨&#xff0c;我…

与Apollo共创生态:Apollo7周年大会自动驾驶生态利剑出鞘

前言 4月22日&#xff0c;百度Apollo在北京车展前夕举办了以“破晓•拥抱智变时刻”为主题的智能汽车产品发布会&#xff0c;围绕汽车智能化&#xff0c;发布了智驾、智舱、智图等全新升级的“驾舱图”系列产品。 1、7周年大会 自2013年百度开始布局自动驾驶&#xff0c;201…

PotatoPie 4.0 实验教程(24) —— FPGA实现摄像头图像中心差分变换

为什么要对图像进行中心差分变换&#xff1f; 对图像进行中心差分变换的主要目的是计算图像中每个像素点的梯度。梯度在图像处理中是一个非常重要的概念&#xff0c;它可以用来描述图像中灰度变化的快慢和方向&#xff0c;常用于边缘检测、特征提取和图像增强等任务中。 具体…

对React-Fiber的理解,它解决了什么问题?

React V15 在渲染时&#xff0c;会递归比对 VirtualDOM 树&#xff0c;找出需要变动的节点&#xff0c;然后同步更新它们&#xff0c; 一气呵成。这个过程期间&#xff0c; React 会占据浏览器资源&#xff0c;这会导致用户触发的事件得不到响应&#xff0c;并且会导致掉帧&…

js试手练习

8.idaas.yundasys.com:10443/frontend/login#/login 搜索punlickKey&#xff0c;第二个 然后进加载器&#xff0c;全部折叠发现在fdd5全扣 注意的是输入账号时不会触发xhr要在登录那里打断点进入 9.m.ctyun.cn/wap/main/auth/login 搜索password: 往上找加载器&#xff0c;w…

windows服务启动提示‘服务没有响应控制功能’(mysql启动报错)

在安装mysql的时候&#xff0c;在windows服务项启动 或 使用命令net start mysql 时启动是报错&#xff0c;提示 服务没有响应控制功能 发生原因&#xff1a; Windows10 x64 或 更高的操作系统&#xff0c;有些系统缺少一些组件 解决办法&#xff1a; 1、下载最新的 Microsoft …

clickhouse安装部署

虚拟机&#xff1a;virtualbox7.0 操作系统&#xff1a;ubuntu server 22.04.3 虚拟机硬件&#xff1a;cpu 1&#xff0c;内存 2G&#xff0c; 硬盘 100G 采用默认安装 参照 https://clickhouse.com/docs/en/install#quick-install 安装部署 对于Debian、Ubuntu&#xff0c…

版本比对sql

弹窗 index <template><el-dialogtitle"版本":visible.sync"dialogVisible"width"55%"center:close-on-click-modal"false":close-on-press-escape"false":before-close"beforeClose"open"open&q…

【Linux网络】DHCP原理与配置

目录 一、DHCP工作原理 1.了解DHCP服务 2.使用DHCP的好处 3.DHCP的分配方式 二、DHCP的租约过程 三、DHCP场景应用实验 一、DHCP工作原理 1.了解DHCP服务 DHCP&#xff08;Dynamic Host Configuration Protocol&#xff0c;动态主机配置协议&#xff09; 由Internet工作…

[Unity]打包Android后xxx方法丢失。

记录一个坑&#xff1a; Editor下C#一段反射代码运行正常&#xff0c;但是打包后报错。最后发现是PlayerSettings里的Managed Stripping Level&#xff08;托管堆代码剥离级别&#xff09;导致的&#xff0c;项目默认的是Medium。改成Low确实好使&#xff0c;但是会造成包体大…

Redis(四) 主从、哨兵、集群环境搭建

结合前三期 Redis(一) Redis简介(Redis(一) Redis简介-CSDN博客) Redis(二) 可编程性(Redis(二) 可编程性-CSDN博客) Redis(三) 事务与发布订阅(Redis(三) 事务与发布订阅-CSDN博客) 目录 1.0 Redis主从 1.1 Redis 主从结构的基本原理和工作方式 1.2 Redis 主从结构的好处 …

【MyBatis】使用MyBatis框架在两张表是一对多的情况下,进行分步查询,发现对查询出来的结果进行封装时没有将实体类的id进行赋值

Catalog MyBatis在两张表是一对多的情况下,进行分步查询&#xff0c;发现对查询出来的结果进行封装时没有将实体类的id进行赋值1. 表结构2. 场景3. 实现方式具体步骤 4 .测试5. 解决方法 MyBatis在两张表是一对多的情况下,进行分步查询&#xff0c;发现对查询出来的结果进行封装…

企业工厂如何逆风翻盘:VR全景打破多重桎梏

现阶段&#xff0c;制造业工厂面临的困境&#xff0c;就是用着上百万的设备&#xff0c;却赚着几毛钱的利润。传统的工厂参观方式也存在着很多的局限性&#xff0c;例如时间上不方便、不能实地参访、生产线具有隐患等&#xff0c;都会使得参观者不能深入地了解工厂的生产环境和…

Python初级笔记6 函数

函数概念 函数是一段具有特定功能的代码的集合。函数的目的主要在于降低编程难度与增加代码复用。一组语句等价于一个函数&#xff0c;&#xff0c;需要使用这组语句的地方直接调用函数名即可。函数的定义也叫函数的声明&#xff0c;定义后的函数不能直接运行需要通过调用 函数…

《苍穹外卖》Day12部分知识点记录——数据统计-Excel报表

一、工作台 需求分析和设计 接口设计 今日数据接口订单管理接口菜品总览接口套餐总览接口订单搜索&#xff08;已完成&#xff09;各个状态的订单数量统计&#xff08;已完成&#xff09; 代码实现 今日数据接口 1. WorkspaceController 注意不要导错包了 package com.sk…

【经典算法】LeetCode104二叉树的最大深度(Java/C/Python3实现含注释说明,Easy)

目录 题目描述思路及实现方式一&#xff1a;递归思路代码实现Java版本C语言版本Python3版本Go语言版本 复杂度分析 方式二&#xff1a;广度优先搜索(BFS)思路代码实现Java版本C语言版本Python3版本 复杂度分析 总结相似题目 标签(题目类型)&#xff1a;树、深度优先搜索(DFS)、…

正点原子[第二期]Linux之ARM(MX6U)裸机篇学习笔记-6.5

前言&#xff1a; 本文是根据哔哩哔哩网站上“正点原子[第二期]Linux之ARM&#xff08;MX6U&#xff09;裸机篇”视频的学习笔记&#xff0c;在这里会记录下正点原子 I.MX6ULL 开发板的配套视频教程所作的实验和学习笔记内容。本文大量引用了正点原子教学视频和链接中的内容。…

二叉树的创建

##根据中序和后续遍历构建二叉树 根据遍历的顺序不同构建二叉树 必须要有中序遍历的参与 BTNode* createBTree(const char* inOrder,const char* posOrder, int num) { if (num 0) { return nullptr; } BTNode* node new BTNode; node->data …