异构数据库迁移与同步(二)之otter

背景

异构数据库迁移与同步(一)之yugong

应用场景

Portal控制中心迁移
迁移步骤:

  1. Oracle数据迁移到MySQL;
  2. 前端只读SPA页面上线;
  3. MySQL数据实时同步到Oracle,
  4. 老Portal控制中心相关Oracle表锁写
  5. 前端可写SPA页面(开发)上线;
  6. Portal老页面下线;
  7. 完成控制中心模块的迁移,MySQL->Oracle实时同步直至老Portal所有读控制中心相关Oracle数据表接口下线所有。

在此次迁移过程中需==要一段时间内将MySQL数据实时同步到Oracle==来保证==新旧模块并行==直至旧模块全部下线。

需求

  • 指定数据表迁移
  • 支持字段的增删
  • 支持字段的大小写转换
  • 不停机同步
  • 数据流方向:MySQL -> Oracle

工具选型

yugong暂时不支持MySQL数据源,基于异构数据库迁移的工具选型分析,采用otter进行MySQL->Oracle的数据同步。
otter原理-异地机房

探究otter

定位:基于数据库增量日志解析,准实时同步到本机房或异地机房的mysql/oracle数据库. 一个分布式数据库同步系统。

功能

  • 异构库同步
  • 单机房同步
    • 数据库版本升级
    • 数据表迁移
    • 异步二级索引
  • 异地机房同步
    • 机房容灾
  • 双向同步
    • 避免回环算法
    • 数据一致性算法 (保证双A机房模式下,数据保证最终一致性)
  • 文件同步
    • 站点镜像 (进行数据复制的同时,复制关联的图片,比如复制产品数据,同时复制产品图片).

原理

原理描述

  • 基于Canal开源产品,获取数据库增量日志数据。Canal[kə’næl]?
  • 典型管理系统架构,manager(web管理)+node(工作节点)
    • manager运行时推送同步配置到node节点
    • node节点将同步状态反馈到manager上
  • 基于zookeeper,解决分布式状态调度的,允许多node节点之间协同工作.

Canal简介
基于数据库增量日志解析,提供增量数据订阅&消费,目前开源版本支持5.7及以下mysql
mysql主从同步
Canal原理

  • mysql主备复制
  • canal工作原理
    • canal模拟mysql slave的交互协议,伪装自己为mysql slave,向mysql master发送dump协议
    • mysql master收到dump请求,开始推送binary log给slave(也就是canal)
    • canal解析binary log对象(原始为byte流)

核心算法

otter的同步速度相比于mysql的复制,约有5倍左右的性能提升,这取决于其同步算法的实现. 抛弃了强一致性,得到了性能提升。
入库算法:采取了按pk hash并行载入+batch合并的优化。

调度模型、双向回环控制、数据一致性、高可用、扩展性,当然这些都不讲,自己研究吧。

小试otter

数据库

canal支持mixed,row,statement多种日志协议的解析,但配合otter进行数据库同步,目前仅支持==row协议==的同步,使用时需要注意.

产生binlog

[mysqld]
log-bin=mysql-bin #添加这一行就ok
binlog-format=ROW #选择row模式
server_id=1 #配置mysql replaction需要定义,不能和canal的slaveId重复

mysql slave的相关权限

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

otter manager

环境准备

  • 配置信息存储
    • 安装mysql
    • 初始化otter manager系统表
  • 安装zookeeper
    • otter.properties中指定一个就近的zookeeper集群

目录结构

drwxr-xr-x  2 root root 4096 7月  24 11:34 bin
drwxr-xr-x 2 root root 4096 7月 24 11:33 conf
-
-rwsrwsrwt 1 root root 4209 9月 23 2014 jetty.xml
-rwsrwsrwt 1 root root 7019 9月 23 2014 logback.xml
-rwsrwsrwt 1 root root 1405 7月 24 11:33 otter.properties

drwxr-xr-x 2 root root 4096 7月 2 18:08 lib
drwxr-xr-x 25 root root 4096 7月 25 13:48 logs
-
-rw-r--r-- 1 root root 8741 7月 24 11:40 alarm.log
-rw-r--r-- 1 root root 3740 7月 24 11:34 communication.log
-rw-r--r-- 1 root root 6553 7月 25 13:48 manager.log
-rw-r--r-- 1 root root 46657 7月 24 11:42 monitor_info.log
-rw-r--r-- 1 root root 0 7月 2 18:11 monitor_trigger.log
-rw-r--r-- 1 root root 0 7月 2 18:11 position.log
drwxr-xr-x 8 root root 4096 7月 2 18:08 webapp

修改配置

## otter manager domain name
otter.domainName = 192.168.32.74
## otter manager http port
otter.port = 8888
## jetty web config xml
otter.jetty = jetty.xml

## otter manager database config
otter.database.driver.class.name = com.mysql.jdbc.Driver
otter.database.driver.url = jdbc:mysql://192.168.30.253:3306/otter
otter.database.driver.username = otter
otter.database.driver.password = otter

## otter communication port
otter.communication.manager.port = 1099

## otter communication pool size
otter.communication.pool.size = 10

## default zookeeper address
otter.zookeeper.cluster.default = 192.168.30.253:2181
## default zookeeper sesstion timeout = 60s
otter.zookeeper.sessionTimeout = 60000

## otter arbitrate connect manager config
otter.manager.address = ${otter.domainName}:${otter.communication.manager.port}

## should run in product mode , true/false
otter.manager.productionMode = true

## self-monitor enable or disable
otter.manager.monitor.self.enable = true
## self-montir interval , default 120s
otter.manager.monitor.self.interval = 120
## auto-recovery paused enable or disable
otter.manager.monitor.recovery.paused = true
# manager email user config
otter.manager.monitor.email.host = anonymousrelay.chinacache.com
otter.manager.monitor.email.username = bandwidth-monitor@chinacache.com
otter.manager.monitor.email.password = ***********
otter.manager.monitor.email.stmp.port = 465

启动停止

查看日志

2013-08-14 13:19:45.911 [] WARN  com.alibaba.otter.manager.deployer.JettyEmbedServer - ##Jetty Embed Server is startup!
2013-08-14 13:19:45.911 [] WARN com.alibaba.otter.manager.deployer.OtterManagerLauncher - ## the manager server is running now ......

访问
URL:http://192.168.32.74:8888/login.htm

otter node

环境准备

  • 安装otter manager
  • 在manager页面为node定义配置信息,并生一个唯一id.
    • 访问manager页面的机器管理
    • 机器添加完成后,跳转到机器列表页面,获取对应的机器序号nid

      node这种设计,是为解决单机部署多实例而设计的,允许单机多node指定不同的端口

目录结构

drwxr-xr-x 2 root root 4096 7月  24 11:38 bin
drwxr-xr-x 2 root root 4096 7月 24 11:38 conf
-
-rwsrwsrwt 1 root root 8091 9月 23 2014 logback.xml
-rw-r--r-- 1 root root 2 7月 2 20:13 nid ##node的序号存放文件
-rwsrwsrwt 1 root root 455 7月 2 20:24 otter.properties
drwxr-xr-x 2 root root 4096 7月 2 20:24 download
drwxr-xr-x 2 root root 4096 7月 2 20:24 extend
drwxr-xr-x 2 root root 4096 7月 2 20:24 htdocs
drwxr-xr-x 2 root root 4096 7月 2 20:11 lib
drwxrwxrwx 4 root root 4096 7月 3 10:27 logs
-
drwxr-xr-x 7 root root 4096 7月 24 10:57 1
-
-rw-r--r-- 1 root root 39853 7月 24 17:32 1.log ##node处理数据的过程日志
-rw-r--r-- 1 root root 44392 7月 24 17:32 row_select.log ## Canal数据接入日志,包含binlog的positon、时间戳等信息

drwxr-xr-x 7 root root 4096 7月 24 10:57 node
-
-rw-r--r-- 1 root root 95345 7月 24 17:32 node.log ##node的运行日志

修改配置

  • nid配置
echo 1 > conf/nid
  • otter.properties配置修改
# otter node root dir
otter.nodeHome = ${user.dir}/../

## otter node dir
otter.htdocs.dir = ${otter.nodeHome}/htdocs
otter.download.dir = ${otter.nodeHome}/download
otter.extend.dir= ${otter.nodeHome}/extend

## default zookeeper sesstion timeout = 60s
otter.zookeeper.sessionTimeout = 60000

## otter communication pool size
otter.communication.pool.size = 10

## otter arbitrate & node connect manager config
otter.manager.address = 192.168.32.74:1099

启动停止

查看日志

2013-08-14 15:42:16.886 [main] INFO  com.alibaba.otter.node.deployer.OtterLauncher - INFO ## the otter server is running now ......

验证
访问manager页面的机器管理 查看对应的节点状态

Portal控制中心在线迁移&同步

  • 控制中心数据Oracle迁移到MySQL,并开启同步(Oracle->MySQL)
  • 上线SPA版信控系统(MySQL只读)
  • 新旧Portal稳定并行一段时间。。。
  • 控制中心相关Oracle表禁止老Portal写操作
  • 关闭Oracle-MySQL同步,开启MySQL->Oracle同步(长期运行直至老Portal不再有控制中心相关Oracle表读操作)
  • 上线SPA版控制中心(MySQL可读可写)
  • 新旧Portal并行,直至老Portal所有功能下线
  • Portal4上线运行
  • 关闭MySQL->Oracle同步

采坑记录

  • manager页面的ip配置不正确,即使manager和node部署在同一台机器上,尽量用局域网IP
  • Oracle数据约束暂时停用

    alter table PORTAL_RESOURCE disable novalidate constraint FK_PORTAL_RESOURCE_PARENT_ID;

    alter table PORTAL_ROLE_TO_RESOURCE disable novalidate constraint FK_PORTAL_R_TO_R_RESOURCEID;

    alter table PORTAL_USER_TO_ROLE disable novalidate constraint FK_PORTAL_U_TO_R_ROLEID;

    alter table PORTAL_ROLE_TO_RESOURCE disable novalidate constraint FK_PORTAL_R_TO_R_ROLEID;
  • 源库&目标库使用联合主键时目标库会高频率报主键重复

本文作者:haozi
原文链接:http://blog.chuangzhi8.cn/2018/08/26/异构数据库迁移与同步-二-之otter/
版权归作者所有,转载请注明出处

haozi wechat
扫二维码关注我
鼓励原创