diff --git a/.gitignore b/.gitignore index 3f1a5d6b..90bd720f 100644 --- a/.gitignore +++ b/.gitignore @@ -14,3 +14,5 @@ jtester.properties .idea/ *.iml .DS_Store +*.tar.gz +*.rpm diff --git a/README.md b/README.md index 456bd2db..6af316ae 100644 --- a/README.md +++ b/README.md @@ -1,12 +1,6 @@
- -

最新更新

-
    -
  1. canal QQ讨论群已经建立,群号:161559791 ,欢迎加入进行技术讨论。
  2. -
  3. canal消费端项目开源: Otter(分布式数据库同步系统),地址:https://github.com/alibaba/otter
  4. -
- +

背景

早期,阿里巴巴B2B公司因为存在杭州和美国双机房部署,存在跨机房同步的业务需求。不过早期的数据库同步业务,主要是基于trigger的方式获取增量变更,不过从2010年开始,阿里系公司开始逐步的尝试基于数据库的日志解析,获取增量变更进行同步,由此衍生出了增量订阅&消费的业务,从此开启了一段新纪元。

ps. 目前内部版本已经支持mysql和oracle部分版本的日志解析,当前的canal开源版本支持5.7及以下的版本(阿里内部mysql 5.7.13, 5.6.10, mysql 5.5.18和5.1.40/48)

@@ -44,6 +38,16 @@
  • canal解析binary log对象(原始为byte流)
  • +

    重要版本更新说明

    + +canal 1.1.x系列,参考release文档:版本发布信息 + +1. 整体性能测试&优化,提升了150%. #726 参考: 【[Performance](https://github.com/alibaba/canal/wiki/Performance)】 +2. 原生支持prometheus监控 #765 【[Prometheus QuickStart](https://github.com/alibaba/canal/wiki/Prometheus-QuickStart)】 +3. 原生支持kafka消息投递 #695 【[Canal Kafka/RocketMQ QuickStart](https://github.com/alibaba/canal/wiki/Canal-Kafka-RocketMQ-QuickStart)】 +4. 原生支持aliyun rds的binlog订阅 (解决自动主备切换/oss binlog离线解析) 参考: 【[Aliyun RDS QuickStart](https://github.com/alibaba/canal/wiki/aliyun-RDS-QuickStart)】 +5. 原生支持docker镜像 #801 参考: 【[Docker QuickStart](https://github.com/alibaba/canal/wiki/Docker-QuickStart)】 +

    相关文档

    See the wiki page for : wiki文档 @@ -52,20 +56,41 @@ See the wiki page for : wiki文 +

    多语言业务

    + +1. canal整体交互协议设计上使用了protobuf3.0,理论上可以支持绝大部分的多语言场景,欢迎大家提交多客户端的PR + * canal java客户端: https://github.com/alibaba/canal/wiki/ClientExample + * canal c#客户端开源项目地址: https://github.com/CanalSharp/CanalSharp + * canal go客户端开源项目地址: https://github.com/CanalClient/canal-go +2. canal作为MySQL binlog的增量获取工具,可以将数据投递到MQ系统中,比如Kafka/RocketMQ,可以借助于MQ的多语言能力 + * 参考文档: [Canal Kafka/RocketMQ QuickStart](https://github.com/alibaba/canal/wiki/Canal-Kafka-RocketMQ-QuickStart) +

    相关资料

    * ADC阿里技术嘉年华分享ppt (放在google docs上,可能需要翻墙): ppt下载 -* [与阿里巴巴的RocketMQ配合使用](https://github.com/alibaba/RocketMQ) +* [与阿里巴巴的RocketMQ配合使用](https://github.com/apache/RocketMQ)

    相关开源

      @@ -73,6 +98,14 @@ See the wiki page for : wiki文
    1. 阿里巴巴去Oracle数据迁移同步工具(目标支持MySQL/DRDS):http://github.com/alibaba/yugong
    +

    相关产品

    +
      +
    1. 阿里云分布式数据库DRDS
    2. +
    3. 阿里云数据传输服务DTS
    4. +
    5. 阿里云数据库备份服务DBS
    6. +
    7. 阿里云数据管理服务DMS
    8. +
    +

    问题反馈

    1. qq交流群: 161559791
    2. @@ -81,9 +114,13 @@ See the wiki page for : wiki文
    3. 报告issue:issues
    -
    -【招聘】阿里巴巴中间件团队招聘JAVA高级工程师
    -岗位主要为技术型内容(非业务部门),阿里中间件整个体系对于未来想在技术上有所沉淀的同学还是非常有帮助的
    -工作地点:杭州、北京均可. ps. 阿里待遇向来都是不错的,有意者可以QQ、微博私聊. 
    -具体招聘内容:https://job.alibaba.com/zhaopin/position_detail.htm?positionId=32666
    -
    +

    最新更新

    +
      +
    1. canal发布重大版本更新1.1.0,具体releaseNode参考:https://github.com/alibaba/canal/releases/tag/canal-1.1.0
    2. +
    3. canal c#客户端开源项目地址: https://github.com/CanalClient/CanalSharp ,推荐!
    4. +
    5. canal QQ讨论群已经建立,群号:161559791 ,欢迎加入进行技术讨论。
    6. +
    7. canal消费端项目开源: Otter(分布式数据库同步系统),地址:https://github.com/alibaba/otter
    8. + +
    9. Canal已在阿里云推出商业化版本 数据传输服务DTS, 开通即用,免去部署维护的昂贵使用成本。DTS针对阿里云RDS、DRDS等产品进行了适配,解决了Binlog日志回收,主备切换、VPC网络切换等场景下的订阅高可用问题。同时,针对RDS进行了针对性的性能优化。出于稳定性、性能及成本的考虑,强烈推荐阿里云用户使用DTS产品。DTS产品使用文档
    10. +DTS支持阿里云RDS&DRDS的Binlog日志实时订阅,现推出首月免费体验,限时限量,立即体验>>> +
    diff --git a/client-adapter/README.md b/client-adapter/README.md new file mode 100644 index 00000000..5d9ab5ce --- /dev/null +++ b/client-adapter/README.md @@ -0,0 +1,545 @@ +## 基本说明 +canal 1.1.1版本之后, 增加客户端数据落地的适配及启动功能, 目前支持功能: +* 客户端启动器 +* 同步管理REST接口 +* 日志适配器, 作为DEMO +* HBase的数据同步(表对表同步), ETL功能 +* (后续支持) ElasticSearch多表数据同步,ETL功能 + +## 环境版本 +* 操作系统:无要求 +* java版本: jdk1.8 以上 +* canal 版本: 请下载最新的安装包,本文以当前v1.1.1 的canal.deployer-1.1.1.tar.gz为例 +* MySQL版本 :5.7.18 +* HBase版本: Apache HBase 1.1.2, 若和服务端版本不一致可自行替换客户端HBase依赖 + +## 一、适配器启动器 +client-adapter分为适配器和启动器两部分, 适配器为多个fat jar, 每个适配器会将自己所需的依赖打成一个包, 以SPI的方式让启动器动态加载 + + +启动器为 SpringBoot 项目, 支持canal-client启动的同时提供相关REST管理接口, 运行目录结构为: +``` +- bin + restart.sh + startup.bat + startup.sh + stop.sh +- lib + client-adapter.logger-1.1.1-jar-with-dependencies.jar + client-adapter.hbase-1.1.1-jar-with-dependencies.jar + ... +- conf + application.yml + - hbase + mytest_person2.yml +- logs +``` +以上目录结构最终会打包成 canal-adapter-launcher.tar.gz 压缩包 + +## 二、启动器 +### 2.1 启动器配置 application.yml +#### canal相关配置部分说明 +``` +canal.conf: + canalServerHost: 127.0.0.1:11111 # 对应单机模式下的canal server的ip:port + zookeeperHosts: slave1:2181 # 对应集群模式下的zk地址, 如果配置了canalServerHost, 则以canalServerHost为准 + bootstrapServers: slave1:6667 # kafka或rocketMQ地址, 与canalServerHost不能并存 + flatMessage: true # 扁平message开关, 是否以json字符串形式投递数据, 仅在kafka/rocketMQ模式下有效 + canalInstances: # canal实例组, 如果是tcp模式可配置此项 + - instance: example # 对应canal destination + groups: # 对应适配器分组, 分组间的适配器并行运行 + - outAdapters: # 适配器列表, 分组内的适配串行运行 + - name: logger # 适配器SPI名 + - name: hbase + properties: # HBase相关连接参数 + hbase.zookeeper.quorum: slave1 + hbase.zookeeper.property.clientPort: 2181 + zookeeper.znode.parent: /hbase + mqTopics: # MQ topic租, 如果是kafka或者rockeMQ模式可配置此项, 与canalInstances不能并存 + - mqMode: kafka # MQ的模式: kafak/rocketMQ + topic: example # MQ topic + groups: # group组 + - groupId: g2 # group id + outAdapters: # 适配器列表, 以下配置和canalInstances中一样 + - name: logger +``` +#### 适配器相关配置部分说明 +``` +adapter.conf: + datasourceConfigs: # 数据源配置列表, 数据源将在适配器中用于ETL、数据同步回查等使用 + defaultDS: # 数据源 dataSourceKey, 适配器中通过该值获取指定数据源 + url: jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true + username: root + password: 121212 + adapterConfigs: # 适配器内部配置列表 + - hbase/mytest_person2.yml # 类型/配置文件名, 这里示例就是对应HBase适配器hbase目录下的mytest_person2.yml文件 +``` +## 2.2 同步管理REST接口 +#### 2.2.1 查询所有订阅同步的canal destination或MQ topic +``` +curl http://127.0.0.1:8081/destinations +``` +#### 2.2.2 数据同步开关 +``` +curl http://127.0.0.1:8081/syncSwitch/example/off -X PUT +``` +针对 example 这个canal destination/MQ topic 进行开关操作. off代表关闭, 该destination/topic下的同步将阻塞或者断开连接不再接收数据, on代表开启 + +注: 如果在配置文件中配置了 zookeeperHosts 项, 则会使用分布式锁来控制HA中的数据同步开关, 如果是单机模式则使用本地锁来控制开关 +#### 2.2.3 数据同步开关状态 +``` +curl http://127.0.0.1:8081/syncSwitch/example +``` +查看指定 canal destination/MQ topic 的数据同步开关状态 +#### 2.2.4 手动ETL +``` +curl http://127.0.0.1:8081/etl/hbase/mytest_person2.yml -X POST -d "params=2018-10-21 00:00:00" +``` +导入数据到指定类型的库 +#### 2.2.5 查看相关库总数据 +``` +curl http://127.0.0.1:8081/count/hbase/mytest_person2.yml +``` +### 2.3 启动canal-adapter示例 +#### 2.3.1 启动canal server (单机模式), 参考: [Canal QuickStart](https://github.com/alibaba/canal/wiki/QuickStart) +#### 2.3.2 修改conf/application.yml为: +``` +server: + port: 8081 +logging: + level: + com.alibaba.otter.canal.client.adapter.hbase: DEBUG +spring: + jackson: + date-format: yyyy-MM-dd HH:mm:ss + time-zone: GMT+8 + default-property-inclusion: non_null + +canal.conf: + canalServerHost: 127.0.0.1:11111 + flatMessage: true + canalInstances: + - instance: example + adapterGroups: + - outAdapters: + - name: logger +``` +启动 +``` +bin/startup.sh +``` + +## 三、HBase适配器 +### 3.1 修改启动器配置: application.yml +``` +server: + port: 8081 +logging: + level: + com.alibaba.otter.canal.client.adapter.hbase: DEBUG +spring: + jackson: + date-format: yyyy-MM-dd HH:mm:ss + time-zone: GMT+8 + default-property-inclusion: non_null + +canal.conf: + canalServerHost: 127.0.0.1:11111 + flatMessage: true + srcDataSources: + defaultDS: + url: jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true + username: root + password: 121212 + canalInstances: + - instance: example + adapterGroups: + - outAdapters: + - name: hbase + properties: + hbase.zookeeper.quorum: slave1 + hbase.zookeeper.property.clientPort: 2181 + zookeeper.znode.parent: /hbase +``` +adapter将会自动加载 conf/hbase 下的所有.yml结尾的配置文件 +### 3.2 适配器表映射文件 +修改 conf/hbase/mytest_person.yml文件: +``` +dataSourceKey: defaultDS # 对应application.yml中的datasourceConfigs下的配置 +hbaseMapping: # mysql--HBase的单表映射配置 + mode: STRING # HBase中的存储类型, 默认统一存为String, 可选: #PHOENIX #NATIVE #STRING + # NATIVE: 以java类型为主, PHOENIX: 将类型转换为Phoenix对应的类型 + destination: example # 对应 canal destination/MQ topic 名称 + database: mytest # 数据库名/schema名 + table: person # 表名 + hbaseTable: MYTEST.PERSON # HBase表名 + family: CF # 默认统一Column Family名称 + uppercaseQualifier: true # 字段名转大写, 默认为true + commitBatch: 3000 # 批量提交的大小, ETL中用到 + #rowKey: id,type # 复合字段rowKey不能和columns中的rowKey并存 + # 复合rowKey会以 '|' 分隔 + columns: # 字段映射, 如果不配置将自动映射所有字段, + # 并取第一个字段为rowKey, HBase字段名以mysql字段名为主 + id: ROWKE + name: CF:NAME + email: EMAIL # 如果column family为默认CF, 则可以省略 + type: # 如果HBase字段和mysql字段名一致, 则可以省略 + c_time: + birthday: +``` +如果涉及到类型转换,可以如下形式: +``` +... + columns: + id: ROWKE$STRING + ... + type: TYPE$BYTE + ... +``` +类型转换涉及到Java类型和Phoenix类型两种, 分别定义如下: +``` +#Java 类型转换, 对应配置 mode: NATIVE +$DEFAULT +$STRING +$INTEGER +$LONG +$SHORT +$BOOLEAN +$FLOAT +$DOUBLE +$BIGDECIMAL +$DATE +$BYTE +$BYTES +``` +``` +#Phoenix 类型转换, 对应配置 mode: PHOENIX +$DEFAULT 对应PHOENIX里的VARCHAR +$UNSIGNED_INT 对应PHOENIX里的UNSIGNED_INT 4字节 +$UNSIGNED_LONG 对应PHOENIX里的UNSIGNED_LONG 8字节 +$UNSIGNED_TINYINT 对应PHOENIX里的UNSIGNED_TINYINT 1字节 +$UNSIGNED_SMALLINT 对应PHOENIX里的UNSIGNED_SMALLINT 2字节 +$UNSIGNED_FLOAT 对应PHOENIX里的UNSIGNED_FLOAT 4字节 +$UNSIGNED_DOUBLE 对应PHOENIX里的UNSIGNED_DOUBLE 8字节 +$INTEGER 对应PHOENIX里的INTEGER 4字节 +$BIGINT 对应PHOENIX里的BIGINT 8字节 +$TINYINT 对应PHOENIX里的TINYINT 1字节 +$SMALLINT 对应PHOENIX里的SMALLINT 2字节 +$FLOAT 对应PHOENIX里的FLOAT 4字节 +$DOUBLE 对应PHOENIX里的DOUBLE 8字节 +$BOOLEAN 对应PHOENIX里的BOOLEAN 1字节 +$TIME 对应PHOENIX里的TIME 8字节 +$DATE 对应PHOENIX里的DATE 8字节 +$TIMESTAMP 对应PHOENIX里的TIMESTAMP 12字节 +$UNSIGNED_TIME 对应PHOENIX里的UNSIGNED_TIME 8字节 +$UNSIGNED_DATE 对应PHOENIX里的UNSIGNED_DATE 8字节 +$UNSIGNED_TIMESTAMP 对应PHOENIX里的UNSIGNED_TIMESTAMP 12字节 +$VARCHAR 对应PHOENIX里的VARCHAR 动态长度 +$VARBINARY 对应PHOENIX里的VARBINARY 动态长度 +$DECIMAL 对应PHOENIX里的DECIMAL 动态长度 +``` +如果不配置将以java对象原生类型默认映射转换 +### 3.3 启动HBase数据同步 +#### 创建HBase表 +在HBase shell中运行: +``` +create 'MYTEST.PERSON', {NAME=>'CF'} +``` +#### 启动canal-adapter启动器 +``` +bin/startup.sh +``` +#### 验证 +修改mysql mytest.person表的数据, 将会自动同步到HBase的MYTEST.PERSON表下面, 并会打出DML的log + + +## 四、关系型数据库适配器 + +RDB adapter 用于适配mysql到任意关系型数据库(需支持jdbc)的数据同步及导入 + +### 4.1 修改启动器配置: application.yml, 这里以oracle目标库为例 +``` +server: + port: 8081 +logging: + level: + com.alibaba.otter.canal.client.adapter.rdb: DEBUG +...... + +canal.conf: + canalServerHost: 127.0.0.1:11111 + srcDataSources: + defaultDS: + url: jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true + username: root + password: 121212 + canalInstances: + - instance: example + groups: + - outAdapters: + - name: rdb # 指定为rdb类型同步 + key: oracle1 # 指定adapter的唯一key, 与表映射配置中outerAdapterKey对应 + properties: + jdbc.driverClassName: oracle.jdbc.OracleDriver # jdbc驱动名, jdbc的jar包需要自行放致lib目录下 + jdbc.url: jdbc:oracle:thin:@localhost:49161:XE # jdbc url + jdbc.username: mytest # jdbc username + jdbc.password: m121212 # jdbc password + threads: 5 # 并行执行的线程数, 默认为1 + commitSize: 3000 # 批次提交的最大行数 +``` +其中 outAdapter 的配置: name统一为rdb, key为对应的数据源的唯一标识需和下面的表映射文件中的outerAdapterKey对应, properties为目标库jdb的相关参数 +adapter将会自动加载 conf/rdb 下的所有.yml结尾的表映射配置文件 + +### 4.2 适配器表映射文件 +修改 conf/rdb/mytest_user.yml文件: +``` +dataSourceKey: defaultDS # 源数据源的key, 对应上面配置的srcDataSources中的值 +destination: example # cannal的instance或者MQ的topic +outerAdapterKey: oracle1 # adapter key, 对应上面配置outAdapters中的key +concurrent: true # 是否按主键hase并行同步, 并行同步的表必须保证主键不会更改及主键不能为其他同步表的外键!! +dbMapping: + database: mytest # 源数据源的database/shcema + table: user # 源数据源表名 + targetTable: mytest.tb_user # 目标数据源的库名.表名 + targetPk: # 主键映射 + id: id # 如果是复合主键可以换行映射多个 +# mapAll: true # 是否整表映射, 要求源表和目标表字段名一模一样 (如果targetColumns也配置了映射,则以targetColumns配置为准) + targetColumns: # 字段映射, 格式: 目标表字段: 源表字段, 如果字段名一样源表字段名可不填 + id: + name: + role_id: + c_time: + test1: +``` +导入的类型以目标表的元类型为准, 将自动转换 + +### 4.3 启动RDB数据同步 +#### 将目标库的jdbc jar包放入lib文件夹, 这里放入ojdbc6.jar + +#### 启动canal-adapter启动器 +``` +bin/startup.sh +``` +#### 验证 +修改mysql mytest.user表的数据, 将会自动同步到Oracle的MYTEST.TB_USER表下面, 并会打出DML的log + + +## 五、ElasticSearch适配器 +### 5.1 修改启动器配置: application.yml +``` +server: + port: 8081 +logging: + level: + com.alibaba.otter.canal.client.adapter.es: DEBUG +spring: + jackson: + date-format: yyyy-MM-dd HH:mm:ss + time-zone: GMT+8 + default-property-inclusion: non_null + +canal.conf: + canalServerHost: 127.0.0.1:11111 + flatMessage: true + srcDataSources: + defaultDS: + url: jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true + username: root + password: 121212 + canalInstances: + - instance: example + adapterGroups: + - outAdapters: + - name: es + hosts: 127.0.0.1:9300 # es 集群地址, 逗号分隔 + properties: + cluster.name: elasticsearch # es cluster name +``` +adapter将会自动加载 conf/es 下的所有.yml结尾的配置文件 +### 5.2 适配器表映射文件 +修改 conf/es/mytest_user.yml文件: +``` +dataSourceKey: defaultDS # 源数据源的key, 对应上面配置的srcDataSources中的值 +destination: example # cannal的instance或者MQ的topic +esMapping: + _index: mytest_user # es 的索引名称 + _type: _doc # es 的doc名称 + _id: _id # es 的_id, 如果不配置该项必须配置下面的pk项_id则会由es自动分配 +# pk: id # 如果不需要_id, 则需要指定一个属性为主键属性 + # sql映射 + sql: "select a.id as _id, a.name as _name, a.role_id as _role_id, b.role_name as _role_name, + a.c_time as _c_time, c.labels as _labels from user a + left join role b on b.id=a.role_id + left join (select user_id, group_concat(label order by id desc separator ';') as labels from label + group by user_id) c on c.user_id=a.id" +# objFields: +# _labels: array:; # 数组或者对象属性, array:; 代表以;字段里面是以;分隔的 +# _obj: obj:{"test":"123"} + etlCondition: "where a.c_time>='{0}'" # etl 的条件参数 + commitBatch: 3000 # 提交批大小 +``` +sql映射说明: + +sql支持多表关联自由组合, 但是有一定的限制: +1. 主表不能为子查询语句 +2. 只能使用left outer join即最左表一定要是主表 +3. 关联从表如果是子查询不能有多张表 +4. 主sql中不能有where查询条件(从表子查询中可以有where条件但是不推荐, 可能会造成数据同步的不一致, 比如修改了where条件中的字段内容) +5. 关联条件只允许主外键的'='操作不能出现其他常量判断比如: on a.role_id=b.id and b.statues=1 +6. 关联条件必须要有一个字段出现在主查询语句中比如: on a.role_id=b.id 其中的 a.role_id 或者 b.id 必须出现在主select语句中 + + +Elastic Search的mapping 属性与sql的查询值将一一对应(不支持 select *), 比如: select a.id as _id, a.name, a.email as _email from user, 其中name将映射到es mapping的name field, _email将 +映射到mapping的_email field, 这里以别名(如果有别名)作为最终的映射字段. 这里的_id可以填写到配置文件的 _id: _id映射. + +#### 5.2.1.单表映射索引示例sql: +``` +select a.id as _id, a.name, a.role_id, a.c_time from user a +``` +该sql对应的es mapping示例: +``` +{ + "mytest_user": { + "mappings": { + "_doc": { + "properties": { + "name": { + "type": "text" + }, + "role_id": { + "type": "long" + }, + "c_time": { + "type": "date" + } + } + } + } + } +} +``` + +#### 5.2.2.单表映射索引示例sql带函数或运算操作: +``` +select a.id as _id, concat(a.name,'_test') as name, a.role_id+10000 as role_id, a.c_time from user a +``` +函数字段后必须跟上别名, 该sql对应的es mapping示例: +``` +{ + "mytest_user": { + "mappings": { + "_doc": { + "properties": { + "name": { + "type": "text" + }, + "role_id": { + "type": "long" + }, + "c_time": { + "type": "date" + } + } + } + } + } +} +``` + +#### 5.2.3.多表映射(一对一, 多对一)索引示例sql: +``` +select a.id as _id, a.name, a.role_id, b.role_name, a.c_time from user a +left join role b on b.id = a.role_id +``` +注:这里join操作只能是left outer join, 第一张表必须为主表!! + +该sql对应的es mapping示例: +``` +{ + "mytest_user": { + "mappings": { + "_doc": { + "properties": { + "name": { + "type": "text" + }, + "role_id": { + "type": "long" + }, + "role_name": { + "type": "text" + }, + "c_time": { + "type": "date" + } + } + } + } + } +} +``` + +#### 5.2.4.多表映射(一对多)索引示例sql: +``` +select a.id as _id, a.name, a.role_id, c.labels, a.c_time from user a +left join (select user_id, group_concat(label order by id desc separator ';') as labels from label + group by user_id) c on c.user_id=a.id +``` +注:left join 后的子查询只允许一张表, 即子查询中不能再包含子查询或者关联!! + +该sql对应的es mapping示例: +``` +{ + "mytest_user": { + "mappings": { + "_doc": { + "properties": { + "name": { + "type": "text" + }, + "role_id": { + "type": "long" + }, + "c_time": { + "type": "date" + }, + "labels": { + "type": "text" + } + } + } + } + } +} +``` + +#### 5.2.5.其它类型的sql示例: +- geo type +``` +select ... concat(IFNULL(a.latitude, 0), ',', IFNULL(a.longitude, 0)) AS location, ... +``` +- 复合主键 +``` +select concat(a.id,'_',b.type) as _id, ... from user a left join role b on b.id=a.role_id +``` +- 数组字段 +``` +select a.id as _id, a.name, a.role_id, c.labels, a.c_time from user a +left join (select user_id, group_concat(label order by id desc separator ';') as labels from label + group by user_id) c on c.user_id=a.id +``` +配置中使用: +``` +objFields: + labels: array:; +``` + +### 5.3 启动ES数据同步 +#### 启动canal-adapter启动器 +``` +bin/startup.sh +``` +#### 验证 +1. 新增mysql mytest.user表的数据, 将会自动同步到es的mytest_user索引下面, 并会打出DML的log +2. 修改mysql mytest.role表的role_name, 将会自动同步es的mytest_user索引中的role_name数据 +3. 新增或者修改mysql mytest.label表的label, 将会自动同步es的mytest_user索引中的labels数据 \ No newline at end of file diff --git a/client-adapter/common/pom.xml b/client-adapter/common/pom.xml new file mode 100644 index 00000000..8a6d75fa --- /dev/null +++ b/client-adapter/common/pom.xml @@ -0,0 +1,36 @@ + + + + canal.client-adapter + com.alibaba.otter + 1.1.3-SNAPSHOT + + 4.0.0 + com.alibaba.otter + client-adapter.common + jar + canal client adapter common module for otter ${project.version} + + + com.alibaba.otter + canal.protocol + 1.1.3-SNAPSHOT + + + joda-time + joda-time + 2.9.4 + + + com.alibaba + druid + 1.1.9 + + + mysql + mysql-connector-java + 5.1.40 + + + + diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/OuterAdapter.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/OuterAdapter.java new file mode 100644 index 00000000..37786222 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/OuterAdapter.java @@ -0,0 +1,68 @@ +package com.alibaba.otter.canal.client.adapter; + +import java.util.List; +import java.util.Map; + +import com.alibaba.otter.canal.client.adapter.support.Dml; +import com.alibaba.otter.canal.client.adapter.support.EtlResult; +import com.alibaba.otter.canal.client.adapter.support.OuterAdapterConfig; +import com.alibaba.otter.canal.client.adapter.support.SPI; + +/** + * 外部适配器接口 + * + * @author reweerma 2018-8-18 下午10:14:02 + * @version 1.0.0 + */ +@SPI("logger") +public interface OuterAdapter { + + /** + * 外部适配器初始化接口 + * + * @param configuration 外部适配器配置信息 + */ + void init(OuterAdapterConfig configuration); + + /** + * 往适配器中同步数据 + * + * @param dmls 数据包 + */ + void sync(List dmls); + + /** + * 外部适配器销毁接口 + */ + void destroy(); + + /** + * Etl操作 + * + * @param task 任务名, 对应配置名 + * @param params etl筛选条件 + */ + default EtlResult etl(String task, List params) { + throw new UnsupportedOperationException("unsupported operation"); + } + + /** + * 计算总数 + * + * @param task 任务名, 对应配置名 + * @return 总数 + */ + default Map count(String task) { + throw new UnsupportedOperationException("unsupported operation"); + } + + /** + * 通过task获取对应的destination + * + * @param task 任务名, 对应配置名 + * @return destination + */ + default String getDestination(String task) { + return null; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/CanalClientConfig.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/CanalClientConfig.java new file mode 100644 index 00000000..3574b678 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/CanalClientConfig.java @@ -0,0 +1,192 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; + +/** + * 配置信息类 + * + * @author rewerma 2018-8-18 下午10:40:12 + * @version 1.0.0 + */ +public class CanalClientConfig { + + // 单机模式下canal server的ip:port + private String canalServerHost; + // 集群模式下的zk地址,如果配置了单机地址则以单机为准!! + private String zookeeperHosts; + // kafka or rocket mq 地址 + private String mqServers; + // 是否已flatMessage模式传输,只适用于mq模式 + private Boolean flatMessage = true; + // 批大小 + private Integer batchSize; + // 同步分批提交大小 + private Integer syncBatchSize = 1000; + // 重试次数 + private Integer retries; + // 消费超时时间 + private Long timeout; + // 模式 tcp kafka rocketMQ + private String mode = "tcp"; + // aliyun ak/sk + private String accessKey; + private String secretKey; + + // canal adapters 配置 + private List canalAdapters; + + public String getCanalServerHost() { + return canalServerHost; + } + + public void setCanalServerHost(String canalServerHost) { + this.canalServerHost = canalServerHost; + } + + public String getZookeeperHosts() { + return zookeeperHosts; + } + + public void setZookeeperHosts(String zookeeperHosts) { + this.zookeeperHosts = zookeeperHosts; + } + + public String getMqServers() { + return mqServers; + } + + public void setMqServers(String mqServers) { + this.mqServers = mqServers; + } + + public Boolean getFlatMessage() { + return flatMessage; + } + + public void setFlatMessage(Boolean flatMessage) { + this.flatMessage = flatMessage; + } + + public Integer getBatchSize() { + return batchSize; + } + + public void setBatchSize(Integer batchSize) { + this.batchSize = batchSize; + } + + public Integer getRetries() { + return retries; + } + + public Integer getSyncBatchSize() { + return syncBatchSize; + } + + public void setSyncBatchSize(Integer syncBatchSize) { + this.syncBatchSize = syncBatchSize; + } + + public void setRetries(Integer retries) { + this.retries = retries; + } + + public Long getTimeout() { + return timeout; + } + + public void setTimeout(Long timeout) { + this.timeout = timeout; + } + + public String getMode() { + return mode; + } + + public void setMode(String mode) { + this.mode = mode; + } + + public String getAccessKey() { + return accessKey; + } + + public void setAccessKey(String accessKey) { + this.accessKey = accessKey; + } + + public String getSecretKey() { + return secretKey; + } + + public void setSecretKey(String secretKey) { + this.secretKey = secretKey; + } + + public List getCanalAdapters() { + return canalAdapters; + } + + public void setCanalAdapters(List canalAdapters) { + this.canalAdapters = canalAdapters; + } + + public static class CanalAdapter { + + private String instance; // 实例名 + + private List groups; // 适配器分组列表 + + public String getInstance() { + return instance; + } + + public void setInstance(String instance) { + if (instance != null) { + this.instance = instance.trim(); + } + } + + public List getGroups() { + return groups; + } + + public void setGroups(List groups) { + this.groups = groups; + } + } + + public static class Group { + + // group id + private String groupId = "default"; + private List outerAdapters; // 适配器列表 + private Map outerAdaptersMap = new LinkedHashMap<>(); + + public String getGroupId() { + return groupId; + } + + public void setGroupId(String groupId) { + this.groupId = groupId; + } + + public List getOuterAdapters() { + return outerAdapters; + } + + public void setOuterAdapters(List outerAdapters) { + this.outerAdapters = outerAdapters; + } + + public Map getOuterAdaptersMap() { + return outerAdaptersMap; + } + + public void setOuterAdaptersMap(Map outerAdaptersMap) { + this.outerAdaptersMap = outerAdaptersMap; + } + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Constant.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Constant.java new file mode 100644 index 00000000..9a75f765 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Constant.java @@ -0,0 +1,6 @@ +package com.alibaba.otter.canal.client.adapter.support; + +public class Constant { + + public static final String CONF_DIR = "conf"; +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/DatasourceConfig.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/DatasourceConfig.java new file mode 100644 index 00000000..acc07dd1 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/DatasourceConfig.java @@ -0,0 +1,81 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +import com.alibaba.druid.pool.DruidDataSource; + +/** + * 数据源配置 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +public class DatasourceConfig { + + public final static Map DATA_SOURCES = new ConcurrentHashMap<>(); // key对应的数据源 + + private String driver = "com.mysql.jdbc.Driver"; // 默认为mysql jdbc驱动 + private String url; // jdbc url + private String database; // jdbc database + private String type = "mysql"; // 类型, 默认为mysql + private String username; // jdbc username + private String password; // jdbc password + private Integer maxActive = 3; // 连接池最大连接数,默认为3 + + public String getDriver() { + return driver; + } + + public void setDriver(String driver) { + this.driver = driver; + } + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + this.url = url; + } + + public String getDatabase() { + return database; + } + + public void setDatabase(String database) { + this.database = database; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + public String getUsername() { + return username; + } + + public void setUsername(String username) { + this.username = username; + } + + public String getPassword() { + return password; + } + + public void setPassword(String password) { + this.password = password; + } + + public Integer getMaxActive() { + return maxActive; + } + + public void setMaxActive(Integer maxActive) { + this.maxActive = maxActive; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Dml.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Dml.java new file mode 100644 index 00000000..1d5357b4 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Dml.java @@ -0,0 +1,118 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.io.Serializable; +import java.util.List; +import java.util.Map; + +/** + * DML操作转换对象 + * + * @author rewerma 2018-8-19 下午11:30:49 + * @version 1.0.0 + */ +public class Dml implements Serializable { + + private static final long serialVersionUID = 2611556444074013268L; + + private String destination; // 对应canal的实例或者MQ的topic + private String database; // 数据库或schema + private String table; // 表名 + private String type; // 类型: INSERT UPDATE DELETE + // binlog executeTime + private Long es; // 执行耗时 + // dml build timeStamp + private Long ts; // 同步时间 + private String sql; // 执行的sql, dml sql为空 + private List> data; // 数据列表 + private List> old; // 旧数据列表, 用于update, size和data的size一一对应 + + public String getDestination() { + return destination; + } + + public void setDestination(String destination) { + this.destination = destination; + } + + public String getDatabase() { + return database; + } + + public void setDatabase(String database) { + this.database = database; + } + + public String getTable() { + return table; + } + + public void setTable(String table) { + this.table = table; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + public Long getTs() { + return ts; + } + + public void setTs(Long ts) { + this.ts = ts; + } + + public String getSql() { + return sql; + } + + public void setSql(String sql) { + this.sql = sql; + } + + public List> getData() { + return data; + } + + public void setData(List> data) { + this.data = data; + } + + public List> getOld() { + return old; + } + + public void setOld(List> old) { + this.old = old; + } + + public Long getEs() { + return es; + } + + public void setEs(Long es) { + this.es = es; + } + + public void clear() { + database = null; + table = null; + type = null; + ts = null; + es = null; + data = null; + old = null; + sql = null; + } + + @Override + public String toString() { + return "Dml{" + "destination='" + destination + '\'' + ", database='" + database + '\'' + ", table='" + table + + '\'' + ", type='" + type + '\'' + ", es=" + es + ", ts=" + ts + ", sql='" + sql + '\'' + ", data=" + + data + ", old=" + old + '}'; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/EtlResult.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/EtlResult.java new file mode 100644 index 00000000..498af7a3 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/EtlResult.java @@ -0,0 +1,44 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.io.Serializable; + +/** + * ETL的结果对象 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +public class EtlResult implements Serializable { + + private static final long serialVersionUID = 4250522736289866505L; + + private boolean succeeded = false; + + private String resultMessage; + + private String errorMessage; + + public boolean getSucceeded() { + return succeeded; + } + + public void setSucceeded(boolean succeeded) { + this.succeeded = succeeded; + } + + public String getResultMessage() { + return resultMessage; + } + + public void setResultMessage(String resultMessage) { + this.resultMessage = resultMessage; + } + + public String getErrorMessage() { + return errorMessage; + } + + public void setErrorMessage(String errorMessage) { + this.errorMessage = errorMessage; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/ExtensionLoader.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/ExtensionLoader.java new file mode 100644 index 00000000..41d1864e --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/ExtensionLoader.java @@ -0,0 +1,421 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.io.BufferedReader; +import java.io.File; +import java.io.InputStreamReader; +import java.net.MalformedURLException; +import java.net.URL; +import java.net.URLClassLoader; +import java.nio.file.Paths; +import java.util.Arrays; +import java.util.Enumeration; +import java.util.HashMap; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import java.util.regex.Pattern; + +import org.apache.commons.lang.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +/** + * SPI 类加载器 + * + * @author rewerma 2018-8-19 下午11:30:49 + * @version 1.0.0 + */ +public class ExtensionLoader { + + private static final Logger logger = LoggerFactory.getLogger(ExtensionLoader.class); + + private static final String SERVICES_DIRECTORY = "META-INF/services/"; + + private static final String CANAL_DIRECTORY = "META-INF/canal/"; + + private static final String DEFAULT_CLASSLOADER_POLICY = "internal"; + + private static final Pattern NAME_SEPARATOR = Pattern.compile("\\s*[,]+\\s*"); + + private static final ConcurrentMap, ExtensionLoader> EXTENSION_LOADERS = new ConcurrentHashMap<>(); + + private static final ConcurrentMap, Object> EXTENSION_INSTANCES = new ConcurrentHashMap<>(); + + private static final ConcurrentMap EXTENSION_KEY_INSTANCE = new ConcurrentHashMap<>(); + + private final Class type; + + private final String classLoaderPolicy; + + private final ConcurrentMap, String> cachedNames = new ConcurrentHashMap<>(); + + private final Holder>> cachedClasses = new Holder<>(); + + private final ConcurrentMap> cachedInstances = new ConcurrentHashMap<>(); + + private String cachedDefaultName; + + private ConcurrentHashMap exceptions = new ConcurrentHashMap<>(); + + private static boolean withExtensionAnnotation(Class type) { + return type.isAnnotationPresent(SPI.class); + } + + public static ExtensionLoader getExtensionLoader(Class type) { + return getExtensionLoader(type, DEFAULT_CLASSLOADER_POLICY); + } + + @SuppressWarnings("unchecked") + public static ExtensionLoader getExtensionLoader(Class type, String classLoaderPolicy) { + if (type == null) throw new IllegalArgumentException("Extension type == null"); + if (!type.isInterface()) { + throw new IllegalArgumentException("Extension type(" + type + ") is not interface!"); + } + if (!withExtensionAnnotation(type)) { + throw new IllegalArgumentException("Extension type(" + type + ") is not extension, because WITHOUT @" + + SPI.class.getSimpleName() + " Annotation!"); + } + + ExtensionLoader loader = (ExtensionLoader) EXTENSION_LOADERS.get(type); + if (loader == null) { + EXTENSION_LOADERS.putIfAbsent(type, new ExtensionLoader(type, classLoaderPolicy)); + loader = (ExtensionLoader) EXTENSION_LOADERS.get(type); + } + return loader; + } + + private ExtensionLoader(Class type, String classLoaderPolicy){ + this.type = type; + this.classLoaderPolicy = classLoaderPolicy; + } + + /** + * 返回指定名字的扩展 + * + * @param name + * @return + */ + @SuppressWarnings("unchecked") + public T getExtension(String name) { + if (name == null || name.length() == 0) throw new IllegalArgumentException("Extension name == null"); + if ("true".equals(name)) { + return getDefaultExtension(); + } + Holder holder = cachedInstances.get(name); + if (holder == null) { + cachedInstances.putIfAbsent(name, new Holder<>()); + holder = cachedInstances.get(name); + } + Object instance = holder.get(); + if (instance == null) { + synchronized (holder) { + instance = holder.get(); + if (instance == null) { + instance = createExtension(name); + holder.set(instance); + } + } + } + return (T) instance; + } + + @SuppressWarnings("unchecked") + public T getExtension(String name, String key) { + if (name == null || name.length() == 0) throw new IllegalArgumentException("Extension name == null"); + if ("true".equals(name)) { + return getDefaultExtension(); + } + String extKey = name + "-" + StringUtils.trimToEmpty(key); + Holder holder = cachedInstances.get(extKey); + if (holder == null) { + cachedInstances.putIfAbsent(extKey, new Holder<>()); + holder = cachedInstances.get(extKey); + } + Object instance = holder.get(); + if (instance == null) { + synchronized (holder) { + instance = holder.get(); + if (instance == null) { + instance = createExtension(name, key); + holder.set(instance); + } + } + } + return (T) instance; + } + + /** + * 返回缺省的扩展,如果没有设置则返回null + */ + public T getDefaultExtension() { + getExtensionClasses(); + if (null == cachedDefaultName || cachedDefaultName.length() == 0 || "true".equals(cachedDefaultName)) { + return null; + } + return getExtension(cachedDefaultName); + } + + @SuppressWarnings("unchecked") + private T createExtension(String name) { + Class clazz = getExtensionClasses().get(name); + if (clazz == null) { + throw new IllegalStateException("Extension instance(name: " + name + ", class: " + type + + ") could not be instantiated: class could not be found"); + } + try { + T instance = (T) EXTENSION_INSTANCES.get(clazz); + if (instance == null) { + EXTENSION_INSTANCES.putIfAbsent(clazz, (T) clazz.newInstance()); + instance = (T) EXTENSION_INSTANCES.get(clazz); + } + return instance; + } catch (Throwable t) { + throw new IllegalStateException("Extension instance(name: " + name + ", class: " + type + + ") could not be instantiated: " + t.getMessage(), t); + } + } + + @SuppressWarnings("unchecked") + private T createExtension(String name, String key) { + Class clazz = getExtensionClasses().get(name); + if (clazz == null) { + throw new IllegalStateException("Extension instance(name: " + name + ", class: " + type + + ") could not be instantiated: class could not be found"); + } + try { + T instance = (T) EXTENSION_KEY_INSTANCE.get(name + "-" + key); + if (instance == null) { + EXTENSION_KEY_INSTANCE.putIfAbsent(name + "-" + key, clazz.newInstance()); + instance = (T) EXTENSION_KEY_INSTANCE.get(name + "-" + key); + } + return instance; + } catch (Throwable t) { + throw new IllegalStateException("Extension instance(name: " + name + ", class: " + type + + ") could not be instantiated: " + t.getMessage(), t); + } + } + + private Map> getExtensionClasses() { + Map> classes = cachedClasses.get(); + if (classes == null) { + synchronized (cachedClasses) { + classes = cachedClasses.get(); + if (classes == null) { + classes = loadExtensionClasses(); + cachedClasses.set(classes); + } + } + } + + return classes; + } + + private String getJarDirectoryPath() { + URL url = Thread.currentThread().getContextClassLoader().getResource(""); + String dirtyPath; + if (url != null) { + dirtyPath = url.toString(); + } else { + File file = new File(""); + dirtyPath = file.getAbsolutePath(); + } + String jarPath = dirtyPath.replaceAll("^.*file:/", ""); // removes + // file:/ and + // everything + // before it + jarPath = jarPath.replaceAll("jar!.*", "jar"); // removes everything + // after .jar, if .jar + // exists in dirtyPath + jarPath = jarPath.replaceAll("%20", " "); // necessary if path has + // spaces within + if (!jarPath.endsWith(".jar")) { // this is needed if you plan to run + // the app using Spring Tools Suit play + // button. + jarPath = jarPath.replaceAll("/classes/.*", "/classes/"); + } + return Paths.get(jarPath).getParent().toString(); // Paths - from java 8 + } + + private Map> loadExtensionClasses() { + final SPI defaultAnnotation = type.getAnnotation(SPI.class); + if (defaultAnnotation != null) { + String value = defaultAnnotation.value(); + if ((value = value.trim()).length() > 0) { + String[] names = NAME_SEPARATOR.split(value); + if (names.length > 1) { + throw new IllegalStateException("more than 1 default extension name on extension " + type.getName() + + ": " + Arrays.toString(names)); + } + if (names.length == 1) cachedDefaultName = names[0]; + } + } + + Map> extensionClasses = new HashMap>(); + + // 1. plugin folder,customized extension classLoader (jar_dir/plugin) + String dir = File.separator + this.getJarDirectoryPath() + File.separator + "plugin"; + + File externalLibDir = new File(dir); + if (!externalLibDir.exists()) { + externalLibDir = new File(File.separator + this.getJarDirectoryPath() + File.separator + "canal-adapter" + + File.separator + "plugin"); + } + logger.info("extension classpath dir: " + externalLibDir.getAbsolutePath()); + if (externalLibDir.exists()) { + File[] files = externalLibDir.listFiles((dir1, name) -> name.endsWith(".jar")); + if (files != null) { + for (File f : files) { + URL url; + try { + url = f.toURI().toURL(); + } catch (MalformedURLException e) { + throw new RuntimeException("load extension jar failed!", e); + } + + ClassLoader parent = Thread.currentThread().getContextClassLoader(); + URLClassLoader localClassLoader; + if (classLoaderPolicy == null || "".equals(classLoaderPolicy) + || DEFAULT_CLASSLOADER_POLICY.equalsIgnoreCase(classLoaderPolicy)) { + localClassLoader = new URLClassExtensionLoader(new URL[] { url }); + } else { + localClassLoader = new URLClassLoader(new URL[] { url }, parent); + } + + loadFile(extensionClasses, CANAL_DIRECTORY, localClassLoader); + loadFile(extensionClasses, SERVICES_DIRECTORY, localClassLoader); + } + } + } + // 只加载外部spi, 不加载classpath + // 2. load inner extension class with default classLoader + // ClassLoader classLoader = findClassLoader(); + // loadFile(extensionClasses, CANAL_DIRECTORY, classLoader); + // loadFile(extensionClasses, SERVICES_DIRECTORY, classLoader); + + return extensionClasses; + } + + private void loadFile(Map> extensionClasses, String dir, ClassLoader classLoader) { + String fileName = dir + type.getName(); + try { + Enumeration urls; + if (classLoader != null) { + urls = classLoader.getResources(fileName); + } else { + urls = ClassLoader.getSystemResources(fileName); + } + if (urls != null) { + while (urls.hasMoreElements()) { + URL url = urls.nextElement(); + try { + BufferedReader reader = null; + try { + reader = new BufferedReader(new InputStreamReader(url.openStream(), "utf-8")); + String line = null; + while ((line = reader.readLine()) != null) { + final int ci = line.indexOf('#'); + if (ci >= 0) line = line.substring(0, ci); + line = line.trim(); + if (line.length() > 0) { + try { + String name = null; + int i = line.indexOf('='); + if (i > 0) { + name = line.substring(0, i).trim(); + line = line.substring(i + 1).trim(); + } + if (line.length() > 0) { + Class clazz = classLoader.loadClass(line); + // Class clazz = + // Class.forName(line, true, + // classLoader); + if (!type.isAssignableFrom(clazz)) { + throw new IllegalStateException("Error when load extension class(interface: " + + type + + ", class line: " + + clazz.getName() + + "), class " + + clazz.getName() + + "is not subtype of interface."); + } else { + try { + clazz.getConstructor(type); + } catch (NoSuchMethodException e) { + clazz.getConstructor(); + String[] names = NAME_SEPARATOR.split(name); + if (names != null && names.length > 0) { + for (String n : names) { + if (!cachedNames.containsKey(clazz)) { + cachedNames.put(clazz, n); + } + Class c = extensionClasses.get(n); + if (c == null) { + extensionClasses.put(n, clazz); + } else if (c != clazz) { + cachedNames.remove(clazz); + throw new IllegalStateException("Duplicate extension " + + type.getName() + + " name " + n + " on " + + c.getName() + " and " + + clazz.getName()); + } + } + } + } + } + } + } catch (Throwable t) { + IllegalStateException e = new IllegalStateException("Failed to load extension class(interface: " + + type + + ", class line: " + + line + + ") in " + + url + + ", cause: " + + t.getMessage(), + t); + exceptions.put(line, e); + } + } + } // end of while read lines + } finally { + if (reader != null) { + reader.close(); + } + } + } catch (Throwable t) { + logger.error("Exception when load extension class(interface: " + type + ", class file: " + url + + ") in " + url, t); + } + } // end of while urls + } + } catch (Throwable t) { + logger.error("Exception when load extension class(interface: " + type + ", description file: " + fileName + + ").", t); + } + } + + @SuppressWarnings("unused") + private static ClassLoader findClassLoader() { + return ExtensionLoader.class.getClassLoader(); + } + + @Override + public String toString() { + return this.getClass().getName() + "[" + type.getName() + "]"; + } + + private static class Holder { + + private volatile T value; + + private void set(T value) { + this.value = value; + } + + private T get() { + return value; + } + + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/JdbcTypeUtil.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/JdbcTypeUtil.java new file mode 100644 index 00000000..c24ff7de --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/JdbcTypeUtil.java @@ -0,0 +1,149 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.math.BigDecimal; +import java.math.BigInteger; +import java.sql.*; + +import org.joda.time.DateTime; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +/** + * 类型转换工具类 + * + * @author rewerma 2018-8-19 下午06:14:23 + * @version 1.0.0 + */ +public class JdbcTypeUtil { + + private static Logger logger = LoggerFactory.getLogger(JdbcTypeUtil.class); + + public static Object getRSData(ResultSet rs, String columnName, int jdbcType) throws SQLException { + if (jdbcType == Types.BIT || jdbcType == Types.BOOLEAN) { + return rs.getByte(columnName); + } else { + return rs.getObject(columnName); + } + } + + public static Class jdbcType2javaType(int jdbcType) { + switch (jdbcType) { + case Types.BIT: + case Types.BOOLEAN: + // return Boolean.class; + case Types.TINYINT: + return Byte.TYPE; + case Types.SMALLINT: + return Short.class; + case Types.INTEGER: + return Integer.class; + case Types.BIGINT: + return Long.class; + case Types.DECIMAL: + case Types.NUMERIC: + return BigDecimal.class; + case Types.REAL: + return Float.class; + case Types.FLOAT: + case Types.DOUBLE: + return Double.class; + case Types.CHAR: + case Types.VARCHAR: + case Types.LONGVARCHAR: + return String.class; + case Types.BINARY: + case Types.VARBINARY: + case Types.LONGVARBINARY: + case Types.BLOB: + return byte[].class; + case Types.DATE: + return java.sql.Date.class; + case Types.TIME: + return Time.class; + case Types.TIMESTAMP: + return Timestamp.class; + default: + return String.class; + } + } + + public static Object typeConvert(String columnName, String value, int sqlType, String mysqlType) { + if (value == null || value.equals("")) { + return null; + } + + try { + Object res; + switch (sqlType) { + case Types.INTEGER: + res = Integer.parseInt(value); + break; + case Types.SMALLINT: + res = Short.parseShort(value); + break; + case Types.BIT: + case Types.TINYINT: + res = Byte.parseByte(value); + break; + case Types.BIGINT: + if (mysqlType.startsWith("bigint") && mysqlType.endsWith("unsigned")) { + res = new BigInteger(value); + } else { + res = Long.parseLong(value); + } + break; + // case Types.BIT: + case Types.BOOLEAN: + res = !"0".equals(value); + break; + case Types.DOUBLE: + case Types.FLOAT: + res = Double.parseDouble(value); + break; + case Types.REAL: + res = Float.parseFloat(value); + break; + case Types.DECIMAL: + case Types.NUMERIC: + res = new BigDecimal(value); + break; + case Types.BINARY: + case Types.VARBINARY: + case Types.LONGVARBINARY: + case Types.BLOB: + res = value.getBytes("ISO-8859-1"); + break; + case Types.DATE: + if (!value.startsWith("0000-00-00")) { + value = value.trim().replace(" ", "T"); + DateTime dt = new DateTime(value); + res = new Date(dt.toDate().getTime()); + } else { + res = null; + } + break; + case Types.TIME: + value = "T" + value; + DateTime dt = new DateTime(value); + res = new Time(dt.toDate().getTime()); + break; + case Types.TIMESTAMP: + if (!value.startsWith("0000-00-00")) { + value = value.trim().replace(" ", "T"); + dt = new DateTime(value); + res = new Timestamp(dt.toDate().getTime()); + } else { + res = null; + } + break; + case Types.CLOB: + default: + res = value; + } + return res; + } catch (Exception e) { + logger.error("table: {} column: {}, failed convert type {} to {}", columnName, value, sqlType); + return value; + } + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/MappingConfigsLoader.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/MappingConfigsLoader.java new file mode 100644 index 00000000..a7c8d7d6 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/MappingConfigsLoader.java @@ -0,0 +1,71 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStream; +import java.net.URL; +import java.nio.charset.StandardCharsets; +import java.util.HashMap; +import java.util.Map; + +public class MappingConfigsLoader { + + public static Map loadConfigs(String name) { + Map configContentMap = new HashMap<>(); + + // 先取本地文件,再取类路径 + File configDir = new File(".." + File.separator + Constant.CONF_DIR + File.separator + name); + if (!configDir.exists()) { + URL url = MappingConfigsLoader.class.getClassLoader().getResource(""); + if (url != null) { + configDir = new File(url.getPath() + name + File.separator); + } + } + + File[] files = configDir.listFiles(); + if (files != null) { + for (File file : files) { + String fileName = file.getName(); + if (!fileName.endsWith(".yml")) { + continue; + } + try (InputStream in = new FileInputStream(file)) { + byte[] bytes = new byte[in.available()]; + in.read(bytes); + String configContent = new String(bytes, StandardCharsets.UTF_8); + configContentMap.put(fileName, configContent); + } catch (IOException e) { + throw new RuntimeException("Read " + name + "mapping config: " + fileName + " error. ", e); + } + } + } + + return configContentMap; + } + + public static String loadConfig(String name) { + // 先取本地文件,再取类路径 + File filePath = new File(".." + File.separator + Constant.CONF_DIR + File.separator + name); + if (!filePath.exists()) { + URL url = MappingConfigsLoader.class.getClassLoader().getResource(""); + if (url != null) { + filePath = new File(url.getPath() + name); + } + } + if (filePath.exists()) { + String fileName = filePath.getName(); + if (!fileName.endsWith(".yml")) { + return null; + } + try (InputStream in = new FileInputStream(filePath)) { + byte[] bytes = new byte[in.available()]; + in.read(bytes); + return new String(bytes, StandardCharsets.UTF_8); + } catch (IOException e) { + throw new RuntimeException("Read mapping config: " + filePath.getAbsolutePath() + " error. ", e); + } + } + return null; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/MessageUtil.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/MessageUtil.java new file mode 100644 index 00000000..e40c9204 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/MessageUtil.java @@ -0,0 +1,181 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.util.ArrayList; +import java.util.HashSet; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.FlatMessage; +import com.alibaba.otter.canal.protocol.Message; + +/** + * Message对象解析工具类 + * + * @author rewerma 2018-8-19 下午06:14:23 + * @version 1.0.0 + */ +public class MessageUtil { + + public static List parse4Dml(String destination, Message message) { + if (message == null) { + return null; + } + List entries = message.getEntries(); + List dmls = new ArrayList(entries.size()); + for (CanalEntry.Entry entry : entries) { + if (entry.getEntryType() == CanalEntry.EntryType.TRANSACTIONBEGIN + || entry.getEntryType() == CanalEntry.EntryType.TRANSACTIONEND) { + continue; + } + + CanalEntry.RowChange rowChange; + try { + rowChange = CanalEntry.RowChange.parseFrom(entry.getStoreValue()); + } catch (Exception e) { + throw new RuntimeException("ERROR ## parser of eromanga-event has an error , data:" + entry.toString(), + e); + } + + CanalEntry.EventType eventType = rowChange.getEventType(); + + final Dml dml = new Dml(); + dml.setDestination(destination); + dml.setDatabase(entry.getHeader().getSchemaName()); + dml.setTable(entry.getHeader().getTableName()); + dml.setType(eventType.toString()); + dml.setEs(entry.getHeader().getExecuteTime()); + dml.setTs(System.currentTimeMillis()); + dml.setSql(rowChange.getSql()); + dmls.add(dml); + List> data = new ArrayList<>(); + List> old = new ArrayList<>(); + + if (!rowChange.getIsDdl()) { + Set updateSet = new HashSet<>(); + for (CanalEntry.RowData rowData : rowChange.getRowDatasList()) { + if (eventType != CanalEntry.EventType.INSERT && eventType != CanalEntry.EventType.UPDATE + && eventType != CanalEntry.EventType.DELETE) { + continue; + } + + Map row = new LinkedHashMap<>(); + List columns; + + if (eventType == CanalEntry.EventType.DELETE) { + columns = rowData.getBeforeColumnsList(); + } else { + columns = rowData.getAfterColumnsList(); + } + + for (CanalEntry.Column column : columns) { + row.put(column.getName(), + JdbcTypeUtil.typeConvert(column.getName(), + column.getValue(), + column.getSqlType(), + column.getMysqlType())); + // 获取update为true的字段 + if (column.getUpdated()) { + updateSet.add(column.getName()); + } + } + if (!row.isEmpty()) { + data.add(row); + } + + if (eventType == CanalEntry.EventType.UPDATE) { + Map rowOld = new LinkedHashMap<>(); + for (CanalEntry.Column column : rowData.getBeforeColumnsList()) { + if (updateSet.contains(column.getName())) { + rowOld.put(column.getName(), + JdbcTypeUtil.typeConvert(column.getName(), + column.getValue(), + column.getSqlType(), + column.getMysqlType())); + } + } + // update操作将记录修改前的值 + if (!rowOld.isEmpty()) { + old.add(rowOld); + } + } + } + if (!data.isEmpty()) { + dml.setData(data); + } + if (!old.isEmpty()) { + dml.setOld(old); + } + } + } + + return dmls; + } + + public static List flatMessage2Dml(String destination, List flatMessages) { + List dmls = new ArrayList(flatMessages.size()); + for (FlatMessage flatMessage : flatMessages) { + Dml dml = flatMessage2Dml(destination, flatMessage); + if (dml != null) { + dmls.add(dml); + } + } + + return dmls; + } + + public static Dml flatMessage2Dml(String destination, FlatMessage flatMessage) { + if (flatMessage == null) { + return null; + } + Dml dml = new Dml(); + dml.setDestination(destination); + dml.setDatabase(flatMessage.getDatabase()); + dml.setTable(flatMessage.getTable()); + dml.setType(flatMessage.getType()); + dml.setTs(flatMessage.getTs()); + dml.setEs(flatMessage.getEs()); + dml.setSql(flatMessage.getSql()); + if (flatMessage.getSqlType() == null || flatMessage.getMysqlType() == null) { + throw new RuntimeException("SqlType or mysqlType is null"); + } + List> data = flatMessage.getData(); + if (data != null) { + dml.setData(changeRows(data, flatMessage.getSqlType(), flatMessage.getMysqlType())); + } + List> old = flatMessage.getOld(); + if (old != null) { + dml.setOld(changeRows(old, flatMessage.getSqlType(), flatMessage.getMysqlType())); + } + return dml; + } + + private static List> changeRows(List> rows, Map sqlTypes, + Map mysqlTypes) { + List> result = new ArrayList<>(); + for (Map row : rows) { + Map resultRow = new LinkedHashMap<>(); + for (Map.Entry entry : row.entrySet()) { + String columnName = entry.getKey(); + String columnValue = entry.getValue(); + + Integer sqlType = sqlTypes.get(columnName); + if (sqlType == null) { + continue; + } + + String mysqlType = mysqlTypes.get(columnName); + if (mysqlType == null) { + continue; + } + + Object finalValue = JdbcTypeUtil.typeConvert(columnName, columnValue, sqlType, mysqlType); + resultRow.put(columnName, finalValue); + } + result.add(resultRow); + } + return result; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/OuterAdapterConfig.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/OuterAdapterConfig.java new file mode 100644 index 00000000..a767b203 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/OuterAdapterConfig.java @@ -0,0 +1,62 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.util.Map; + +/** + * 外部适配器配置信息类 + * + * @author rewerma 2018-8-18 下午10:15:12 + * @version 1.0.0 + */ +public class OuterAdapterConfig { + + private String name; // 适配器名称, 如: logger, hbase, es + + private String key; // 适配器唯一键 + + private String hosts; // 适配器内部的地址, 比如对应es该参数可以填写es的server地址 + + private String zkHosts; // 适配器内部的ZK地址, 比如对应HBase该参数可以填写HBase对应的ZK地址 + + private Map properties; // 其余参数, 可填写适配器中的所需的配置信息 + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getKey() { + return key; + } + + public void setKey(String key) { + this.key = key; + } + + public String getHosts() { + return hosts; + } + + public void setHosts(String hosts) { + this.hosts = hosts; + } + + public Map getProperties() { + return properties; + } + + public void setProperties(Map properties) { + this.properties = properties; + } + + public String getZkHosts() { + return zkHosts; + } + + public void setZkHosts(String zkHosts) { + this.zkHosts = zkHosts; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Result.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Result.java new file mode 100644 index 00000000..6e9a9954 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Result.java @@ -0,0 +1,57 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.io.Serializable; +import java.util.Date; + +/** + * 用于rest的结果返回对象 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +public class Result implements Serializable { + + private static final long serialVersionUID = -3276409502352405716L; + public Integer code = 20000; + public Object data; + public String message; + public Date sysTime; + + public static Result createSuccess(String message) { + Result result = new Result(); + result.setMessage(message); + return result; + } + + public Integer getCode() { + return code; + } + + public void setCode(Integer code) { + this.code = code; + } + + public Object getData() { + return data; + } + + public void setData(Object data) { + this.data = data; + } + + public String getMessage() { + return message; + } + + public void setMessage(String message) { + this.message = message; + } + + public Date getSysTime() { + return sysTime; + } + + public void setSysTime(Date sysTime) { + this.sysTime = sysTime; + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/SPI.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/SPI.java new file mode 100644 index 00000000..b4f89b6a --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/SPI.java @@ -0,0 +1,22 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.lang.annotation.Documented; +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +/** + * SPI装载器注解 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@Documented +@Retention(RetentionPolicy.RUNTIME) +@Target({ ElementType.TYPE }) +public @interface SPI { + + // Default SPI name + String value() default ""; +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/URLClassExtensionLoader.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/URLClassExtensionLoader.java new file mode 100644 index 00000000..725d23e8 --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/URLClassExtensionLoader.java @@ -0,0 +1,88 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.io.IOException; +import java.net.URL; +import java.net.URLClassLoader; +import java.util.Enumeration; +import java.util.NoSuchElementException; + +public class URLClassExtensionLoader extends URLClassLoader { + public URLClassExtensionLoader(URL[] urls) { + super(urls); + } + + @Override + public Class loadClass(String name) throws ClassNotFoundException { + Class c = findLoadedClass(name); + if (c != null) { + return c; + } + + if (name.startsWith("java.") || name.startsWith("org.slf4j.") + || name.startsWith("org.apache.logging") + || name.startsWith("org.apache.commons.logging.")) { + // || name.startsWith("org.apache.hadoop.")) + // { + c = super.loadClass(name); + } + if (c != null) return c; + + try { + // 先加载jar内的class,可避免jar冲突 + c = findClass(name); + } catch (ClassNotFoundException e) { + c = null; + } + if (c != null) { + return c; + } + + return super.loadClass(name); + } + + @Override + public Enumeration getResources(String name) throws IOException { + @SuppressWarnings("unchecked") + Enumeration[] tmp = (Enumeration[]) new Enumeration[2]; + + tmp[0] = findResources(name); // local class + // path first + // tmp[1] = super.getResources(name); + + return new CompoundEnumeration<>(tmp); + } + + private static class CompoundEnumeration implements Enumeration { + + private Enumeration[] enums; + private int index = 0; + + public CompoundEnumeration(Enumeration[] enums){ + this.enums = enums; + } + + private boolean next() { + while (this.index < this.enums.length) { + if (this.enums[this.index] != null && this.enums[this.index].hasMoreElements()) { + return true; + } + + ++this.index; + } + + return false; + } + + public boolean hasMoreElements() { + return this.next(); + } + + public E nextElement() { + if (!this.next()) { + throw new NoSuchElementException(); + } else { + return this.enums[this.index].nextElement(); + } + } + } +} diff --git a/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Util.java b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Util.java new file mode 100644 index 00000000..e3c8032c --- /dev/null +++ b/client-adapter/common/src/main/java/com/alibaba/otter/canal/client/adapter/support/Util.java @@ -0,0 +1,120 @@ +package com.alibaba.otter.canal.client.adapter.support; + +import java.io.File; +import java.net.URL; +import java.sql.Connection; +import java.sql.ResultSet; +import java.sql.SQLException; +import java.sql.Statement; +import java.util.function.Consumer; +import java.util.function.Function; + +import javax.sql.DataSource; + +import org.apache.commons.lang.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +public class Util { + + private static final Logger logger = LoggerFactory.getLogger(Util.class); + + /** + * 通过DS执行sql + */ + public static Object sqlRS(DataSource ds, String sql, Function fun) throws SQLException { + Connection conn = null; + Statement stmt = null; + ResultSet rs = null; + try { + conn = ds.getConnection(); + stmt = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY); + stmt.setFetchSize(Integer.MIN_VALUE); + rs = stmt.executeQuery(sql); + return fun.apply(rs); + } finally { + if (rs != null) { + try { + rs.close(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + if (stmt != null) { + try { + stmt.close(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + if (conn != null) { + try { + conn.close(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + } + } + + /** + * sql执行获取resultSet + * + * @param conn sql connection + * @param sql sql + * @param consumer 回调方法 + */ + public static void sqlRS(Connection conn, String sql, Consumer consumer) { + Statement stmt = null; + ResultSet rs = null; + try { + stmt = conn.createStatement(); + rs = stmt.executeQuery(sql); + consumer.accept(rs); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } finally { + if (rs != null) { + try { + rs.close(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + if (stmt != null) { + try { + stmt.close(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + } + } + + public static File getConfDirPath() { + return getConfDirPath(""); + } + + public static File getConfDirPath(String subConf) { + URL url = Util.class.getClassLoader().getResource(""); + String path; + if (url != null) { + path = url.getPath(); + } else { + path = new File("").getAbsolutePath(); + } + File file = null; + if (path != null) { + file = new File( + path + ".." + File.separator + Constant.CONF_DIR + File.separator + StringUtils.trimToEmpty(subConf)); + if (!file.exists()) { + file = new File(path + StringUtils.trimToEmpty(subConf)); + } + } + if (file == null || !file.exists()) { + throw new RuntimeException("Config dir not found."); + } + + return file; + } +} diff --git a/client-adapter/elasticsearch/pom.xml b/client-adapter/elasticsearch/pom.xml new file mode 100644 index 00000000..35711014 --- /dev/null +++ b/client-adapter/elasticsearch/pom.xml @@ -0,0 +1,95 @@ + + + + canal.client-adapter + com.alibaba.otter + 1.1.3-SNAPSHOT + + 4.0.0 + com.alibaba.otter + client-adapter.elasticsearch + jar + canal client adapter elasticsearch module for otter ${project.version} + + + + com.alibaba.otter + client-adapter.common + ${project.version} + provided + + + org.yaml + snakeyaml + 1.19 + provided + + + com.alibaba.fastsql + fastsql + 2.0.0_preview_644 + + + org.elasticsearch + elasticsearch + 6.2.3 + + + org.elasticsearch.client + transport + 6.2.3 + + + + junit + junit + 4.12 + test + + + + + + + org.apache.maven.plugins + maven-assembly-plugin + 2.4 + + + jar-with-dependencies + + + + + make-assembly + package + + single + + + + + + maven-antrun-plugin + + + package + + run + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/ESAdapter.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/ESAdapter.java new file mode 100644 index 00000000..9bb56792 --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/ESAdapter.java @@ -0,0 +1,227 @@ +package com.alibaba.otter.canal.client.adapter.es; + +import java.net.InetAddress; +import java.util.HashMap; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import javax.sql.DataSource; + +import org.elasticsearch.action.search.SearchResponse; +import org.elasticsearch.client.transport.TransportClient; +import org.elasticsearch.common.settings.Settings; +import org.elasticsearch.common.transport.TransportAddress; +import org.elasticsearch.transport.client.PreBuiltTransportClient; + +import com.alibaba.druid.pool.DruidDataSource; +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig.ESMapping; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfigLoader; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem; +import com.alibaba.otter.canal.client.adapter.es.config.SqlParser; +import com.alibaba.otter.canal.client.adapter.es.monitor.ESConfigMonitor; +import com.alibaba.otter.canal.client.adapter.es.service.ESEtlService; +import com.alibaba.otter.canal.client.adapter.es.service.ESSyncService; +import com.alibaba.otter.canal.client.adapter.es.support.ESTemplate; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; +import com.alibaba.otter.canal.client.adapter.support.EtlResult; +import com.alibaba.otter.canal.client.adapter.support.OuterAdapterConfig; +import com.alibaba.otter.canal.client.adapter.support.SPI; + +/** + * ES外部适配器 + * + * @author rewerma 2018-10-20 + * @version 1.0.0 + */ +@SPI("es") +public class ESAdapter implements OuterAdapter { + + private Map esSyncConfig = new ConcurrentHashMap<>(); // 文件名对应配置 + private Map> dbTableEsSyncConfig = new ConcurrentHashMap<>(); // schema-table对应配置 + + private TransportClient transportClient; + + private ESSyncService esSyncService; + + private ESConfigMonitor esConfigMonitor; + + public TransportClient getTransportClient() { + return transportClient; + } + + public ESSyncService getEsSyncService() { + return esSyncService; + } + + public Map getEsSyncConfig() { + return esSyncConfig; + } + + public Map> getDbTableEsSyncConfig() { + return dbTableEsSyncConfig; + } + + @Override + public void init(OuterAdapterConfig configuration) { + try { + Map esSyncConfigTmp = ESSyncConfigLoader.load(); + // 过滤不匹配的key的配置 + esSyncConfigTmp.forEach((key, config) -> { + if ((config.getOuterAdapterKey() == null && configuration.getKey() == null) + || (config.getOuterAdapterKey() != null && config.getOuterAdapterKey() + .equalsIgnoreCase(configuration.getKey()))) { + esSyncConfig.put(key, config); + } + }); + + for (Map.Entry entry : esSyncConfig.entrySet()) { + String configName = entry.getKey(); + ESSyncConfig config = entry.getValue(); + SchemaItem schemaItem = SqlParser.parse(config.getEsMapping().getSql()); + config.getEsMapping().setSchemaItem(schemaItem); + + DruidDataSource dataSource = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (dataSource == null || dataSource.getUrl() == null) { + throw new RuntimeException("No data source found: " + config.getDataSourceKey()); + } + Pattern pattern = Pattern.compile(".*:(.*)://.*/(.*)\\?.*$"); + Matcher matcher = pattern.matcher(dataSource.getUrl()); + if (!matcher.find()) { + throw new RuntimeException("Not found the schema of jdbc-url: " + config.getDataSourceKey()); + } + String schema = matcher.group(2); + + schemaItem.getAliasTableItems() + .values() + .forEach(tableItem -> { + Map esSyncConfigMap = dbTableEsSyncConfig.computeIfAbsent(schema + + "-" + + tableItem.getTableName(), + k -> new HashMap<>()); + esSyncConfigMap.put(configName, config); + }); + } + + Map properties = configuration.getProperties(); + Settings.Builder settingBuilder = Settings.builder(); + properties.forEach(settingBuilder::put); + Settings settings = settingBuilder.build(); + transportClient = new PreBuiltTransportClient(settings); + String[] hostArray = configuration.getHosts().split(","); + for (String host : hostArray) { + int i = host.indexOf(":"); + transportClient.addTransportAddress(new TransportAddress(InetAddress.getByName(host.substring(0, i)), + Integer.parseInt(host.substring(i + 1)))); + } + ESTemplate esTemplate = new ESTemplate(transportClient); + esSyncService = new ESSyncService(esTemplate); + + esConfigMonitor = new ESConfigMonitor(); + esConfigMonitor.init(this); + } catch (Exception e) { + throw new RuntimeException(e); + } + } + + public void sync(List dmls) { + for (Dml dml : dmls) { + sync(dml); + } + } + + public void sync(Dml dml) { + String database = dml.getDatabase(); + String table = dml.getTable(); + Map configMap = dbTableEsSyncConfig.get(database + "-" + table); + esSyncService.sync(configMap.values(), dml); + } + + @Override + public EtlResult etl(String task, List params) { + EtlResult etlResult = new EtlResult(); + ESSyncConfig config = esSyncConfig.get(task); + if (config != null) { + DataSource dataSource = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + ESEtlService esEtlService = new ESEtlService(transportClient, config); + if (dataSource != null) { + return esEtlService.importData(params, false); + } else { + etlResult.setSucceeded(false); + etlResult.setErrorMessage("DataSource not found"); + return etlResult; + } + } else { + StringBuilder resultMsg = new StringBuilder(); + boolean resSuccess = true; + // ds不为空说明传入的是datasourceKey + for (ESSyncConfig configTmp : esSyncConfig.values()) { + // 取所有的destination为task的配置 + if (configTmp.getDestination().equals(task)) { + ESEtlService esEtlService = new ESEtlService(transportClient, configTmp); + EtlResult etlRes = esEtlService.importData(params, false); + if (!etlRes.getSucceeded()) { + resSuccess = false; + resultMsg.append(etlRes.getErrorMessage()).append("\n"); + } else { + resultMsg.append(etlRes.getResultMessage()).append("\n"); + } + } + } + if (resultMsg.length() > 0) { + etlResult.setSucceeded(resSuccess); + if (resSuccess) { + etlResult.setResultMessage(resultMsg.toString()); + } else { + etlResult.setErrorMessage(resultMsg.toString()); + } + return etlResult; + } + } + etlResult.setSucceeded(false); + etlResult.setErrorMessage("Task not found"); + return etlResult; + } + + @Override + public Map count(String task) { + ESSyncConfig config = esSyncConfig.get(task); + ESMapping mapping = config.getEsMapping(); + SearchResponse response = transportClient.prepareSearch(mapping.get_index()) + .setTypes(mapping.get_type()) + .setSize(0) + .get(); + + long rowCount = response.getHits().getTotalHits(); + Map res = new LinkedHashMap<>(); + res.put("esIndex", mapping.get_index()); + res.put("count", rowCount); + return res; + } + + @Override + public void destroy() { + if (transportClient != null) { + transportClient.close(); + } + } + + @Override + public String getDestination(String task) { + if (esConfigMonitor != null) { + esConfigMonitor.destroy(); + } + + ESSyncConfig config = esSyncConfig.get(task); + if (config != null) { + return config.getDestination(); + } + return null; + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/ESSyncConfig.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/ESSyncConfig.java new file mode 100644 index 00000000..65087437 --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/ESSyncConfig.java @@ -0,0 +1,194 @@ +package com.alibaba.otter.canal.client.adapter.es.config; + +import java.util.ArrayList; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; + +/** + * ES 映射配置 + * + * @author rewerma 2018-11-01 + * @version 1.0.0 + */ +public class ESSyncConfig { + + private String dataSourceKey; // 数据源key + + private String outerAdapterKey; // adapter key + + private String destination; // canal destination + + private ESMapping esMapping; + + public void validate() { + if (esMapping._index == null) { + throw new NullPointerException("esMapping._index"); + } + if (esMapping._type == null) { + throw new NullPointerException("esMapping._type"); + } + if (esMapping._id == null && esMapping.pk == null) { + throw new NullPointerException("esMapping._id and esMapping.pk"); + } + if (esMapping.sql == null) { + throw new NullPointerException("esMapping.sql"); + } + } + + public String getDataSourceKey() { + return dataSourceKey; + } + + public void setDataSourceKey(String dataSourceKey) { + this.dataSourceKey = dataSourceKey; + } + + public String getOuterAdapterKey() { + return outerAdapterKey; + } + + public void setOuterAdapterKey(String outerAdapterKey) { + this.outerAdapterKey = outerAdapterKey; + } + + public String getDestination() { + return destination; + } + + public void setDestination(String destination) { + this.destination = destination; + } + + public ESMapping getEsMapping() { + return esMapping; + } + + public void setEsMapping(ESMapping esMapping) { + this.esMapping = esMapping; + } + + public static class ESMapping { + + private String _index; + private String _type; + private String _id; + private String pk; + private String parent; + private String sql; + // 对象字段, 例: objFields: + // - _labels: array:; + private Map objFields = new LinkedHashMap<>(); + private List skips = new ArrayList<>(); + private int commitBatch = 1000; + private String etlCondition; + private boolean syncByTimestamp = false; // 是否按时间戳定时同步 + private Long syncInterval; // 同步时间间隔 + + private SchemaItem schemaItem; // sql解析结果模型 + + public String get_index() { + return _index; + } + + public void set_index(String _index) { + this._index = _index; + } + + public String get_type() { + return _type; + } + + public void set_type(String _type) { + this._type = _type; + } + + public String get_id() { + return _id; + } + + public void set_id(String _id) { + this._id = _id; + } + + public String getPk() { + return pk; + } + + public void setPk(String pk) { + this.pk = pk; + } + + public String getParent() { + return parent; + } + + public void setParent(String parent) { + this.parent = parent; + } + + public Map getObjFields() { + return objFields; + } + + public void setObjFields(Map objFields) { + this.objFields = objFields; + } + + public List getSkips() { + return skips; + } + + public void setSkips(List skips) { + this.skips = skips; + } + + public String getSql() { + return sql; + } + + public void setSql(String sql) { + this.sql = sql; + } + + public int getCommitBatch() { + return commitBatch; + } + + public void setCommitBatch(int commitBatch) { + this.commitBatch = commitBatch; + } + + public String getEtlCondition() { + return etlCondition; + } + + public void setEtlCondition(String etlCondition) { + this.etlCondition = etlCondition; + } + + public Long getSyncInterval() { + return syncInterval; + } + + public void setSyncInterval(Long syncInterval) { + this.syncInterval = syncInterval; + } + + public boolean isSyncByTimestamp() { + return syncByTimestamp; + } + + public void setSyncByTimestamp(boolean syncByTimestamp) { + this.syncByTimestamp = syncByTimestamp; + } + + public SchemaItem getSchemaItem() { + return schemaItem; + } + + public void setSchemaItem(SchemaItem schemaItem) { + this.schemaItem = schemaItem; + } + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/ESSyncConfigLoader.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/ESSyncConfigLoader.java new file mode 100644 index 00000000..e83a96e6 --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/ESSyncConfigLoader.java @@ -0,0 +1,41 @@ +package com.alibaba.otter.canal.client.adapter.es.config; + +import java.util.LinkedHashMap; +import java.util.Map; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.yaml.snakeyaml.Yaml; + +import com.alibaba.otter.canal.client.adapter.support.MappingConfigsLoader; + +/** + * ES 配置装载器 + * + * @author rewerma 2018-11-01 + * @version 1.0.0 + */ +public class ESSyncConfigLoader { + + private static Logger logger = LoggerFactory.getLogger(ESSyncConfigLoader.class); + + public static synchronized Map load() { + logger.info("## Start loading es mapping config ... "); + + Map esSyncConfig = new LinkedHashMap<>(); + + Map configContentMap = MappingConfigsLoader.loadConfigs("es"); + configContentMap.forEach((fileName, content) -> { + ESSyncConfig config = new Yaml().loadAs(content, ESSyncConfig.class); + try { + config.validate(); + } catch (Exception e) { + throw new RuntimeException("ERROR Config: " + fileName + " " + e.getMessage(), e); + } + esSyncConfig.put(fileName, config); + }); + + logger.info("## ES mapping config loaded"); + return esSyncConfig; + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/SchemaItem.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/SchemaItem.java new file mode 100644 index 00000000..fc6e076c --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/SchemaItem.java @@ -0,0 +1,422 @@ +package com.alibaba.otter.canal.client.adapter.es.config; + +import java.util.ArrayList; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; + +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig.ESMapping; + +/** + * ES 映射配置视图 + * + * @author rewerma 2018-11-01 + * @version 1.0.0 + */ +public class SchemaItem { + + private Map aliasTableItems = new LinkedHashMap<>(); // 别名对应表名 + private Map selectFields = new LinkedHashMap<>(); // 查询字段 + private String sql; + + private volatile Map> tableItemAliases; + private volatile Map> columnFields; + private volatile Boolean allFieldsSimple; + + public void init() { + this.getTableItemAliases(); + this.getColumnFields(); + this.isAllFieldsSimple(); + aliasTableItems.values().forEach(tableItem -> { + tableItem.getRelationTableFields(); + tableItem.getRelationSelectFieldItems(); + }); + } + + public Map getAliasTableItems() { + return aliasTableItems; + } + + public void setAliasTableItems(Map aliasTableItems) { + this.aliasTableItems = aliasTableItems; + } + + public String getSql() { + return sql; + } + + public void setSql(String sql) { + this.sql = sql; + } + + public Map getSelectFields() { + return selectFields; + } + + public void setSelectFields(Map selectFields) { + this.selectFields = selectFields; + } + + public Map> getTableItemAliases() { + if (tableItemAliases == null) { + synchronized (SchemaItem.class) { + if (tableItemAliases == null) { + tableItemAliases = new LinkedHashMap<>(); + aliasTableItems.forEach((alias, tableItem) -> { + List aliases = tableItemAliases + .computeIfAbsent(tableItem.getTableName().toLowerCase(), k -> new ArrayList<>()); + aliases.add(tableItem); + }); + } + } + } + return tableItemAliases; + } + + public Map> getColumnFields() { + if (columnFields == null) { + synchronized (SchemaItem.class) { + if (columnFields == null) { + columnFields = new LinkedHashMap<>(); + getSelectFields() + .forEach((fieldName, fieldItem) -> fieldItem.getColumnItems().forEach(columnItem -> { + TableItem tableItem = getAliasTableItems().get(columnItem.getOwner()); + // if (!tableItem.isSubQuery()) { + List fieldItems = columnFields.computeIfAbsent( + columnItem.getOwner() + "." + columnItem.getColumnName(), + k -> new ArrayList<>()); + fieldItems.add(fieldItem); + // } else { + // tableItem.getSubQueryFields().forEach(subQueryField -> { + // List fieldItems = columnFields.computeIfAbsent( + // columnItem.getOwner() + "." + subQueryField.getColumn().getColumnName(), + // k -> new ArrayList<>()); + // fieldItems.add(fieldItem); + // }); + // } + })); + } + } + } + return columnFields; + } + + public boolean isAllFieldsSimple() { + if (allFieldsSimple == null) { + synchronized (SchemaItem.class) { + if (allFieldsSimple == null) { + allFieldsSimple = true; + + for (FieldItem fieldItem : getSelectFields().values()) { + if (fieldItem.isMethod() || fieldItem.isBinaryOp()) { + allFieldsSimple = false; + break; + } + } + } + } + } + + return allFieldsSimple; + } + + public TableItem getMainTable() { + if (!aliasTableItems.isEmpty()) { + return aliasTableItems.values().iterator().next(); + } else { + return null; + } + } + + public FieldItem getIdFieldItem(ESMapping mapping) { + if (mapping.get_id() != null) { + return getSelectFields().get(mapping.get_id()); + } else { + return getSelectFields().get(mapping.getPk()); + } + } + + public static class TableItem { + + private SchemaItem schemaItem; + + private String schema; + private String tableName; + private String alias; + private String subQuerySql; + private List subQueryFields = new ArrayList<>(); + private List relationFields = new ArrayList<>(); + + private boolean main; + private boolean subQuery; + + private volatile Map> relationTableFields; // 当前表关联条件字段对应主表查询字段 + private volatile List relationSelectFieldItems; // 子表所在主表的查询字段 + + public TableItem(SchemaItem schemaItem){ + this.schemaItem = schemaItem; + } + + public SchemaItem getSchemaItem() { + return schemaItem; + } + + public void setSchemaItem(SchemaItem schemaItem) { + this.schemaItem = schemaItem; + } + + public String getSchema() { + return schema; + } + + public void setSchema(String schema) { + this.schema = schema; + } + + public String getTableName() { + return tableName; + } + + public void setTableName(String tableName) { + this.tableName = tableName; + } + + public String getAlias() { + return alias; + } + + public void setAlias(String alias) { + this.alias = alias; + } + + public String getSubQuerySql() { + return subQuerySql; + } + + public void setSubQuerySql(String subQuerySql) { + this.subQuerySql = subQuerySql; + } + + public boolean isMain() { + return main; + } + + public void setMain(boolean main) { + this.main = main; + } + + public boolean isSubQuery() { + return subQuery; + } + + public void setSubQuery(boolean subQuery) { + this.subQuery = subQuery; + } + + public List getSubQueryFields() { + return subQueryFields; + } + + public void setSubQueryFields(List subQueryFields) { + this.subQueryFields = subQueryFields; + } + + public List getRelationFields() { + return relationFields; + } + + public void setRelationFields(List relationFields) { + this.relationFields = relationFields; + } + + public Map> getRelationTableFields() { + if (relationTableFields == null) { + synchronized (SchemaItem.class) { + if (relationTableFields == null) { + relationTableFields = new LinkedHashMap<>(); + + getRelationFields().forEach(relationFieldsPair -> { + FieldItem leftFieldItem = relationFieldsPair.getLeftFieldItem(); + FieldItem rightFieldItem = relationFieldsPair.getRightFieldItem(); + FieldItem currentTableRelField = null; + if (getAlias().equals(leftFieldItem.getOwner())) { + currentTableRelField = leftFieldItem; + } else if (getAlias().equals(rightFieldItem.getOwner())) { + currentTableRelField = rightFieldItem; + } + + if (currentTableRelField != null) { + List selectFieldItem = getSchemaItem().getColumnFields() + .get(leftFieldItem.getOwner() + "." + leftFieldItem.getColumn().getColumnName()); + if (selectFieldItem != null && !selectFieldItem.isEmpty()) { + relationTableFields.put(currentTableRelField, selectFieldItem); + } else { + selectFieldItem = getSchemaItem().getColumnFields() + .get(rightFieldItem.getOwner() + "." + + rightFieldItem.getColumn().getColumnName()); + if (selectFieldItem != null && !selectFieldItem.isEmpty()) { + relationTableFields.put(currentTableRelField, selectFieldItem); + } else { + throw new UnsupportedOperationException( + "Relation condition column must in select columns."); + } + } + } + }); + } + } + } + return relationTableFields; + } + + public List getRelationSelectFieldItems() { + if (relationSelectFieldItems == null) { + synchronized (SchemaItem.class) { + if (relationSelectFieldItems == null) { + relationSelectFieldItems = new ArrayList<>(); + for (FieldItem fieldItem : schemaItem.getSelectFields().values()) { + if (fieldItem.getOwners().contains(getAlias())) { + relationSelectFieldItems.add(fieldItem); + } + } + } + } + } + return relationSelectFieldItems; + } + } + + public static class RelationFieldsPair { + + private FieldItem leftFieldItem; + private FieldItem rightFieldItem; + + public RelationFieldsPair(FieldItem leftFieldItem, FieldItem rightFieldItem){ + this.leftFieldItem = leftFieldItem; + this.rightFieldItem = rightFieldItem; + } + + public FieldItem getLeftFieldItem() { + return leftFieldItem; + } + + public void setLeftFieldItem(FieldItem leftFieldItem) { + this.leftFieldItem = leftFieldItem; + } + + public FieldItem getRightFieldItem() { + return rightFieldItem; + } + + public void setRightFieldItem(FieldItem rightFieldItem) { + this.rightFieldItem = rightFieldItem; + } + } + + public static class FieldItem { + + private String fieldName; + private List columnItems = new ArrayList<>(); + private List owners = new ArrayList<>(); + + private boolean method; + private boolean binaryOp; + + public String getFieldName() { + return fieldName; + } + + public void setFieldName(String fieldName) { + this.fieldName = fieldName; + } + + public List getColumnItems() { + return columnItems; + } + + public void setColumnItems(List columnItems) { + this.columnItems = columnItems; + } + + public boolean isMethod() { + return method; + } + + public void setMethod(boolean method) { + this.method = method; + } + + public boolean isBinaryOp() { + return binaryOp; + } + + public void setBinaryOp(boolean binaryOp) { + this.binaryOp = binaryOp; + } + + public List getOwners() { + return owners; + } + + public void setOwners(List owners) { + this.owners = owners; + } + + public void addColumn(ColumnItem columnItem) { + columnItems.add(columnItem); + } + + public ColumnItem getColumn() { + if (!columnItems.isEmpty()) { + return columnItems.get(0); + } else { + return null; + } + } + + public String getOwner() { + if (!owners.isEmpty()) { + return owners.get(0); + } else { + return null; + } + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + + FieldItem fieldItem = (FieldItem) o; + + return fieldName != null ? fieldName.equals(fieldItem.fieldName) : fieldItem.fieldName == null; + } + + @Override + public int hashCode() { + return fieldName != null ? fieldName.hashCode() : 0; + } + } + + public static class ColumnItem { + + private String owner; + private String columnName; + + public String getOwner() { + return owner; + } + + public void setOwner(String owner) { + this.owner = owner; + } + + public String getColumnName() { + return columnName; + } + + public void setColumnName(String columnName) { + this.columnName = columnName; + } + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/SqlParser.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/SqlParser.java new file mode 100644 index 00000000..0c2d7b2c --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/config/SqlParser.java @@ -0,0 +1,210 @@ +package com.alibaba.otter.canal.client.adapter.es.config; + +import static com.alibaba.fastsql.sql.ast.expr.SQLBinaryOperator.BooleanAnd; +import static com.alibaba.fastsql.sql.ast.expr.SQLBinaryOperator.Equality; + +import java.util.ArrayList; +import java.util.List; +import java.util.stream.Collectors; + +import com.alibaba.fastsql.sql.SQLUtils; +import com.alibaba.fastsql.sql.ast.SQLExpr; +import com.alibaba.fastsql.sql.ast.expr.SQLBinaryOpExpr; +import com.alibaba.fastsql.sql.ast.expr.SQLIdentifierExpr; +import com.alibaba.fastsql.sql.ast.expr.SQLMethodInvokeExpr; +import com.alibaba.fastsql.sql.ast.expr.SQLPropertyExpr; +import com.alibaba.fastsql.sql.ast.statement.*; +import com.alibaba.fastsql.sql.dialect.mysql.ast.statement.MySqlSelectQueryBlock; +import com.alibaba.fastsql.sql.dialect.mysql.parser.MySqlStatementParser; +import com.alibaba.fastsql.sql.parser.ParserException; +import com.alibaba.fastsql.sql.parser.SQLStatementParser; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.ColumnItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.FieldItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.RelationFieldsPair; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.TableItem; + +/** + * ES同步指定sql格式解析 + * + * @author rewerma 2018-10-26 下午03:45:49 + * @version 1.0.0 + */ +public class SqlParser { + + /** + * 解析sql + * + * @param sql sql + * @return 视图对象 + */ + public static SchemaItem parse(String sql) { + try { + SQLStatementParser parser = new MySqlStatementParser(sql); + SQLSelectStatement statement = (SQLSelectStatement) parser.parseStatement(); + MySqlSelectQueryBlock sqlSelectQueryBlock = (MySqlSelectQueryBlock) statement.getSelect().getQuery(); + + SchemaItem schemaItem = new SchemaItem(); + schemaItem.setSql(SQLUtils.toMySqlString(sqlSelectQueryBlock)); + SQLTableSource sqlTableSource = sqlSelectQueryBlock.getFrom(); + List tableItems = new ArrayList<>(); + SqlParser.visitSelectTable(schemaItem, sqlTableSource, tableItems, null); + tableItems.forEach(tableItem -> schemaItem.getAliasTableItems().put(tableItem.getAlias(), tableItem)); + + List fieldItems = collectSelectQueryFields(sqlSelectQueryBlock); + fieldItems.forEach(fieldItem -> schemaItem.getSelectFields().put(fieldItem.getFieldName(), fieldItem)); + + schemaItem.init(); + + if (schemaItem.getAliasTableItems().isEmpty() || schemaItem.getSelectFields().isEmpty()) { + throw new ParserException("Parse sql error"); + } + return schemaItem; + } catch (Exception e) { + throw new ParserException(); + } + } + + /** + * 归集字段 + * + * @param sqlSelectQueryBlock sqlSelectQueryBlock + * @return 字段属性列表 + */ + private static List collectSelectQueryFields(MySqlSelectQueryBlock sqlSelectQueryBlock) { + return sqlSelectQueryBlock.getSelectList().stream().map(selectItem -> { + FieldItem fieldItem = new FieldItem(); + fieldItem.setFieldName(selectItem.getAlias()); + visitColumn(selectItem.getExpr(), fieldItem); + return fieldItem; + }).collect(Collectors.toList()); + } + + /** + * 解析字段 + * + * @param expr sql expr + * @param fieldItem 字段属性 + */ + private static void visitColumn(SQLExpr expr, FieldItem fieldItem) { + if (expr instanceof SQLIdentifierExpr) { + // 无owner + SQLIdentifierExpr identifierExpr = (SQLIdentifierExpr) expr; + if (fieldItem.getFieldName() == null) { + fieldItem.setFieldName(identifierExpr.getName()); + } + ColumnItem columnItem = new ColumnItem(); + columnItem.setColumnName(identifierExpr.getName()); + fieldItem.getOwners().add(null); + fieldItem.addColumn(columnItem); + } else if (expr instanceof SQLPropertyExpr) { + // 有owner + SQLPropertyExpr sqlPropertyExpr = (SQLPropertyExpr) expr; + if (fieldItem.getFieldName() == null) { + fieldItem.setFieldName(sqlPropertyExpr.getName()); + } + fieldItem.getOwners().add(sqlPropertyExpr.getOwnernName()); + ColumnItem columnItem = new ColumnItem(); + columnItem.setColumnName(sqlPropertyExpr.getName()); + columnItem.setOwner(sqlPropertyExpr.getOwnernName()); + fieldItem.addColumn(columnItem); + } else if (expr instanceof SQLMethodInvokeExpr) { + SQLMethodInvokeExpr methodInvokeExpr = (SQLMethodInvokeExpr) expr; + fieldItem.setMethod(true); + for (SQLExpr sqlExpr : methodInvokeExpr.getArguments()) { + visitColumn(sqlExpr, fieldItem); + } + } else if (expr instanceof SQLBinaryOpExpr) { + SQLBinaryOpExpr sqlBinaryOpExpr = (SQLBinaryOpExpr) expr; + fieldItem.setBinaryOp(true); + visitColumn(sqlBinaryOpExpr.getLeft(), fieldItem); + visitColumn(sqlBinaryOpExpr.getRight(), fieldItem); + } + } + + /** + * 解析表 + * + * @param schemaItem 视图对象 + * @param sqlTableSource sqlTableSource + * @param tableItems 表对象列表 + * @param tableItemTmp 表对象(临时) + */ + private static void visitSelectTable(SchemaItem schemaItem, SQLTableSource sqlTableSource, + List tableItems, TableItem tableItemTmp) { + if (sqlTableSource instanceof SQLExprTableSource) { + SQLExprTableSource sqlExprTableSource = (SQLExprTableSource) sqlTableSource; + TableItem tableItem; + if (tableItemTmp != null) { + tableItem = tableItemTmp; + } else { + tableItem = new TableItem(schemaItem); + } + tableItem.setSchema(sqlExprTableSource.getSchema()); + tableItem.setTableName(sqlExprTableSource.getTableName()); + if (tableItem.getAlias() == null) { + tableItem.setAlias(sqlExprTableSource.getAlias()); + } + if (tableItems.isEmpty()) { + // 第一张表为主表 + tableItem.setMain(true); + } + tableItems.add(tableItem); + } else if (sqlTableSource instanceof SQLJoinTableSource) { + SQLJoinTableSource sqlJoinTableSource = (SQLJoinTableSource) sqlTableSource; + SQLTableSource leftTableSource = sqlJoinTableSource.getLeft(); + visitSelectTable(schemaItem, leftTableSource, tableItems, null); + SQLTableSource rightTableSource = sqlJoinTableSource.getRight(); + TableItem rightTableItem = new TableItem(schemaItem); + // 解析on条件字段 + visitOnCondition(sqlJoinTableSource.getCondition(), rightTableItem); + visitSelectTable(schemaItem, rightTableSource, tableItems, rightTableItem); + + } else if (sqlTableSource instanceof SQLSubqueryTableSource) { + SQLSubqueryTableSource subQueryTableSource = (SQLSubqueryTableSource) sqlTableSource; + MySqlSelectQueryBlock sqlSelectQuery = (MySqlSelectQueryBlock) subQueryTableSource.getSelect().getQuery(); + TableItem tableItem; + if (tableItemTmp != null) { + tableItem = tableItemTmp; + } else { + tableItem = new TableItem(schemaItem); + } + tableItem.setAlias(subQueryTableSource.getAlias()); + tableItem.setSubQuerySql(SQLUtils.toMySqlString(sqlSelectQuery)); + tableItem.setSubQuery(true); + tableItem.setSubQueryFields(collectSelectQueryFields(sqlSelectQuery)); + visitSelectTable(schemaItem, sqlSelectQuery.getFrom(), tableItems, tableItem); + } + } + + /** + * 解析on条件 + * + * @param expr sql expr + * @param tableItem 表对象 + */ + private static void visitOnCondition(SQLExpr expr, TableItem tableItem) { + if (!(expr instanceof SQLBinaryOpExpr)) { + throw new UnsupportedOperationException(); + } + SQLBinaryOpExpr sqlBinaryOpExpr = (SQLBinaryOpExpr) expr; + if (sqlBinaryOpExpr.getOperator() == BooleanAnd) { + visitOnCondition(sqlBinaryOpExpr.getLeft(), tableItem); + visitOnCondition(sqlBinaryOpExpr.getRight(), tableItem); + } else if (sqlBinaryOpExpr.getOperator() == Equality) { + FieldItem leftFieldItem = new FieldItem(); + visitColumn(sqlBinaryOpExpr.getLeft(), leftFieldItem); + if (leftFieldItem.getColumnItems().size() != 1 || leftFieldItem.isMethod() || leftFieldItem.isBinaryOp()) { + throw new UnsupportedOperationException("Unsupported for complex of on-condition"); + } + FieldItem rightFieldItem = new FieldItem(); + visitColumn(sqlBinaryOpExpr.getRight(), rightFieldItem); + if (rightFieldItem.getColumnItems().size() != 1 || rightFieldItem.isMethod() + || rightFieldItem.isBinaryOp()) { + throw new UnsupportedOperationException("Unsupported for complex of on-condition"); + } + tableItem.getRelationFields().add(new RelationFieldsPair(leftFieldItem, rightFieldItem)); + } else { + throw new UnsupportedOperationException("Unsupported for complex of on-condition"); + } + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/monitor/ESConfigMonitor.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/monitor/ESConfigMonitor.java new file mode 100644 index 00000000..3b19b39e --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/monitor/ESConfigMonitor.java @@ -0,0 +1,151 @@ +package com.alibaba.otter.canal.client.adapter.es.monitor; + +import java.io.File; +import java.util.HashMap; +import java.util.Map; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import org.apache.commons.io.filefilter.FileFilterUtils; +import org.apache.commons.io.monitor.FileAlterationListenerAdaptor; +import org.apache.commons.io.monitor.FileAlterationMonitor; +import org.apache.commons.io.monitor.FileAlterationObserver; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.yaml.snakeyaml.Yaml; + +import com.alibaba.druid.pool.DruidDataSource; +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem; +import com.alibaba.otter.canal.client.adapter.es.config.SqlParser; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.MappingConfigsLoader; +import com.alibaba.otter.canal.client.adapter.support.Util; + +public class ESConfigMonitor { + + private static final Logger logger = LoggerFactory.getLogger(ESConfigMonitor.class); + + private static final String adapterName = "es"; + + private ESAdapter esAdapter; + + private FileAlterationMonitor fileMonitor; + + public void init(ESAdapter esAdapter) { + this.esAdapter = esAdapter; + File confDir = Util.getConfDirPath(adapterName); + try { + FileAlterationObserver observer = new FileAlterationObserver(confDir, + FileFilterUtils.and(FileFilterUtils.fileFileFilter(), FileFilterUtils.suffixFileFilter("yml"))); + FileListener listener = new FileListener(); + observer.addListener(listener); + fileMonitor = new FileAlterationMonitor(3000, observer); + fileMonitor.start(); + + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + public void destroy() { + try { + fileMonitor.stop(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private class FileListener extends FileAlterationListenerAdaptor { + + @Override + public void onFileCreate(File file) { + super.onFileCreate(file); + try { + // 加载新增的配置文件 + String configContent = MappingConfigsLoader.loadConfig(adapterName + File.separator + file.getName()); + ESSyncConfig config = new Yaml().loadAs(configContent, ESSyncConfig.class); + config.validate(); + addConfigToCache(file, config); + + logger.info("Add a new es mapping config: {} to canal adapter", file.getName()); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + @Override + public void onFileChange(File file) { + super.onFileChange(file); + + try { + if (esAdapter.getEsSyncConfig().containsKey(file.getName())) { + // 加载配置文件 + String configContent = MappingConfigsLoader + .loadConfig(adapterName + File.separator + file.getName()); + ESSyncConfig config = new Yaml().loadAs(configContent, ESSyncConfig.class); + config.validate(); + if (esAdapter.getEsSyncConfig().containsKey(file.getName())) { + deleteConfigFromCache(file); + } + addConfigToCache(file, config); + + logger.info("Change a es mapping config: {} of canal adapter", file.getName()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + @Override + public void onFileDelete(File file) { + super.onFileDelete(file); + + try { + if (esAdapter.getEsSyncConfig().containsKey(file.getName())) { + deleteConfigFromCache(file); + + logger.info("Delete a es mapping config: {} of canal adapter", file.getName()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private void addConfigToCache(File file, ESSyncConfig config) { + esAdapter.getEsSyncConfig().put(file.getName(), config); + + SchemaItem schemaItem = SqlParser.parse(config.getEsMapping().getSql()); + config.getEsMapping().setSchemaItem(schemaItem); + + DruidDataSource dataSource = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (dataSource == null || dataSource.getUrl() == null) { + throw new RuntimeException("No data source found: " + config.getDataSourceKey()); + } + Pattern pattern = Pattern.compile(".*:(.*)://.*/(.*)\\?.*$"); + Matcher matcher = pattern.matcher(dataSource.getUrl()); + if (!matcher.find()) { + throw new RuntimeException("Not found the schema of jdbc-url: " + config.getDataSourceKey()); + } + String schema = matcher.group(2); + + schemaItem.getAliasTableItems().values().forEach(tableItem -> { + Map esSyncConfigMap = esAdapter.getDbTableEsSyncConfig() + .computeIfAbsent(schema + "-" + tableItem.getTableName(), k -> new HashMap<>()); + esSyncConfigMap.put(file.getName(), config); + }); + + } + + private void deleteConfigFromCache(File file) { + esAdapter.getEsSyncConfig().remove(file.getName()); + for (Map configMap : esAdapter.getDbTableEsSyncConfig().values()) { + if (configMap != null) { + configMap.remove(file.getName()); + } + } + + } + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/service/ESEtlService.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/service/ESEtlService.java new file mode 100644 index 00000000..51f0a924 --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/service/ESEtlService.java @@ -0,0 +1,286 @@ +package com.alibaba.otter.canal.client.adapter.es.service; + +import java.util.*; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; +import java.util.concurrent.atomic.AtomicLong; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import javax.sql.DataSource; + +import org.elasticsearch.action.bulk.BulkItemResponse; +import org.elasticsearch.action.bulk.BulkRequestBuilder; +import org.elasticsearch.action.bulk.BulkResponse; +import org.elasticsearch.action.search.SearchResponse; +import org.elasticsearch.client.transport.TransportClient; +import org.elasticsearch.index.query.QueryBuilders; +import org.elasticsearch.rest.RestStatus; +import org.elasticsearch.search.SearchHit; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.druid.pool.DruidDataSource; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig.ESMapping; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.FieldItem; +import com.alibaba.otter.canal.client.adapter.es.support.ESSyncUtil; +import com.alibaba.otter.canal.client.adapter.es.support.ESTemplate; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.EtlResult; +import com.google.common.base.Joiner; + +/** + * ES ETL Service + * + * @author rewerma 2018-11-01 + * @version 1.0.0 + */ +public class ESEtlService { + + private static Logger logger = LoggerFactory.getLogger(ESEtlService.class); + + private TransportClient transportClient; + private ESTemplate esTemplate; + private ESSyncConfig config; + + public ESEtlService(TransportClient transportClient, ESSyncConfig config){ + this.transportClient = transportClient; + this.esTemplate = new ESTemplate(transportClient); + this.config = config; + } + + public EtlResult importData(List params, boolean bulk) { + EtlResult etlResult = new EtlResult(); + AtomicLong impCount = new AtomicLong(); + List errMsg = new ArrayList<>(); + String esIndex = ""; + if (config == null) { + logger.warn("esSycnCofnig is null, etl go end !"); + etlResult.setErrorMessage("esSycnCofnig is null, etl go end !"); + return etlResult; + } + + ESMapping mapping = config.getEsMapping(); + + esIndex = mapping.get_index(); + DruidDataSource dataSource = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + Pattern pattern = Pattern.compile(".*:(.*)://.*/(.*)\\?.*$"); + Matcher matcher = pattern.matcher(dataSource.getUrl()); + if (!matcher.find()) { + throw new RuntimeException("Not found the schema of jdbc-url: " + config.getDataSourceKey()); + } + String schema = matcher.group(2); + + logger.info("etl from db: {}, to es index: {}", schema, esIndex); + long start = System.currentTimeMillis(); + try { + String sql = mapping.getSql(); + + // 拼接条件 + if (mapping.getEtlCondition() != null && params != null) { + String etlCondition = mapping.getEtlCondition(); + int size = params.size(); + for (int i = 0; i < size; i++) { + etlCondition = etlCondition.replace("{" + i + "}", params.get(i)); + } + + sql += " " + etlCondition; + } + + if (logger.isDebugEnabled()) { + logger.debug("etl sql : {}", mapping.getSql()); + } + + if (bulk) { + // 获取总数 + String countSql = "SELECT COUNT(1) FROM ( " + sql + ") _CNT "; + long cnt = (Long) ESSyncUtil.sqlRS(dataSource, countSql, rs -> { + Long count = null; + try { + if (rs.next()) { + count = ((Number) rs.getObject(1)).longValue(); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + return count == null ? 0L : count; + }); + + // 当大于1万条记录时开启多线程 + if (cnt >= 10000) { + int threadCount = 3; // TODO 从配置读取默认为3 + long perThreadCnt = cnt / threadCount; + ExecutorService executor = Executors.newFixedThreadPool(threadCount); + List> futures = new ArrayList<>(threadCount); + for (int i = 0; i < threadCount; i++) { + long offset = i * perThreadCnt; + Long size = null; + if (i != threadCount - 1) { + size = perThreadCnt; + } + String sqlFinal; + if (size != null) { + sqlFinal = sql + " LIMIT " + offset + "," + size; + } else { + sqlFinal = sql + " LIMIT " + offset + "," + cnt; + } + Future future = executor + .submit(() -> executeSqlImport(dataSource, sqlFinal, mapping, impCount, errMsg)); + futures.add(future); + } + + for (Future future : futures) { + future.get(); + } + + executor.shutdown(); + } else { + executeSqlImport(dataSource, sql, mapping, impCount, errMsg); + } + } else { + logger.info("自动ETL,无需统计记录总条数,直接进行ETL, index: {}", esIndex); + executeSqlImport(dataSource, sql, mapping, impCount, errMsg); + } + + logger.info("数据全量导入完成,一共导入 {} 条数据, 耗时: {}", impCount.get(), System.currentTimeMillis() - start); + etlResult.setResultMessage("导入ES索引 " + esIndex + " 数据:" + impCount.get() + " 条"); + } catch (Exception e) { + logger.error(e.getMessage(), e); + errMsg.add(esIndex + " etl failed! ==>" + e.getMessage()); + } + if (errMsg.isEmpty()) { + etlResult.setSucceeded(true); + } else { + etlResult.setErrorMessage(Joiner.on("\n").join(errMsg)); + } + return etlResult; + } + + private void processFailBulkResponse(BulkResponse bulkResponse, boolean hasParent) { + for (BulkItemResponse response : bulkResponse.getItems()) { + if (!response.isFailed()) { + continue; + } + + if (response.getFailure().getStatus() == RestStatus.NOT_FOUND) { + logger.warn(response.getFailureMessage()); + } else { + logger.error("全量导入数据有误 {}", response.getFailureMessage()); + throw new RuntimeException("全量数据 etl 异常: " + response.getFailureMessage()); + } + } + } + + private boolean executeSqlImport(DataSource ds, String sql, ESMapping mapping, AtomicLong impCount, + List errMsg) { + try { + ESSyncUtil.sqlRS(ds, sql, rs -> { + int count = 0; + try { + BulkRequestBuilder bulkRequestBuilder = transportClient.prepareBulk(); + + long batchBegin = System.currentTimeMillis(); + while (rs.next()) { + Map esFieldData = new LinkedHashMap<>(); + for (FieldItem fieldItem : mapping.getSchemaItem().getSelectFields().values()) { + + // 如果是主键字段则不插入 + if (fieldItem.getFieldName().equals(mapping.get_id())) { + continue; + } + + String fieldName = fieldItem.getFieldName(); + if (mapping.getSkips().contains(fieldName)) { + continue; + } + + Object val = esTemplate.getValFromRS(mapping, rs, fieldName, fieldName); + esFieldData.put(fieldName, val); + } + Object idVal = null; + if (mapping.get_id() != null) { + idVal = rs.getObject(mapping.get_id()); + } + + if (idVal != null) { + if (mapping.getParent() == null) { + bulkRequestBuilder.add(transportClient + .prepareIndex(mapping.get_index(), mapping.get_type(), idVal.toString()) + .setSource(esFieldData)); + } else { + // ignore + } + } else { + idVal = rs.getObject(mapping.getPk()); + if (mapping.getParent() == null) { + // 删除pk对应的数据 + SearchResponse response = transportClient.prepareSearch(mapping.get_index()) + .setTypes(mapping.get_type()) + .setQuery(QueryBuilders.termQuery(mapping.getPk(), idVal)) + .get(); + for (SearchHit hit : response.getHits()) { + bulkRequestBuilder.add(transportClient + .prepareDelete(mapping.get_index(), mapping.get_type(), hit.getId())); + } + + bulkRequestBuilder + .add(transportClient.prepareIndex(mapping.get_index(), mapping.get_type()) + .setSource(esFieldData)); + } else { + // ignore + } + } + + if (bulkRequestBuilder.numberOfActions() % mapping.getCommitBatch() == 0 + && bulkRequestBuilder.numberOfActions() > 0) { + long esBatchBegin = System.currentTimeMillis(); + BulkResponse rp = bulkRequestBuilder.execute().actionGet(); + if (rp.hasFailures()) { + this.processFailBulkResponse(rp, Objects.nonNull(mapping.getParent())); + } + + if (logger.isDebugEnabled()) { + logger.debug("全量数据批量导入批次耗时: {}, es执行时间: {}, 批次大小: {}, index; {}", + (System.currentTimeMillis() - batchBegin), + (System.currentTimeMillis() - esBatchBegin), + bulkRequestBuilder.numberOfActions(), + mapping.get_index()); + } + batchBegin = System.currentTimeMillis(); + bulkRequestBuilder = transportClient.prepareBulk(); + } + count++; + impCount.incrementAndGet(); + } + + if (bulkRequestBuilder.numberOfActions() > 0) { + long esBatchBegin = System.currentTimeMillis(); + BulkResponse rp = bulkRequestBuilder.execute().actionGet(); + if (rp.hasFailures()) { + this.processFailBulkResponse(rp, Objects.nonNull(mapping.getParent())); + } + if (logger.isDebugEnabled()) { + logger.debug("全量数据批量导入最后批次耗时: {}, es执行时间: {}, 批次大小: {}, index; {}", + (System.currentTimeMillis() - batchBegin), + (System.currentTimeMillis() - esBatchBegin), + bulkRequestBuilder.numberOfActions(), + mapping.get_index()); + } + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + errMsg.add(mapping.get_index() + " etl failed! ==>" + e.getMessage()); + throw new RuntimeException(e); + } + return count; + }); + + return true; + } catch (Exception e) { + logger.error(e.getMessage(), e); + return false; + } + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/service/ESSyncService.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/service/ESSyncService.java new file mode 100644 index 00000000..823a9d4c --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/service/ESSyncService.java @@ -0,0 +1,862 @@ +package com.alibaba.otter.canal.client.adapter.es.service; + +import java.util.Collection; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; + +import javax.sql.DataSource; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.serializer.SerializerFeature; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig.ESMapping; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.ColumnItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.FieldItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.TableItem; +import com.alibaba.otter.canal.client.adapter.es.support.ESSyncUtil; +import com.alibaba.otter.canal.client.adapter.es.support.ESTemplate; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +/** + * ES 同步 Service + * + * @author rewerma 2018-11-01 + * @version 1.0.0 + */ +public class ESSyncService { + + private static Logger logger = LoggerFactory.getLogger(ESSyncService.class); + + private ESTemplate esTemplate; + + public ESSyncService(ESTemplate esTemplate){ + this.esTemplate = esTemplate; + } + + public void sync(Collection esSyncConfigs, Dml dml) { + long begin = System.currentTimeMillis(); + if (esSyncConfigs != null) { + if (logger.isTraceEnabled()) { + logger.trace("Destination: {}, database:{}, table:{}, type:{}, effect index count: {}", + dml.getDestination(), + dml.getDatabase(), + dml.getTable(), + dml.getType(), + esSyncConfigs.size()); + } + + for (ESSyncConfig config : esSyncConfigs) { + if (logger.isTraceEnabled()) { + logger.trace("Prepared to sync index: {}, destination: {}", + config.getEsMapping().get_index(), + dml.getDestination()); + } + this.sync(config, dml); + if (logger.isTraceEnabled()) { + logger.trace("Sync completed: {}, destination: {}", + config.getEsMapping().get_index(), + dml.getDestination()); + } + } + if (logger.isTraceEnabled()) { + logger.trace("Sync elapsed time: {} ms, effect index count:{}, destination: {}", + (System.currentTimeMillis() - begin), + esSyncConfigs.size(), + dml.getDestination()); + } + if (logger.isDebugEnabled()) { + logger.debug("DML: {}", JSON.toJSONString(dml, SerializerFeature.WriteMapNullValue)); + } + } + } + + public void sync(ESSyncConfig config, Dml dml) { + try { + // 如果是按时间戳定时更新则返回 + if (config.getEsMapping().isSyncByTimestamp()) { + return; + } + + long begin = System.currentTimeMillis(); + + String type = dml.getType(); + if (type != null && type.equalsIgnoreCase("INSERT")) { + insert(config, dml); + } else if (type != null && type.equalsIgnoreCase("UPDATE")) { + update(config, dml); + } else if (type != null && type.equalsIgnoreCase("DELETE")) { + delete(config, dml); + } + + if (logger.isTraceEnabled()) { + logger.trace("Sync elapsed time: {} ms,destination: {}, es index: {}", + (System.currentTimeMillis() - begin), + dml.getDestination(), + config.getEsMapping().get_index()); + } + } catch (Exception e) { + logger.error("sync error, es index: {}, DML : {}", config.getEsMapping().get_index(), dml); + logger.error(e.getMessage(), e); + } + } + + /** + * 插入操作dml + * + * @param config es配置 + * @param dml dml数据 + */ + private void insert(ESSyncConfig config, Dml dml) { + List> dataList = dml.getData(); + if (dataList == null || dataList.isEmpty()) { + return; + } + SchemaItem schemaItem = config.getEsMapping().getSchemaItem(); + for (Map data : dataList) { + if (data == null || data.isEmpty()) { + continue; + } + + if (schemaItem.getAliasTableItems().size() == 1 && schemaItem.isAllFieldsSimple()) { + // ------单表 & 所有字段都为简单字段------ + singleTableSimpleFiledInsert(config, dml, data); + } else { + // ------是主表 查询sql来插入------ + if (schemaItem.getMainTable().getTableName().equalsIgnoreCase(dml.getTable())) { + mainTableInsert(config, dml, data); + } + + // 从表的操作 + for (TableItem tableItem : schemaItem.getAliasTableItems().values()) { + if (tableItem.isMain()) { + continue; + } + if (!tableItem.getTableName().equals(dml.getTable())) { + continue; + } + // 关联条件出现在主表查询条件是否为简单字段 + boolean allFieldsSimple = true; + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + if (fieldItem.isMethod() || fieldItem.isBinaryOp()) { + allFieldsSimple = false; + break; + } + } + // 所有查询字段均为简单字段 + if (allFieldsSimple) { + // 不是子查询 + if (!tableItem.isSubQuery()) { + // ------关联表简单字段插入------ + Map esFieldData = new LinkedHashMap<>(); + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + Object value = esTemplate.getValFromData(config.getEsMapping(), + data, + fieldItem.getFieldName(), + fieldItem.getColumn().getColumnName()); + esFieldData.put(fieldItem.getFieldName(), value); + } + + joinTableSimpleFieldOperation(config, dml, data, tableItem, esFieldData); + } else { + // ------关联子表简单字段插入------ + subTableSimpleFieldOperation(config, dml, data, null, tableItem); + } + } else { + // ------关联子表复杂字段插入 执行全sql更新es------ + wholeSqlOperation(config, dml, data, null, tableItem); + } + } + } + } + } + + /** + * 更新操作dml + * + * @param config es配置 + * @param dml dml数据 + */ + private void update(ESSyncConfig config, Dml dml) { + List> dataList = dml.getData(); + List> oldList = dml.getOld(); + if (dataList == null || dataList.isEmpty() || oldList == null || oldList.isEmpty()) { + return; + } + SchemaItem schemaItem = config.getEsMapping().getSchemaItem(); + int i = 0; + for (Map data : dataList) { + Map old = oldList.get(i); + if (data == null || data.isEmpty() || old == null || old.isEmpty()) { + continue; + } + + if (schemaItem.getAliasTableItems().size() == 1 && schemaItem.isAllFieldsSimple()) { + // ------单表 & 所有字段都为简单字段------ + singleTableSimpleFiledUpdate(config, dml, data, old); + } else { + // ------主表 查询sql来更新------ + if (schemaItem.getMainTable().getTableName().equalsIgnoreCase(dml.getTable())) { + ESMapping mapping = config.getEsMapping(); + String idFieldName = mapping.get_id() == null ? mapping.getPk() : mapping.get_id(); + FieldItem idFieldItem = schemaItem.getSelectFields().get(idFieldName); + + boolean idFieldSimple = true; + if (idFieldItem.isMethod() || idFieldItem.isBinaryOp()) { + idFieldSimple = false; + } + + boolean allUpdateFieldSimple = true; + out: for (FieldItem fieldItem : schemaItem.getSelectFields().values()) { + for (ColumnItem columnItem : fieldItem.getColumnItems()) { + if (old.containsKey(columnItem.getColumnName())) { + if (fieldItem.isMethod() || fieldItem.isBinaryOp()) { + allUpdateFieldSimple = false; + break out; + } + } + } + } + + // 不支持主键更新!! + + // 判断是否有外键更新 + boolean fkChanged = false; + for (TableItem tableItem : schemaItem.getAliasTableItems().values()) { + if (tableItem.isMain()) { + continue; + } + boolean changed = false; + for (List fieldItems : tableItem.getRelationTableFields().values()) { + for (FieldItem fieldItem : fieldItems) { + if (old.containsKey(fieldItem.getColumn().getColumnName())) { + fkChanged = true; + changed = true; + break; + } + } + } + // 如果外键有修改,则更新所对应该表的所有查询条件数据 + if (changed) { + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + fieldItem.getColumnItems() + .forEach(columnItem -> old.put(columnItem.getColumnName(), null)); + } + } + } + + // 判断主键和所更新的字段是否全为简单字段 + if (idFieldSimple && allUpdateFieldSimple && !fkChanged) { + singleTableSimpleFiledUpdate(config, dml, data, old); + } else { + mainTableUpdate(config, dml, data, old); + } + } + + // 从表的操作 + for (TableItem tableItem : schemaItem.getAliasTableItems().values()) { + if (tableItem.isMain()) { + continue; + } + if (!tableItem.getTableName().equals(dml.getTable())) { + continue; + } + + // 关联条件出现在主表查询条件是否为简单字段 + boolean allFieldsSimple = true; + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + if (fieldItem.isMethod() || fieldItem.isBinaryOp()) { + allFieldsSimple = false; + break; + } + } + + // 所有查询字段均为简单字段 + if (allFieldsSimple) { + // 不是子查询 + if (!tableItem.isSubQuery()) { + // ------关联表简单字段更新------ + Map esFieldData = new LinkedHashMap<>(); + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + if (old.containsKey(fieldItem.getColumn().getColumnName())) { + Object value = esTemplate.getValFromData(config.getEsMapping(), + data, + fieldItem.getFieldName(), + fieldItem.getColumn().getColumnName()); + esFieldData.put(fieldItem.getFieldName(), value); + } + } + joinTableSimpleFieldOperation(config, dml, data, tableItem, esFieldData); + } else { + // ------关联子表简单字段更新------ + subTableSimpleFieldOperation(config, dml, data, old, tableItem); + } + } else { + // ------关联子表复杂字段更新 执行全sql更新es------ + wholeSqlOperation(config, dml, data, old, tableItem); + } + } + } + + i++; + } + } + + /** + * 删除操作dml + * + * @param config es配置 + * @param dml dml数据 + */ + private void delete(ESSyncConfig config, Dml dml) { + List> dataList = dml.getData(); + if (dataList == null || dataList.isEmpty()) { + return; + } + SchemaItem schemaItem = config.getEsMapping().getSchemaItem(); + + for (Map data : dataList) { + if (data == null || data.isEmpty()) { + continue; + } + + ESMapping mapping = config.getEsMapping(); + + // ------是主表------ + if (schemaItem.getMainTable().getTableName().equalsIgnoreCase(dml.getTable())) { + FieldItem idFieldItem = schemaItem.getIdFieldItem(mapping); + // 主键为简单字段 + if (!idFieldItem.isMethod() && !idFieldItem.isBinaryOp()) { + Object idVal = esTemplate.getValFromData(mapping, + data, + idFieldItem.getFieldName(), + idFieldItem.getColumn().getColumnName()); + + if (logger.isTraceEnabled()) { + logger.trace("Main table delete es index, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + boolean result = esTemplate.delete(mapping, idVal); + if (!result) { + logger.error("Main table delete es index error, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + } else { + // ------主键带函数, 查询sql获取主键删除------ + mainTableDelete(config, dml, data); + } + } + + // 从表的操作 + for (TableItem tableItem : schemaItem.getAliasTableItems().values()) { + if (tableItem.isMain()) { + continue; + } + if (!tableItem.getTableName().equals(dml.getTable())) { + continue; + } + + // 关联条件出现在主表查询条件是否为简单字段 + boolean allFieldsSimple = true; + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + if (fieldItem.isMethod() || fieldItem.isBinaryOp()) { + allFieldsSimple = false; + break; + } + } + + // 所有查询字段均为简单字段 + if (allFieldsSimple) { + // 不是子查询 + if (!tableItem.isSubQuery()) { + // ------关联表简单字段更新为null------ + Map esFieldData = new LinkedHashMap<>(); + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + esFieldData.put(fieldItem.getFieldName(), null); + } + joinTableSimpleFieldOperation(config, dml, data, tableItem, esFieldData); + } else { + // ------关联子表简单字段更新------ + subTableSimpleFieldOperation(config, dml, data, null, tableItem); + } + } else { + // ------关联子表复杂字段更新 执行全sql更新es------ + wholeSqlOperation(config, dml, data, null, tableItem); + } + } + } + } + + /** + * 单表简单字段insert + * + * @param config es配置 + * @param dml dml信息 + * @param data 单行dml数据 + */ + private void singleTableSimpleFiledInsert(ESSyncConfig config, Dml dml, Map data) { + ESMapping mapping = config.getEsMapping(); + Map esFieldData = new LinkedHashMap<>(); + Object idVal = esTemplate.getESDataFromDmlData(mapping, data, esFieldData); + + if (logger.isTraceEnabled()) { + logger.trace("Single table insert ot es index, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + boolean result = esTemplate.insert(mapping, idVal, esFieldData); + if (!result) { + logger.error("Single table insert to es index error, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + } + + /** + * 主表(单表)复杂字段insert + * + * @param config es配置 + * @param dml dml信息 + * @param data 单行dml数据 + */ + private void mainTableInsert(ESSyncConfig config, Dml dml, Map data) { + ESMapping mapping = config.getEsMapping(); + String sql = mapping.getSql(); + String condition = ESSyncUtil.pkConditionSql(mapping, data); + sql = ESSyncUtil.appendCondition(sql, condition); + DataSource ds = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (logger.isTraceEnabled()) { + logger.trace("Main table insert ot es index by query sql, destination:{}, table: {}, index: {}, sql: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + sql.replace("\n", " ")); + } + ESSyncUtil.sqlRS(ds, sql, rs -> { + try { + while (rs.next()) { + Map esFieldData = new LinkedHashMap<>(); + Object idVal = esTemplate.getESDataFromRS(mapping, rs, esFieldData); + + if (logger.isTraceEnabled()) { + logger.trace( + "Main table insert ot es index by query sql, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + boolean result = esTemplate.insert(mapping, idVal, esFieldData); + if (!result) { + logger.error( + "Main table insert to es index by query sql error, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + } + } catch (Exception e) { + throw new RuntimeException(e); + } + return 0; + }); + } + + private void mainTableDelete(ESSyncConfig config, Dml dml, Map data) { + ESMapping mapping = config.getEsMapping(); + String sql = mapping.getSql(); + String condition = ESSyncUtil.pkConditionSql(mapping, data); + sql = ESSyncUtil.appendCondition(sql, condition); + DataSource ds = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (logger.isTraceEnabled()) { + logger.trace("Main table delete es index by query sql, destination:{}, table: {}, index: {}, sql: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + sql.replace("\n", " ")); + } + ESSyncUtil.sqlRS(ds, sql, rs -> { + try { + while (rs.next()) { + Object idVal = esTemplate.getIdValFromRS(mapping, rs); + + if (logger.isTraceEnabled()) { + logger.trace( + "Main table delete ot es index by query sql, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + boolean result = esTemplate.delete(mapping, idVal); + if (!result) { + logger.error( + "Main table delete to es index by query sql error, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + } + } catch (Exception e) { + throw new RuntimeException(e); + } + return 0; + }); + } + + /** + * 关联表主表简单字段operation + * + * @param config es配置 + * @param dml dml信息 + * @param data 单行dml数据 + * @param tableItem 当前表配置 + */ + private void joinTableSimpleFieldOperation(ESSyncConfig config, Dml dml, Map data, + TableItem tableItem, Map esFieldData) { + ESMapping mapping = config.getEsMapping(); + + Map paramsTmp = new LinkedHashMap<>(); + for (Map.Entry> entry : tableItem.getRelationTableFields().entrySet()) { + for (FieldItem fieldItem : entry.getValue()) { + if (fieldItem.getColumnItems().size() == 1) { + Object value = esTemplate.getValFromData(mapping, + data, + fieldItem.getFieldName(), + entry.getKey().getColumn().getColumnName()); + + String fieldName = fieldItem.getFieldName(); + // 判断是否是主键 + if (fieldName.equals(mapping.get_id())) { + fieldName = "_id"; + } + paramsTmp.put(fieldName, value); + } + } + } + + if (logger.isDebugEnabled()) { + logger.trace("Join table update es index by foreign key, destination:{}, table: {}, index: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index()); + } + boolean result = esTemplate.updateByQuery(config, paramsTmp, esFieldData); + if (!result) { + logger.error("Join table update es index by foreign key error, destination:{}, table: {}, index: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index()); + } + } + + /** + * 关联子查询, 主表简单字段operation + * + * @param config es配置 + * @param dml dml信息 + * @param data 单行dml数据 + * @param old 单行old数据 + * @param tableItem 当前表配置 + */ + private void subTableSimpleFieldOperation(ESSyncConfig config, Dml dml, Map data, + Map old, TableItem tableItem) { + ESMapping mapping = config.getEsMapping(); + StringBuilder sql = new StringBuilder( + "SELECT * FROM (" + tableItem.getSubQuerySql() + ") " + tableItem.getAlias() + " WHERE "); + + for (FieldItem fkFieldItem : tableItem.getRelationTableFields().keySet()) { + String columnName = fkFieldItem.getColumn().getColumnName(); + Object value = esTemplate.getValFromData(mapping, data, fkFieldItem.getFieldName(), columnName); + ESSyncUtil.appendCondition(sql, value, tableItem.getAlias(), columnName); + } + int len = sql.length(); + sql.delete(len - 5, len); + DataSource ds = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (logger.isTraceEnabled()) { + logger.trace("Join table update es index by query sql, destination:{}, table: {}, index: {}, sql: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + sql.toString().replace("\n", " ")); + } + ESSyncUtil.sqlRS(ds, sql.toString(), rs -> { + try { + while (rs.next()) { + Map esFieldData = new LinkedHashMap<>(); + + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + if (old != null) { + out: for (FieldItem fieldItem1 : tableItem.getSubQueryFields()) { + for (ColumnItem columnItem0 : fieldItem.getColumnItems()) { + if (fieldItem1.getFieldName().equals(columnItem0.getColumnName())) + for (ColumnItem columnItem : fieldItem1.getColumnItems()) { + if (old.containsKey(columnItem.getColumnName())) { + Object val = esTemplate.getValFromRS(mapping, + rs, + fieldItem.getFieldName(), + fieldItem.getColumn().getColumnName()); + esFieldData.put(fieldItem.getFieldName(), val); + break out; + } + } + } + } + } else { + Object val = esTemplate.getValFromRS(mapping, + rs, + fieldItem.getFieldName(), + fieldItem.getColumn().getColumnName()); + esFieldData.put(fieldItem.getFieldName(), val); + } + } + + Map paramsTmp = new LinkedHashMap<>(); + for (Map.Entry> entry : tableItem.getRelationTableFields().entrySet()) { + for (FieldItem fieldItem : entry.getValue()) { + if (fieldItem.getColumnItems().size() == 1) { + Object value = esTemplate.getValFromRS(mapping, + rs, + fieldItem.getFieldName(), + entry.getKey().getColumn().getColumnName()); + String fieldName = fieldItem.getFieldName(); + // 判断是否是主键 + if (fieldName.equals(mapping.get_id())) { + fieldName = "_id"; + } + paramsTmp.put(fieldName, value); + } + } + } + + if (logger.isDebugEnabled()) { + logger.trace("Join table update es index by query sql, destination:{}, table: {}, index: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index()); + } + boolean result = esTemplate.updateByQuery(config, paramsTmp, esFieldData); + if (!result) { + logger.error( + "Join table update es index by query sql error, destination:{}, table: {}, index: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index()); + } + } + } catch (Exception e) { + throw new RuntimeException(e); + } + return 0; + }); + } + + /** + * 关联(子查询), 主表复杂字段operation, 全sql执行 + * + * @param config es配置 + * @param dml dml信息 + * @param data 单行dml数据 + * @param tableItem 当前表配置 + */ + private void wholeSqlOperation(ESSyncConfig config, Dml dml, Map data, Map old, + TableItem tableItem) { + ESMapping mapping = config.getEsMapping(); + StringBuilder sql = new StringBuilder(mapping.getSql() + " WHERE "); + + for (FieldItem fkFieldItem : tableItem.getRelationTableFields().keySet()) { + String columnName = fkFieldItem.getColumn().getColumnName(); + Object value = esTemplate.getValFromData(mapping, data, fkFieldItem.getFieldName(), columnName); + ESSyncUtil.appendCondition(sql, value, tableItem.getAlias(), columnName); + } + int len = sql.length(); + sql.delete(len - 5, len); + DataSource ds = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (logger.isTraceEnabled()) { + logger.trace("Join table update es index by query whole sql, destination:{}, table: {}, index: {}, sql: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + sql.toString().replace("\n", " ")); + } + ESSyncUtil.sqlRS(ds, sql.toString(), rs -> { + try { + while (rs.next()) { + Map esFieldData = new LinkedHashMap<>(); + for (FieldItem fieldItem : tableItem.getRelationSelectFieldItems()) { + if (old != null) { + // 从表子查询 + out: for (FieldItem fieldItem1 : tableItem.getSubQueryFields()) { + for (ColumnItem columnItem0 : fieldItem.getColumnItems()) { + if (fieldItem1.getFieldName().equals(columnItem0.getColumnName())) + for (ColumnItem columnItem : fieldItem1.getColumnItems()) { + if (old.containsKey(columnItem.getColumnName())) { + Object val = esTemplate.getValFromRS(mapping, + rs, + fieldItem.getFieldName(), + fieldItem.getFieldName()); + esFieldData.put(fieldItem.getFieldName(), val); + break out; + } + } + } + } + // 从表非子查询 + for (FieldItem fieldItem1 : tableItem.getRelationSelectFieldItems()) { + if (fieldItem1.equals(fieldItem)) { + for (ColumnItem columnItem : fieldItem1.getColumnItems()) { + if (old.containsKey(columnItem.getColumnName())) { + Object val = esTemplate.getValFromRS(mapping, + rs, + fieldItem.getFieldName(), + fieldItem.getFieldName()); + esFieldData.put(fieldItem.getFieldName(), val); + break; + } + } + } + } + } else { + Object val = esTemplate + .getValFromRS(mapping, rs, fieldItem.getFieldName(), fieldItem.getFieldName()); + esFieldData.put(fieldItem.getFieldName(), val); + } + } + + Map paramsTmp = new LinkedHashMap<>(); + for (Map.Entry> entry : tableItem.getRelationTableFields().entrySet()) { + for (FieldItem fieldItem : entry.getValue()) { + Object value = esTemplate + .getValFromRS(mapping, rs, fieldItem.getFieldName(), fieldItem.getFieldName()); + String fieldName = fieldItem.getFieldName(); + // 判断是否是主键 + if (fieldName.equals(mapping.get_id())) { + fieldName = "_id"; + } + paramsTmp.put(fieldName, value); + } + } + + if (logger.isDebugEnabled()) { + logger.trace( + "Join table update es index by query whole sql, destination:{}, table: {}, index: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index()); + } + boolean result = esTemplate.updateByQuery(config, paramsTmp, esFieldData); + if (!result) { + logger.error( + "Join table update es index by query whole sql error, destination:{}, table: {}, index: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index()); + } + } + } catch (Exception e) { + throw new RuntimeException(e); + } + return 0; + }); + } + + /** + * 单表简单字段update + * + * @param config es配置 + * @param dml dml信息 + * @param data 单行data数据 + * @param old 单行old数据 + */ + private void singleTableSimpleFiledUpdate(ESSyncConfig config, Dml dml, Map data, + Map old) { + ESMapping mapping = config.getEsMapping(); + Map esFieldData = new LinkedHashMap<>(); + + Object idVal = esTemplate.getESDataFromDmlData(mapping, data, old, esFieldData); + + if (logger.isTraceEnabled()) { + logger.trace("Main table update ot es index, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + boolean result = esTemplate.update(mapping, idVal, esFieldData); + if (!result) { + logger.error("Main table update to es index error, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + } + + /** + * 主表(单表)复杂字段update + * + * @param config es配置 + * @param dml dml信息 + * @param data 单行dml数据 + */ + private void mainTableUpdate(ESSyncConfig config, Dml dml, Map data, Map old) { + ESMapping mapping = config.getEsMapping(); + String sql = mapping.getSql(); + String condition = ESSyncUtil.pkConditionSql(mapping, data); + sql = ESSyncUtil.appendCondition(sql, condition); + DataSource ds = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (logger.isTraceEnabled()) { + logger.trace("Main table update ot es index by query sql, destination:{}, table: {}, index: {}, sql: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + sql.replace("\n", " ")); + } + ESSyncUtil.sqlRS(ds, sql, rs -> { + try { + while (rs.next()) { + Map esFieldData = new LinkedHashMap<>(); + Object idVal = esTemplate.getESDataFromRS(mapping, rs, old, esFieldData); + + if (logger.isTraceEnabled()) { + logger.trace( + "Main table update ot es index by query sql, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + boolean result = esTemplate.update(mapping, idVal, esFieldData); + if (!result) { + logger.error( + "Main table update to es index by query sql error, destination:{}, table: {}, index: {}, id: {}", + config.getDestination(), + dml.getTable(), + mapping.get_index(), + idVal); + } + } + } catch (Exception e) { + throw new RuntimeException(e); + } + return 0; + }); + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/support/ESSyncUtil.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/support/ESSyncUtil.java new file mode 100644 index 00000000..cf8f8fd4 --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/support/ESSyncUtil.java @@ -0,0 +1,335 @@ +package com.alibaba.otter.canal.client.adapter.es.support; + +import java.io.IOException; +import java.io.InputStream; +import java.nio.charset.StandardCharsets; +import java.sql.*; +import java.util.*; +import java.util.Date; +import java.util.function.Function; + +import javax.sql.DataSource; + +import org.apache.commons.codec.binary.Base64; +import org.joda.time.DateTime; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.fastjson.JSON; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig.ESMapping; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.ColumnItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.TableItem; + +/** + * ES 同步工具同类 + * + * @author rewerma 2018-11-01 + * @version 1.0.0 + */ +public class ESSyncUtil { + + private static Logger logger = LoggerFactory.getLogger(ESSyncUtil.class); + + public static Object convertToEsObj(Object val, String fieldInfo) { + if (val == null) { + return null; + } + if (fieldInfo.startsWith("array:")) { + String separator = fieldInfo.substring("array:".length()).trim(); + String[] values = val.toString().split(separator); + return Arrays.asList(values); + } else if (fieldInfo.startsWith("object")) { + return JSON.parse(val.toString()); + } + return null; + } + + /** + * 类型转换为Mapping中对应的类型 + */ + public static Object typeConvert(Object val, String esType) { + if (val == null) { + return null; + } + if (esType == null) { + return val; + } + Object res = null; + if ("integer".equals(esType)) { + if (val instanceof Number) { + res = ((Number) val).intValue(); + } else { + res = Integer.parseInt(val.toString()); + } + } else if ("long".equals(esType)) { + if (val instanceof Number) { + res = ((Number) val).longValue(); + } else { + res = Long.parseLong(val.toString()); + } + } else if ("short".equals(esType)) { + if (val instanceof Number) { + res = ((Number) val).shortValue(); + } else { + res = Short.parseShort(val.toString()); + } + } else if ("byte".equals(esType)) { + if (val instanceof Number) { + res = ((Number) val).byteValue(); + } else { + res = Byte.parseByte(val.toString()); + } + } else if ("double".equals(esType)) { + if (val instanceof Number) { + res = ((Number) val).doubleValue(); + } else { + res = Double.parseDouble(val.toString()); + } + } else if ("float".equals(esType) || "half_float".equals(esType) || "scaled_float".equals(esType)) { + if (val instanceof Number) { + res = ((Number) val).floatValue(); + } else { + res = Float.parseFloat(val.toString()); + } + } else if ("boolean".equals(esType)) { + if (val instanceof Boolean) { + res = val; + } else if (val instanceof Number) { + int v = ((Number) val).intValue(); + res = v != 0; + } else { + res = Boolean.parseBoolean(val.toString()); + } + } else if ("date".equals(esType)) { + if (val instanceof java.sql.Time) { + DateTime dateTime = new DateTime(((java.sql.Time) val).getTime()); + if (dateTime.getMillisOfSecond() != 0) { + res = dateTime.toString("HH:mm:ss.SSS"); + } else { + res = dateTime.toString("HH:mm:ss"); + } + } else if (val instanceof java.sql.Timestamp) { + DateTime dateTime = new DateTime(((java.sql.Timestamp) val).getTime()); + if (dateTime.getMillisOfSecond() != 0) { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss.SSS+08:00"); + } else { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss+08:00"); + } + } else if (val instanceof java.sql.Date || val instanceof Date) { + DateTime dateTime; + if (val instanceof java.sql.Date) { + dateTime = new DateTime(((java.sql.Date) val).getTime()); + } else { + dateTime = new DateTime(((Date) val).getTime()); + } + if (dateTime.getHourOfDay() == 0 && dateTime.getMinuteOfHour() == 0 && dateTime.getSecondOfMinute() == 0 + && dateTime.getMillisOfSecond() == 0) { + res = dateTime.toString("yyyy-MM-dd"); + } else { + if (dateTime.getMillisOfSecond() != 0) { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss.SSS+08:00"); + } else { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss+08:00"); + } + } + } else if (val instanceof Long) { + DateTime dateTime = new DateTime(((Long) val).longValue()); + if (dateTime.getHourOfDay() == 0 && dateTime.getMinuteOfHour() == 0 && dateTime.getSecondOfMinute() == 0 + && dateTime.getMillisOfSecond() == 0) { + res = dateTime.toString("yyyy-MM-dd"); + } else if (dateTime.getMillisOfSecond() != 0) { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss.SSS+08:00"); + } else { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss+08:00"); + } + } else if (val instanceof String) { + String v = ((String) val).trim(); + if (v.length() > 18 && v.charAt(4) == '-' && v.charAt(7) == '-' && v.charAt(10) == ' ' + && v.charAt(13) == ':' && v.charAt(16) == ':') { + String dt = v.substring(0, 10) + "T" + v.substring(11); + DateTime dateTime = new DateTime(dt); + if (dateTime.getMillisOfSecond() != 0) { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss.SSS+08:00"); + } else { + res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss+08:00"); + } + } else if (v.length() == 10 && v.charAt(4) == '-' && v.charAt(7) == '-') { + DateTime dateTime = new DateTime(v); + res = dateTime.toString("yyyy-MM-dd"); + } + } + } else if ("binary".equals(esType)) { + if (val instanceof byte[]) { + Base64 base64 = new Base64(); + res = base64.encodeAsString((byte[]) val); + } else if (val instanceof Blob) { + byte[] b = blobToBytes((Blob) val); + Base64 base64 = new Base64(); + res = base64.encodeAsString(b); + } else if (val instanceof String) { + // 对应canal中的单字节编码 + byte[] b = ((String) val).getBytes(StandardCharsets.ISO_8859_1); + Base64 base64 = new Base64(); + res = base64.encodeAsString(b); + } + } else if ("geo_point".equals(esType)) { + if (!(val instanceof String)) { + logger.error("es type is geo_point, but source type is not String"); + return val; + } + + if (!((String) val).contains(",")) { + logger.error("es type is geo_point, source value not contains ',' separator"); + return val; + } + + String[] point = ((String) val).split(","); + Map location = new HashMap<>(); + location.put("lat", Double.valueOf(point[0].trim())); + location.put("lon", Double.valueOf(point[1].trim())); + return location; + } else if ("array".equals(esType)) { + if ("".equals(val.toString().trim())) { + res = new ArrayList<>(); + } else { + String value = val.toString(); + String separator = ","; + if (!value.contains(",")) { + if (value.contains(";")) { + separator = ";"; + } else if (value.contains("|")) { + separator = "|"; + } else if (value.contains("-")) { + separator = "-"; + } + } + String[] values = value.split(separator); + return Arrays.asList(values); + } + } else if ("object".equals(esType)) { + if ("".equals(val.toString().trim())) { + res = new HashMap<>(); + } else { + res = JSON.parseObject(val.toString(), Map.class); + } + } else { + // 其他类全以字符串处理 + res = val.toString(); + } + + return res; + } + + /** + * Blob转byte[] + */ + private static byte[] blobToBytes(Blob blob) { + try (InputStream is = blob.getBinaryStream()) { + byte[] b = new byte[(int) blob.length()]; + is.read(b); + return b; + } catch (IOException | SQLException e) { + logger.error(e.getMessage()); + return null; + } + } + + /** + * 拼接主键条件 + * + * @param mapping + * @param data + * @return + */ + public static String pkConditionSql(ESMapping mapping, Map data) { + Set idColumns = new LinkedHashSet<>(); + SchemaItem schemaItem = mapping.getSchemaItem(); + + TableItem mainTable = schemaItem.getMainTable(); + + for (ColumnItem idColumnItem : schemaItem.getIdFieldItem(mapping).getColumnItems()) { + if ((mainTable.getAlias() == null && idColumnItem.getOwner() == null) + || (mainTable.getAlias() != null && mainTable.getAlias().equals(idColumnItem.getOwner()))) { + idColumns.add(idColumnItem); + } + } + + if (idColumns.isEmpty()) { + throw new RuntimeException("Not found primary key field in main table"); + } + + // 拼接condition + StringBuilder condition = new StringBuilder(" "); + for (ColumnItem idColumn : idColumns) { + Object idVal = data.get(idColumn.getColumnName()); + if (mainTable.getAlias() != null) condition.append(mainTable.getAlias()).append("."); + condition.append(idColumn.getColumnName()).append("="); + if (idVal instanceof String) { + condition.append("'").append(idVal).append("' AND "); + } else { + condition.append(idVal).append(" AND "); + } + } + + if (condition.toString().endsWith("AND ")) { + int len2 = condition.length(); + condition.delete(len2 - 4, len2); + } + return condition.toString(); + } + + public static String appendCondition(String sql, String condition) { + return sql + " WHERE " + condition + " "; + } + + public static void appendCondition(StringBuilder sql, Object value, String owner, String columnName) { + if (value instanceof String) { + sql.append(owner).append(".").append(columnName).append("='").append(value).append("' AND "); + } else { + sql.append(owner).append(".").append(columnName).append("=").append(value).append(" AND "); + } + } + + /** + * 执行查询sql + */ + public static Object sqlRS(DataSource ds, String sql, Function fun) { + Connection conn = null; + Statement smt = null; + ResultSet rs = null; + try { + conn = ds.getConnection(); + smt = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY); + smt.setFetchSize(Integer.MIN_VALUE); + rs = smt.executeQuery(sql); + + return fun.apply(rs); + } catch (SQLException e) { + logger.error("sqlRs has error, sql: {} ", sql); + throw new RuntimeException(e); + } finally { + if (rs != null) { + try { + rs.close(); + } catch (SQLException e) { + logger.error("error to close result set"); + } + } + if (smt != null) { + try { + smt.close(); + } catch (SQLException e) { + logger.error("error to close statement"); + } + } + if (conn != null) { + try { + conn.close(); + } catch (SQLException e) { + logger.error("error to close db connection"); + } + } + } + } +} diff --git a/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/support/ESTemplate.java b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/support/ESTemplate.java new file mode 100644 index 00000000..e57b89b7 --- /dev/null +++ b/client-adapter/elasticsearch/src/main/java/com/alibaba/otter/canal/client/adapter/es/support/ESTemplate.java @@ -0,0 +1,526 @@ +package com.alibaba.otter.canal.client.adapter.es.support; + +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.*; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.TimeUnit; + +import javax.sql.DataSource; + +import com.alibaba.fastjson.JSON; +import org.elasticsearch.action.bulk.BulkItemResponse; +import org.elasticsearch.action.bulk.BulkRequestBuilder; +import org.elasticsearch.action.bulk.BulkResponse; +import org.elasticsearch.action.search.SearchResponse; +import org.elasticsearch.client.transport.TransportClient; +import org.elasticsearch.cluster.metadata.MappingMetaData; +import org.elasticsearch.common.collect.ImmutableOpenMap; +import org.elasticsearch.index.query.BoolQueryBuilder; +import org.elasticsearch.index.query.QueryBuilder; +import org.elasticsearch.index.query.QueryBuilders; +import org.elasticsearch.index.reindex.BulkByScrollResponse; +import org.elasticsearch.index.reindex.UpdateByQueryAction; +import org.elasticsearch.index.reindex.UpdateByQueryRequestBuilder; +import org.elasticsearch.rest.RestStatus; +import org.elasticsearch.script.Script; +import org.elasticsearch.script.ScriptType; +import org.elasticsearch.search.SearchHit; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.util.CollectionUtils; + +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig.ESMapping; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.ColumnItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.FieldItem; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; + +/** + * ES 操作模板 + * + * @author rewerma 2018-11-01 + * @version 1.0.0 + */ +public class ESTemplate { + + private static final Logger logger = LoggerFactory.getLogger(ESTemplate.class); + + private static final int MAX_BATCH_SIZE = 1000; + + private TransportClient transportClient; + + public ESTemplate(TransportClient transportClient){ + this.transportClient = transportClient; + } + + /** + * 插入数据 + * + * @param mapping + * @param pkVal + * @param esFieldData + * @return + */ + public boolean insert(ESMapping mapping, Object pkVal, Map esFieldData) { + BulkRequestBuilder bulkRequestBuilder = transportClient.prepareBulk(); + if (mapping.get_id() != null) { + bulkRequestBuilder + .add(transportClient.prepareIndex(mapping.get_index(), mapping.get_type(), pkVal.toString()) + .setSource(esFieldData)); + } else { + SearchResponse response = transportClient.prepareSearch(mapping.get_index()) + .setTypes(mapping.get_type()) + .setQuery(QueryBuilders.termQuery(mapping.getPk(), pkVal)) + .setSize(MAX_BATCH_SIZE) + .get(); + for (SearchHit hit : response.getHits()) { + bulkRequestBuilder + .add(transportClient.prepareDelete(mapping.get_index(), mapping.get_type(), hit.getId())); + } + bulkRequestBuilder + .add(transportClient.prepareIndex(mapping.get_index(), mapping.get_type()).setSource(esFieldData)); + } + return commitBulkRequest(bulkRequestBuilder); + } + + /** + * 根据主键更新数据 + * + * @param mapping + * @param pkVal + * @param esFieldData + * @return + */ + public boolean update(ESMapping mapping, Object pkVal, Map esFieldData) { + BulkRequestBuilder bulkRequestBuilder = transportClient.prepareBulk(); + append4Update(bulkRequestBuilder, mapping, pkVal, esFieldData); + return commitBulkRequest(bulkRequestBuilder); + } + + public void append4Update(BulkRequestBuilder bulkRequestBuilder, ESMapping mapping, Object pkVal, + Map esFieldData) { + if (mapping.get_id() != null) { + bulkRequestBuilder + .add(transportClient.prepareUpdate(mapping.get_index(), mapping.get_type(), pkVal.toString()) + .setDoc(esFieldData)); + } else { + SearchResponse response = transportClient.prepareSearch(mapping.get_index()) + .setTypes(mapping.get_type()) + .setQuery(QueryBuilders.termQuery(mapping.getPk(), pkVal)) + .setSize(MAX_BATCH_SIZE) + .get(); + for (SearchHit hit : response.getHits()) { + bulkRequestBuilder + .add(transportClient.prepareUpdate(mapping.get_index(), mapping.get_type(), hit.getId()) + .setDoc(esFieldData)); + } + } + } + + /** + * update by query + * + * @param config + * @param paramsTmp + * @param esFieldData + * @return + */ + public boolean updateByQuery(ESSyncConfig config, Map paramsTmp, Map esFieldData) { + if (paramsTmp.isEmpty()) { + return false; + } + ESMapping mapping = config.getEsMapping(); + BoolQueryBuilder queryBuilder = QueryBuilders.boolQuery(); + paramsTmp.forEach((fieldName, value) -> queryBuilder.must(QueryBuilders.termsQuery(fieldName, value))); + + SearchResponse response = transportClient.prepareSearch(mapping.get_index()) + .setTypes(mapping.get_type()) + .setSize(0) + .setQuery(queryBuilder) + .get(); + long count = response.getHits().getTotalHits(); + // 如果更新量大于Max, 查询sql批量更新 + if (count > MAX_BATCH_SIZE) { + BulkRequestBuilder bulkRequestBuilder = transportClient.prepareBulk(); + + DataSource ds = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + // 查询sql更新 + StringBuilder sql = new StringBuilder("SELECT * FROM (" + mapping.getSql() + ") _v WHERE "); + paramsTmp.forEach( + (fieldName, value) -> sql.append("_v.").append(fieldName).append("=").append(value).append(" AND ")); + int len = sql.length(); + sql.delete(len - 4, len); + ESSyncUtil.sqlRS(ds, sql.toString(), rs -> { + int exeCount = 1; + try { + BulkRequestBuilder bulkRequestBuilderTmp = bulkRequestBuilder; + while (rs.next()) { + Object idVal = getIdValFromRS(mapping, rs); + append4Update(bulkRequestBuilderTmp, mapping, idVal, esFieldData); + + if (exeCount % mapping.getCommitBatch() == 0 && bulkRequestBuilderTmp.numberOfActions() > 0) { + commitBulkRequest(bulkRequestBuilderTmp); + bulkRequestBuilderTmp = transportClient.prepareBulk(); + } + exeCount++; + } + + if (bulkRequestBuilder.numberOfActions() > 0) { + commitBulkRequest(bulkRequestBuilderTmp); + } + } catch (Exception e) { + throw new RuntimeException(e); + } + return 0; + }); + return true; + } else { + return updateByQuery(mapping, queryBuilder, esFieldData, 1); + } + } + + private boolean updateByQuery(ESMapping mapping, QueryBuilder queryBuilder, Map esFieldData, + int counter) { + if (CollectionUtils.isEmpty(esFieldData)) { + return true; + } + + StringBuilder sb = new StringBuilder(); + esFieldData.forEach((key, value) -> { + if (value instanceof Map) { + HashMap mapValue = (HashMap) value; + if (mapValue.containsKey("lon") && mapValue.containsKey("lat") && mapValue.size() == 2) { + sb.append("ctx._source") + .append("['") + .append(key) + .append("']") + .append(" = [") + .append(mapValue.get("lon")) + .append(", ") + .append(mapValue.get("lat")) + .append("];"); + } else { + sb.append("ctx._source").append("[\"").append(key).append("\"]").append(" = "); + sb.append(JSON.toJSONString(value)); + sb.append(";"); + } + } else if (value instanceof List) { + sb.append("ctx._source").append("[\"").append(key).append("\"]").append(" = "); + sb.append(JSON.toJSONString(value)); + sb.append(";"); + } else if (value instanceof String) { + sb.append("ctx._source") + .append("['") + .append(key) + .append("']") + .append(" = '") + .append(value) + .append("';"); + } else { + sb.append("ctx._source").append("['").append(key).append("']").append(" = ").append(value).append(";"); + } + }); + String scriptLine = sb.toString(); + if (logger.isTraceEnabled()) { + logger.trace(scriptLine); + } + + UpdateByQueryRequestBuilder updateByQuery = UpdateByQueryAction.INSTANCE.newRequestBuilder(transportClient); + updateByQuery.source(mapping.get_index()) + .abortOnVersionConflict(false) + .filter(queryBuilder) + .script(new Script(ScriptType.INLINE, "painless", scriptLine, Collections.emptyMap())); + + BulkByScrollResponse response = updateByQuery.get(); + if (logger.isTraceEnabled()) { + logger.trace("updateByQuery response: {}", response.getStatus()); + } + if (!CollectionUtils.isEmpty(response.getSearchFailures())) { + logger.error("script update_for_search has search error: " + response.getBulkFailures()); + return false; + } + + if (!CollectionUtils.isEmpty(response.getBulkFailures())) { + logger.error("script update_for_search has update error: " + response.getBulkFailures()); + return false; + } + + if (response.getStatus().getVersionConflicts() > 0) { + if (counter >= 3) { + logger.error("第 {} 次执行updateByQuery, 依旧存在分片版本冲突,不再继续重试。", counter); + return false; + } + logger.warn("本次updateByQuery存在分片版本冲突,准备重新执行..."); + try { + TimeUnit.SECONDS.sleep(1); + } catch (InterruptedException e) { + // ignore + } + return updateByQuery(mapping, queryBuilder, esFieldData, ++counter); + } + + return true; + } + + /** + * 通过主键删除数据 + * + * @param mapping + * @param pkVal + * @return + */ + public boolean delete(ESMapping mapping, Object pkVal) { + BulkRequestBuilder bulkRequestBuilder = transportClient.prepareBulk(); + if (mapping.get_id() != null) { + bulkRequestBuilder + .add(transportClient.prepareDelete(mapping.get_index(), mapping.get_type(), pkVal.toString())); + } else { + SearchResponse response = transportClient.prepareSearch(mapping.get_index()) + .setTypes(mapping.get_type()) + .setQuery(QueryBuilders.termQuery(mapping.getPk(), pkVal)) + .setSize(MAX_BATCH_SIZE) + .get(); + for (SearchHit hit : response.getHits()) { + bulkRequestBuilder + .add(transportClient.prepareDelete(mapping.get_index(), mapping.get_type(), hit.getId())); + } + } + return commitBulkRequest(bulkRequestBuilder); + } + + /** + * 批量提交 + * + * @param bulkRequestBuilder + * @return + */ + private static boolean commitBulkRequest(BulkRequestBuilder bulkRequestBuilder) { + if (bulkRequestBuilder.numberOfActions() > 0) { + BulkResponse response = bulkRequestBuilder.execute().actionGet(); + if (response.hasFailures()) { + for (BulkItemResponse itemResponse : response.getItems()) { + if (!itemResponse.isFailed()) { + continue; + } + + if (itemResponse.getFailure().getStatus() == RestStatus.NOT_FOUND) { + logger.warn(itemResponse.getFailureMessage()); + } else { + logger.error("ES sync commit error: {}", itemResponse.getFailureMessage()); + } + } + } + + return !response.hasFailures(); + } + return true; + } + + public Object getValFromRS(ESMapping mapping, ResultSet resultSet, String fieldName, + String columnName) throws SQLException { + String esType = getEsType(mapping, fieldName); + + Object value = resultSet.getObject(columnName); + if (value instanceof Boolean) { + if (!"boolean".equals(esType)) { + value = resultSet.getByte(columnName); + } + } + + // 如果是对象类型 + if (mapping.getObjFields().containsKey(fieldName)) { + return ESSyncUtil.convertToEsObj(value, mapping.getObjFields().get(fieldName)); + } else { + return ESSyncUtil.typeConvert(value, esType); + } + } + + public Object getESDataFromRS(ESMapping mapping, ResultSet resultSet, + Map esFieldData) throws SQLException { + SchemaItem schemaItem = mapping.getSchemaItem(); + String idFieldName = mapping.get_id() == null ? mapping.getPk() : mapping.get_id(); + Object resultIdVal = null; + for (FieldItem fieldItem : schemaItem.getSelectFields().values()) { + Object value = getValFromRS(mapping, resultSet, fieldItem.getFieldName(), fieldItem.getFieldName()); + + if (fieldItem.getFieldName().equals(idFieldName)) { + resultIdVal = value; + } + + if (!fieldItem.getFieldName().equals(mapping.get_id()) + && !mapping.getSkips().contains(fieldItem.getFieldName())) { + esFieldData.put(fieldItem.getFieldName(), value); + } + } + return resultIdVal; + } + + public Object getIdValFromRS(ESMapping mapping, ResultSet resultSet) throws SQLException { + SchemaItem schemaItem = mapping.getSchemaItem(); + String idFieldName = mapping.get_id() == null ? mapping.getPk() : mapping.get_id(); + Object resultIdVal = null; + for (FieldItem fieldItem : schemaItem.getSelectFields().values()) { + Object value = getValFromRS(mapping, resultSet, fieldItem.getFieldName(), fieldItem.getFieldName()); + + if (fieldItem.getFieldName().equals(idFieldName)) { + resultIdVal = value; + break; + } + } + return resultIdVal; + } + + public Object getESDataFromRS(ESMapping mapping, ResultSet resultSet, Map dmlOld, + Map esFieldData) throws SQLException { + SchemaItem schemaItem = mapping.getSchemaItem(); + String idFieldName = mapping.get_id() == null ? mapping.getPk() : mapping.get_id(); + Object resultIdVal = null; + for (FieldItem fieldItem : schemaItem.getSelectFields().values()) { + if (fieldItem.getFieldName().equals(idFieldName)) { + resultIdVal = getValFromRS(mapping, resultSet, fieldItem.getFieldName(), fieldItem.getFieldName()); + } + + for (ColumnItem columnItem : fieldItem.getColumnItems()) { + if (dmlOld.containsKey(columnItem.getColumnName()) + && !mapping.getSkips().contains(fieldItem.getFieldName())) { + esFieldData.put(fieldItem.getFieldName(), + getValFromRS(mapping, resultSet, fieldItem.getFieldName(), fieldItem.getFieldName())); + break; + } + } + } + return resultIdVal; + } + + public Object getValFromData(ESMapping mapping, Map dmlData, String fieldName, String columnName) { + String esType = getEsType(mapping, fieldName); + Object value = dmlData.get(columnName); + if (value instanceof Byte) { + if ("boolean".equals(esType)) { + value = ((Byte) value).intValue() != 0; + } + } + + // 如果是对象类型 + if (mapping.getObjFields().containsKey(fieldName)) { + return ESSyncUtil.convertToEsObj(value, mapping.getObjFields().get(fieldName)); + } else { + return ESSyncUtil.typeConvert(value, esType); + } + } + + /** + * 将dml的data转换为es的data + * + * @param mapping 配置mapping + * @param dmlData dml data + * @param esFieldData es data + * @return 返回 id 值 + */ + public Object getESDataFromDmlData(ESMapping mapping, Map dmlData, + Map esFieldData) { + SchemaItem schemaItem = mapping.getSchemaItem(); + String idFieldName = mapping.get_id() == null ? mapping.getPk() : mapping.get_id(); + Object resultIdVal = null; + for (FieldItem fieldItem : schemaItem.getSelectFields().values()) { + String columnName = fieldItem.getColumnItems().iterator().next().getColumnName(); + Object value = getValFromData(mapping, dmlData, fieldItem.getFieldName(), columnName); + + if (fieldItem.getFieldName().equals(idFieldName)) { + resultIdVal = value; + } + + if (!fieldItem.getFieldName().equals(mapping.get_id()) + && !mapping.getSkips().contains(fieldItem.getFieldName())) { + esFieldData.put(fieldItem.getFieldName(), value); + } + } + return resultIdVal; + } + + /** + * 将dml的data, old转换为es的data + * + * @param mapping 配置mapping + * @param dmlData dml data + * @param esFieldData es data + * @return 返回 id 值 + */ + public Object getESDataFromDmlData(ESMapping mapping, Map dmlData, Map dmlOld, + Map esFieldData) { + SchemaItem schemaItem = mapping.getSchemaItem(); + String idFieldName = mapping.get_id() == null ? mapping.getPk() : mapping.get_id(); + Object resultIdVal = null; + for (FieldItem fieldItem : schemaItem.getSelectFields().values()) { + String columnName = fieldItem.getColumnItems().iterator().next().getColumnName(); + + if (fieldItem.getFieldName().equals(idFieldName)) { + resultIdVal = getValFromData(mapping, dmlData, fieldItem.getFieldName(), columnName); + } + + if (dmlOld.get(columnName) != null && !mapping.getSkips().contains(fieldItem.getFieldName())) { + esFieldData.put(fieldItem.getFieldName(), + getValFromData(mapping, dmlData, fieldItem.getFieldName(), columnName)); + } + } + return resultIdVal; + } + + /** + * es 字段类型本地缓存 + */ + private static ConcurrentMap> esFieldTypes = new ConcurrentHashMap<>(); + + /** + * 获取es mapping中的属性类型 + * + * @param mapping mapping配置 + * @param fieldName 属性名 + * @return 类型 + */ + @SuppressWarnings("unchecked") + private String getEsType(ESMapping mapping, String fieldName) { + String key = mapping.get_index() + "-" + mapping.get_type(); + Map fieldType = esFieldTypes.get(key); + if (fieldType == null) { + ImmutableOpenMap mappings; + try { + mappings = transportClient.admin() + .cluster() + .prepareState() + .execute() + .actionGet() + .getState() + .getMetaData() + .getIndices() + .get(mapping.get_index()) + .getMappings(); + } catch (NullPointerException e) { + throw new IllegalArgumentException("Not found the mapping info of index: " + mapping.get_index()); + } + MappingMetaData mappingMetaData = mappings.get(mapping.get_type()); + if (mappingMetaData == null) { + throw new IllegalArgumentException("Not found the mapping info of index: " + mapping.get_index()); + } + + fieldType = new LinkedHashMap<>(); + + Map sourceMap = mappingMetaData.getSourceAsMap(); + Map esMapping = (Map) sourceMap.get("properties"); + for (Map.Entry entry : esMapping.entrySet()) { + Map value = (Map) entry.getValue(); + if (value.containsKey("properties")) { + fieldType.put(entry.getKey(), "object"); + } else { + fieldType.put(entry.getKey(), (String) value.get("type")); + } + } + esFieldTypes.put(key, fieldType); + } + + return fieldType.get(fieldName); + } +} diff --git a/client-adapter/elasticsearch/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter b/client-adapter/elasticsearch/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter new file mode 100644 index 00000000..b30310ee --- /dev/null +++ b/client-adapter/elasticsearch/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter @@ -0,0 +1 @@ +es=com.alibaba.otter.canal.client.adapter.es.ESAdapter \ No newline at end of file diff --git a/client-adapter/elasticsearch/src/main/resources/es/mytest_user.yml b/client-adapter/elasticsearch/src/main/resources/es/mytest_user.yml new file mode 100644 index 00000000..849420a3 --- /dev/null +++ b/client-adapter/elasticsearch/src/main/resources/es/mytest_user.yml @@ -0,0 +1,16 @@ +dataSourceKey: defaultDS +destination: example +esMapping: + _index: mytest_user + _type: _doc + _id: _id +# pk: id + sql: "select a.id as _id, a.name as _name, a.role_id as _role_id, b.role_name as _role_name, + a.c_time as _c_time, c.labels as _labels from user a + left join role b on b.id=a.role_id + left join (select user_id, group_concat(label order by id desc separator ';') as labels from label + group by user_id) c on c.user_id=a.id" +# objFields: +# _labels: array:; + etlCondition: "where a.c_time>='{0}'" + commitBatch: 3000 diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/ConfigLoadTest.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/ConfigLoadTest.java new file mode 100644 index 00000000..7ab197d1 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/ConfigLoadTest.java @@ -0,0 +1,38 @@ +package com.alibaba.otter.canal.client.adapter.es.test; + +import java.util.Map; + +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfigLoader; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; + +public class ConfigLoadTest { + + @Before + public void before() { + // AdapterConfigs.put("es", "mytest_user.yml"); + // 加载数据源连接池 + DatasourceConfig.DATA_SOURCES.put("defaultDS", TestConstant.dataSource); + } + + @Test + public void testLoad() { + Map configMap = ESSyncConfigLoader.load(); + ESSyncConfig config = configMap.get("mytest_user.yml"); + Assert.assertNotNull(config); + Assert.assertEquals("defaultDS", config.getDataSourceKey()); + ESSyncConfig.ESMapping esMapping = config.getEsMapping(); + Assert.assertEquals("mytest_user", esMapping.get_index()); + Assert.assertEquals("_doc", esMapping.get_type()); + Assert.assertEquals("id", esMapping.get_id()); + Assert.assertNotNull(esMapping.getSql()); + + // Map> dbTableEsSyncConfig = + // ESSyncConfigLoader.getDbTableEsSyncConfig(); + // Assert.assertFalse(dbTableEsSyncConfig.isEmpty()); + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/SqlParseTest.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/SqlParseTest.java new file mode 100644 index 00000000..d07defe9 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/SqlParseTest.java @@ -0,0 +1,47 @@ +package com.alibaba.otter.canal.client.adapter.es.test; + +import java.util.List; +import java.util.Map; + +import org.junit.Assert; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.FieldItem; +import com.alibaba.otter.canal.client.adapter.es.config.SchemaItem.TableItem; +import com.alibaba.otter.canal.client.adapter.es.config.SqlParser; + +public class SqlParseTest { + + @Test + public void parseTest() { + String sql = "select a.id, concat(a.name,'_test') as name, a.role_id, b.name as role_name, c.labels from user a " + + "left join role b on a.role_id=b.id " + + "left join (select user_id, group_concat(label,',') as labels from user_label " + + "group by user_id) c on c.user_id=a.id"; + SchemaItem schemaItem = SqlParser.parse(sql); + + // 通过表名找 TableItem + List tableItems = schemaItem.getTableItemAliases().get("user_label".toLowerCase()); + tableItems.forEach(tableItem -> Assert.assertEquals("c", tableItem.getAlias())); + + TableItem tableItem = tableItems.get(0); + Assert.assertFalse(tableItem.isMain()); + Assert.assertTrue(tableItem.isSubQuery()); + // 通过字段名找 FieldItem + List fieldItems = schemaItem.getColumnFields().get(tableItem.getAlias() + ".label".toLowerCase()); + fieldItems.forEach( + fieldItem -> Assert.assertEquals("c.labels", fieldItem.getOwner() + "." + fieldItem.getFieldName())); + + // 获取当前表关联条件字段 + Map> relationTableFields = tableItem.getRelationTableFields(); + relationTableFields.keySet() + .forEach(fieldItem -> Assert.assertEquals("user_id", fieldItem.getColumn().getColumnName())); + + // 获取关联字段在select中的对应字段 + // List relationSelectFieldItem = + // tableItem.getRelationKeyFieldItems(); + // relationSelectFieldItem.forEach(fieldItem -> Assert.assertEquals("c.labels", + // fieldItem.getOwner() + "." + fieldItem.getColumn().getColumnName())); + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/TestConstant.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/TestConstant.java new file mode 100644 index 00000000..46b0f7a9 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/TestConstant.java @@ -0,0 +1,40 @@ +package com.alibaba.otter.canal.client.adapter.es.test; + +import java.sql.SQLException; + +import com.alibaba.druid.pool.DruidDataSource; + +public class TestConstant { + + public final static String jdbcUrl = "jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true"; + public final static String jdbcUser = "root"; + public final static String jdbcPassword = "121212"; + + public final static String esHosts = "127.0.0.1:9300"; + public final static String clusterNmae = "elasticsearch"; + + public static DruidDataSource dataSource; + + static { + dataSource = new DruidDataSource(); + dataSource.setDriverClassName("com.mysql.jdbc.Driver"); + dataSource.setUrl(jdbcUrl); + dataSource.setUsername(jdbcUser); + dataSource.setPassword(jdbcPassword); + dataSource.setInitialSize(1); + dataSource.setMinIdle(1); + dataSource.setMaxActive(1); + dataSource.setMaxWait(60000); + dataSource.setTimeBetweenEvictionRunsMillis(60000); + dataSource.setMinEvictableIdleTimeMillis(300000); + dataSource.setPoolPreparedStatements(false); + dataSource.setMaxPoolPreparedStatementPerConnectionSize(20); + dataSource.setValidationQuery("select 1"); + try { + dataSource.init(); + } catch (SQLException e) { + e.printStackTrace(); + } + } + +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/Common.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/Common.java new file mode 100644 index 00000000..10d41de1 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/Common.java @@ -0,0 +1,68 @@ +package com.alibaba.otter.canal.client.adapter.es.test.sync; + +import java.sql.Connection; +import java.sql.SQLException; +import java.sql.Statement; +import java.util.HashMap; +import java.util.Map; + +import javax.sql.DataSource; + +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.test.TestConstant; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.OuterAdapterConfig; + +public class Common { + + public static ESAdapter init() { + DatasourceConfig.DATA_SOURCES.put("defaultDS", TestConstant.dataSource); + + OuterAdapterConfig outerAdapterConfig = new OuterAdapterConfig(); + outerAdapterConfig.setName("es"); + outerAdapterConfig.setHosts(TestConstant.esHosts); + Map properties = new HashMap<>(); + properties.put("cluster.name", TestConstant.clusterNmae); + outerAdapterConfig.setProperties(properties); + + ESAdapter esAdapter = new ESAdapter(); + esAdapter.init(outerAdapterConfig); + return esAdapter; + } + + public static void sqlExe(DataSource dataSource, String sql) { + Connection conn = null; + Statement stmt = null; + try { + conn = dataSource.getConnection(); + conn.setAutoCommit(false); + stmt = conn.createStatement(); + stmt.execute(sql); + conn.commit(); + } catch (Exception e) { + if (conn != null) { + try { + conn.rollback(); + } catch (SQLException e1) { + // ignore + } + } + e.printStackTrace(); + } finally { + if (stmt != null) { + try { + stmt.close(); + } catch (SQLException e) { + // ignore + } + } + if (conn != null) { + try { + conn.close(); + } catch (SQLException e) { + // ignore + } + } + } + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/LabelSyncJoinSub2Test.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/LabelSyncJoinSub2Test.java new file mode 100644 index 00000000..966b115b --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/LabelSyncJoinSub2Test.java @@ -0,0 +1,130 @@ +package com.alibaba.otter.canal.client.adapter.es.test.sync; + +import java.util.*; + +import javax.sql.DataSource; + +import org.elasticsearch.action.get.GetResponse; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +public class LabelSyncJoinSub2Test { + + private ESAdapter esAdapter; + + @Before + public void init() { + // AdapterConfigs.put("es", "mytest_user_join_sub2.yml"); + esAdapter = Common.init(); + } + + /** + * 带函数子查询从表插入 + */ + @Test + public void test01() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from label where id=1 or id=2"); + Common.sqlExe(ds, "insert into label (id,user_id,label) values (1,1,'a')"); + Common.sqlExe(ds, "insert into label (id,user_id,label) values (2,1,'b')"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("INSERT"); + dml.setDatabase("mytest"); + dml.setTable("label"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 2L); + data.put("user_id", 1L); + data.put("label", "b"); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("b;a_", response.getSource().get("_labels")); + } + + /** + * 带函数子查询从表更新 + */ + @Test + public void test02() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "update label set label='aa' where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("label"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("user_id", 1L); + data.put("label", "aa"); + dml.setData(dataList); + + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("label", "v"); + dml.setOld(oldList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("b;aa_", response.getSource().get("_labels")); + } + + /** + * 带函数子查询从表删除 + */ + @Test + public void test03() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from label where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("DELETE"); + dml.setDatabase("mytest"); + dml.setTable("label"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("user_id", 1L); + data.put("label", "a"); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("b_", response.getSource().get("_labels")); + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/LabelSyncJoinSubTest.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/LabelSyncJoinSubTest.java new file mode 100644 index 00000000..e8cbbe59 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/LabelSyncJoinSubTest.java @@ -0,0 +1,130 @@ +package com.alibaba.otter.canal.client.adapter.es.test.sync; + +import java.util.*; + +import javax.sql.DataSource; + +import org.elasticsearch.action.get.GetResponse; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +public class LabelSyncJoinSubTest { + + private ESAdapter esAdapter; + + @Before + public void init() { + // AdapterConfigs.put("es", "mytest_user_join_sub.yml"); + esAdapter = Common.init(); + } + + /** + * 子查询从表插入 + */ + @Test + public void test01() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from label where id=1 or id=2"); + Common.sqlExe(ds, "insert into label (id,user_id,label) values (1,1,'a')"); + Common.sqlExe(ds, "insert into label (id,user_id,label) values (2,1,'b')"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("INSERT"); + dml.setDatabase("mytest"); + dml.setTable("label"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 2L); + data.put("user_id", 1L); + data.put("label", "b"); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("b;a", response.getSource().get("_labels")); + } + + /** + * 子查询从表更新 + */ + @Test + public void test02() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "update label set label='aa' where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("label"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("user_id", 1L); + data.put("label", "aa"); + dml.setData(dataList); + + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("label", "a"); + dml.setOld(oldList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("b;aa", response.getSource().get("_labels")); + } + + /** + * 子查询从表删除 + */ + @Test + public void test03() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from label where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("DELETE"); + dml.setDatabase("mytest"); + dml.setTable("label"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("user_id", 1L); + data.put("label", "a"); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("b", response.getSource().get("_labels")); + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/RoleSyncJoinOne2Test.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/RoleSyncJoinOne2Test.java new file mode 100644 index 00000000..0fba73d3 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/RoleSyncJoinOne2Test.java @@ -0,0 +1,95 @@ +package com.alibaba.otter.canal.client.adapter.es.test.sync; + +import java.util.*; + +import javax.sql.DataSource; + +import org.elasticsearch.action.get.GetResponse; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +public class RoleSyncJoinOne2Test { + + private ESAdapter esAdapter; + + @Before + public void init() { + // AdapterConfigs.put("es", "mytest_user_join_one2.yml"); + esAdapter = Common.init(); + } + + /** + * 带函数非子查询从表插入 + */ + @Test + public void test01() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from role where id=1"); + Common.sqlExe(ds, "insert into role (id,role_name) values (1,'admin')"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("INSERT"); + dml.setDatabase("mytest"); + dml.setTable("role"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("role_name", "admin"); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("admin_", response.getSource().get("_role_name")); + } + + /** + * 带函数非子查询从表更新 + */ + @Test + public void test02() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "update role set role_name='admin3' where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("role"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("role_name", "admin3"); + dml.setData(dataList); + + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("role_name", "admin"); + dml.setOld(oldList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("admin3_", response.getSource().get("_role_name")); + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/RoleSyncJoinOneTest.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/RoleSyncJoinOneTest.java new file mode 100644 index 00000000..9739a355 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/RoleSyncJoinOneTest.java @@ -0,0 +1,191 @@ +package com.alibaba.otter.canal.client.adapter.es.test.sync; + +import java.util.*; + +import javax.sql.DataSource; + +import org.elasticsearch.action.get.GetResponse; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +public class RoleSyncJoinOneTest { + + private ESAdapter esAdapter; + + @Before + public void init() { + // AdapterConfigs.put("es", "mytest_user_join_one.yml"); + esAdapter = Common.init(); + } + + /** + * 非子查询从表插入 + */ + @Test + public void test01() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from role where id=1"); + Common.sqlExe(ds, "insert into role (id,role_name) values (1,'admin')"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("INSERT"); + dml.setDatabase("mytest"); + dml.setTable("role"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("role_name", "admin"); + + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("admin", response.getSource().get("_role_name")); + } + + /** + * 非子查询从表更新 + */ + @Test + public void test02() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "update role set role_name='admin2' where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("role"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("role_name", "admin2"); + dml.setData(dataList); + + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("role_name", "admin"); + dml.setOld(oldList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("admin2", response.getSource().get("_role_name")); + } + + /** + * 主表更新外键值 + */ + @Test + public void test03() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from role where id=2"); + Common.sqlExe(ds, "insert into role (id,role_name) values (2,'operator')"); + Common.sqlExe(ds, "update user set role_id=2 where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("role_id", 2L); + dml.setData(dataList); + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("role_id", 1L); + dml.setOld(oldList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("operator", response.getSource().get("_role_name")); + + Common.sqlExe(ds, "update user set role_id=1 where id=1"); + + Dml dml2 = new Dml(); + dml2.setDestination("example"); + dml2.setTs(new Date().getTime()); + dml2.setType("UPDATE"); + dml2.setDatabase("mytest"); + dml2.setTable("user"); + List> dataList2 = new ArrayList<>(); + Map data2 = new LinkedHashMap<>(); + dataList2.add(data2); + data2.put("id", 1L); + data2.put("role_id", 1L); + dml2.setData(dataList2); + List> oldList2 = new ArrayList<>(); + Map old2 = new LinkedHashMap<>(); + oldList2.add(old2); + old2.put("role_id", 2L); + dml2.setOld(oldList2); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml2); + + GetResponse response2 = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("admin2", response2.getSource().get("_role_name")); + } + + /** + * 非子查询从表删除 + */ + @Test + public void test04() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from role where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("DELETE"); + dml.setDatabase("mytest"); + dml.setTable("role"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("role_name", "admin"); + + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertNull(response.getSource().get("_role_name")); + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/UserSyncJoinOneTest.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/UserSyncJoinOneTest.java new file mode 100644 index 00000000..c0e43b61 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/UserSyncJoinOneTest.java @@ -0,0 +1,96 @@ +package com.alibaba.otter.canal.client.adapter.es.test.sync; + +import java.util.*; + +import javax.sql.DataSource; + +import org.elasticsearch.action.get.GetResponse; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +public class UserSyncJoinOneTest { + + private ESAdapter esAdapter; + + @Before + public void init() { + // AdapterConfigs.put("es", "mytest_user_join_one.yml"); + esAdapter = Common.init(); + } + + /** + * 主表带函数插入 + */ + @Test + public void test01() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "delete from user where id=1"); + Common.sqlExe(ds, "insert into user (id,name,role_id) values (1,'Eric',1)"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("INSERT"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("name", "Eric"); + data.put("role_id", 1L); + data.put("c_time", new Date()); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("Eric_", response.getSource().get("_name")); + } + + /** + * 主表带函数更新 + */ + @Test + public void test02() { + DataSource ds = DatasourceConfig.DATA_SOURCES.get("defaultDS"); + Common.sqlExe(ds, "update user set name='Eric2' where id=1"); + + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("name", "Eric2"); + dml.setData(dataList); + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("name", "Eric"); + dml.setOld(oldList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("Eric2_", response.getSource().get("_name")); + } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/UserSyncSingleTest.java b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/UserSyncSingleTest.java new file mode 100644 index 00000000..6bf4b75b --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/UserSyncSingleTest.java @@ -0,0 +1,122 @@ +package com.alibaba.otter.canal.client.adapter.es.test.sync; + +import java.util.*; + +import org.elasticsearch.action.get.GetResponse; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.es.ESAdapter; +import com.alibaba.otter.canal.client.adapter.es.config.ESSyncConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +public class UserSyncSingleTest { + + private ESAdapter esAdapter; + + @Before + public void init() { + // AdapterConfigs.put("es", "mytest_user_single.yml"); + esAdapter = Common.init(); + } + + /** + * 单表插入 + */ + @Test + public void test01() { + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("INSERT"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("name", "Eric"); + data.put("role_id", 1L); + data.put("c_time", new Date()); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("Eric", response.getSource().get("_name")); + } + + /** + * 单表更新 + */ + @Test + public void test02() { + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("name", "Eric2"); + dml.setData(dataList); + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("name", "Eric"); + dml.setOld(oldList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertEquals("Eric2", response.getSource().get("_name")); + } + + /** + * 单表删除 + */ + @Test + public void test03() { + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("DELETE"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("name", "Eric"); + data.put("role_id", 1L); + data.put("c_time", new Date()); + dml.setData(dataList); + + String database = dml.getDatabase(); + String table = dml.getTable(); + Map esSyncConfigs = esAdapter.getDbTableEsSyncConfig().get(database + "-" + table); + + esAdapter.getEsSyncService().sync(esSyncConfigs.values(), dml); + + GetResponse response = esAdapter.getTransportClient().prepareGet("mytest_user", "_doc", "1").get(); + Assert.assertNull(response.getSource()); + } + + // @After + // public void after() { + // esAdapter.destroy(); + // DatasourceConfig.DATA_SOURCES.values().forEach(DruidDataSource::close); + // } +} diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/db_schema.sql b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/db_schema.sql new file mode 100644 index 00000000..bff2e118 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/db_schema.sql @@ -0,0 +1,39 @@ +-- ---------------------------- +-- Table structure for label +-- ---------------------------- +DROP TABLE IF EXISTS `label`; +CREATE TABLE `label` ( + `id` bigint(20) NOT NULL AUTO_INCREMENT, + `user_id` bigint(20) NOT NULL, + `label` varchar(30) NOT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8; + +-- ---------------------------- +-- Table structure for role +-- ---------------------------- +DROP TABLE IF EXISTS `role`; +CREATE TABLE `role` ( + `id` bigint(20) NOT NULL AUTO_INCREMENT, + `role_name` varchar(30) NOT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8; + +-- ---------------------------- +-- Table structure for user +-- ---------------------------- +DROP TABLE IF EXISTS `user`; +CREATE TABLE `user` ( + `id` bigint(20) NOT NULL AUTO_INCREMENT, + `name` varchar(30) NOT NULL, + `c_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP, + `role_id` bigint(20) DEFAULT NULL, + PRIMARY KEY (`id`) +) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8; + +insert into user (id,name,role_id) values (1,'Eric',1); +insert into role (id,role_name) values (1,'admin'); +insert into role (id,role_name) values (2,'operator'); +insert into label (id,user_id,label) values (1,1,'a'); +insert into label (id,user_id,label) values (2,1,'b'); +commit; \ No newline at end of file diff --git a/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/es_mapping.json b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/es_mapping.json new file mode 100644 index 00000000..55b0389a --- /dev/null +++ b/client-adapter/elasticsearch/src/test/java/com/alibaba/otter/canal/client/adapter/es/test/sync/es_mapping.json @@ -0,0 +1,21 @@ +{ + "_doc": { + "properties": { + "_name": { + "type": "text" + }, + "_role_id": { + "type": "long" + }, + "_role_name": { + "type": "text" + }, + "_labels": { + "type": "text" + }, + "_c_time": { + "type": "date" + } + } + } +} \ No newline at end of file diff --git a/client-adapter/elasticsearch/src/test/resources/es/mytest_user_single.yml_ b/client-adapter/elasticsearch/src/test/resources/es/mytest_user_single.yml_ new file mode 100644 index 00000000..23e1b491 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/resources/es/mytest_user_single.yml_ @@ -0,0 +1,8 @@ +dataSourceKey: defaultDS +destination: example +esMapping: + _index: mytest_user + _type: _doc + _id: _id + sql: "select a.id as _id, a.name as _name, a.role_id as _role_id, a.c_time as _c_time from user a" + commitBatch: 3000 \ No newline at end of file diff --git a/client-adapter/elasticsearch/src/test/resources/log4j2-test.xml b/client-adapter/elasticsearch/src/test/resources/log4j2-test.xml new file mode 100644 index 00000000..9c3d2ee6 --- /dev/null +++ b/client-adapter/elasticsearch/src/test/resources/log4j2-test.xml @@ -0,0 +1,13 @@ + + + + + + + + + + + + + \ No newline at end of file diff --git a/kafka-client/src/test/resources/logback.xml b/client-adapter/elasticsearch/src/test/resources/logback-test.xml similarity index 69% rename from kafka-client/src/test/resources/logback.xml rename to client-adapter/elasticsearch/src/test/resources/logback-test.xml index 81fa0712..91f0de80 100644 --- a/kafka-client/src/test/resources/logback.xml +++ b/client-adapter/elasticsearch/src/test/resources/logback-test.xml @@ -1,5 +1,4 @@ - @@ -8,12 +7,7 @@ - - - - - - + \ No newline at end of file diff --git a/client-adapter/hbase/pom.xml b/client-adapter/hbase/pom.xml new file mode 100644 index 00000000..29ee8b33 --- /dev/null +++ b/client-adapter/hbase/pom.xml @@ -0,0 +1,88 @@ + + + + canal.client-adapter + com.alibaba.otter + 1.1.3-SNAPSHOT + + 4.0.0 + com.alibaba.otter + client-adapter.hbase + jar + canal client adapter hbase module for otter ${project.version} + + + com.alibaba.otter + client-adapter.common + ${project.version} + provided + + + org.yaml + snakeyaml + 1.19 + provided + + + org.apache.hbase + hbase-client + 1.1.2 + + + org.slf4j + slf4j-log4j12 + + + + + com.google.guava + guava + 12.0.1 + + + + + + + org.apache.maven.plugins + maven-assembly-plugin + 2.4 + + + jar-with-dependencies + + + + + make-assembly + package + + single + + + + + + maven-antrun-plugin + + + package + + run + + + + + + + + + + + + + + + + + diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/HbaseAdapter.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/HbaseAdapter.java new file mode 100644 index 00000000..e586bfe0 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/HbaseAdapter.java @@ -0,0 +1,213 @@ +package com.alibaba.otter.canal.client.adapter.hbase; + +import java.io.IOException; +import java.util.HashMap; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +import javax.sql.DataSource; + +import org.apache.commons.lang.StringUtils; +import org.apache.hadoop.conf.Configuration; +import org.apache.hadoop.hbase.HBaseConfiguration; +import org.apache.hadoop.hbase.TableName; +import org.apache.hadoop.hbase.client.Connection; +import org.apache.hadoop.hbase.client.ConnectionFactory; +import org.apache.hadoop.hbase.client.HTable; +import org.apache.hadoop.hbase.client.Result; +import org.apache.hadoop.hbase.client.ResultScanner; +import org.apache.hadoop.hbase.client.Scan; +import org.apache.hadoop.hbase.filter.FirstKeyOnlyFilter; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.hbase.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.hbase.config.MappingConfigLoader; +import com.alibaba.otter.canal.client.adapter.hbase.monitor.HbaseConfigMonitor; +import com.alibaba.otter.canal.client.adapter.hbase.service.HbaseEtlService; +import com.alibaba.otter.canal.client.adapter.hbase.service.HbaseSyncService; +import com.alibaba.otter.canal.client.adapter.hbase.support.HbaseTemplate; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; +import com.alibaba.otter.canal.client.adapter.support.EtlResult; +import com.alibaba.otter.canal.client.adapter.support.OuterAdapterConfig; +import com.alibaba.otter.canal.client.adapter.support.SPI; + +/** + * HBase外部适配器 + * + * @author machengyuan 2018-8-21 下午8:45:38 + * @version 1.0.0 + */ +@SPI("hbase") +public class HbaseAdapter implements OuterAdapter { + + private static Logger logger = LoggerFactory.getLogger(HbaseAdapter.class); + + private Map hbaseMapping = new ConcurrentHashMap<>(); // 文件名对应配置 + private Map> mappingConfigCache = new ConcurrentHashMap<>(); // 库名-表名对应配置 + + private Connection conn; + private HbaseSyncService hbaseSyncService; + private HbaseTemplate hbaseTemplate; + + private HbaseConfigMonitor configMonitor; + + public Map getHbaseMapping() { + return hbaseMapping; + } + + public Map> getMappingConfigCache() { + return mappingConfigCache; + } + + @Override + public void init(OuterAdapterConfig configuration) { + try { + Map hbaseMappingTmp = MappingConfigLoader.load(); + // 过滤不匹配的key的配置 + hbaseMappingTmp.forEach((key, mappingConfig) -> { + if ((mappingConfig.getOuterAdapterKey() == null && configuration.getKey() == null) + || (mappingConfig.getOuterAdapterKey() != null + && mappingConfig.getOuterAdapterKey().equalsIgnoreCase(configuration.getKey()))) { + hbaseMapping.put(key, mappingConfig); + } + }); + for (Map.Entry entry : hbaseMapping.entrySet()) { + String configName = entry.getKey(); + MappingConfig mappingConfig = entry.getValue(); + String k = StringUtils.trimToEmpty(mappingConfig.getDestination()) + "." + + mappingConfig.getHbaseMapping().getDatabase() + "." + + mappingConfig.getHbaseMapping().getTable(); + Map configMap = mappingConfigCache.computeIfAbsent(k, k1 -> new HashMap<>()); + configMap.put(configName, mappingConfig); + } + + Map properties = configuration.getProperties(); + + Configuration hbaseConfig = HBaseConfiguration.create(); + properties.forEach(hbaseConfig::set); + conn = ConnectionFactory.createConnection(hbaseConfig); + hbaseTemplate = new HbaseTemplate(conn); + hbaseSyncService = new HbaseSyncService(hbaseTemplate); + + configMonitor = new HbaseConfigMonitor(); + configMonitor.init(this); + } catch (Exception e) { + throw new RuntimeException(e); + } + } + + public void sync(List dmls) { + for (Dml dml : dmls) { + sync(dml); + } + } + + public void sync(Dml dml) { + if (dml == null) { + return; + } + String destination = StringUtils.trimToEmpty(dml.getDestination()); + String database = dml.getDatabase(); + String table = dml.getTable(); + Map configMap = mappingConfigCache.get(destination + "." + database + "." + table); + configMap.values().forEach(config -> hbaseSyncService.sync(config, dml)); + } + + @Override + public EtlResult etl(String task, List params) { + EtlResult etlResult = new EtlResult(); + MappingConfig config = hbaseMapping.get(task); + if (config != null) { + DataSource dataSource = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (dataSource != null) { + return HbaseEtlService.importData(dataSource, hbaseTemplate, config, params); + } else { + etlResult.setSucceeded(false); + etlResult.setErrorMessage("DataSource not found"); + return etlResult; + } + } else { + StringBuilder resultMsg = new StringBuilder(); + boolean resSucc = true; + // ds不为空说明传入的是datasourceKey + for (MappingConfig configTmp : hbaseMapping.values()) { + // 取所有的destination为task的配置 + if (configTmp.getDestination().equals(task)) { + DataSource dataSource = DatasourceConfig.DATA_SOURCES.get(configTmp.getDataSourceKey()); + if (dataSource == null) { + continue; + } + EtlResult etlRes = HbaseEtlService.importData(dataSource, hbaseTemplate, configTmp, params); + if (!etlRes.getSucceeded()) { + resSucc = false; + resultMsg.append(etlRes.getErrorMessage()).append("\n"); + } else { + resultMsg.append(etlRes.getResultMessage()).append("\n"); + } + } + } + if (resultMsg.length() > 0) { + etlResult.setSucceeded(resSucc); + if (resSucc) { + etlResult.setResultMessage(resultMsg.toString()); + } else { + etlResult.setErrorMessage(resultMsg.toString()); + } + return etlResult; + } + } + etlResult.setSucceeded(false); + etlResult.setErrorMessage("Task not found"); + return etlResult; + } + + @Override + public Map count(String task) { + MappingConfig config = hbaseMapping.get(task); + String hbaseTable = config.getHbaseMapping().getHbaseTable(); + long rowCount = 0L; + try { + HTable table = (HTable) conn.getTable(TableName.valueOf(hbaseTable)); + Scan scan = new Scan(); + scan.setFilter(new FirstKeyOnlyFilter()); + ResultScanner resultScanner = table.getScanner(scan); + for (Result result : resultScanner) { + rowCount += result.size(); + } + } catch (IOException e) { + logger.error(e.getMessage(), e); + } + Map res = new LinkedHashMap<>(); + res.put("hbaseTable", hbaseTable); + res.put("count", rowCount); + return res; + } + + @Override + public void destroy() { + if (configMonitor != null) { + configMonitor.destroy(); + } + if (conn != null) { + try { + conn.close(); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + } + + @Override + public String getDestination(String task) { + MappingConfig config = hbaseMapping.get(task); + if (config != null && config.getHbaseMapping() != null) { + return config.getDestination(); + } + return null; + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/config/MappingConfig.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/config/MappingConfig.java new file mode 100644 index 00000000..2d86adee --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/config/MappingConfig.java @@ -0,0 +1,394 @@ +package com.alibaba.otter.canal.client.adapter.hbase.config; + +import java.util.*; + +/** + * HBase表映射配置 + * + * @author rewerma 2018-8-21 下午06:45:49 + * @version 1.0.0 + */ +public class MappingConfig { + + private String dataSourceKey; // 数据源key + + private String outerAdapterKey; // adapter key + + private String destination; // canal实例或MQ的topic + + private HbaseMapping hbaseMapping; // hbase映射配置 + + public String getDataSourceKey() { + return dataSourceKey; + } + + public void setDataSourceKey(String dataSourceKey) { + this.dataSourceKey = dataSourceKey; + } + + public String getOuterAdapterKey() { + return outerAdapterKey; + } + + public void setOuterAdapterKey(String outerAdapterKey) { + this.outerAdapterKey = outerAdapterKey; + } + + public String getDestination() { + return destination; + } + + public void setDestination(String destination) { + this.destination = destination; + } + + public HbaseMapping getHbaseMapping() { + return hbaseMapping; + } + + public void setHbaseMapping(HbaseMapping hbaseMapping) { + this.hbaseMapping = hbaseMapping; + } + + public void validate() { + if (hbaseMapping.database == null || hbaseMapping.database.isEmpty()) { + throw new NullPointerException("hbaseMapping.database"); + } + if (hbaseMapping.table == null || hbaseMapping.table.isEmpty()) { + throw new NullPointerException("hbaseMapping.table"); + } + if (hbaseMapping.hbaseTable == null || hbaseMapping.hbaseTable.isEmpty()) { + throw new NullPointerException("hbaseMapping.hbaseTable"); + } + if (hbaseMapping.mode == null) { + throw new NullPointerException("hbaseMapping.mode"); + } + if (hbaseMapping.rowKey != null && hbaseMapping.rowKeyColumn != null) { + throw new RuntimeException("已配置了复合主键作为RowKey,无需再指定RowKey列"); + } + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + + MappingConfig config = (MappingConfig) o; + + return hbaseMapping != null ? hbaseMapping.equals(config.hbaseMapping) : config.hbaseMapping == null; + } + + @Override + public int hashCode() { + return hbaseMapping != null ? hbaseMapping.hashCode() : 0; + } + + public static class ColumnItem { + + private boolean isRowKey = false; + private Integer rowKeyLen; + private String column; + private String family; + private String qualifier; + private String type; + + public boolean isRowKey() { + return isRowKey; + } + + public void setRowKey(boolean rowKey) { + isRowKey = rowKey; + } + + public Integer getRowKeyLen() { + return rowKeyLen; + } + + public void setRowKeyLen(Integer rowKeyLen) { + this.rowKeyLen = rowKeyLen; + } + + public String getColumn() { + return column; + } + + public void setColumn(String column) { + this.column = column; + } + + public String getFamily() { + return family; + } + + public void setFamily(String family) { + this.family = family; + } + + public String getQualifier() { + return qualifier; + } + + public void setQualifier(String qualifier) { + this.qualifier = qualifier; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + ColumnItem that = (ColumnItem) o; + return Objects.equals(column, that.column); + } + + @Override + public int hashCode() { + + return Objects.hash(column); + } + } + + public enum Mode { + STRING("STRING"), NATIVE("NATIVE"), PHOENIX("PHOENIX"); + + private String type; + + public String getType() { + return type; + } + + Mode(String type){ + this.type = type; + } + } + + public static class HbaseMapping { + + private Mode mode = Mode.STRING; // hbase默认转换格式 + private String database; // 数据库名或schema名 + private String table; // 表面名 + private String hbaseTable; // hbase表名 + private String family = "CF"; // 默认统一column family + private boolean uppercaseQualifier = true; // 是否转大写 + private boolean autoCreateTable = false; // 同步时HBase中表不存在的情况下自动建表 + private String rowKey; // 指定复合主键为rowKey + private Map columns; // 字段映射 + private List excludeColumns; // 不映射的字段 + private ColumnItem rowKeyColumn; // rowKey字段 + private String etlCondition; // etl条件sql + + private Map columnItems = new LinkedHashMap<>(); // 转换后的字段映射列表 + private Set families = new LinkedHashSet<>(); // column family列表 + private int readBatch = 5000; + private int commitBatch = 5000; // etl等批量提交大小 + + public Mode getMode() { + return mode; + } + + public void setMode(Mode mode) { + this.mode = mode; + } + + public String getDatabase() { + return database; + } + + public void setDatabase(String database) { + this.database = database; + } + + public String getTable() { + return table; + } + + public void setTable(String table) { + this.table = table; + } + + public String getHbaseTable() { + return hbaseTable; + } + + public void setHbaseTable(String hbaseTable) { + this.hbaseTable = hbaseTable; + } + + public Map getColumns() { + return columns; + } + + public boolean isAutoCreateTable() { + return autoCreateTable; + } + + public void setAutoCreateTable(boolean autoCreateTable) { + this.autoCreateTable = autoCreateTable; + } + + public int getReadBatch() { + return readBatch; + } + + public void setReadBatch(int readBatch) { + this.readBatch = readBatch; + } + + public int getCommitBatch() { + return commitBatch; + } + + public void setCommitBatch(int commitBatch) { + this.commitBatch = commitBatch; + } + + public String getRowKey() { + return rowKey; + } + + public void setRowKey(String rowKey) { + this.rowKey = rowKey; + } + + public String getEtlCondition() { + return etlCondition; + } + + public void setEtlCondition(String etlCondition) { + this.etlCondition = etlCondition; + } + + public void setColumns(Map columns) { + this.columns = columns; + + if (columns != null) { + for (Map.Entry columnField : columns.entrySet()) { + String field = columnField.getValue(); + String type = null; + if (field != null) { + // 解析类型 + int i = field.indexOf("$"); + if (i > -1) { + type = field.substring(i + 1); + field = field.substring(0, i); + } + } + ColumnItem columnItem = new ColumnItem(); + columnItem.setColumn(columnField.getKey()); + columnItem.setType(type); + if (field != null && field.toUpperCase().startsWith("ROWKEY")) { + int idx = field.toUpperCase().indexOf("LEN:"); + if (idx > -1) { + String len = field.substring(idx + 4); + try { + columnItem.setRowKeyLen(Integer.parseInt(len)); + } catch (Exception e) { + // ignore + } + } + columnItem.setRowKey(true); + rowKeyColumn = columnItem; + } else { + if (field == null || field.equals("")) { + columnItem.setFamily(family); + columnItem.setQualifier(columnField.getKey()); + } else { + int len = field.indexOf(":"); + if (len > -1) { + columnItem.setFamily(field.substring(0, len)); + columnItem.setQualifier(field.substring(len + 1)); + } else { + columnItem.setFamily(family); + columnItem.setQualifier(field); + } + } + if (uppercaseQualifier) { + columnItem.setQualifier(columnItem.getQualifier().toUpperCase()); + } + families.add(columnItem.getFamily()); + } + + columnItems.put(columnField.getKey(), columnItem); + } + } else { + this.columns = new LinkedHashMap<>(); + } + } + + public List getExcludeColumns() { + return excludeColumns; + } + + public void setExcludeColumns(List excludeColumns) { + this.excludeColumns = excludeColumns; + } + + public String getFamily() { + return family; + } + + public void setFamily(String family) { + this.family = family; + if (family == null) { + this.family = "CF"; + } + } + + public boolean isUppercaseQualifier() { + return uppercaseQualifier; + } + + public void setUppercaseQualifier(boolean uppercaseQualifier) { + this.uppercaseQualifier = uppercaseQualifier; + } + + public ColumnItem getRowKeyColumn() { + return rowKeyColumn; + } + + public void setRowKeyColumn(ColumnItem rowKeyColumn) { + this.rowKeyColumn = rowKeyColumn; + } + + public Map getColumnItems() { + return columnItems; + } + + public void setColumnItems(Map columnItems) { + this.columnItems = columnItems; + } + + public Set getFamilies() { + return families; + } + + public void setFamilies(Set families) { + this.families = families; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + + HbaseMapping hbaseMapping = (HbaseMapping) o; + + if (table != null ? !table.equals(hbaseMapping.table) : hbaseMapping.table != null) return false; + return hbaseTable != null ? hbaseTable.equals(hbaseMapping.hbaseTable) : hbaseMapping.hbaseTable == null; + } + + @Override + public int hashCode() { + int result = table != null ? table.hashCode() : 0; + result = 31 * result + (hbaseTable != null ? hbaseTable.hashCode() : 0); + return result; + } + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/config/MappingConfigLoader.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/config/MappingConfigLoader.java new file mode 100644 index 00000000..1f8c05c1 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/config/MappingConfigLoader.java @@ -0,0 +1,46 @@ +package com.alibaba.otter.canal.client.adapter.hbase.config; + +import java.util.LinkedHashMap; +import java.util.Map; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.yaml.snakeyaml.Yaml; + +import com.alibaba.otter.canal.client.adapter.support.MappingConfigsLoader; + +/** + * HBase表映射配置加载器 + * + * @author rewerma 2018-8-21 下午06:45:49 + * @version 1.0.0 + */ +public class MappingConfigLoader { + + private static Logger logger = LoggerFactory.getLogger(MappingConfigLoader.class); + + /** + * 加载HBase表映射配置 + * + * @return 配置名/配置文件名--对象 + */ + public static Map load() { + logger.info("## Start loading hbase mapping config ... "); + + Map result = new LinkedHashMap<>(); + + Map configContentMap = MappingConfigsLoader.loadConfigs("hbase"); + configContentMap.forEach((fileName, content) -> { + MappingConfig config = new Yaml().loadAs(content, MappingConfig.class); + try { + config.validate(); + } catch (Exception e) { + throw new RuntimeException("ERROR load Config: " + fileName + " " + e.getMessage(), e); + } + result.put(fileName, config); + }); + + logger.info("## Hbase mapping config loaded"); + return result; + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/monitor/HbaseConfigMonitor.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/monitor/HbaseConfigMonitor.java new file mode 100644 index 00000000..ae6ddef2 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/monitor/HbaseConfigMonitor.java @@ -0,0 +1,129 @@ +package com.alibaba.otter.canal.client.adapter.hbase.monitor; + +import java.io.File; +import java.util.HashMap; +import java.util.Map; + +import org.apache.commons.io.filefilter.FileFilterUtils; +import org.apache.commons.io.monitor.FileAlterationListenerAdaptor; +import org.apache.commons.io.monitor.FileAlterationMonitor; +import org.apache.commons.io.monitor.FileAlterationObserver; +import org.apache.commons.lang.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.yaml.snakeyaml.Yaml; + +import com.alibaba.otter.canal.client.adapter.hbase.HbaseAdapter; +import com.alibaba.otter.canal.client.adapter.hbase.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.support.MappingConfigsLoader; +import com.alibaba.otter.canal.client.adapter.support.Util; + +public class HbaseConfigMonitor { + + private static final Logger logger = LoggerFactory.getLogger(HbaseConfigMonitor.class); + + private static final String adapterName = "hbase"; + + private HbaseAdapter hbaseAdapter; + + private FileAlterationMonitor fileMonitor; + + public void init(HbaseAdapter hbaseAdapter) { + this.hbaseAdapter = hbaseAdapter; + File confDir = Util.getConfDirPath(adapterName); + try { + FileAlterationObserver observer = new FileAlterationObserver(confDir, + FileFilterUtils.and(FileFilterUtils.fileFileFilter(), FileFilterUtils.suffixFileFilter("yml"))); + FileListener listener = new FileListener(); + observer.addListener(listener); + fileMonitor = new FileAlterationMonitor(3000, observer); + fileMonitor.start(); + + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + public void destroy() { + try { + fileMonitor.stop(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private class FileListener extends FileAlterationListenerAdaptor { + + @Override + public void onFileCreate(File file) { + super.onFileCreate(file); + try { + // 加载新增的配置文件 + String configContent = MappingConfigsLoader.loadConfig(adapterName + File.separator + file.getName()); + MappingConfig config = new Yaml().loadAs(configContent, MappingConfig.class); + config.validate(); + addConfigToCache(file, config); + + logger.info("Add a new hbase mapping config: {} to canal adapter", file.getName()); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + @Override + public void onFileChange(File file) { + super.onFileChange(file); + + try { + if (hbaseAdapter.getHbaseMapping().containsKey(file.getName())) { + // 加载配置文件 + String configContent = MappingConfigsLoader + .loadConfig(adapterName + File.separator + file.getName()); + MappingConfig config = new Yaml().loadAs(configContent, MappingConfig.class); + config.validate(); + if (hbaseAdapter.getHbaseMapping().containsKey(file.getName())) { + deleteConfigFromCache(file); + } + addConfigToCache(file, config); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + @Override + public void onFileDelete(File file) { + super.onFileDelete(file); + + try { + if (hbaseAdapter.getHbaseMapping().containsKey(file.getName())) { + deleteConfigFromCache(file); + + logger.info("Delete a hbase mapping config: {} of canal adapter", file.getName()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private void addConfigToCache(File file, MappingConfig config) { + hbaseAdapter.getHbaseMapping().put(file.getName(), config); + Map configMap = hbaseAdapter.getMappingConfigCache() + .computeIfAbsent(StringUtils.trimToEmpty(config.getDestination()) + "." + + config.getHbaseMapping().getDatabase() + "." + config.getHbaseMapping().getTable(), + k1 -> new HashMap<>()); + configMap.put(file.getName(), config); + } + + private void deleteConfigFromCache(File file) { + + hbaseAdapter.getHbaseMapping().remove(file.getName()); + for (Map configMap : hbaseAdapter.getMappingConfigCache().values()) { + if (configMap != null) { + configMap.remove(file.getName()); + } + } + + } + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/service/HbaseEtlService.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/service/HbaseEtlService.java new file mode 100644 index 00000000..172592e2 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/service/HbaseEtlService.java @@ -0,0 +1,392 @@ +package com.alibaba.otter.canal.client.adapter.hbase.service; + +import java.sql.*; +import java.text.SimpleDateFormat; +import java.util.ArrayList; +import java.util.Date; +import java.util.List; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; +import java.util.concurrent.atomic.AtomicBoolean; +import java.util.concurrent.atomic.AtomicLong; +import java.util.function.Function; + +import javax.sql.DataSource; + +import com.alibaba.otter.canal.client.adapter.support.Util; +import org.apache.hadoop.hbase.util.Bytes; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.client.adapter.hbase.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.hbase.support.*; +import com.alibaba.otter.canal.client.adapter.support.EtlResult; +import com.alibaba.otter.canal.client.adapter.support.JdbcTypeUtil; +import com.google.common.base.Joiner; + +/** + * HBase ETL 操作业务类 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +public class HbaseEtlService { + + private static Logger logger = LoggerFactory.getLogger(HbaseEtlService.class); + + + /** + * 建表 + * + * @param hbaseTemplate + * @param config + */ + public static void createTable(HbaseTemplate hbaseTemplate, MappingConfig config) { + try { + // 判断hbase表是否存在,不存在则建表 + MappingConfig.HbaseMapping hbaseMapping = config.getHbaseMapping(); + if (!hbaseTemplate.tableExists(hbaseMapping.getHbaseTable())) { + hbaseTemplate.createTable(hbaseMapping.getHbaseTable(), hbaseMapping.getFamily()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + throw new RuntimeException(e); + } + } + + /** + * 导入数据 + * + * @param ds 数据源 + * @param hbaseTemplate hbaseTemplate + * @param config 配置 + * @param params 筛选条件 + * @return 导入结果 + */ + public static EtlResult importData(DataSource ds, HbaseTemplate hbaseTemplate, MappingConfig config, + List params) { + EtlResult etlResult = new EtlResult(); + AtomicLong successCount = new AtomicLong(); + List errMsg = new ArrayList<>(); + String hbaseTable = ""; + try { + if (config == null) { + logger.error("Config is null!"); + etlResult.setSucceeded(false); + etlResult.setErrorMessage("Config is null!"); + return etlResult; + } + MappingConfig.HbaseMapping hbaseMapping = config.getHbaseMapping(); + hbaseTable = hbaseMapping.getHbaseTable(); + + long start = System.currentTimeMillis(); + + if (params != null && params.size() == 1 && "rebuild".equalsIgnoreCase(params.get(0))) { + logger.info(hbaseMapping.getHbaseTable() + " rebuild is starting!"); + // 如果表存在则删除 + if (hbaseTemplate.tableExists(hbaseMapping.getHbaseTable())) { + hbaseTemplate.disableTable(hbaseMapping.getHbaseTable()); + hbaseTemplate.deleteTable(hbaseMapping.getHbaseTable()); + } + params = null; + } else { + logger.info(hbaseMapping.getHbaseTable() + " etl is starting!"); + } + createTable(hbaseTemplate, config); + + // 拼接sql + String sql = "SELECT * FROM " + config.getHbaseMapping().getDatabase() + "." + hbaseMapping.getTable(); + + // 拼接条件 + if (params != null && params.size() == 1 && hbaseMapping.getEtlCondition() == null) { + AtomicBoolean stExists = new AtomicBoolean(false); + // 验证是否有SYS_TIME字段 + Util.sqlRS(ds, sql, rs -> { + try { + ResultSetMetaData rsmd = rs.getMetaData(); + int cnt = rsmd.getColumnCount(); + for (int i = 1; i <= cnt; i++) { + String columnName = rsmd.getColumnName(i); + if ("SYS_TIME".equalsIgnoreCase(columnName)) { + stExists.set(true); + break; + } + } + } catch (Exception e) { + // ignore + } + return null; + }); + if (stExists.get()) { + sql += " WHERE SYS_TIME >= '" + params.get(0) + "' "; + } + } else if (hbaseMapping.getEtlCondition() != null && params != null) { + String etlCondition = hbaseMapping.getEtlCondition(); + int size = params.size(); + for (int i = 0; i < size; i++) { + etlCondition = etlCondition.replace("{" + i + "}", params.get(i)); + } + + sql += " " + etlCondition; + } + + // 获取总数 + String countSql = "SELECT COUNT(1) FROM ( " + sql + ") _CNT "; + long cnt = (Long) Util.sqlRS(ds, countSql, rs -> { + Long count = null; + try { + if (rs.next()) { + count = ((Number) rs.getObject(1)).longValue(); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + return count == null ? 0 : count; + }); + + // 当大于1万条记录时开启多线程 + if (cnt >= 10000) { + int threadCount = 3; + long perThreadCnt = cnt / threadCount; + ExecutorService executor = Executors.newFixedThreadPool(threadCount); + List> futures = new ArrayList<>(threadCount); + for (int i = 0; i < threadCount; i++) { + long offset = i * perThreadCnt; + Long size = null; + if (i != threadCount - 1) { + size = perThreadCnt; + } + String sqlFinal; + if (size != null) { + sqlFinal = sql + " LIMIT " + offset + "," + size; + } else { + sqlFinal = sql + " LIMIT " + offset + "," + cnt; + } + Future future = executor.submit( + () -> executeSqlImport(ds, sqlFinal, hbaseMapping, hbaseTemplate, successCount, errMsg)); + futures.add(future); + } + + for (Future future : futures) { + future.get(); + } + + executor.shutdown(); + } else { + executeSqlImport(ds, sql, hbaseMapping, hbaseTemplate, successCount, errMsg); + } + + logger.info(hbaseMapping.getHbaseTable() + " etl completed in: " + + (System.currentTimeMillis() - start) / 1000 + "s!"); + + etlResult.setResultMessage("导入HBase表 " + hbaseMapping.getHbaseTable() + " 数据:" + successCount.get() + " 条"); + } catch (Exception e) { + logger.error(e.getMessage(), e); + errMsg.add(hbaseTable + " etl failed! ==>" + e.getMessage()); + } + + if (errMsg.isEmpty()) { + etlResult.setSucceeded(true); + } else { + etlResult.setErrorMessage(Joiner.on("\n").join(errMsg)); + } + return etlResult; + } + + /** + * 执行导入 + * + * @param ds + * @param sql + * @param hbaseMapping + * @param hbaseTemplate + * @param successCount + * @param errMsg + * @return + */ + private static boolean executeSqlImport(DataSource ds, String sql, MappingConfig.HbaseMapping hbaseMapping, + HbaseTemplate hbaseTemplate, AtomicLong successCount, List errMsg) { + try { + Util.sqlRS(ds, sql, rs -> { + int i = 1; + + try { + boolean complete = false; + List rows = new ArrayList<>(); + String[] rowKeyColumns = null; + if (hbaseMapping.getRowKey() != null) { + rowKeyColumns = hbaseMapping.getRowKey().trim().split(","); + } + while (rs.next()) { + int cc = rs.getMetaData().getColumnCount(); + int[] jdbcTypes = new int[cc]; + Class[] classes = new Class[cc]; + for (int j = 1; j <= cc; j++) { + int jdbcType = rs.getMetaData().getColumnType(j); + jdbcTypes[j - 1] = jdbcType; + classes[j - 1] = JdbcTypeUtil.jdbcType2javaType(jdbcType); + } + HRow row = new HRow(); + + if (rowKeyColumns != null) { + // 取rowKey字段拼接 + StringBuilder rowKeyVale = new StringBuilder(); + for (String rowKeyColumnName : rowKeyColumns) { + Object obj = rs.getObject(rowKeyColumnName); + if (obj != null) { + rowKeyVale.append(obj.toString()); + } + rowKeyVale.append("|"); + } + int len = rowKeyVale.length(); + if (len > 0) { + rowKeyVale.delete(len - 1, len); + } + row.setRowKey(Bytes.toBytes(rowKeyVale.toString())); + } + + for (int j = 1; j <= cc; j++) { + String columnName = rs.getMetaData().getColumnName(j); + + Object val = JdbcTypeUtil.getRSData(rs, columnName, jdbcTypes[j - 1]); + if (val == null) { + continue; + } + + MappingConfig.ColumnItem columnItem = hbaseMapping.getColumnItems().get(columnName); + // 没有配置映射 + if (columnItem == null) { + String family = hbaseMapping.getFamily(); + String qualifile = columnName; + if (hbaseMapping.isUppercaseQualifier()) { + qualifile = qualifile.toUpperCase(); + } + if (MappingConfig.Mode.STRING == hbaseMapping.getMode()) { + if (hbaseMapping.getRowKey() == null && j == 1) { + row.setRowKey(Bytes.toBytes(val.toString())); + } else { + row.addCell(family, qualifile, Bytes.toBytes(val.toString())); + } + } else if (MappingConfig.Mode.NATIVE == hbaseMapping.getMode()) { + Type type = Type.getType(classes[j - 1]); + if (hbaseMapping.getRowKey() == null && j == 1) { + row.setRowKey(TypeUtil.toBytes(val, type)); + } else { + row.addCell(family, qualifile, TypeUtil.toBytes(val, type)); + } + } else if (MappingConfig.Mode.PHOENIX == hbaseMapping.getMode()) { + PhType phType = PhType.getType(classes[j - 1]); + if (hbaseMapping.getRowKey() == null && j == 1) { + row.setRowKey(PhTypeUtil.toBytes(val, phType)); + } else { + row.addCell(family, qualifile, PhTypeUtil.toBytes(val, phType)); + } + } + } else { + // 如果不需要类型转换 + if (columnItem.getType() == null || "".equals(columnItem.getType())) { + if (val instanceof java.sql.Date) { + SimpleDateFormat dateFmt = new SimpleDateFormat("yyyy-MM-dd"); + val = dateFmt.format((Date) val); + } else if (val instanceof Timestamp) { + SimpleDateFormat datetimeFmt = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); + val = datetimeFmt.format((Date) val); + } + + byte[] valBytes = Bytes.toBytes(val.toString()); + if (columnItem.isRowKey()) { + if (columnItem.getRowKeyLen() != null) { + valBytes = Bytes.toBytes(limitLenNum(columnItem.getRowKeyLen(), val)); + row.setRowKey(valBytes); + } else { + row.setRowKey(valBytes); + } + } else { + row.addCell(columnItem.getFamily(), columnItem.getQualifier(), valBytes); + } + } else { + if (MappingConfig.Mode.STRING == hbaseMapping.getMode()) { + byte[] valBytes = Bytes.toBytes(val.toString()); + if (columnItem.isRowKey()) { + if (columnItem.getRowKeyLen() != null) { + valBytes = Bytes.toBytes(limitLenNum(columnItem.getRowKeyLen(), val)); + } + row.setRowKey(valBytes); + } else { + row.addCell(columnItem.getFamily(), columnItem.getQualifier(), valBytes); + } + } else if (MappingConfig.Mode.NATIVE == hbaseMapping.getMode()) { + Type type = Type.getType(columnItem.getType()); + if (columnItem.isRowKey()) { + if (columnItem.getRowKeyLen() != null) { + String v = limitLenNum(columnItem.getRowKeyLen(), val); + row.setRowKey(Bytes.toBytes(v)); + } else { + row.setRowKey(TypeUtil.toBytes(val, type)); + } + } else { + row.addCell(columnItem.getFamily(), + columnItem.getQualifier(), + TypeUtil.toBytes(val, type)); + } + } else if (MappingConfig.Mode.PHOENIX == hbaseMapping.getMode()) { + PhType phType = PhType.getType(columnItem.getType()); + if (columnItem.isRowKey()) { + row.setRowKey(PhTypeUtil.toBytes(val, phType)); + } else { + row.addCell(columnItem.getFamily(), + columnItem.getQualifier(), + PhTypeUtil.toBytes(val, phType)); + } + } + } + } + } + + if (row.getRowKey() == null) throw new RuntimeException("RowKey 值为空"); + + rows.add(row); + complete = false; + if (i % hbaseMapping.getCommitBatch() == 0 && !rows.isEmpty()) { + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + rows.clear(); + complete = true; + } + i++; + successCount.incrementAndGet(); + if (logger.isDebugEnabled()) { + logger.debug("successful import count:" + successCount.get()); + } + } + + if (!complete && !rows.isEmpty()) { + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + } + + } catch (Exception e) { + logger.error(hbaseMapping.getHbaseTable() + " etl failed! ==>" + e.getMessage(), e); + errMsg.add(hbaseMapping.getHbaseTable() + " etl failed! ==>" + e.getMessage()); + // throw new RuntimeException(e); + } + return i; + }); + return true; + } catch (Exception e) { + logger.error(e.getMessage(), e); + return false; + } + } + + private static String limitLenNum(int len, Object val) { + if (val == null) { + return null; + } + if (val instanceof Number) { + return String.format("%0" + len + "d", (Number) ((Number) val).longValue()); + } else if (val instanceof String) { + return String.format("%0" + len + "d", Long.parseLong((String) val)); + } + return null; + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/service/HbaseSyncService.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/service/HbaseSyncService.java new file mode 100644 index 00000000..3ec58369 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/service/HbaseSyncService.java @@ -0,0 +1,459 @@ +package com.alibaba.otter.canal.client.adapter.hbase.service; + +import java.util.*; + +import org.apache.hadoop.hbase.util.Bytes; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.serializer.SerializerFeature; +import com.alibaba.otter.canal.client.adapter.hbase.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.hbase.support.*; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +/** + * HBase同步操作业务 + * + * @author rewerma 2018-8-21 下午06:45:49 + * @version 1.0.0 + */ +public class HbaseSyncService { + + private Logger logger = LoggerFactory.getLogger(this.getClass()); + + private HbaseTemplate hbaseTemplate; // HBase操作模板 + + public HbaseSyncService(HbaseTemplate hbaseTemplate){ + this.hbaseTemplate = hbaseTemplate; + } + + public void sync(MappingConfig config, Dml dml) { + try { + if (config != null) { + String type = dml.getType(); + if (type != null && type.equalsIgnoreCase("INSERT")) { + insert(config, dml); + } else if (type != null && type.equalsIgnoreCase("UPDATE")) { + update(config, dml); + } else if (type != null && type.equalsIgnoreCase("DELETE")) { + delete(config, dml); + } + if (logger.isDebugEnabled()) { + logger.debug("DML: {}", JSON.toJSONString(dml, SerializerFeature.WriteMapNullValue)); + } + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + /** + * 插入操作 + * + * @param config 配置项 + * @param dml DML数据 + */ + private void insert(MappingConfig config, Dml dml) { + List> data = dml.getData(); + if (data == null || data.isEmpty()) { + return; + } + + MappingConfig.HbaseMapping hbaseMapping = config.getHbaseMapping(); + + // if (!validHTable(config)) { + // logger.error("HBase table '{}' not exists", + // hbaseMapping.getHbaseTable()); + // return; + // } + int i = 1; + boolean complete = false; + List rows = new ArrayList<>(); + for (Map r : data) { + HRow hRow = new HRow(); + + // 拼接复合rowKey + if (hbaseMapping.getRowKey() != null) { + String[] rowKeyColumns = hbaseMapping.getRowKey().trim().split(","); + String rowKeyVale = getRowKeys(rowKeyColumns, r); + // params.put("rowKey", Bytes.toBytes(rowKeyVale)); + hRow.setRowKey(Bytes.toBytes(rowKeyVale)); + } + + convertData2Row(hbaseMapping, hRow, r); + if (hRow.getRowKey() == null) { + throw new RuntimeException("empty rowKey"); + } + rows.add(hRow); + complete = false; + if (i % config.getHbaseMapping().getCommitBatch() == 0 && !rows.isEmpty()) { + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + rows.clear(); + complete = true; + } + i++; + } + if (!complete && !rows.isEmpty()) { + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + } + + } + + /** + * 将Map数据转换为HRow行数据 + * + * @param hbaseMapping hbase映射配置 + * @param hRow 行对象 + * @param data Map数据 + */ + private static void convertData2Row(MappingConfig.HbaseMapping hbaseMapping, HRow hRow, Map data) { + Map columnItems = hbaseMapping.getColumnItems(); + int i = 0; + for (Map.Entry entry : data.entrySet()) { + if (hbaseMapping.getExcludeColumns() != null && hbaseMapping.getExcludeColumns().contains(entry.getKey())) { + continue; + } + if (entry.getValue() != null) { + MappingConfig.ColumnItem columnItem = columnItems.get(entry.getKey()); + + byte[] bytes = typeConvert(columnItem, hbaseMapping, entry.getValue()); + + if (columnItem == null) { + String familyName = hbaseMapping.getFamily(); + String qualifier = entry.getKey(); + if (hbaseMapping.isUppercaseQualifier()) { + qualifier = qualifier.toUpperCase(); + } + + if (hbaseMapping.getRowKey() == null && i == 0) { + hRow.setRowKey(bytes); + } else { + hRow.addCell(familyName, qualifier, bytes); + } + } else { + if (columnItem.isRowKey()) { + if (columnItem.getRowKeyLen() != null && entry.getValue() != null) { + if (entry.getValue() instanceof Number) { + String v = String.format("%0" + columnItem.getRowKeyLen() + "d", + ((Number) entry.getValue()).longValue()); + bytes = Bytes.toBytes(v); + } else { + try { + String v = String.format("%0" + columnItem.getRowKeyLen() + "d", + Integer.parseInt((String) entry.getValue())); + bytes = Bytes.toBytes(v); + } catch (Exception e) { + // ignore + } + } + } + hRow.setRowKey(bytes); + } else { + hRow.addCell(columnItem.getFamily(), columnItem.getQualifier(), bytes); + } + } + } + i++; + } + } + + /** + * 更新操作 + * + * @param config 配置对象 + * @param dml dml对象 + */ + private void update(MappingConfig config, Dml dml) { + List> data = dml.getData(); + List> old = dml.getOld(); + if (old == null || old.isEmpty() || data == null || data.isEmpty()) { + return; + } + + MappingConfig.HbaseMapping hbaseMapping = config.getHbaseMapping(); + + // if (!validHTable(config)) { + // logger.error("HBase table '{}' not exists", + // hbaseMapping.getHbaseTable()); + // return; + // } + + MappingConfig.ColumnItem rowKeyColumn = hbaseMapping.getRowKeyColumn(); + int index = 0; + int i = 1; + boolean complete = false; + List rows = new ArrayList<>(); + out: for (Map r : data) { + byte[] rowKeyBytes; + + if (hbaseMapping.getRowKey() != null) { + String[] rowKeyColumns = hbaseMapping.getRowKey().trim().split(","); + + // 判断是否有复合主键修改 + for (String updateColumn : old.get(index).keySet()) { + for (String rowKeyColumnName : rowKeyColumns) { + if (rowKeyColumnName.equalsIgnoreCase(updateColumn)) { + // 调用删除插入操作 + deleteAndInsert(config, dml); + continue out; + } + } + } + + String rowKeyVale = getRowKeys(rowKeyColumns, r); + rowKeyBytes = Bytes.toBytes(rowKeyVale); + } else if (rowKeyColumn == null) { + Map rowKey = data.get(0); + rowKeyBytes = typeConvert(null, hbaseMapping, rowKey.values().iterator().next()); + } else { + rowKeyBytes = getRowKeyBytes(hbaseMapping, rowKeyColumn, r); + } + if (rowKeyBytes == null) throw new RuntimeException("rowKey值为空"); + + Map columnItems = hbaseMapping.getColumnItems(); + HRow hRow = new HRow(rowKeyBytes); + for (String updateColumn : old.get(index).keySet()) { + if (hbaseMapping.getExcludeColumns() != null + && hbaseMapping.getExcludeColumns().contains(updateColumn)) { + continue; + } + MappingConfig.ColumnItem columnItem = columnItems.get(updateColumn); + if (columnItem == null) { + String family = hbaseMapping.getFamily(); + String qualifier = updateColumn; + if (hbaseMapping.isUppercaseQualifier()) { + qualifier = qualifier.toUpperCase(); + } + + Object newVal = r.get(updateColumn); + + if (newVal == null) { + hRow.addCell(family, qualifier, null); + } else { + hRow.addCell(family, qualifier, typeConvert(null, hbaseMapping, newVal)); + } + } else { + // 排除修改id的情况 + if (columnItem.isRowKey()) continue; + + Object newVal = r.get(updateColumn); + if (newVal == null) { + hRow.addCell(columnItem.getFamily(), columnItem.getQualifier(), null); + } else { + hRow.addCell(columnItem.getFamily(), + columnItem.getQualifier(), + typeConvert(columnItem, hbaseMapping, newVal)); + } + } + } + rows.add(hRow); + complete = false; + if (i % config.getHbaseMapping().getCommitBatch() == 0 && !rows.isEmpty()) { + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + rows.clear(); + complete = true; + } + i++; + index++; + } + if (!complete && !rows.isEmpty()) { + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + } + } + + private void delete(MappingConfig config, Dml dml) { + List> data = dml.getData(); + if (data == null || data.isEmpty()) { + return; + } + + MappingConfig.HbaseMapping hbaseMapping = config.getHbaseMapping(); + + // if (!validHTable(config)) { + // logger.error("HBase table '{}' not exists", + // hbaseMapping.getHbaseTable()); + // return; + // } + + MappingConfig.ColumnItem rowKeyColumn = hbaseMapping.getRowKeyColumn(); + boolean complete = false; + int i = 1; + Set rowKeys = new HashSet<>(); + for (Map r : data) { + byte[] rowKeyBytes; + + if (hbaseMapping.getRowKey() != null) { + String[] rowKeyColumns = hbaseMapping.getRowKey().trim().split(","); + String rowKeyVale = getRowKeys(rowKeyColumns, r); + rowKeyBytes = Bytes.toBytes(rowKeyVale); + } else if (rowKeyColumn == null) { + // 如果不需要类型转换 + Map rowKey = data.get(0); + rowKeyBytes = typeConvert(null, hbaseMapping, rowKey.values().iterator().next()); + } else { + rowKeyBytes = getRowKeyBytes(hbaseMapping, rowKeyColumn, r); + } + if (rowKeyBytes == null) throw new RuntimeException("rowKey值为空"); + rowKeys.add(rowKeyBytes); + complete = false; + if (i % config.getHbaseMapping().getCommitBatch() == 0 && !rowKeys.isEmpty()) { + hbaseTemplate.deletes(hbaseMapping.getHbaseTable(), rowKeys); + rowKeys.clear(); + complete = true; + } + i++; + } + if (!complete && !rowKeys.isEmpty()) { + hbaseTemplate.deletes(hbaseMapping.getHbaseTable(), rowKeys); + } + } + + private void deleteAndInsert(MappingConfig config, Dml dml) { + List> data = dml.getData(); + List> old = dml.getOld(); + if (old == null || old.isEmpty() || data == null || data.isEmpty()) { + return; + } + MappingConfig.HbaseMapping hbaseMapping = config.getHbaseMapping(); + + String[] rowKeyColumns = hbaseMapping.getRowKey().trim().split(","); + + int index = 0; + int i = 1; + boolean complete = false; + Set rowKeys = new HashSet<>(); + List rows = new ArrayList<>(); + for (Map r : data) { + // 拼接老的rowKey + List updateSubRowKey = new ArrayList<>(); + for (String rowKeyColumnName : rowKeyColumns) { + for (String updateColumn : old.get(index).keySet()) { + if (rowKeyColumnName.equalsIgnoreCase(updateColumn)) { + updateSubRowKey.add(rowKeyColumnName); + } + } + } + if (updateSubRowKey.isEmpty()) { + throw new RuntimeException("没有更新复合主键的RowKey"); + } + StringBuilder oldRowKey = new StringBuilder(); + StringBuilder newRowKey = new StringBuilder(); + for (String rowKeyColumnName : rowKeyColumns) { + newRowKey.append(r.get(rowKeyColumnName).toString()).append("|"); + if (!updateSubRowKey.contains(rowKeyColumnName)) { + // 从data取 + oldRowKey.append(r.get(rowKeyColumnName).toString()).append("|"); + } else { + // 从old取 + oldRowKey.append(old.get(index).get(rowKeyColumnName).toString()).append("|"); + } + } + int len = newRowKey.length(); + newRowKey.delete(len - 1, len); + len = oldRowKey.length(); + oldRowKey.delete(len - 1, len); + byte[] newRowKeyBytes = Bytes.toBytes(newRowKey.toString()); + byte[] oldRowKeyBytes = Bytes.toBytes(oldRowKey.toString()); + + rowKeys.add(oldRowKeyBytes); + HRow row = new HRow(newRowKeyBytes); + convertData2Row(hbaseMapping, row, r); + rows.add(row); + complete = false; + if (i % config.getHbaseMapping().getCommitBatch() == 0 && !rows.isEmpty()) { + hbaseTemplate.deletes(hbaseMapping.getHbaseTable(), rowKeys); + + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + rowKeys.clear(); + rows.clear(); + complete = true; + } + i++; + index++; + } + if (!complete && !rows.isEmpty()) { + hbaseTemplate.deletes(hbaseMapping.getHbaseTable(), rowKeys); + hbaseTemplate.puts(hbaseMapping.getHbaseTable(), rows); + } + } + + /** + * 根据对应的类型进行转换 + * + * @param columnItem 列项配置 + * @param hbaseMapping hbase映射配置 + * @param value 值 + * @return 复合字段rowKey + */ + private static byte[] typeConvert(MappingConfig.ColumnItem columnItem, MappingConfig.HbaseMapping hbaseMapping, + Object value) { + if (value == null) { + return null; + } + byte[] bytes = null; + if (columnItem == null || columnItem.getType() == null || "".equals(columnItem.getType())) { + if (MappingConfig.Mode.STRING == hbaseMapping.getMode()) { + bytes = Bytes.toBytes(value.toString()); + } else if (MappingConfig.Mode.NATIVE == hbaseMapping.getMode()) { + bytes = TypeUtil.toBytes(value); + } else if (MappingConfig.Mode.PHOENIX == hbaseMapping.getMode()) { + PhType phType = PhType.getType(value.getClass()); + bytes = PhTypeUtil.toBytes(value, phType); + } + } else { + if (hbaseMapping.getMode() == MappingConfig.Mode.STRING) { + bytes = Bytes.toBytes(value.toString()); + } else if (hbaseMapping.getMode() == MappingConfig.Mode.NATIVE) { + Type type = Type.getType(columnItem.getType()); + bytes = TypeUtil.toBytes(value, type); + } else if (hbaseMapping.getMode() == MappingConfig.Mode.PHOENIX) { + PhType phType = PhType.getType(columnItem.getType()); + bytes = PhTypeUtil.toBytes(value, phType); + } + } + return bytes; + } + + /** + * 获取复合字段作为rowKey的拼接 + * + * @param rowKeyColumns 复合rowK对应的字段 + * @param data 数据 + * @return + */ + private static String getRowKeys(String[] rowKeyColumns, Map data) { + StringBuilder rowKeyValue = new StringBuilder(); + for (String rowKeyColumnName : rowKeyColumns) { + Object obj = data.get(rowKeyColumnName); + if (obj != null) { + rowKeyValue.append(obj.toString()); + } + rowKeyValue.append("|"); + } + int len = rowKeyValue.length(); + if (len > 0) { + rowKeyValue.delete(len - 1, len); + } + return rowKeyValue.toString(); + } + + private static byte[] getRowKeyBytes(MappingConfig.HbaseMapping hbaseMapping, MappingConfig.ColumnItem rowKeyColumn, + Map rowData) { + Object val = rowData.get(rowKeyColumn.getColumn()); + String v = null; + if (rowKeyColumn.getRowKeyLen() != null) { + if (val instanceof Number) { + v = String.format("%0" + rowKeyColumn.getRowKeyLen() + "d", (Number) ((Number) val).longValue()); + } else if (val instanceof String) { + v = String.format("%0" + rowKeyColumn.getRowKeyLen() + "d", Long.parseLong((String) val)); + } + } + if (v != null) { + return Bytes.toBytes(v); + } else { + return typeConvert(rowKeyColumn, hbaseMapping, val); + } + } + +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/HRow.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/HRow.java new file mode 100644 index 00000000..adeb2ff5 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/HRow.java @@ -0,0 +1,84 @@ +package com.alibaba.otter.canal.client.adapter.hbase.support; + +import java.util.ArrayList; +import java.util.List; + +/** + * HBase操作对象类 + * + * @author machengyuan 2018-8-21 下午10:12:34 + * @version 1.0.0 + */ +public class HRow { + + private byte[] rowKey; + private List cells = new ArrayList<>(); + + public HRow(){ + } + + public HRow(byte[] rowKey){ + this.rowKey = rowKey; + } + + public byte[] getRowKey() { + return rowKey; + } + + public void setRowKey(byte[] rowKey) { + this.rowKey = rowKey; + } + + public List getCells() { + return cells; + } + + public void setCells(List cells) { + this.cells = cells; + } + + public void addCell(String family, String qualifier, byte[] value) { + HCell hCell = new HCell(family, qualifier, value); + cells.add(hCell); + } + + public static class HCell { + + private String family; + private String qualifier; + private byte[] value; + + public HCell(){ + } + + public HCell(String family, String qualifier, byte[] value){ + this.family = family; + this.qualifier = qualifier; + this.value = value; + } + + public String getFamily() { + return family; + } + + public void setFamily(String family) { + this.family = family; + } + + public String getQualifier() { + return qualifier; + } + + public void setQualifier(String qualifier) { + this.qualifier = qualifier; + } + + public byte[] getValue() { + return value; + } + + public void setValue(byte[] value) { + this.value = value; + } + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/HbaseTemplate.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/HbaseTemplate.java new file mode 100644 index 00000000..1956dbfb --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/HbaseTemplate.java @@ -0,0 +1,163 @@ +package com.alibaba.otter.canal.client.adapter.hbase.support; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; +import java.util.Set; + +import org.apache.hadoop.hbase.HColumnDescriptor; +import org.apache.hadoop.hbase.HTableDescriptor; +import org.apache.hadoop.hbase.TableName; +import org.apache.hadoop.hbase.client.Connection; +import org.apache.hadoop.hbase.client.Delete; +import org.apache.hadoop.hbase.client.HBaseAdmin; +import org.apache.hadoop.hbase.client.HTable; +import org.apache.hadoop.hbase.client.Put; +import org.apache.hadoop.hbase.util.Bytes; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +/** + * HBase操作模板 + * + * @author machengyuan 2018-8-21 下午10:12:34 + * @version 1.0.0 + */ +public class HbaseTemplate { + + private Logger logger = LoggerFactory.getLogger(this.getClass()); + + private Connection conn; + + public HbaseTemplate(Connection conn){ + this.conn = conn; + } + + public boolean tableExists(String tableName) { + try (HBaseAdmin admin = (HBaseAdmin) conn.getAdmin()) { + + return admin.tableExists(TableName.valueOf(tableName)); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + + public void createTable(String tableName, String... familyNames) { + try (HBaseAdmin admin = (HBaseAdmin) conn.getAdmin()) { + + HTableDescriptor desc = new HTableDescriptor(TableName.valueOf(tableName)); + // 添加列簇 + if (familyNames != null) { + for (String familyName : familyNames) { + HColumnDescriptor hcd = new HColumnDescriptor(familyName); + desc.addFamily(hcd); + } + } + admin.createTable(desc); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + + public void disableTable(String tableName) { + try (HBaseAdmin admin = (HBaseAdmin) conn.getAdmin()) { + admin.disableTable(tableName); + } catch (IOException e) { + logger.error(e.getMessage(), e); + throw new RuntimeException(e); + } + } + + public void deleteTable(String tableName) { + try (HBaseAdmin admin = (HBaseAdmin) conn.getAdmin()) { + if (admin.isTableEnabled(tableName)) { + disableTable(tableName); + } + admin.deleteTable(tableName); + } catch (IOException e) { + logger.error(e.getMessage(), e); + throw new RuntimeException(e); + } + } + + /** + * 插入一行数据 + * + * @param tableName 表名 + * @param hRow 行数据对象 + * @return 是否成功 + */ + public Boolean put(String tableName, HRow hRow) { + boolean flag = false; + try { + HTable table = (HTable) conn.getTable(TableName.valueOf(tableName)); + Put put = new Put(hRow.getRowKey()); + for (HRow.HCell hCell : hRow.getCells()) { + put.addColumn(Bytes.toBytes(hCell.getFamily()), Bytes.toBytes(hCell.getQualifier()), hCell.getValue()); + } + table.put(put); + flag = true; + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + return flag; + + } + + /** + * 批量插入 + * + * @param tableName 表名 + * @param rows 行数据对象集合 + * @return 是否成功 + */ + public Boolean puts(String tableName, List rows) { + boolean flag = false; + try { + HTable table = (HTable) conn.getTable(TableName.valueOf(tableName)); + List puts = new ArrayList<>(); + for (HRow hRow : rows) { + Put put = new Put(hRow.getRowKey()); + for (HRow.HCell hCell : hRow.getCells()) { + put.addColumn(Bytes.toBytes(hCell.getFamily()), + Bytes.toBytes(hCell.getQualifier()), + hCell.getValue()); + } + puts.add(put); + } + if (!puts.isEmpty()) { + table.put(puts); + } + flag = true; + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + return flag; + } + + /** + * 批量删除数据 + * + * @param tableName 表名 + * @param rowKeys rowKey集合 + * @return 是否成功 + */ + public Boolean deletes(String tableName, Set rowKeys) { + boolean flag = false; + try { + HTable table = (HTable) conn.getTable(TableName.valueOf(tableName)); + List deletes = new ArrayList<>(); + for (byte[] rowKey : rowKeys) { + Delete delete = new Delete(rowKey); + deletes.add(delete); + } + if (!deletes.isEmpty()) { + table.delete(deletes); + } + flag = true; + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + return flag; + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/PhType.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/PhType.java new file mode 100644 index 00000000..0a6a74d5 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/PhType.java @@ -0,0 +1,73 @@ +package com.alibaba.otter.canal.client.adapter.hbase.support; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.math.BigDecimal; +import java.math.BigInteger; +import java.sql.Time; +import java.sql.Timestamp; +import java.util.Date; + +/** + * Phoenix类型 + * + * @author machengyuan 2018-8-21 下午06:12:34 + * @version 1.0.0 + */ +public enum PhType { + DEFAULT, UNSIGNED_INT, UNSIGNED_LONG, UNSIGNED_TINYINT, UNSIGNED_SMALLINT, UNSIGNED_FLOAT, + UNSIGNED_DOUBLE, INTEGER, BIGINT, TINYINT, SMALLINT, FLOAT, DOUBLE, DECIMAL, BOOLEAN, UNSIGNED_TIME, + UNSIGNED_DATE, UNSIGNED_TIMESTAMP, TIME, DATE, TIMESTAMP, VARCHAR, VARBINARY; + + private static Logger logger = LoggerFactory.getLogger(PhType.class); + + public static PhType getType(Class javaType) { + if (javaType == null) return DEFAULT; + PhType phType; + if (Integer.class == javaType || int.class == javaType) { + phType = INTEGER; + } else if (Long.class == javaType || long.class == javaType) { + phType = BIGINT; + } else if (Byte.class == javaType || byte.class == javaType) { + phType = TINYINT; + } else if (Short.class == javaType || short.class == javaType) { + phType = SMALLINT; + } else if (Float.class == javaType || float.class == javaType) { + phType = FLOAT; + } else if (Double.class == javaType || double.class == javaType) { + phType = DOUBLE; + } else if (Boolean.class == javaType || boolean.class == javaType) { + phType = BOOLEAN; + } else if (java.sql.Date.class == javaType) { + phType = DATE; + } else if (Time.class == javaType) { + phType = DATE; + } else if (Timestamp.class == javaType) { + phType = TIMESTAMP; + } else if (Date.class == javaType) { + phType = DATE; + } else if (byte[].class == javaType) { + phType = VARBINARY; + } else if (String.class == javaType) { + phType = VARCHAR; + } else if (BigDecimal.class == javaType) { + phType = DECIMAL; + } else if (BigInteger.class == javaType) { + phType = UNSIGNED_LONG; + } else { + phType = DEFAULT; + } + return phType; + } + + public static PhType getType(String type) { + if (type == null) return DEFAULT; + try { + return PhType.valueOf(type.toUpperCase()); + } catch (Exception e) { + logger.error(e.getMessage(), e); + return DEFAULT; + } + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/PhTypeUtil.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/PhTypeUtil.java new file mode 100644 index 00000000..a3a8e0b9 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/PhTypeUtil.java @@ -0,0 +1,620 @@ +package com.alibaba.otter.canal.client.adapter.hbase.support; + +import java.math.BigDecimal; +import java.math.BigInteger; +import java.math.MathContext; +import java.math.RoundingMode; +import java.sql.Timestamp; +import java.util.Date; + +import org.apache.hadoop.hbase.util.Bytes; +import org.joda.time.DateTime; + +import com.google.common.math.LongMath; + +/** + * Phoenix类型转换工具类 + * + * @author machengyuan 2018-8-21 下午06:14:26 + * @version 1.0.0 + */ +public class PhTypeUtil { + + public static byte[] toBytes(Object v, PhType phType) { + if (v == null) return null; + byte[] b = null; + if (phType == PhType.DEFAULT) { + PhType phType1 = PhType.getType(v.getClass()); + if (phType1 != null && phType1 != PhType.DEFAULT) { + toBytes(v, phType1); + } + } else if (phType == PhType.INTEGER) { + b = new byte[Bytes.SIZEOF_INT]; + encodeInt(((Number) v).intValue(), b, 0); + } else if (phType == PhType.UNSIGNED_INT) { + b = new byte[Bytes.SIZEOF_INT]; + encodeUnsignedInt(((Number) v).intValue(), b, 0); + } else if (phType == PhType.BIGINT) { + b = new byte[Bytes.SIZEOF_LONG]; + encodeLong(((Number) v).longValue(), b, 0); + } else if (phType == PhType.UNSIGNED_LONG) { + b = new byte[Bytes.SIZEOF_LONG]; + encodeUnsignedLong(((Number) v).longValue(), b, 0); + } else if (phType == PhType.SMALLINT) { + b = new byte[Bytes.SIZEOF_SHORT]; + encodeShort(((Number) v).shortValue(), b, 0); + } else if (phType == PhType.UNSIGNED_SMALLINT) { + b = new byte[Bytes.SIZEOF_SHORT]; + encodeUnsignedShort(((Number) v).shortValue(), b, 0); + } else if (phType == PhType.TINYINT) { + b = new byte[Bytes.SIZEOF_BYTE]; + encodeByte(((Number) v).byteValue(), b, 0); + } else if (phType == PhType.UNSIGNED_TINYINT) { + b = new byte[Bytes.SIZEOF_BYTE]; + encodeUnsignedByte(((Number) v).byteValue(), b, 0); + } else if (phType == PhType.FLOAT) { + b = new byte[Bytes.SIZEOF_FLOAT]; + encodeFloat(((Number) v).floatValue(), b, 0); + } else if (phType == PhType.UNSIGNED_FLOAT) { + b = new byte[Bytes.SIZEOF_FLOAT]; + encodeUnsignedFloat(((Number) v).floatValue(), b, 0); + } else if (phType == PhType.DOUBLE) { + b = new byte[Bytes.SIZEOF_DOUBLE]; + encodeDouble(((Number) v).doubleValue(), b, 0); + } else if (phType == PhType.UNSIGNED_DOUBLE) { + b = new byte[Bytes.SIZEOF_DOUBLE]; + encodeUnsignedDouble(((Number) v).doubleValue(), b, 0); + } else if (phType == PhType.BOOLEAN) { + if ((Boolean) v) { + b = new byte[] { 1 }; + } else { + b = new byte[] { 0 }; + } + } else if (phType == PhType.TIME || phType == PhType.DATE) { + b = new byte[Bytes.SIZEOF_LONG]; + encodeDate(v, b, 0); + } else if (phType == PhType.TIMESTAMP) { + b = new byte[Bytes.SIZEOF_LONG + Bytes.SIZEOF_INT]; + encodeTimestamp(v, b, 0); + } else if (phType == PhType.UNSIGNED_TIME || phType == PhType.UNSIGNED_DATE) { + b = new byte[Bytes.SIZEOF_LONG]; + encodeUnsignedDate(v, b, 0); + } else if (phType == PhType.UNSIGNED_TIMESTAMP) { + b = new byte[Bytes.SIZEOF_LONG + Bytes.SIZEOF_INT]; + encodeUnsignedTimestamp(v, b, 0); + } else if (phType == PhType.VARBINARY) { + b = (byte[]) v; + } else if (phType == PhType.VARCHAR) { + b = Bytes.toBytes(v.toString()); + } else if (phType == PhType.DECIMAL) { + if (v instanceof BigDecimal) { + b = encodeDecimal(v); + } else if (v instanceof Number) { + b = encodeDecimal(new BigDecimal(v.toString())); + } + } + return b; + } + + public static Object toObject(byte[] b, PhType phType) { + if (b == null) return null; + Object v = null; + if (phType == PhType.INTEGER) { + v = decodeInt(b, 0); + } else if (phType == PhType.UNSIGNED_INT) { + v = decodeUnsignedInt(b, 0); + } else if (phType == PhType.BIGINT) { + v = decodeLong(b, 0); + } else if (phType == PhType.UNSIGNED_LONG) { + v = decodeUnsignedLong(b, 0); + } else if (phType == PhType.SMALLINT) { + v = decodeShort(b, 0); + } else if (phType == PhType.UNSIGNED_SMALLINT) { + v = decodeUnsignedShort(b, 0); + } else if (phType == PhType.TINYINT) { + v = decodeByte(b, 0); + } else if (phType == PhType.UNSIGNED_TINYINT) { + v = decodeUnsignedByte(b, 0); + } else if (phType == PhType.FLOAT) { + v = decodeFloat(b, 0); + } else if (phType == PhType.UNSIGNED_FLOAT) { + v = decodeUnsignedFloat(b, 0); + } else if (phType == PhType.DOUBLE) { + v = decodeDouble(b, 0); + } else if (phType == PhType.UNSIGNED_DOUBLE) { + v = decodeUnsignedDouble(b, 0); + } else if (phType == PhType.BOOLEAN) { + checkForSufficientLength(b, 0, Bytes.SIZEOF_BOOLEAN); + if (b[0] == 1) { + v = true; + } else if (b[0] == 0) { + v = false; + } + } else if (phType == PhType.TIME || phType == PhType.DATE) { + v = new Date(decodeLong(b, 0)); + } else if (phType == PhType.TIMESTAMP) { + long millisDeserialized = decodeLong(b, 0); + Timestamp ts = new Timestamp(millisDeserialized); + int nanosDeserialized = decodeUnsignedInt(b, Bytes.SIZEOF_LONG); + ts.setNanos(nanosDeserialized < 1000000 ? ts.getNanos() + nanosDeserialized : nanosDeserialized); + v = ts; + } else if (phType == PhType.UNSIGNED_TIME || phType == PhType.UNSIGNED_DATE) { + v = new Date(decodeUnsignedLong(b, 0)); + } else if (phType == PhType.UNSIGNED_TIMESTAMP) { + long millisDeserialized = decodeUnsignedLong(b, 0); + Timestamp ts = new Timestamp(millisDeserialized); + int nanosDeserialized = decodeUnsignedInt(b, Bytes.SIZEOF_LONG); + ts.setNanos(nanosDeserialized < 1000000 ? ts.getNanos() + nanosDeserialized : nanosDeserialized); + v = ts; + } else if (phType == PhType.VARBINARY) { + v = b; + } else if (phType == PhType.VARCHAR || phType == PhType.DEFAULT) { + v = Bytes.toString(b); + } else if (phType == PhType.DECIMAL) { + v = decodeDecimal(b, 0, b.length); + } + + return v; + } + + private static int decodeInt(byte[] bytes, int o) { + checkForSufficientLength(bytes, o, Bytes.SIZEOF_INT); + int v; + v = bytes[o] ^ 0x80; // Flip sign bit back + for (int i = 1; i < Bytes.SIZEOF_INT; i++) { + v = (v << 8) + (bytes[o + i] & 0xff); + } + return v; + } + + private static int encodeInt(int v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_INT); + b[o + 0] = (byte) ((v >> 24) ^ 0x80); // Flip sign bit so that INTEGER + // is binary comparable + b[o + 1] = (byte) (v >> 16); + b[o + 2] = (byte) (v >> 8); + b[o + 3] = (byte) v; + return Bytes.SIZEOF_INT; + } + + private static int decodeUnsignedInt(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_INT); + + int v = Bytes.toInt(b, o); + if (v < 0) { + throw new RuntimeException(); + } + return v; + } + + private static int encodeUnsignedInt(int v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_INT); + if (v < 0) { + throw new RuntimeException(); + } + Bytes.putInt(b, o, v); + return Bytes.SIZEOF_INT; + } + + private static long decodeLong(byte[] bytes, int o) { + checkForSufficientLength(bytes, o, Bytes.SIZEOF_LONG); + long v; + byte b = bytes[o]; + v = b ^ 0x80; // Flip sign bit back + for (int i = 1; i < Bytes.SIZEOF_LONG; i++) { + b = bytes[o + i]; + v = (v << 8) + (b & 0xff); + } + return v; + } + + private static int encodeLong(long v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_LONG); + b[o + 0] = (byte) ((v >> 56) ^ 0x80); // Flip sign bit so that INTEGER + // is binary comparable + b[o + 1] = (byte) (v >> 48); + b[o + 2] = (byte) (v >> 40); + b[o + 3] = (byte) (v >> 32); + b[o + 4] = (byte) (v >> 24); + b[o + 5] = (byte) (v >> 16); + b[o + 6] = (byte) (v >> 8); + b[o + 7] = (byte) v; + return Bytes.SIZEOF_LONG; + } + + private static long decodeUnsignedLong(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_LONG); + long v = 0; + for (int i = o; i < o + Bytes.SIZEOF_LONG; i++) { + v <<= 8; + v ^= b[i] & 0xFF; + } + + if (v < 0) { + throw new RuntimeException(); + } + return v; + } + + private static int encodeUnsignedLong(long v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_LONG); + if (v < 0) { + throw new RuntimeException(); + } + Bytes.putLong(b, o, v); + return Bytes.SIZEOF_LONG; + } + + private static short decodeShort(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_SHORT); + int v; + v = b[o] ^ 0x80; // Flip sign bit back + for (int i = 1; i < Bytes.SIZEOF_SHORT; i++) { + v = (v << 8) + (b[o + i] & 0xff); + } + return (short) v; + } + + private static int encodeShort(short v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_SHORT); + b[o + 0] = (byte) ((v >> 8) ^ 0x80); // Flip sign bit so that Short is + // binary comparable + b[o + 1] = (byte) v; + return Bytes.SIZEOF_SHORT; + } + + private static short decodeUnsignedShort(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_SHORT); + short v = Bytes.toShort(b, o); + if (v < 0) { + throw new RuntimeException(); + } + return v; + } + + private static int encodeUnsignedShort(short v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_SHORT); + if (v < 0) { + throw new RuntimeException(); + } + Bytes.putShort(b, o, v); + return Bytes.SIZEOF_SHORT; + } + + private static byte decodeByte(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_BYTE); + int v; + v = b[o] ^ 0x80; // Flip sign bit back + return (byte) v; + } + + private static int encodeByte(byte v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_BYTE); + b[o] = (byte) (v ^ 0x80); // Flip sign bit so that Short is binary + // comparable + return Bytes.SIZEOF_BYTE; + } + + private static byte decodeUnsignedByte(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_BYTE); + byte v = b[o]; + if (v < 0) { + throw new RuntimeException(); + } + return v; + } + + private static int encodeUnsignedByte(byte v, byte[] b, int o) { + if (v < 0) { + throw new RuntimeException(); + } + Bytes.putByte(b, o, v); + return Bytes.SIZEOF_BYTE; + } + + private static float decodeFloat(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_INT); + int value; + value = Bytes.toInt(b, o); + value--; + value ^= (~value >> Integer.SIZE - 1) | Integer.MIN_VALUE; + return Float.intBitsToFloat(value); + } + + private static int encodeFloat(float v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_FLOAT); + int i = Float.floatToIntBits(v); + i = (i ^ ((i >> Integer.SIZE - 1) | Integer.MIN_VALUE)) + 1; + Bytes.putInt(b, o, i); + return Bytes.SIZEOF_FLOAT; + } + + private static float decodeUnsignedFloat(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_FLOAT); + float v = Bytes.toFloat(b, o); + if (v < 0) { + throw new RuntimeException(); + } + return v; + } + + private static int encodeUnsignedFloat(float v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_FLOAT); + if (v < 0) { + throw new RuntimeException(); + } + Bytes.putFloat(b, o, v); + return Bytes.SIZEOF_FLOAT; + } + + private static double decodeDouble(byte[] bytes, int o) { + checkForSufficientLength(bytes, o, Bytes.SIZEOF_LONG); + long l; + l = Bytes.toLong(bytes, o); + l--; + l ^= (~l >> Long.SIZE - 1) | Long.MIN_VALUE; + return Double.longBitsToDouble(l); + } + + private static int encodeDouble(double v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_LONG); + long l = Double.doubleToLongBits(v); + l = (l ^ ((l >> Long.SIZE - 1) | Long.MIN_VALUE)) + 1; + Bytes.putLong(b, o, l); + return Bytes.SIZEOF_LONG; + } + + private static double decodeUnsignedDouble(byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_DOUBLE); + double v = Bytes.toDouble(b, o); + if (v < 0) { + throw new RuntimeException(); + } + return v; + } + + private static int encodeUnsignedDouble(double v, byte[] b, int o) { + checkForSufficientLength(b, o, Bytes.SIZEOF_DOUBLE); + if (v < 0) { + throw new RuntimeException(); + } + Bytes.putDouble(b, o, v); + return Bytes.SIZEOF_DOUBLE; + } + + private static int encodeDate(Object v, byte[] b, int o) { + if (v instanceof Date) { + encodeLong(((Date) v).getTime(), b, 0); + } else if (v instanceof String) { + String dateStr = (String) v; + Date date; + try { + date = parseDatetime(dateStr); + if (date != null) { + encodeLong(date.getTime(), b, 0); + } + } catch (Exception e) { + throw new RuntimeException(e); + } + } + return Bytes.SIZEOF_LONG; + } + + private static int encodeTimestamp(Object v, byte[] b, int o) { + if (v instanceof Timestamp) { + Timestamp ts = (Timestamp) v; + encodeLong(ts.getTime(), b, o); + Bytes.putInt(b, Bytes.SIZEOF_LONG, ts.getNanos() % 1000000); + } else { + encodeDate(v, b, o); + } + return Bytes.SIZEOF_LONG + Bytes.SIZEOF_INT; + } + + private static int encodeUnsignedDate(Object v, byte[] b, int o) { + if (v instanceof Date) { + encodeUnsignedLong(((Date) v).getTime(), b, 0); + } else if (v instanceof String) { + String dateStr = (String) v; + Date date; + try { + date = parseDatetime(dateStr); + if (date != null) { + encodeUnsignedLong(date.getTime(), b, 0); + } + } catch (Exception e) { + throw new RuntimeException(e); + } + } + return Bytes.SIZEOF_LONG; + } + + private static int encodeUnsignedTimestamp(Object v, byte[] b, int o) { + if (v instanceof Timestamp) { + Timestamp ts = (Timestamp) v; + encodeUnsignedLong(ts.getTime(), b, o); + Bytes.putInt(b, Bytes.SIZEOF_LONG, ts.getNanos() % 1000000); + } else { + encodeUnsignedDate(v, b, o); + } + return Bytes.SIZEOF_LONG + Bytes.SIZEOF_INT; + } + + private static byte[] encodeDecimal(Object object) { + if (object == null) { + return new byte[0]; + } + BigDecimal v = (BigDecimal) object; + v = v.round(DEFAULT_MATH_CONTEXT).stripTrailingZeros(); + int len = getLength(v); + byte[] result = new byte[Math.min(len, 21)]; + decimalToBytes(v, result, 0, len); + return result; + } + + private static BigDecimal decodeDecimal(byte[] bytes, int offset, int length) { + if (length == 1 && bytes[offset] == ZERO_BYTE) { + return BigDecimal.ZERO; + } + int signum = ((bytes[offset] & 0x80) == 0) ? -1 : 1; + int scale; + int index; + int digitOffset; + long multiplier = 100L; + int begIndex = offset + 1; + if (signum == 1) { + scale = (byte) (((bytes[offset] & 0x7F) - 65) * -2); + index = offset + length; + digitOffset = POS_DIGIT_OFFSET; + } else { + scale = (byte) ((~bytes[offset] - 65 - 128) * -2); + index = offset + length - (bytes[offset + length - 1] == NEG_TERMINAL_BYTE ? 1 : 0); + digitOffset = -NEG_DIGIT_OFFSET; + } + length = index - offset; + long l = signum * bytes[--index] - digitOffset; + if (l % 10 == 0) { // trailing zero + scale--; // drop trailing zero and compensate in the scale + l /= 10; + multiplier = 10; + } + // Use long arithmetic for as long as we can + while (index > begIndex) { + if (l >= MAX_LONG_FOR_DESERIALIZE || multiplier >= Long.MAX_VALUE / 100) { + multiplier = LongMath.divide(multiplier, 100L, RoundingMode.UNNECESSARY); + break; // Exit loop early so we don't overflow our multiplier + } + int digit100 = signum * bytes[--index] - digitOffset; + l += digit100 * multiplier; + multiplier = LongMath.checkedMultiply(multiplier, 100); + } + + BigInteger bi; + // If still more digits, switch to BigInteger arithmetic + if (index > begIndex) { + bi = BigInteger.valueOf(l); + BigInteger biMultiplier = BigInteger.valueOf(multiplier).multiply(ONE_HUNDRED); + do { + int digit100 = signum * bytes[--index] - digitOffset; + bi = bi.add(biMultiplier.multiply(BigInteger.valueOf(digit100))); + biMultiplier = biMultiplier.multiply(ONE_HUNDRED); + } while (index > begIndex); + if (signum == -1) { + bi = bi.negate(); + } + } else { + bi = BigInteger.valueOf(l * signum); + } + // Update the scale based on the precision + scale += (length - 2) * 2; + BigDecimal v = new BigDecimal(bi, scale); + return v; + } + + private static int getLength(BigDecimal v) { + int signum = v.signum(); + if (signum == 0) { // Special case for zero + return 1; + } + return (signum < 0 ? 2 : 1) + (v.precision() + 1 + (v.scale() % 2 == 0 ? 0 : 1)) / 2; + } + + private static final int MAX_PRECISION = 38; + private static final MathContext DEFAULT_MATH_CONTEXT = new MathContext(MAX_PRECISION, RoundingMode.HALF_UP); + private static final Integer MAX_BIG_DECIMAL_BYTES = 21; + private static final byte ZERO_BYTE = (byte) 0x80; + private static final byte NEG_TERMINAL_BYTE = (byte) 102; + private static final int EXP_BYTE_OFFSET = 65; + private static final int POS_DIGIT_OFFSET = 1; + private static final int NEG_DIGIT_OFFSET = 101; + private static final BigInteger MAX_LONG = BigInteger.valueOf(Long.MAX_VALUE); + private static final BigInteger MIN_LONG = BigInteger.valueOf(Long.MIN_VALUE); + private static final BigInteger ONE_HUNDRED = BigInteger.valueOf(100); + private static final long MAX_LONG_FOR_DESERIALIZE = Long.MAX_VALUE / 1000; + + private static int decimalToBytes(BigDecimal v, byte[] result, final int offset, int length) { + int signum = v.signum(); + if (signum == 0) { + result[offset] = ZERO_BYTE; + return 1; + } + int index = offset + length; + int scale = v.scale(); + int expOffset = scale % 2 * (scale < 0 ? -1 : 1); + int multiplyBy; + BigInteger divideBy; + if (expOffset == 0) { + multiplyBy = 1; + divideBy = ONE_HUNDRED; + } else { + multiplyBy = 10; + divideBy = BigInteger.TEN; + } + // Normalize the scale based on what is necessary to end up with a base + // 100 + // decimal (i.e. 10.123e3) + int digitOffset; + BigInteger compareAgainst; + if (signum == 1) { + digitOffset = POS_DIGIT_OFFSET; + compareAgainst = MAX_LONG; + scale -= (length - 2) * 2; + result[offset] = (byte) ((-(scale + expOffset) / 2 + EXP_BYTE_OFFSET) | 0x80); + } else { + digitOffset = NEG_DIGIT_OFFSET; + compareAgainst = MIN_LONG; + // Scale adjustment shouldn't include terminal byte in length + scale -= (length - 2 - 1) * 2; + result[offset] = (byte) (~(-(scale + expOffset) / 2 + EXP_BYTE_OFFSET + 128) & 0x7F); + if (length <= MAX_BIG_DECIMAL_BYTES) { + result[--index] = NEG_TERMINAL_BYTE; + } else { + // Adjust length and offset down because we don't have enough + // room + length = MAX_BIG_DECIMAL_BYTES; + index = offset + length; + } + } + BigInteger bi = v.unscaledValue(); + // Use BigDecimal arithmetic until we can fit into a long + while (bi.compareTo(compareAgainst) * signum > 0) { + BigInteger[] dandr = bi.divideAndRemainder(divideBy); + bi = dandr[0]; + int digit = dandr[1].intValue(); + result[--index] = (byte) (digit * multiplyBy + digitOffset); + multiplyBy = 1; + divideBy = ONE_HUNDRED; + } + long l = bi.longValue(); + do { + long divBy = 100 / multiplyBy; + long digit = l % divBy; + l /= divBy; + result[--index] = (byte) (digit * multiplyBy + digitOffset); + multiplyBy = 1; + } while (l != 0); + + return length; + } + + private static void checkForSufficientLength(byte[] b, int offset, int requiredLength) { + if (b.length < offset + requiredLength) { + throw new RuntimeException("Expected length of at least " + requiredLength + " bytes, but had " + + (b.length - offset)); + } + } + + private static Date parseDatetime(String dateStr) { + Date date = null; + int len = dateStr.length(); + if (len == 10 && dateStr.charAt(4) == '-' && dateStr.charAt(7) == '-') { + date = new DateTime(dateStr).toDate(); + } else if (len == 8 && dateStr.charAt(2) == ':' && dateStr.charAt(5) == ':') { + date = new DateTime("T" + dateStr).toDate(); + } else if (len >= 19 && dateStr.charAt(4) == '-' && dateStr.charAt(7) == '-' && dateStr.charAt(13) == ':' + && dateStr.charAt(16) == ':') { + date = new DateTime(dateStr.replace(" ", "T")).toDate(); + } + return date; + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/Type.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/Type.java new file mode 100644 index 00000000..bbe3f879 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/Type.java @@ -0,0 +1,67 @@ +package com.alibaba.otter.canal.client.adapter.hbase.support; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.math.BigDecimal; +import java.math.BigInteger; +import java.util.Date; + +/** + * Java类型 + * + * @author machengyuan 2018-8-21 下午06:11:36 + * @version 1.0.0 + */ +public enum Type { + DEFAULT, STRING, INTEGER, LONG, SHORT, BOOLEAN, FLOAT, DOUBLE, BIGDECIMAL, DATE, BYTE, BYTES; + + private static Logger logger = LoggerFactory.getLogger(Type.class); + + public static Type getType(String type) { + if (type == null) { + return DEFAULT; + } + try { + return Type.valueOf(type); + } catch (Exception e) { + logger.error(e.getMessage(), e); + return DEFAULT; + } + } + + public static Type getType(Class javaType) { + if (javaType == null) { + return DEFAULT; + } + Type type; + if (Integer.class == javaType || int.class == javaType) { + type = INTEGER; + } else if (Long.class == javaType || long.class == javaType) { + type = LONG; + } else if (Byte.class == javaType || byte.class == javaType) { + type = BYTE; + } else if (Short.class == javaType || short.class == javaType) { + type = SHORT; + } else if (Float.class == javaType || float.class == javaType) { + type = FLOAT; + } else if (Double.class == javaType || double.class == javaType) { + type = DOUBLE; + } else if (Boolean.class == javaType || boolean.class == javaType) { + type = BOOLEAN; + } else if (Date.class == javaType) { + type = DATE; + } else if (byte[].class == javaType) { + type = BYTES; + } else if (String.class == javaType) { + type = STRING; + } else if (BigDecimal.class == javaType) { + type = BIGDECIMAL; + } else if (BigInteger.class == javaType) { + type = LONG; + } else { + type = DEFAULT; + } + return type; + } +} diff --git a/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/TypeUtil.java b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/TypeUtil.java new file mode 100644 index 00000000..22500a47 --- /dev/null +++ b/client-adapter/hbase/src/main/java/com/alibaba/otter/canal/client/adapter/hbase/support/TypeUtil.java @@ -0,0 +1,189 @@ +package com.alibaba.otter.canal.client.adapter.hbase.support; + +import java.math.BigDecimal; +import java.math.BigInteger; +import java.sql.Time; +import java.sql.Timestamp; +import java.util.Date; + +import org.apache.hadoop.hbase.util.Bytes; + +/** + * Java类型转换工具类 + * + * @author machengyuan 2018-8-21 下午06:12:34 + * @version 1.0.0 + */ +public class TypeUtil { + + public static byte[] toBytes(Object obj) { + if (obj == null) { + return null; + } + byte[] bytes; + Class clazz = obj.getClass(); + if (clazz == String.class) { + bytes = Bytes.toBytes((String) obj); + } else if (clazz == Integer.class || clazz == int.class) { + bytes = Bytes.toBytes((Integer) obj); + } else if (clazz == Long.class || clazz == long.class) { + bytes = Bytes.toBytes((Long) obj); + } else if (clazz == Short.class || clazz == short.class) { + bytes = Bytes.toBytes((Short) obj); + } else if (clazz == Boolean.class || clazz == boolean.class) { + bytes = Bytes.toBytes((Boolean) obj); + } else if (clazz == Float.class || clazz == float.class) { + bytes = Bytes.toBytes((Float) obj); + } else if (clazz == Double.class || clazz == double.class) { + bytes = Bytes.toBytes((Double) obj); + } else if (clazz == Byte.class || clazz == byte.class) { + bytes = new byte[] { (byte) obj }; + } else if (clazz == BigDecimal.class) { + bytes = Bytes.toBytes((BigDecimal) obj); + } else if (clazz == BigInteger.class) { + bytes = Bytes.toBytes(((BigInteger) obj).longValue()); + } else if (clazz == Date.class) { + bytes = Bytes.toBytes(((Date) obj).getTime()); + } else if (clazz == byte[].class) { + bytes = (byte[]) obj; + } else { + // 其余类型统一转换为string + bytes = Bytes.toBytes(obj.toString()); + } + return bytes; + } + + public static byte[] toBytes(Object v, Type type) { + if (v == null) { + return null; + } + byte[] b = null; + if (type == Type.DEFAULT) { + Type type1 = Type.getType(v.getClass()); + if (type1 != null && type1 != Type.DEFAULT) { + b = toBytes(v, type1); + } + } else if (type == Type.STRING) { + b = Bytes.toBytes(v.toString()); + } else if (type == Type.INTEGER) { + b = Bytes.toBytes(((Number) v).intValue()); + } else if (type == Type.LONG) { + b = Bytes.toBytes(((Number) v).longValue()); + } else if (type == Type.SHORT) { + b = Bytes.toBytes(((Number) v).shortValue()); + } else if (type == Type.BYTE) { + b = Bytes.toBytes(((Number) v).byteValue()); + } else if (type == Type.FLOAT) { + b = Bytes.toBytes(((Number) v).floatValue()); + } else if (type == Type.DOUBLE) { + b = Bytes.toBytes(((Number) v).doubleValue()); + } else if (type == Type.BOOLEAN) { + b = Bytes.toBytes(((Boolean) v)); + } else if (type == Type.DATE) { + b = Bytes.toBytes(((Date) v).getTime()); + } else if (type == Type.BYTES) { + b = (byte[]) v; + } else if (type == Type.BIGDECIMAL) { + if (v instanceof BigDecimal) { + b = Bytes.toBytes((BigDecimal) v); + } else { + b = Bytes.toBytes(new BigDecimal(v.toString())); + } + } + return b; + } + + @SuppressWarnings("unchecked") + public static T toObject(byte[] bytes, Class clazz) { + if (bytes == null) { + return null; + } + Object res; + if (String.class == clazz) { + res = Bytes.toString(bytes); + } else if (Integer.class == clazz || int.class == clazz) { + res = Bytes.toInt(bytes); + } else if (Long.class == clazz || long.class == clazz) { + res = Bytes.toLong(bytes); + } else if (Short.class == clazz || short.class == clazz) { + res = Bytes.toShort(bytes); + } else if (Boolean.class == clazz || boolean.class == clazz) { + res = Bytes.toBoolean(bytes); + } else if (Float.class == clazz || float.class == clazz) { + res = Bytes.toFloat(bytes); + } else if (Double.class == clazz || double.class == clazz) { + res = Bytes.toDouble(bytes); + } else if (Byte.class == clazz || byte.class == clazz) { + res = bytes[0]; + } else if (BigDecimal.class == clazz) { + res = Bytes.toBigDecimal(bytes); + } else if (BigInteger.class == clazz) { + res = Bytes.toLong(bytes); + } else if (java.sql.Date.class == clazz) { + long ts = Bytes.toLong(bytes); + res = new java.sql.Date(ts); + } else if (Time.class == clazz) { + long ts = Bytes.toLong(bytes); + res = new Time(ts); + } else if (Timestamp.class == clazz) { + long ts = Bytes.toLong(bytes); + res = new Timestamp(ts); + } else if (Date.class == clazz) { + long ts = Bytes.toLong(bytes); + res = new Date(ts); + } else { + throw new IllegalArgumentException("mismatch class type"); + } + return (T) res; + } + + @SuppressWarnings("unchecked") + public static T toObject(byte[] bytes, Type type) { + if (bytes == null) { + return null; + } + Object res = null; + if (type == Type.STRING || type == Type.DEFAULT) { + res = Bytes.toString(bytes); + } else if (type == Type.INTEGER) { + if (bytes.length == Bytes.SIZEOF_INT) { + res = Bytes.toInt(bytes); + } + } else if (type == Type.LONG) { + if (bytes.length == Bytes.SIZEOF_LONG) { + res = Bytes.toLong(bytes); + } + } else if (type == Type.SHORT) { + if (bytes.length == Bytes.SIZEOF_SHORT) { + res = Bytes.toShort(bytes); + } + } else if (type == Type.BYTE) { + if (bytes.length == Bytes.SIZEOF_BYTE) { + res = bytes[0]; + } + } else if (type == Type.FLOAT) { + if (bytes.length == Bytes.SIZEOF_FLOAT) { + res = Bytes.toFloat(bytes); + } + } else if (type == Type.DOUBLE) { + if (bytes.length == Bytes.SIZEOF_DOUBLE) { + res = Bytes.toDouble(bytes); + } + } else if (type == Type.BOOLEAN) { + if (bytes.length == Bytes.SIZEOF_BOOLEAN) { + res = Bytes.toBoolean(bytes); + } + } else if (type == Type.DATE) { + if (bytes.length == Bytes.SIZEOF_LONG) { + res = new Date(Bytes.toLong(bytes)); + } + } else if (type == Type.BYTES) { + res = bytes; + } else if (type == Type.BIGDECIMAL) { + res = Bytes.toBigDecimal(bytes); + } else { + throw new IllegalArgumentException("mismatch class type"); + } + return (T) res; + } +} diff --git a/client-adapter/hbase/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter b/client-adapter/hbase/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter new file mode 100644 index 00000000..321d49cf --- /dev/null +++ b/client-adapter/hbase/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter @@ -0,0 +1 @@ +hbase=com.alibaba.otter.canal.client.adapter.hbase.HbaseAdapter \ No newline at end of file diff --git a/client-adapter/hbase/src/main/resources/hbase/mytest_person2.yml b/client-adapter/hbase/src/main/resources/hbase/mytest_person2.yml new file mode 100644 index 00000000..0eebad47 --- /dev/null +++ b/client-adapter/hbase/src/main/resources/hbase/mytest_person2.yml @@ -0,0 +1,60 @@ +dataSourceKey: defaultDS +destination: example +hbaseMapping: + mode: STRING #NATIVE #PHOENIX + database: mytest # 数据库名 + table: person2 # 数据库表名 + hbaseTable: MYTEST.PERSON2 # HBase表名 + family: CF # 默认统一Family名称 + uppercaseQualifier: true # 字段名转大写, 默认为true + commitBatch: 3000 # 批量提交的大小 + #rowKey: id,type # 复合字段rowKey不能和columns中的rowKey重复 + columns: + # 数据库字段:HBase对应字段 + id: ROWKEY LEN:15 + name: NAME + email: EMAIL + type: + c_time: C_TIME + birthday: BIRTHDAY +# excludeColumns: +# - lat # 忽略字段 + +# -- NATIVE类型 +# $DEFAULT +# $STRING +# $INTEGER +# $LONG +# $SHORT +# $BOOLEAN +# $FLOAT +# $DOUBLE +# $BIGDECIMAL +# $DATE +# $BYTE +# $BYTES + +# -- PHOENIX类型 +# $DEFAULT 对应PHOENIX里的VARCHAR +# $UNSIGNED_INT 对应PHOENIX里的UNSIGNED_INT 4字节 +# $UNSIGNED_LONG 对应PHOENIX里的UNSIGNED_LONG 8字节 +# $UNSIGNED_TINYINT 对应PHOENIX里的UNSIGNED_TINYINT 1字节 +# $UNSIGNED_SMALLINT 对应PHOENIX里的UNSIGNED_SMALLINT 2字节 +# $UNSIGNED_FLOAT 对应PHOENIX里的UNSIGNED_FLOAT 4字节 +# $UNSIGNED_DOUBLE 对应PHOENIX里的UNSIGNED_DOUBLE 8字节 +# $INTEGER 对应PHOENIX里的INTEGER 4字节 +# $BIGINT 对应PHOENIX里的BIGINT 8字节 +# $TINYINT 对应PHOENIX里的TINYINT 1字节 +# $SMALLINT 对应PHOENIX里的SMALLINT 2字节 +# $FLOAT 对应PHOENIX里的FLOAT 4字节 +# $DOUBLE 对应PHOENIX里的DOUBLE 8字节 +# $BOOLEAN 对应PHOENIX里的BOOLEAN 1字节 +# $TIME 对应PHOENIX里的TIME 8字节 +# $DATE 对应PHOENIX里的DATE 8字节 +# $TIMESTAMP 对应PHOENIX里的TIMESTAMP 12字节 +# $UNSIGNED_TIME 对应PHOENIX里的UNSIGNED_TIME 8字节 +# $UNSIGNED_DATE 对应PHOENIX里的UNSIGNED_DATE 8字节 +# $UNSIGNED_TIMESTAMP 对应PHOENIX里的UNSIGNED_TIMESTAMP 12字节 +# $VARCHAR 对应PHOENIX里的VARCHAR 动态长度 +# $VARBINARY 对应PHOENIX里的VARBINARY 动态长度 +# $DECIMAL 对应PHOENIX里的DECIMAL 动态长度 \ No newline at end of file diff --git a/client-adapter/launcher/pom.xml b/client-adapter/launcher/pom.xml new file mode 100644 index 00000000..32c70028 --- /dev/null +++ b/client-adapter/launcher/pom.xml @@ -0,0 +1,261 @@ + + + + canal.client-adapter + com.alibaba.otter + 1.1.3-SNAPSHOT + + 4.0.0 + com.alibaba.otter + client-adapter.launcher + jar + canal client adapter launcher module for otter ${project.version} + + + + + org.springframework.boot + spring-boot-dependencies + 2.0.1.RELEASE + pom + import + + + + + + + com.alibaba.otter + client-adapter.common + ${project.version} + + + com.alibaba.otter + canal.client + 1.1.3-SNAPSHOT + + + org.yaml + snakeyaml + 1.19 + + + org.springframework.boot + spring-boot-starter-web + + + org.springframework.boot + spring-boot-configuration-processor + provided + + + org.springframework.cloud + spring-cloud-context + 2.0.0.RELEASE + + + org.apache.curator + curator-recipes + 2.10.0 + + + + org.apache.rocketmq + rocketmq-client + 4.3.0 + + + + org.apache.kafka + kafka-clients + 1.1.1 + + + + + org.postgresql + postgresql + 42.1.4 + + + com.oracle + ojdbc6 + 11.2.0.3 + + + com.microsoft.sqlserver + mssql-jdbc + 7.0.0.jre8 + + + + + com.alibaba.otter + client-adapter.logger + ${project.version} + + + * + * + + + jar-with-dependencies + provided + + + com.alibaba.otter + client-adapter.hbase + ${project.version} + + + * + * + + + jar-with-dependencies + provided + + + com.alibaba.otter + client-adapter.elasticsearch + ${project.version} + + + * + * + + + jar-with-dependencies + provided + + + com.alibaba.otter + client-adapter.rdb + ${project.version} + + + * + * + + + jar-with-dependencies + provided + + + + + + + org.apache.maven.plugins + maven-dependency-plugin + 2.10 + + + copy-dependencies-to-canal-client-service + package + + copy-dependencies + + + jar-with-dependencies + ${project.basedir}/target/canal-adapter/plugin + + + + + + org.apache.maven.plugins + maven-assembly-plugin + 2.2.1 + + + assemble + + single + + package + + + + false + false + + + + org.apache.maven.plugins + maven-jar-plugin + 3.0.2 + + + + true + lib/ + com.alibaba.otter.canal.adapter.launcher.CanalAdapterApplication + + + + **/*.properties + **/*.xml + **/*.yml + static/** + templates/** + + + + + + + + + dev + + true + + env + !release + + + + + + + maven-assembly-plugin + + + ${basedir}/src/main/assembly/dev.xml + + canal-adapter + ${project.build.directory} + + + + + + + + + release + + + env + release + + + + + + + maven-assembly-plugin + + + ${basedir}/src/main/assembly/release.xml + + canal.adapter-${project.version} + ${project.basedir}/../../target + + + + + + + diff --git a/client-adapter/launcher/src/main/assembly/dev.xml b/client-adapter/launcher/src/main/assembly/dev.xml new file mode 100644 index 00000000..7beaf269 --- /dev/null +++ b/client-adapter/launcher/src/main/assembly/dev.xml @@ -0,0 +1,69 @@ + + dist + + dir + + false + + + . + / + + README* + + + + ./src/main/bin + bin + + **/* + + 0755 + + + ./src/main/resources + /conf + + **/* + + + + + ../elasticsearch/src/main/resources/es + /conf/es + + **/* + + + + ../hbase/src/main/resources/hbase + /conf/hbase + + **/* + + + + ../rdb/src/main/resources/ + /conf + + META-INF/** + + + + target + logs + + **/* + + + + + + lib + + junit:junit + + + + diff --git a/client-adapter/launcher/src/main/assembly/release.xml b/client-adapter/launcher/src/main/assembly/release.xml new file mode 100644 index 00000000..456b4a6a --- /dev/null +++ b/client-adapter/launcher/src/main/assembly/release.xml @@ -0,0 +1,74 @@ + + dist + + tar.gz + + false + + + . + / + + README* + + + + ./src/main/bin + bin + + **/* + + 0755 + + + ./src/main/resources + /conf + + **/* + + + + + ../elasticsearch/src/main/resources/es + /conf/es + + **/* + + + + ../hbase/src/main/resources/hbase + /conf/hbase + + **/* + + + + ../rdb/src/main/resources/ + /conf + + META-INF/** + + + + target + logs + + **/* + + + + ${project.basedir}/target/canal-adapter/plugin + /plugin/ + + + + + lib + + junit:junit + + + + \ No newline at end of file diff --git a/client-adapter/launcher/src/main/bin/restart.sh b/client-adapter/launcher/src/main/bin/restart.sh new file mode 100644 index 00000000..63749ce5 --- /dev/null +++ b/client-adapter/launcher/src/main/bin/restart.sh @@ -0,0 +1,5 @@ +#!/bin/bash + +sh stop.sh + +sh startup.sh diff --git a/client-adapter/launcher/src/main/bin/startup.bat b/client-adapter/launcher/src/main/bin/startup.bat new file mode 100755 index 00000000..0c464dff --- /dev/null +++ b/client-adapter/launcher/src/main/bin/startup.bat @@ -0,0 +1,22 @@ +@echo off +@if not "%ECHO%" == "" echo %ECHO% +@if "%OS%" == "Windows_NT" setlocal + +set ENV_PATH=.\ +if "%OS%" == "Windows_NT" set ENV_PATH=%~dp0% + +set conf_dir=%ENV_PATH%\..\conf + +set CLASSPATH=%conf_dir% +set CLASSPATH=%conf_dir%\..\lib\*;%CLASSPATH% + +set JAVA_MEM_OPTS= -Xms128m -Xmx512m -XX:PermSize=128m +set JAVA_OPTS_EXT= -Djava.awt.headless=true -Djava.net.preferIPv4Stack=true -Dapplication.codeset=UTF-8 -Dfile.encoding=UTF-8 +set ADAPTER_OPTS= -DappName=canal-adapter + +set JAVA_OPTS= %JAVA_MEM_OPTS% %JAVA_OPTS_EXT% %ADAPTER_OPTS% + +set CMD_STR= java %JAVA_OPTS% -classpath "%CLASSPATH%" com.alibaba.otter.canal.adapter.launcher.CanalAdapterApplication +echo start cmd : %CMD_STR% + +java %JAVA_OPTS% -classpath "%CLASSPATH%" com.alibaba.otter.canal.adapter.launcher.CanalAdapterApplication \ No newline at end of file diff --git a/client-adapter/launcher/src/main/bin/startup.sh b/client-adapter/launcher/src/main/bin/startup.sh new file mode 100644 index 00000000..650fba7d --- /dev/null +++ b/client-adapter/launcher/src/main/bin/startup.sh @@ -0,0 +1,67 @@ +#!/bin/bash + +current_path=`pwd` +case "`uname`" in + Linux) + bin_abs_path=$(readlink -f $(dirname $0)) + ;; + *) + bin_abs_path=`cd $(dirname $0); pwd` + ;; +esac +base=${bin_abs_path}/.. +export LANG=en_US.UTF-8 +export BASE=$base + +if [ -f $base/bin/adapter.pid ] ; then + echo "found adapter.pid , Please run stop.sh first ,then startup.sh" 2>&2 + exit 1 +fi + +if [ ! -d $base/logs ] ; then + mkdir -p $base/logs +fi + +## set java path +if [ -z "$JAVA" ] ; then + JAVA=$(which java) +fi + +ALIBABA_JAVA="/usr/alibaba/java/bin/java" +TAOBAO_JAVA="/opt/taobao/java/bin/java" +if [ -z "$JAVA" ]; then + if [ -f $ALIBABA_JAVA ] ; then + JAVA=$ALIBABA_JAVA + elif [ -f $TAOBAO_JAVA ] ; then + JAVA=$TAOBAO_JAVA + else + echo "Cannot find a Java JDK. Please set either set JAVA or put java (>=1.5) in your PATH." 2>&2 + exit 1 + fi +fi + +str=`file -L $JAVA | grep 64-bit` +if [ -n "$str" ]; then + JAVA_OPTS="-server -Xms2048m -Xmx3072m -Xmn1024m -XX:SurvivorRatio=2 -XX:PermSize=96m -XX:MaxPermSize=256m -Xss256k -XX:-UseAdaptiveSizePolicy -XX:MaxTenuringThreshold=15 -XX:+DisableExplicitGC -XX:+UseConcMarkSweepGC -XX:+CMSParallelRemarkEnabled -XX:+UseCMSCompactAtFullCollection -XX:+UseFastAccessorMethods -XX:+UseCMSInitiatingOccupancyOnly -XX:+HeapDumpOnOutOfMemoryError" +else + JAVA_OPTS="-server -Xms1024m -Xmx1024m -XX:NewSize=256m -XX:MaxNewSize=256m -XX:MaxPermSize=128m " +fi + +JAVA_OPTS=" $JAVA_OPTS -Djava.awt.headless=true -Djava.net.preferIPv4Stack=true -Dfile.encoding=UTF-8" +ADAPTER_OPTS="-DappName=canal-adapter" + +for i in $base/lib/*; + do CLASSPATH=$i:"$CLASSPATH"; +done + +CLASSPATH="$base/conf:$CLASSPATH"; + +echo "cd to $bin_abs_path for workaround relative path" +cd $bin_abs_path + +echo CLASSPATH :$CLASSPATH +$JAVA $JAVA_OPTS $ADAPTER_OPTS -classpath .:$CLASSPATH com.alibaba.otter.canal.adapter.launcher.CanalAdapterApplication 1>>$base/logs/adapter.log 2>&1 & +echo $! > $base/bin/adapter.pid + +echo "cd to $current_path for continue" +cd $current_path \ No newline at end of file diff --git a/kafka/src/main/bin/stop.sh b/client-adapter/launcher/src/main/bin/stop.sh similarity index 88% rename from kafka/src/main/bin/stop.sh rename to client-adapter/launcher/src/main/bin/stop.sh index f398749c..fbdd5317 100644 --- a/kafka/src/main/bin/stop.sh +++ b/client-adapter/launcher/src/main/bin/stop.sh @@ -37,15 +37,15 @@ get_pid() { } base=`dirname $0`/.. -pidfile=$base/bin/canal.pid +pidfile=$base/bin/adapter.pid if [ ! -f "$pidfile" ];then - echo "canal is not running. exists" + echo "canal-adapter is not running. exists" exit fi pid=`cat $pidfile` if [ "$pid" == "" ] ; then - pid=`get_pid "appName=otter-canal"` + pid=`get_pid "appName=canal-adapter"` fi echo -e "`hostname`: stopping canal $pid ... " @@ -54,7 +54,7 @@ kill $pid LOOPS=0 while (true); do - gpid=`get_pid "appName=otter-canal" "$pid"` + gpid=`get_pid "appName=canal-adapter" "$pid"` if [ "$gpid" == "" ] ; then echo "Oook! cost:$LOOPS" `rm $pidfile` diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/CanalAdapterApplication.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/CanalAdapterApplication.java new file mode 100644 index 00000000..3d2ef585 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/CanalAdapterApplication.java @@ -0,0 +1,21 @@ +package com.alibaba.otter.canal.adapter.launcher; + +import org.springframework.boot.Banner; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +/** + * 启动入口 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@SpringBootApplication +public class CanalAdapterApplication { + + public static void main(String[] args) { + SpringApplication application = new SpringApplication(CanalAdapterApplication.class); + application.setBannerMode(Banner.Mode.OFF); + application.run(args); + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/EtlLock.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/EtlLock.java new file mode 100644 index 00000000..5fd5f3fe --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/EtlLock.java @@ -0,0 +1,120 @@ +package com.alibaba.otter.canal.adapter.launcher.common; + +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.locks.ReentrantLock; + +import javax.annotation.PostConstruct; +import javax.annotation.Resource; + +import org.apache.curator.framework.CuratorFramework; +import org.apache.curator.framework.recipes.locks.InterProcessMutex; +import org.springframework.stereotype.Component; + +import com.alibaba.otter.canal.adapter.launcher.config.CuratorClient; + +/** + * Etl 同步锁 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@Component +public class EtlLock { + + private static final Map LOCAL_LOCK = new ConcurrentHashMap<>(); + + private static final Map DISTRIBUTED_LOCK = new ConcurrentHashMap<>(); + + private static Mode mode = Mode.LOCAL; + + @Resource + private CuratorClient curatorClient; + + @PostConstruct + public void init() { + CuratorFramework curator = curatorClient.getCurator(); + if (curator != null) { + mode = Mode.DISTRIBUTED; + } else { + mode = Mode.LOCAL; + } + } + + private ReentrantLock getLock(String key) { + ReentrantLock lock = LOCAL_LOCK.get(key); + if (lock == null) { + synchronized (EtlLock.class) { + lock = LOCAL_LOCK.get(key); + if (lock == null) { + lock = new ReentrantLock(); + LOCAL_LOCK.put(key, lock); + } + } + } + return lock; + } + + private InterProcessMutex getRemoteLock(String key) { + InterProcessMutex lock = DISTRIBUTED_LOCK.get(key); + if (lock == null) { + synchronized (EtlLock.class) { + lock = DISTRIBUTED_LOCK.get(key); + if (lock == null) { + lock = new InterProcessMutex(curatorClient.getCurator(), key); + DISTRIBUTED_LOCK.put(key, lock); + } + } + } + return lock; + } + + public void lock(String key) throws Exception { + if (mode == Mode.LOCAL) { + getLock(key).lock(); + } else { + InterProcessMutex lock = getRemoteLock(key); + lock.acquire(); + } + } + + public boolean tryLock(String key, long timeout, TimeUnit unit) { + try { + if (mode == Mode.LOCAL) { + return getLock(key).tryLock(timeout, unit); + } else { + InterProcessMutex lock = getRemoteLock(key); + return lock.acquire(timeout, unit); + } + } catch (Exception e) { + return false; + } + } + + public boolean tryLock(String key) { + try { + if (mode == Mode.LOCAL) { + return getLock(key).tryLock(); + } else { + InterProcessMutex lock = getRemoteLock(key); + return lock.acquire(500, TimeUnit.MILLISECONDS); + } + } catch (Exception e) { + return false; + } + } + + public void unlock(String key) { + if (mode == Mode.LOCAL) { + getLock(key).unlock(); + } else { + InterProcessMutex lock = getRemoteLock(key); + try { + lock.release(); + } catch (Exception e) { + // ignore + } + } + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/Mode.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/Mode.java new file mode 100644 index 00000000..ac73b85e --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/Mode.java @@ -0,0 +1,6 @@ +package com.alibaba.otter.canal.adapter.launcher.common; + +public enum Mode { + LOCAL, // 本地模式 + DISTRIBUTED // 分布式 +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/SyncSwitch.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/SyncSwitch.java new file mode 100644 index 00000000..c0e5d394 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/common/SyncSwitch.java @@ -0,0 +1,214 @@ +package com.alibaba.otter.canal.adapter.launcher.common; + +import java.nio.charset.StandardCharsets; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.TimeoutException; + +import javax.annotation.PostConstruct; +import javax.annotation.Resource; + +import org.apache.curator.framework.CuratorFramework; +import org.apache.curator.framework.recipes.cache.NodeCache; +import org.apache.zookeeper.CreateMode; +import org.apache.zookeeper.data.Stat; +import org.springframework.stereotype.Component; + +import com.alibaba.otter.canal.adapter.launcher.config.AdapterCanalConfig; +import com.alibaba.otter.canal.adapter.launcher.config.CuratorClient; +import com.alibaba.otter.canal.common.utils.BooleanMutex; + +/** + * 同步开关 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@Component +public class SyncSwitch { + + private static final String SYN_SWITCH_ZK_NODE = "/sync-switch/"; + + private static final Map LOCAL_LOCK = new ConcurrentHashMap<>(); + + private static final Map DISTRIBUTED_LOCK = new ConcurrentHashMap<>(); + + private static Mode mode = Mode.LOCAL; + + @Resource + private AdapterCanalConfig adapterCanalConfig; + @Resource + private CuratorClient curatorClient; + + @PostConstruct + public void init() { + CuratorFramework curator = curatorClient.getCurator(); + if (curator != null) { + mode = Mode.DISTRIBUTED; + DISTRIBUTED_LOCK.clear(); + for (String destination : adapterCanalConfig.DESTINATIONS) { + // 对应每个destination注册锁 + BooleanMutex mutex = new BooleanMutex(true); + initMutex(curator, destination, mutex); + DISTRIBUTED_LOCK.put(destination, mutex); + startListen(destination, mutex); + } + } else { + mode = Mode.LOCAL; + LOCAL_LOCK.clear(); + for (String destination : adapterCanalConfig.DESTINATIONS) { + // 对应每个destination注册锁 + LOCAL_LOCK.put(destination, new BooleanMutex(true)); + } + } + } + + @SuppressWarnings("resource") + private synchronized void startListen(String destination, BooleanMutex mutex) { + try { + String path = SYN_SWITCH_ZK_NODE + destination; + CuratorFramework curator = curatorClient.getCurator(); + NodeCache nodeCache = new NodeCache(curator, path); + nodeCache.start(); + nodeCache.getListenable().addListener(() -> initMutex(curator, destination, mutex)); + } catch (Exception e) { + throw new RuntimeException(e.getMessage()); + } + } + + private synchronized void initMutex(CuratorFramework curator, String destination, BooleanMutex mutex) { + try { + String path = SYN_SWITCH_ZK_NODE + destination; + Stat stat = curator.checkExists().forPath(path); + if (stat == null) { + if (!mutex.state()) { + mutex.set(true); + } + } else { + String data = new String(curator.getData().forPath(path), StandardCharsets.UTF_8); + if ("on".equals(data)) { + if (!mutex.state()) { + mutex.set(true); + } + } else { + if (mutex.state()) { + mutex.set(false); + } + } + } + } catch (Exception e) { + throw new RuntimeException(e.getMessage()); + } + } + + public synchronized void off(String destination) { + if (mode == Mode.LOCAL) { + BooleanMutex mutex = LOCAL_LOCK.get(destination); + if (mutex != null && mutex.state()) { + mutex.set(false); + } + } else { + try { + String path = SYN_SWITCH_ZK_NODE + destination; + try { + curatorClient.getCurator() + .create() + .creatingParentContainersIfNeeded() + .withMode(CreateMode.PERSISTENT) + .forPath(path, "off".getBytes(StandardCharsets.UTF_8)); + } catch (Exception e) { + curatorClient.getCurator().setData().forPath(path, "off".getBytes(StandardCharsets.UTF_8)); + } + } catch (Exception e) { + throw new RuntimeException(e); + } + } + } + + public synchronized void on(String destination) { + if (mode == Mode.LOCAL) { + BooleanMutex mutex = LOCAL_LOCK.get(destination); + if (mutex != null && !mutex.state()) { + mutex.set(true); + } + } else { + try { + String path = SYN_SWITCH_ZK_NODE + destination; + try { + curatorClient.getCurator() + .create() + .creatingParentContainersIfNeeded() + .withMode(CreateMode.PERSISTENT) + .forPath(path, "on".getBytes(StandardCharsets.UTF_8)); + } catch (Exception e) { + curatorClient.getCurator().setData().forPath(path, "on".getBytes(StandardCharsets.UTF_8)); + } + } catch (Exception e) { + throw new RuntimeException(e); + } + } + } + + public synchronized void release(String destination) { + if (mode == Mode.LOCAL) { + BooleanMutex mutex = LOCAL_LOCK.get(destination); + if (mutex != null && !mutex.state()) { + mutex.set(true); + } + } + if (mode == Mode.DISTRIBUTED) { + BooleanMutex mutex = DISTRIBUTED_LOCK.get(destination); + if (mutex != null && !mutex.state()) { + mutex.set(true); + } + } + } + + public Boolean status(String destination) { + if (mode == Mode.LOCAL) { + BooleanMutex mutex = LOCAL_LOCK.get(destination); + if (mutex != null) { + return mutex.state(); + } else { + return null; + } + } else { + BooleanMutex mutex = DISTRIBUTED_LOCK.get(destination); + if (mutex != null) { + return mutex.state(); + } else { + return null; + } + } + } + + public void get(String destination) throws InterruptedException { + if (mode == Mode.LOCAL) { + BooleanMutex mutex = LOCAL_LOCK.get(destination); + if (mutex != null) { + mutex.get(); + } + } else { + BooleanMutex mutex = DISTRIBUTED_LOCK.get(destination); + if (mutex != null) { + mutex.get(); + } + } + } + + public void get(String destination, long timeout, TimeUnit unit) throws InterruptedException, TimeoutException { + if (mode == Mode.LOCAL) { + BooleanMutex mutex = LOCAL_LOCK.get(destination); + if (mutex != null) { + mutex.get(timeout, unit); + } + } else { + BooleanMutex mutex = DISTRIBUTED_LOCK.get(destination); + if (mutex != null) { + mutex.get(timeout, unit); + } + } + } + +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/AdapterCanalConfig.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/AdapterCanalConfig.java new file mode 100644 index 00000000..3ad0d5f7 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/AdapterCanalConfig.java @@ -0,0 +1,79 @@ +package com.alibaba.otter.canal.adapter.launcher.config; + +import java.sql.SQLException; +import java.util.LinkedHashSet; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.stereotype.Component; + +import com.alibaba.druid.pool.DruidDataSource; +import com.alibaba.otter.canal.client.adapter.support.CanalClientConfig; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; + +/** + * canal 的相关配置类 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@Component +@ConfigurationProperties(prefix = "canal.conf") +public class AdapterCanalConfig extends CanalClientConfig { + + public final Set DESTINATIONS = new LinkedHashSet<>(); + + private Map srcDataSources; + + @Override + public void setCanalAdapters(List canalAdapters) { + super.setCanalAdapters(canalAdapters); + + if (canalAdapters != null) { + synchronized (DESTINATIONS) { + DESTINATIONS.clear(); + for (CanalAdapter canalAdapter : canalAdapters) { + if (canalAdapter.getInstance() != null) { + DESTINATIONS.add(canalAdapter.getInstance()); + } + } + } + } + } + + public Map getSrcDataSources() { + return srcDataSources; + } + + @SuppressWarnings("resource") + public void setSrcDataSources(Map srcDataSources) { + this.srcDataSources = srcDataSources; + + if (srcDataSources != null) { + for (Map.Entry entry : srcDataSources.entrySet()) { + DatasourceConfig datasourceConfig = entry.getValue(); + // 加载数据源连接池 + DruidDataSource ds = new DruidDataSource(); + ds.setDriverClassName(datasourceConfig.getDriver()); + ds.setUrl(datasourceConfig.getUrl()); + ds.setUsername(datasourceConfig.getUsername()); + ds.setPassword(datasourceConfig.getPassword()); + ds.setInitialSize(1); + ds.setMinIdle(1); + ds.setMaxActive(datasourceConfig.getMaxActive()); + ds.setMaxWait(60000); + ds.setTimeBetweenEvictionRunsMillis(60000); + ds.setMinEvictableIdleTimeMillis(300000); + ds.setValidationQuery("select 1"); + try { + ds.init(); + } catch (SQLException e) { + throw new RuntimeException(e.getMessage(), e); + } + DatasourceConfig.DATA_SOURCES.put(entry.getKey(), ds); + } + } + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/CuratorClient.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/CuratorClient.java new file mode 100644 index 00000000..0ec60392 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/CuratorClient.java @@ -0,0 +1,42 @@ +package com.alibaba.otter.canal.adapter.launcher.config; + +import javax.annotation.PostConstruct; +import javax.annotation.Resource; + +import org.apache.curator.framework.CuratorFramework; +import org.apache.curator.framework.CuratorFrameworkFactory; +import org.apache.curator.retry.ExponentialBackoffRetry; +import org.springframework.stereotype.Component; + +/** + * curator 配置类 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@Component +public class CuratorClient { + + @Resource + private AdapterCanalConfig adapterCanalConfig; + + private CuratorFramework curator = null; + + @PostConstruct + public void init() { + if (adapterCanalConfig.getZookeeperHosts() != null) { + curator = CuratorFrameworkFactory.builder() + .connectString(adapterCanalConfig.getZookeeperHosts()) + .retryPolicy(new ExponentialBackoffRetry(1000, 3)) + .sessionTimeoutMs(6000) + .connectionTimeoutMs(3000) + .namespace("canal-adapter") + .build(); + curator.start(); + } + } + + public CuratorFramework getCurator() { + return curator; + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/SpringContext.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/SpringContext.java new file mode 100644 index 00000000..987371e2 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/config/SpringContext.java @@ -0,0 +1,34 @@ +package com.alibaba.otter.canal.adapter.launcher.config; + +import org.springframework.beans.BeansException; +import org.springframework.context.ApplicationContext; +import org.springframework.context.ApplicationContextAware; +import org.springframework.stereotype.Component; + +/** + * spring util配置类 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@Component +public class SpringContext implements ApplicationContextAware { + + private static ApplicationContext context; + + /* + * 注入ApplicationContext + */ + public void setApplicationContext(final ApplicationContext context) throws BeansException { + // 在加载Spring时自动获得context + SpringContext.context = context; + } + + public static Object getBean(final String beanName) { + return SpringContext.context.getBean(beanName); + } + + public static Object getBean(final Class clz) { + return context.getBean(clz); + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/AbstractCanalAdapterWorker.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/AbstractCanalAdapterWorker.java new file mode 100644 index 00000000..db87bf01 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/AbstractCanalAdapterWorker.java @@ -0,0 +1,243 @@ +package com.alibaba.otter.canal.adapter.launcher.loader; + +import java.util.ArrayList; +import java.util.List; +import java.util.concurrent.ExecutionException; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; +import java.util.concurrent.TimeUnit; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.adapter.launcher.common.SyncSwitch; +import com.alibaba.otter.canal.adapter.launcher.config.SpringContext; +import com.alibaba.otter.canal.client.CanalMQConnector; +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.support.CanalClientConfig; +import com.alibaba.otter.canal.client.adapter.support.Dml; +import com.alibaba.otter.canal.client.adapter.support.MessageUtil; +import com.alibaba.otter.canal.protocol.FlatMessage; +import com.alibaba.otter.canal.protocol.Message; + +/** + * 适配器工作线程抽象类 + * + * @author rewerma 2018-8-19 下午11:30:49 + * @version 1.0.0 + */ +public abstract class AbstractCanalAdapterWorker { + + protected final Logger logger = LoggerFactory.getLogger(this.getClass()); + + protected String canalDestination; // canal实例 + protected List> canalOuterAdapters; // 外部适配器 + protected CanalClientConfig canalClientConfig; // 配置 + protected ExecutorService groupInnerExecutorService; // 组内工作线程池 + protected volatile boolean running = false; // 是否运行中 + protected Thread thread = null; + protected Thread.UncaughtExceptionHandler handler = (t, e) -> logger.error("parse events has an error", e); + + protected SyncSwitch syncSwitch; + + public AbstractCanalAdapterWorker(List> canalOuterAdapters){ + this.canalOuterAdapters = canalOuterAdapters; + this.groupInnerExecutorService = Executors.newFixedThreadPool(canalOuterAdapters.size()); + syncSwitch = (SyncSwitch) SpringContext.getBean(SyncSwitch.class); + } + + protected void writeOut(final Message message) { + List> futures = new ArrayList<>(); + // 组间适配器并行运行 + canalOuterAdapters.forEach(outerAdapters -> { + final List adapters = outerAdapters; + futures.add(groupInnerExecutorService.submit(() -> { + try { + // 组内适配器穿行运行,尽量不要配置组内适配器 + adapters.forEach(adapter -> { + long begin = System.currentTimeMillis(); + List dmls = MessageUtil.parse4Dml(canalDestination, message); + if (dmls != null) { + batchSync(dmls, adapter); + + if (logger.isDebugEnabled()) { + logger.debug("{} elapsed time: {}", + adapter.getClass().getName(), + (System.currentTimeMillis() - begin)); + } + } + }); + return true; + } catch (Exception e) { + return false; + } + })); + + // 等待所有适配器写入完成 + // 由于是组间并发操作,所以将阻塞直到耗时最久的工作组操作完成 + futures.forEach(future -> { + try { + if (!future.get()) { + logger.error("Outer adapter write failed"); + } + } catch (InterruptedException | ExecutionException e) { + // ignore + } + }); + }); + } + + private void writeOut(final List flatMessages) { + List> futures = new ArrayList<>(); + // 组间适配器并行运行 + canalOuterAdapters.forEach(outerAdapters -> { + futures.add(groupInnerExecutorService.submit(() -> { + try { + // 组内适配器穿行运行,尽量不要配置组内适配器 + outerAdapters.forEach(adapter -> { + long begin = System.currentTimeMillis(); + List dmls = MessageUtil.flatMessage2Dml(canalDestination, flatMessages); + batchSync(dmls, adapter); + + if (logger.isDebugEnabled()) { + logger.debug("{} elapsed time: {}", + adapter.getClass().getName(), + (System.currentTimeMillis() - begin)); + } + }); + return true; + } catch (Exception e) { + return false; + } + })); + + // 等待所有适配器写入完成 + // 由于是组间并发操作,所以将阻塞直到耗时最久的工作组操作完成 + futures.forEach(future -> { + try { + if (!future.get()) { + logger.error("Outer adapter write failed"); + } + } catch (InterruptedException | ExecutionException e) { + // ignore + } + }); + }); + } + + @SuppressWarnings("unchecked") + protected void mqWriteOutData(int retry, long timeout, final boolean flatMessage, CanalMQConnector connector, + ExecutorService workerExecutor) { + for (int i = 0; i < retry; i++) { + try { + List messages; + if (!flatMessage) { + messages = connector.getListWithoutAck(100L, TimeUnit.MILLISECONDS); + } else { + messages = connector.getFlatListWithoutAck(100L, TimeUnit.MILLISECONDS); + } + if (messages != null) { + Future future = workerExecutor.submit(() -> { + if (flatMessage) { + // batch write + writeOut((List) messages); + } else { + for (final Object message : messages) { + writeOut((Message) message); + } + } + return true; + }); + + try { + future.get(timeout, TimeUnit.MILLISECONDS); + } catch (Exception e) { + future.cancel(true); + throw e; + } + } + connector.ack(); + break; + } catch (Throwable e) { + if (i == retry - 1) { + connector.ack(); + } else { + connector.rollback(); + } + + logger.error(e.getMessage(), e); + try { + TimeUnit.SECONDS.sleep(1L); + } catch (InterruptedException e1) { + // ignore + } + } + } + } + + /** + * 分批同步 + * + * @param dmls + * @param adapter + */ + private void batchSync(List dmls, OuterAdapter adapter) { + // 分批同步 + if (dmls.size() <= canalClientConfig.getSyncBatchSize()) { + adapter.sync(dmls); + } else { + int len = 0; + List dmlsBatch = new ArrayList<>(); + for (Dml dml : dmls) { + dmlsBatch.add(dml); + len += dml.getData().size(); + if (len >= canalClientConfig.getSyncBatchSize()) { + adapter.sync(dmlsBatch); + dmlsBatch.clear(); + len = 0; + } + } + adapter.sync(dmlsBatch); + } + } + + public void start() { + if (!running) { + thread = new Thread(this::process); + thread.setUncaughtExceptionHandler(handler); + thread.start(); + running = true; + } + } + + protected abstract void process(); + + public void stop() { + try { + if (!running) { + return; + } + + running = false; + + syncSwitch.release(canalDestination); + + logger.info("destination {} is waiting for adapters' worker thread die!", canalDestination); + if (thread != null) { + try { + thread.join(); + } catch (InterruptedException e) { + // ignore + } + } + groupInnerExecutorService.shutdown(); + logger.info("destination {} adapters worker thread dead!", canalDestination); + canalOuterAdapters.forEach(outerAdapters -> outerAdapters.forEach(OuterAdapter::destroy)); + logger.info("destination {} all adapters destroyed!", canalDestination); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterKafkaWorker.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterKafkaWorker.java new file mode 100644 index 00000000..050bbf65 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterKafkaWorker.java @@ -0,0 +1,79 @@ +package com.alibaba.otter.canal.adapter.launcher.loader; + +import java.util.List; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.TimeUnit; + +import org.apache.kafka.common.errors.WakeupException; + +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.support.CanalClientConfig; +import com.alibaba.otter.canal.client.kafka.KafkaCanalConnector; + +/** + * kafka对应的client适配器工作线程 + * + * @author rewerma 2018-8-19 下午11:30:49 + * @version 1.0.0 + */ +public class CanalAdapterKafkaWorker extends AbstractCanalAdapterWorker { + + private KafkaCanalConnector connector; + private String topic; + private boolean flatMessage; + + public CanalAdapterKafkaWorker(CanalClientConfig canalClientConfig, String bootstrapServers, String topic, + String groupId, List> canalOuterAdapters, boolean flatMessage){ + super(canalOuterAdapters); + this.canalClientConfig = canalClientConfig; + this.topic = topic; + this.canalDestination = topic; + this.flatMessage = flatMessage; + this.connector = new KafkaCanalConnector(bootstrapServers, + topic, + null, + groupId, + canalClientConfig.getBatchSize(), + flatMessage); + connector.setSessionTimeout(30L, TimeUnit.SECONDS); + } + + @Override + protected void process() { + while (!running) + ; + ExecutorService workerExecutor = Executors.newSingleThreadExecutor(); + int retry = canalClientConfig.getRetries() == null || canalClientConfig.getRetries() == 0 ? 1 : canalClientConfig.getRetries(); + long timeout = canalClientConfig.getTimeout() == null ? 30000 : canalClientConfig.getTimeout(); // 默认超时30秒 + + while (running) { + try { + syncSwitch.get(canalDestination); + logger.info("=============> Start to connect topic: {} <=============", this.topic); + connector.connect(); + logger.info("=============> Start to subscribe topic: {} <=============", this.topic); + connector.subscribe(); + logger.info("=============> Subscribe topic: {} succeed <=============", this.topic); + while (running) { + Boolean status = syncSwitch.status(canalDestination); + if (status != null && !status) { + connector.disconnect(); + break; + } + mqWriteOutData(retry, timeout, flatMessage, connector, workerExecutor); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + try { + connector.unsubscribe(); + } catch (WakeupException e) { + // No-op. Continue process + } + connector.disconnect(); + logger.info("=============> Disconnect topic: {} <=============", this.topic); + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterLoader.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterLoader.java new file mode 100644 index 00000000..80d5371a --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterLoader.java @@ -0,0 +1,198 @@ +package com.alibaba.otter.canal.adapter.launcher.loader; + +import java.net.InetSocketAddress; +import java.net.SocketAddress; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; + +import org.apache.commons.lang.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.support.CanalClientConfig; +import com.alibaba.otter.canal.client.adapter.support.ExtensionLoader; +import com.alibaba.otter.canal.client.adapter.support.OuterAdapterConfig; + +/** + * 外部适配器的加载器 + * + * @version 1.0.0 + */ +public class CanalAdapterLoader { + + private static final Logger logger = LoggerFactory.getLogger(CanalAdapterLoader.class); + + private CanalClientConfig canalClientConfig; + + private Map canalWorkers = new HashMap<>(); + + private Map canalMQWorker = new HashMap<>(); + + private ExtensionLoader loader; + + public CanalAdapterLoader(CanalClientConfig canalClientConfig){ + this.canalClientConfig = canalClientConfig; + } + + /** + * 初始化canal-client + */ + public void init() { + loader = ExtensionLoader.getExtensionLoader(OuterAdapter.class); + + String canalServerHost = this.canalClientConfig.getCanalServerHost(); + SocketAddress sa = null; + if (canalServerHost != null) { + String[] ipPort = canalServerHost.split(":"); + sa = new InetSocketAddress(ipPort[0], Integer.parseInt(ipPort[1])); + } + String zkHosts = this.canalClientConfig.getZookeeperHosts(); + + if ("tcp".equalsIgnoreCase(canalClientConfig.getMode())) { + // 初始化canal-client的适配器 + for (CanalClientConfig.CanalAdapter canalAdapter : canalClientConfig.getCanalAdapters()) { + List> canalOuterAdapterGroups = new ArrayList<>(); + + for (CanalClientConfig.Group connectorGroup : canalAdapter.getGroups()) { + List canalOutConnectors = new ArrayList<>(); + for (OuterAdapterConfig c : connectorGroup.getOuterAdapters()) { + loadConnector(c, canalOutConnectors); + } + canalOuterAdapterGroups.add(canalOutConnectors); + } + CanalAdapterWorker worker; + if (sa != null) { + worker = new CanalAdapterWorker(canalClientConfig, + canalAdapter.getInstance(), + sa, + canalOuterAdapterGroups); + } else if (zkHosts != null) { + worker = new CanalAdapterWorker(canalClientConfig, + canalAdapter.getInstance(), + zkHosts, + canalOuterAdapterGroups); + } else { + throw new RuntimeException("No canal server connector found"); + } + canalWorkers.put(canalAdapter.getInstance(), worker); + worker.start(); + logger.info("Start adapter for canal instance: {} succeed", canalAdapter.getInstance()); + } + } else if ("kafka".equalsIgnoreCase(canalClientConfig.getMode())) { + // 初始化canal-client-kafka的适配器 + for (CanalClientConfig.CanalAdapter canalAdapter : canalClientConfig.getCanalAdapters()) { + for (CanalClientConfig.Group group : canalAdapter.getGroups()) { + List> canalOuterAdapterGroups = new ArrayList<>(); + List canalOuterAdapters = new ArrayList<>(); + for (OuterAdapterConfig config : group.getOuterAdapters()) { + loadConnector(config, canalOuterAdapters); + } + canalOuterAdapterGroups.add(canalOuterAdapters); + + CanalAdapterKafkaWorker canalKafkaWorker = new CanalAdapterKafkaWorker(canalClientConfig, + canalClientConfig.getMqServers(), + canalAdapter.getInstance(), + group.getGroupId(), + canalOuterAdapterGroups, + canalClientConfig.getFlatMessage()); + canalMQWorker.put(canalAdapter.getInstance() + "-kafka-" + group.getGroupId(), canalKafkaWorker); + canalKafkaWorker.start(); + logger.info("Start adapter for canal-client mq topic: {} succeed", canalAdapter.getInstance() + "-" + + group.getGroupId()); + } + } + } else if ("rocketMQ".equalsIgnoreCase(canalClientConfig.getMode())) { + // 初始化canal-client-rocketMQ的适配器 + for (CanalClientConfig.CanalAdapter canalAdapter : canalClientConfig.getCanalAdapters()) { + for (CanalClientConfig.Group group : canalAdapter.getGroups()) { + List> canalOuterAdapterGroups = new ArrayList<>(); + List canalOuterAdapters = new ArrayList<>(); + for (OuterAdapterConfig config : group.getOuterAdapters()) { + loadConnector(config, canalOuterAdapters); + } + canalOuterAdapterGroups.add(canalOuterAdapters); + CanalAdapterRocketMQWorker rocketMQWorker = new CanalAdapterRocketMQWorker(canalClientConfig, + canalClientConfig.getMqServers(), + canalAdapter.getInstance(), + group.getGroupId(), + canalOuterAdapterGroups, + canalClientConfig.getAccessKey(), + canalClientConfig.getSecretKey(), + canalClientConfig.getFlatMessage()); + canalMQWorker.put(canalAdapter.getInstance() + "-rocketmq-" + group.getGroupId(), rocketMQWorker); + rocketMQWorker.start(); + + logger.info("Start adapter for canal-client mq topic: {} succeed", canalAdapter.getInstance() + "-" + + group.getGroupId()); + } + } + } + } + + private void loadConnector(OuterAdapterConfig config, List canalOutConnectors) { + try { + OuterAdapter adapter; + adapter = loader.getExtension(config.getName(), StringUtils.trimToEmpty(config.getKey())); + + ClassLoader cl = Thread.currentThread().getContextClassLoader(); + // 替换ClassLoader + Thread.currentThread().setContextClassLoader(adapter.getClass().getClassLoader()); + adapter.init(config); + Thread.currentThread().setContextClassLoader(cl); + canalOutConnectors.add(adapter); + logger.info("Load canal adapter: {} succeed", config.getName()); + } catch (Exception e) { + logger.error("Load canal adapter: {} failed", config.getName(), e); + } + } + + /** + * 销毁所有适配器 为防止canal实例太多造成销毁阻塞, 并行销毁 + */ + public void destroy() { + if (!canalWorkers.isEmpty()) { + ExecutorService stopExecutorService = Executors.newFixedThreadPool(canalWorkers.size()); + List> futures = new ArrayList<>(); + for (CanalAdapterWorker canalAdapterWorker : canalWorkers.values()) { + futures.add(stopExecutorService.submit(() -> { + canalAdapterWorker.stop(); + return true; + })); + } + futures.forEach(future -> { + try { + future.get(); + } catch (Exception e) { + // ignore + } + }); + stopExecutorService.shutdown(); + } + + if (!canalMQWorker.isEmpty()) { + ExecutorService stopMQWorkerService = Executors.newFixedThreadPool(canalMQWorker.size()); + List> futures = new ArrayList<>(); + for (AbstractCanalAdapterWorker canalAdapterMQWorker : canalMQWorker.values()) { + futures.add(stopMQWorkerService.submit(() -> { + canalAdapterMQWorker.stop(); + return true; + })); + } + futures.forEach(future -> { + try { + future.get(); + } catch (Exception e) { + // ignore + } + }); + stopMQWorkerService.shutdown(); + } + logger.info("All canal adapters destroyed"); + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterRocketMQWorker.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterRocketMQWorker.java new file mode 100644 index 00000000..2e737353 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterRocketMQWorker.java @@ -0,0 +1,74 @@ +package com.alibaba.otter.canal.adapter.launcher.loader; + +import java.util.List; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; + +import org.apache.kafka.common.errors.WakeupException; + +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.support.CanalClientConfig; +import com.alibaba.otter.canal.client.rocketmq.RocketMQCanalConnector; + +/** + * rocketmq对应的client适配器工作线程 + * + * @version 1.0.0 + */ +public class CanalAdapterRocketMQWorker extends AbstractCanalAdapterWorker { + + private RocketMQCanalConnector connector; + private String topic; + private boolean flatMessage; + + public CanalAdapterRocketMQWorker(CanalClientConfig canalClientConfig, String nameServers, String topic, + String groupId, List> canalOuterAdapters, String accessKey, + String secretKey, boolean flatMessage){ + super(canalOuterAdapters); + this.canalClientConfig = canalClientConfig; + this.topic = topic; + this.flatMessage = flatMessage; + this.canalDestination = topic; + this.connector = new RocketMQCanalConnector(nameServers, topic, groupId, accessKey, secretKey, flatMessage); + logger.info("RocketMQ consumer config topic:{}, nameServer:{}, groupId:{}", topic, nameServers, groupId); + } + + @Override + protected void process() { + while (!running) + ; + + ExecutorService workerExecutor = Executors.newSingleThreadExecutor(); + int retry = canalClientConfig.getRetries() == null || canalClientConfig.getRetries() == 0 ? 1 : canalClientConfig.getRetries(); + long timeout = canalClientConfig.getTimeout() == null ? 30000 : canalClientConfig.getTimeout(); // 默认超时30秒 + + while (running) { + try { + syncSwitch.get(canalDestination); + logger.info("=============> Start to connect topic: {} <=============", this.topic); + connector.connect(); + logger.info("=============> Start to subscribe topic: {}<=============", this.topic); + connector.subscribe(); + logger.info("=============> Subscribe topic: {} succeed<=============", this.topic); + while (running) { + Boolean status = syncSwitch.status(canalDestination); + if (status != null && !status) { + connector.disconnect(); + break; + } + mqWriteOutData(retry, timeout, flatMessage, connector, workerExecutor); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + try { + connector.unsubscribe(); + } catch (WakeupException e) { + // No-op. Continue process + } + connector.disconnect(); + logger.info("=============> Disconnect topic: {} <=============", this.topic); + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterService.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterService.java new file mode 100644 index 00000000..79eb0be1 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterService.java @@ -0,0 +1,85 @@ +package com.alibaba.otter.canal.adapter.launcher.loader; + +import javax.annotation.PostConstruct; +import javax.annotation.PreDestroy; +import javax.annotation.Resource; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.cloud.context.config.annotation.RefreshScope; +import org.springframework.stereotype.Component; + +import com.alibaba.druid.pool.DruidDataSource; +import com.alibaba.otter.canal.adapter.launcher.common.SyncSwitch; +import com.alibaba.otter.canal.adapter.launcher.config.AdapterCanalConfig; +import com.alibaba.otter.canal.adapter.launcher.config.SpringContext; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; + +/** + * 适配器启动业务类 + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@Component +@RefreshScope +public class CanalAdapterService { + + private static final Logger logger = LoggerFactory.getLogger(CanalAdapterService.class); + + private CanalAdapterLoader adapterLoader; + + @Resource + private AdapterCanalConfig adapterCanalConfig; + + // 注入bean保证优先注册 + @Resource + private SpringContext springContext; + @Resource + private SyncSwitch syncSwitch; + + private volatile boolean running = false; + + @PostConstruct + public synchronized void init() { + if (running) { + return; + } + try { + logger.info("## start the canal client adapters."); + adapterLoader = new CanalAdapterLoader(adapterCanalConfig); + adapterLoader.init(); + running = true; + logger.info("## the canal client adapters are running now ......"); + } catch (Exception e) { + logger.error("## something goes wrong when starting up the canal client adapters:", e); + } + } + + @PreDestroy + public synchronized void destroy() { + if (!running) { + return; + } + try { + running = false; + logger.info("## stop the canal client adapters"); + if (adapterLoader != null) { + adapterLoader.destroy(); + adapterLoader = null; + } + for (DruidDataSource druidDataSource : DatasourceConfig.DATA_SOURCES.values()) { + try { + druidDataSource.close(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + DatasourceConfig.DATA_SOURCES.clear(); + } catch (Throwable e) { + logger.warn("## something goes wrong when stopping canal client adapters:", e); + } finally { + logger.info("## canal client adapters are down."); + } + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterWorker.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterWorker.java new file mode 100644 index 00000000..15207d84 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/loader/CanalAdapterWorker.java @@ -0,0 +1,191 @@ +package com.alibaba.otter.canal.adapter.launcher.loader; + +import java.net.SocketAddress; +import java.util.List; +import java.util.concurrent.*; + +import com.alibaba.otter.canal.client.CanalConnector; +import com.alibaba.otter.canal.client.CanalConnectors; +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.support.CanalClientConfig; +import com.alibaba.otter.canal.client.impl.ClusterCanalConnector; +import com.alibaba.otter.canal.client.impl.SimpleCanalConnector; +import com.alibaba.otter.canal.protocol.Message; + +/** + * 原生canal-server对应的client适配器工作线程 + * + * @author rewrema 2018-8-19 下午11:30:49 + * @version 1.0.0 + */ +public class CanalAdapterWorker extends AbstractCanalAdapterWorker { + + private static final int BATCH_SIZE = 50; + private static final int SO_TIMEOUT = 0; + + private CanalConnector connector; + + /** + * 单台client适配器worker的构造方法 + * + * @param canalDestination canal实例名 + * @param address canal-server地址 + * @param canalOuterAdapters 外部适配器组 + */ + public CanalAdapterWorker(CanalClientConfig canalClientConfig, String canalDestination, SocketAddress address, + List> canalOuterAdapters){ + super(canalOuterAdapters); + this.canalClientConfig = canalClientConfig; + this.canalDestination = canalDestination; + connector = CanalConnectors.newSingleConnector(address, canalDestination, "", ""); + } + + /** + * HA模式下client适配器worker的构造方法 + * + * @param canalDestination canal实例名 + * @param zookeeperHosts zookeeper地址 + * @param canalOuterAdapters 外部适配器组 + */ + public CanalAdapterWorker(CanalClientConfig canalClientConfig, String canalDestination, String zookeeperHosts, + List> canalOuterAdapters){ + super(canalOuterAdapters); + this.canalDestination = canalDestination; + this.canalClientConfig = canalClientConfig; + connector = CanalConnectors.newClusterConnector(zookeeperHosts, canalDestination, "", ""); + ((ClusterCanalConnector) connector).setSoTimeout(SO_TIMEOUT); + } + + @Override + protected void process() { + while (!running) + ; // waiting until running == true + + ExecutorService workerExecutor = Executors.newSingleThreadExecutor(); + int retry = canalClientConfig.getRetries() == null + || canalClientConfig.getRetries() == 0 ? 1 : canalClientConfig.getRetries(); + long timeout = canalClientConfig.getTimeout() == null ? 300000 : canalClientConfig.getTimeout(); // 默认超时5分钟 + Integer batchSize = canalClientConfig.getBatchSize(); + if (batchSize == null) { + batchSize = BATCH_SIZE; + } + + while (running) { + try { + syncSwitch.get(canalDestination); + + logger.info("=============> Start to connect destination: {} <=============", this.canalDestination); + connector.connect(); + logger.info("=============> Start to subscribe destination: {} <=============", this.canalDestination); + connector.subscribe(); + logger.info("=============> Subscribe destination: {} succeed <=============", this.canalDestination); + while (running) { + try { + syncSwitch.get(canalDestination, 1L, TimeUnit.MINUTES); + } catch (TimeoutException e) { + break; + } + if (!running) { + break; + } + + for (int i = 0; i < retry; i++) { + Message message = connector.getWithoutAck(batchSize); // 获取指定数量的数据 + long batchId = message.getId(); + try { + int size = message.getEntries().size(); + if (batchId == -1 || size == 0) { + Thread.sleep(500); + } else { + Future future = workerExecutor.submit(() -> { + if (logger.isDebugEnabled()) { + logger.debug("destination: {} batchId: {} batchSize: {} ", + canalDestination, + batchId, + size); + } + long begin = System.currentTimeMillis(); + writeOut(message); + if (logger.isDebugEnabled()) { + logger.debug("destination: {} batchId: {} elapsed time: {} ms", + canalDestination, + batchId, + System.currentTimeMillis() - begin); + } + return true; + }); + + try { + future.get(timeout, TimeUnit.MILLISECONDS); + } catch (Exception e) { + future.cancel(true); + throw e; + } + } + connector.ack(batchId); // 提交确认 + break; + } catch (Exception e) { + if (i != retry - 1) { + connector.rollback(batchId); // 处理失败, 回滚数据 + } else { + connector.ack(batchId); + } + logger.error("sync error!", e); + Thread.sleep(500); + } + } + } + + } catch (Exception e) { + logger.error("process error!", e); + } finally { + connector.disconnect(); + logger.info("=============> Disconnect destination: {} <=============", this.canalDestination); + } + + if (running) { // is reconnect + try { + Thread.sleep(1000); + } catch (InterruptedException e) { + // ignore + } + } + } + + workerExecutor.shutdown(); + } + + @Override + public void stop() { + try { + if (!running) { + return; + } + + if (connector instanceof ClusterCanalConnector) { + ((ClusterCanalConnector) connector).stopRunning(); + } else if (connector instanceof SimpleCanalConnector) { + ((SimpleCanalConnector) connector).stopRunning(); + } + + running = false; + + syncSwitch.release(canalDestination); + + logger.info("destination {} is waiting for adapters' worker thread die!", canalDestination); + if (thread != null) { + try { + thread.join(); + } catch (InterruptedException e) { + // ignore + } + } + groupInnerExecutorService.shutdown(); + logger.info("destination {} adapters worker thread dead!", canalDestination); + canalOuterAdapters.forEach(outerAdapters -> outerAdapters.forEach(OuterAdapter::destroy)); + logger.info("destination {} all adapters destroyed!", canalDestination); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/monitor/ApplicationConfigMonitor.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/monitor/ApplicationConfigMonitor.java new file mode 100644 index 00000000..8d519184 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/monitor/ApplicationConfigMonitor.java @@ -0,0 +1,90 @@ +package com.alibaba.otter.canal.adapter.launcher.monitor; + +import java.io.File; +import java.io.FileReader; +import java.util.Map; + +import javax.annotation.PostConstruct; +import javax.annotation.PreDestroy; +import javax.annotation.Resource; + +import org.apache.commons.io.filefilter.FileFilterUtils; +import org.apache.commons.io.monitor.FileAlterationListenerAdaptor; +import org.apache.commons.io.monitor.FileAlterationMonitor; +import org.apache.commons.io.monitor.FileAlterationObserver; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.cloud.context.refresh.ContextRefresher; +import org.springframework.stereotype.Component; +import org.yaml.snakeyaml.Yaml; + +import com.alibaba.otter.canal.adapter.launcher.loader.CanalAdapterService; +import com.alibaba.otter.canal.client.adapter.support.Util; + +@Component +public class ApplicationConfigMonitor { + + private static final Logger logger = LoggerFactory.getLogger(ApplicationConfigMonitor.class); + + @Resource + private ContextRefresher contextRefresher; + + @Resource + private CanalAdapterService canalAdapterService; + + private FileAlterationMonitor fileMonitor; + + @PostConstruct + public void init() { + File confDir = Util.getConfDirPath(); + try { + FileAlterationObserver observer = new FileAlterationObserver(confDir, + FileFilterUtils.and(FileFilterUtils.fileFileFilter(), + FileFilterUtils.prefixFileFilter("application"), + FileFilterUtils.suffixFileFilter("yml"))); + FileListener listener = new FileListener(); + observer.addListener(listener); + fileMonitor = new FileAlterationMonitor(3000, observer); + fileMonitor.start(); + + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + @PreDestroy + public void destroy() { + try { + fileMonitor.stop(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private class FileListener extends FileAlterationListenerAdaptor { + + @Override + public void onFileChange(File file) { + super.onFileChange(file); + try { + // 检查yml格式 + new Yaml().loadAs(new FileReader(file), Map.class); + + canalAdapterService.destroy(); + + // refresh context + contextRefresher.refresh(); + + try { + Thread.sleep(2000); + } catch (InterruptedException e) { + // ignore + } + canalAdapterService.init(); + logger.info("## adapter application config reloaded."); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/rest/CommonRest.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/rest/CommonRest.java new file mode 100644 index 00000000..302206be --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/rest/CommonRest.java @@ -0,0 +1,209 @@ +package com.alibaba.otter.canal.adapter.launcher.rest; + +import java.util.*; + +import javax.annotation.PostConstruct; +import javax.annotation.Resource; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.web.bind.annotation.*; + +import com.alibaba.otter.canal.adapter.launcher.common.EtlLock; +import com.alibaba.otter.canal.adapter.launcher.common.SyncSwitch; +import com.alibaba.otter.canal.adapter.launcher.config.AdapterCanalConfig; +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.support.EtlResult; +import com.alibaba.otter.canal.client.adapter.support.ExtensionLoader; +import com.alibaba.otter.canal.client.adapter.support.Result; + +/** + * 适配器操作Rest + * + * @author rewerma @ 2018-10-20 + * @version 1.0.0 + */ +@RestController +public class CommonRest { + + private static Logger logger = LoggerFactory.getLogger(CommonRest.class); + + private static final String ETL_LOCK_ZK_NODE = "/sync-etl/"; + + private ExtensionLoader loader; + + @Resource + private SyncSwitch syncSwitch; + @Resource + private EtlLock etlLock; + + @Resource + private AdapterCanalConfig adapterCanalConfig; + + @PostConstruct + public void init() { + loader = ExtensionLoader.getExtensionLoader(OuterAdapter.class); + } + + /** + * ETL curl http://127.0.0.1:8081/etl/rdb/oracle1/mytest_user.yml -X POST + * + * @param type 类型 hbase, es + * @param key adapter key + * @param task 任务名对应配置文件名 mytest_user.yml + * @param params etl where条件参数, 为空全部导入 + */ + @PostMapping("/etl/{type}/{key}/{task}") + public EtlResult etl(@PathVariable String type, @PathVariable String key, @PathVariable String task, + @RequestParam(name = "params", required = false) String params) { + OuterAdapter adapter = loader.getExtension(type, key); + String destination = adapter.getDestination(task); + String lockKey = destination == null ? task : destination; + + boolean locked = etlLock.tryLock(ETL_LOCK_ZK_NODE + type + "-" + lockKey); + if (!locked) { + EtlResult result = new EtlResult(); + result.setSucceeded(false); + result.setErrorMessage(task + " 有其他进程正在导入中, 请稍后再试"); + return result; + } + try { + + Boolean oriSwitchStatus; + if (destination != null) { + oriSwitchStatus = syncSwitch.status(destination); + if (oriSwitchStatus != null && oriSwitchStatus) { + syncSwitch.off(destination); + } + } else { + // task可能为destination,直接锁task + oriSwitchStatus = syncSwitch.status(task); + if (oriSwitchStatus != null && oriSwitchStatus) { + syncSwitch.off(task); + } + } + try { + List paramArray = null; + if (params != null) { + paramArray = Arrays.asList(params.trim().split(";")); + } + return adapter.etl(task, paramArray); + } finally { + if (destination != null && oriSwitchStatus != null && oriSwitchStatus) { + syncSwitch.on(destination); + } else if (destination == null && oriSwitchStatus != null && oriSwitchStatus) { + syncSwitch.on(task); + } + } + } finally { + etlLock.unlock(ETL_LOCK_ZK_NODE + type + "-" + lockKey); + } + } + + /** + * ETL curl http://127.0.0.1:8081/etl/hbase/mytest_person2.yml -X POST + * + * @param type 类型 hbase, es + * @param task 任务名对应配置文件名 mytest_person2.yml + * @param params etl where条件参数, 为空全部导入 + */ + @PostMapping("/etl/{type}/{task}") + public EtlResult etl(@PathVariable String type, @PathVariable String task, + @RequestParam(name = "params", required = false) String params) { + return etl(type, null, task, params); + } + + /** + * 统计总数 curl http://127.0.0.1:8081/count/rdb/oracle1/mytest_user.yml + * + * @param type 类型 hbase, es + * @param key adapter key + * @param task 任务名对应配置文件名 mytest_person2.yml + * @return + */ + @GetMapping("/count/{type}/{key}/{task}") + public Map count(@PathVariable String type, @PathVariable String key, @PathVariable String task) { + OuterAdapter adapter = loader.getExtension(type, key); + return adapter.count(task); + } + + /** + * 统计总数 curl http://127.0.0.1:8081/count/hbase/mytest_person2.yml + * + * @param type 类型 hbase, es + * @param task 任务名对应配置文件名 mytest_person2.yml + * @return + */ + @GetMapping("/count/{type}/{task}") + public Map count(@PathVariable String type, @PathVariable String task) { + return count(type, null, task); + } + + /** + * 返回所有实例 curl http://127.0.0.1:8081/destinations + */ + @GetMapping("/destinations") + public List> destinations() { + List> result = new ArrayList<>(); + Set destinations = adapterCanalConfig.DESTINATIONS; + for (String destination : destinations) { + Map resMap = new LinkedHashMap<>(); + Boolean status = syncSwitch.status(destination); + String resStatus = "none"; + if (status != null && status) { + resStatus = "on"; + } else if (status != null && !status) { + resStatus = "off"; + } + resMap.put("destination", destination); + resMap.put("status", resStatus); + result.add(resMap); + } + return result; + } + + /** + * 实例同步开关 curl http://127.0.0.1:8081/syncSwitch/example/off -X PUT + * + * @param destination 实例名称 + * @param status 开关状态: off on + * @return + */ + @PutMapping("/syncSwitch/{destination}/{status}") + public Result etl(@PathVariable String destination, @PathVariable String status) { + if (status.equals("on")) { + syncSwitch.on(destination); + logger.info("#Destination: {} sync on", destination); + return Result.createSuccess("实例: " + destination + " 开启同步成功"); + } else if (status.equals("off")) { + syncSwitch.off(destination); + logger.info("#Destination: {} sync off", destination); + return Result.createSuccess("实例: " + destination + " 关闭同步成功"); + } else { + Result result = new Result(); + result.setCode(50000); + result.setMessage("实例: " + destination + " 操作失败"); + return result; + } + } + + /** + * 获取实例开关状态 curl http://127.0.0.1:8081/syncSwitch/example + * + * @param destination 实例名称 + * @return + */ + @GetMapping("/syncSwitch/{destination}") + public Map etl(@PathVariable String destination) { + Boolean status = syncSwitch.status(destination); + String resStatus = "none"; + if (status != null && status) { + resStatus = "on"; + } else if (status != null && !status) { + resStatus = "off"; + } + Map res = new LinkedHashMap<>(); + res.put("stauts", resStatus); + return res; + } +} diff --git a/client-adapter/launcher/src/main/resources/application.yml b/client-adapter/launcher/src/main/resources/application.yml new file mode 100644 index 00000000..098bc1f3 --- /dev/null +++ b/client-adapter/launcher/src/main/resources/application.yml @@ -0,0 +1,62 @@ +server: + port: 8081 +logging: + level: + org.springframework: WARN + com.alibaba.otter.canal.client.adapter.hbase: DEBUG + com.alibaba.otter.canal.client.adapter.es: DEBUG + com.alibaba.otter.canal.client.adapter.rdb: DEBUG +spring: + jackson: + date-format: yyyy-MM-dd HH:mm:ss + time-zone: GMT+8 + default-property-inclusion: non_null + +canal.conf: + canalServerHost: 127.0.0.1:11111 +# zookeeperHosts: slave1:2181 +# mqServers: slave1:6667 #or rocketmq +# flatMessage: true + batchSize: 500 + syncBatchSize: 1000 + retries: 0 + timeout: + accessKey: + secretKey: + mode: tcp # kafka rocketMQ +# srcDataSources: +# defaultDS: +# url: jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true +# username: root +# password: 121212 + canalAdapters: + - instance: example # canal instance Name or mq topic name + groups: + - groupId: g1 + outerAdapters: + - name: logger +# - name: rdb +# key: oracle1 +# properties: +# jdbc.driverClassName: oracle.jdbc.OracleDriver +# jdbc.url: jdbc:oracle:thin:@localhost:49161:XE +# jdbc.username: mytest +# jdbc.password: m121212 +# - name: rdb +# key: postgres1 +# properties: +# jdbc.driverClassName: org.postgresql.Driver +# jdbc.url: jdbc:postgresql://localhost:5432/postgres +# jdbc.username: postgres +# jdbc.password: 121212 +# threads: 1 +# commitSize: 3000 +# - name: hbase +# properties: +# hbase.zookeeper.quorum: 127.0.0.1 +# hbase.zookeeper.property.clientPort: 2181 +# zookeeper.znode.parent: /hbase +# - name: es +# hosts: 127.0.0.1:9300 +# properties: +# cluster.name: elasticsearch \ No newline at end of file diff --git a/client-adapter/logger/pom.xml b/client-adapter/logger/pom.xml new file mode 100644 index 00000000..11c8d53e --- /dev/null +++ b/client-adapter/logger/pom.xml @@ -0,0 +1,46 @@ + + + + canal.client-adapter + com.alibaba.otter + 1.1.3-SNAPSHOT + + 4.0.0 + com.alibaba.otter + client-adapter.logger + jar + canal client adapter logger example module for otter ${project.version} + + + com.alibaba.otter + client-adapter.common + ${project.version} + provided + + + + + + + + org.apache.maven.plugins + maven-assembly-plugin + 2.4 + + + jar-with-dependencies + + + + + make-assembly + package + + single + + + + + + + diff --git a/client-adapter/logger/src/main/java/com/alibaba/otter/canal/client/adapter/logger/LoggerAdapterExample.java b/client-adapter/logger/src/main/java/com/alibaba/otter/canal/client/adapter/logger/LoggerAdapterExample.java new file mode 100644 index 00000000..bd7c87ab --- /dev/null +++ b/client-adapter/logger/src/main/java/com/alibaba/otter/canal/client/adapter/logger/LoggerAdapterExample.java @@ -0,0 +1,46 @@ +package com.alibaba.otter.canal.client.adapter.logger; + +import java.util.List; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.serializer.SerializerFeature; +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.support.Dml; +import com.alibaba.otter.canal.client.adapter.support.OuterAdapterConfig; +import com.alibaba.otter.canal.client.adapter.support.SPI; + +/** + * 外部适配器示例 + * + * @author machengyuan 2018-8-19 下午11:45:38 + * @version 1.0.0 + */ +@SPI("logger") +// logger参数对应CanalOuterAdapterConfiguration配置中的name +public class LoggerAdapterExample implements OuterAdapter { + + private Logger logger = LoggerFactory.getLogger(this.getClass()); + + @Override + public void init(OuterAdapterConfig configuration) { + + } + + public void sync(List dmls) { + for (Dml dml : dmls) { + sync(dml); + } + } + + public void sync(Dml dml) { + logger.info("DML: {}", JSON.toJSONString(dml, SerializerFeature.WriteMapNullValue)); + } + + @Override + public void destroy() { + + } +} diff --git a/client-adapter/logger/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter b/client-adapter/logger/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter new file mode 100644 index 00000000..bfeae48e --- /dev/null +++ b/client-adapter/logger/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter @@ -0,0 +1 @@ +logger=com.alibaba.otter.canal.client.adapter.logger.LoggerAdapterExample \ No newline at end of file diff --git a/client-adapter/pom.xml b/client-adapter/pom.xml new file mode 100644 index 00000000..dd216b25 --- /dev/null +++ b/client-adapter/pom.xml @@ -0,0 +1,128 @@ + + + 4.0.0 + com.alibaba.otter + canal.client-adapter + 1.1.3-SNAPSHOT + pom + canal client adapter module for otter ${project.version} + + com.alibaba.otter + canal + 1.1.3-SNAPSHOT + + + + UTF-8 + true + true + 1.8 + 1.8 + UTF-8 + + + + common + logger + hbase + elasticsearch + launcher + rdb + + + + + Apache License, Version 2.0 + http://www.apache.org/licenses/LICENSE-2.0 + + + + + git@github.com:alibaba/canal.git + scm:git:git@github.com:alibaba/canal.git + scm:git:git@github.com:alibaba/canal.git + + + + + central + http://repo1.maven.org/maven2 + + true + + + false + + + + java.net + http://download.java.net/maven/2/ + + true + + + false + + + + aliyun + http://maven.aliyun.com/nexus/content/groups/public/ + + true + + + false + + + + sonatype + sonatype + https://oss.sonatype.org/content/repositories/snapshots + + false + + + true + + + + sonatype-release + sonatype-release + https://oss.sonatype.org/service/local/repositories/releases/content + + false + + + true + + + + + + + + org.apache.maven.plugins + maven-compiler-plugin + 3.7.0 + + ${java_source_version} + ${java_target_version} + ${file_encoding} + + + + + + + + sonatype-nexus-snapshots + Sonatype Nexus Snapshots + https://oss.sonatype.org/content/repositories/snapshots/ + + + sonatype-nexus-staging + Nexus Release Repository + https://oss.sonatype.org/service/local/staging/deploy/maven2/ + + + \ No newline at end of file diff --git a/client-adapter/rdb/pom.xml b/client-adapter/rdb/pom.xml new file mode 100644 index 00000000..458e8ab2 --- /dev/null +++ b/client-adapter/rdb/pom.xml @@ -0,0 +1,97 @@ + + + + canal.client-adapter + com.alibaba.otter + 1.1.3-SNAPSHOT + + 4.0.0 + com.alibaba.otter + client-adapter.rdb + jar + canal client adapter rdb module for otter ${project.version} + + + + com.alibaba.otter + client-adapter.common + ${project.version} + provided + + + org.yaml + snakeyaml + 1.19 + provided + + + + org.postgresql + postgresql + 42.1.4 + test + + + com.oracle + ojdbc6 + 11.2.0.3 + test + + + com.microsoft.sqlserver + mssql-jdbc + 7.0.0.jre8 + test + + + junit + junit + 4.12 + test + + + + + + + org.apache.maven.plugins + maven-assembly-plugin + 2.4 + + + jar-with-dependencies + + + + + make-assembly + package + + single + + + + + + maven-antrun-plugin + + + package + + run + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/RdbAdapter.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/RdbAdapter.java new file mode 100644 index 00000000..ae38b124 --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/RdbAdapter.java @@ -0,0 +1,216 @@ +package com.alibaba.otter.canal.client.adapter.rdb; + +import java.sql.Connection; +import java.sql.SQLException; +import java.util.HashMap; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; + +import javax.sql.DataSource; + +import org.apache.commons.lang.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.druid.pool.DruidDataSource; +import com.alibaba.otter.canal.client.adapter.OuterAdapter; +import com.alibaba.otter.canal.client.adapter.rdb.config.ConfigLoader; +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.rdb.monitor.RdbConfigMonitor; +import com.alibaba.otter.canal.client.adapter.rdb.service.RdbEtlService; +import com.alibaba.otter.canal.client.adapter.rdb.service.RdbSyncService; +import com.alibaba.otter.canal.client.adapter.support.*; + +@SPI("rdb") +public class RdbAdapter implements OuterAdapter { + + private static Logger logger = LoggerFactory.getLogger(RdbAdapter.class); + + private Map rdbMapping = new HashMap<>(); // 文件名对应配置 + private Map> mappingConfigCache = new HashMap<>(); // 库名-表名对应配置 + + private DruidDataSource dataSource; + + private RdbSyncService rdbSyncService; + + private ExecutorService executor = Executors.newFixedThreadPool(1); + + private RdbConfigMonitor rdbConfigMonitor; + + public Map getRdbMapping() { + return rdbMapping; + } + + public Map> getMappingConfigCache() { + return mappingConfigCache; + } + + @Override + public void init(OuterAdapterConfig configuration) { + Map rdbMappingTmp = ConfigLoader.load(); + // 过滤不匹配的key的配置 + rdbMappingTmp.forEach((key, mappingConfig) -> { + if ((mappingConfig.getOuterAdapterKey() == null && configuration.getKey() == null) + || (mappingConfig.getOuterAdapterKey() != null + && mappingConfig.getOuterAdapterKey().equalsIgnoreCase(configuration.getKey()))) { + rdbMapping.put(key, mappingConfig); + } + }); + for (Map.Entry entry : rdbMapping.entrySet()) { + String configName = entry.getKey(); + MappingConfig mappingConfig = entry.getValue(); + Map configMap = mappingConfigCache + .computeIfAbsent(StringUtils.trimToEmpty(mappingConfig.getDestination()) + "." + + mappingConfig.getDbMapping().getDatabase() + "." + + mappingConfig.getDbMapping().getTable(), + k1 -> new HashMap<>()); + configMap.put(configName, mappingConfig); + } + + Map properties = configuration.getProperties(); + dataSource = new DruidDataSource(); + dataSource.setDriverClassName(properties.get("jdbc.driverClassName")); + dataSource.setUrl(properties.get("jdbc.url")); + dataSource.setUsername(properties.get("jdbc.username")); + dataSource.setPassword(properties.get("jdbc.password")); + dataSource.setInitialSize(1); + dataSource.setMinIdle(1); + dataSource.setMaxActive(20); + dataSource.setMaxWait(60000); + dataSource.setTimeBetweenEvictionRunsMillis(60000); + dataSource.setMinEvictableIdleTimeMillis(300000); + + try { + dataSource.init(); + } catch (SQLException e) { + logger.error("ERROR ## failed to initial datasource: " + properties.get("jdbc.url"), e); + } + + String threads = properties.get("threads"); + // String commitSize = properties.get("commitSize"); + + rdbSyncService = new RdbSyncService(mappingConfigCache, + dataSource, + threads != null ? Integer.valueOf(threads) : null); + + rdbConfigMonitor = new RdbConfigMonitor(); + rdbConfigMonitor.init(configuration.getKey(), this); + } + + @Override + public void sync(List dmls) { + rdbSyncService.sync(dmls); + } + + @Override + public EtlResult etl(String task, List params) { + EtlResult etlResult = new EtlResult(); + MappingConfig config = rdbMapping.get(task); + if (config != null) { + DataSource srcDataSource = DatasourceConfig.DATA_SOURCES.get(config.getDataSourceKey()); + if (srcDataSource != null) { + return RdbEtlService.importData(srcDataSource, dataSource, config, params); + } else { + etlResult.setSucceeded(false); + etlResult.setErrorMessage("DataSource not found"); + return etlResult; + } + } else { + StringBuilder resultMsg = new StringBuilder(); + boolean resSucc = true; + // ds不为空说明传入的是destination + for (MappingConfig configTmp : rdbMapping.values()) { + // 取所有的destination为task的配置 + if (configTmp.getDestination().equals(task)) { + DataSource srcDataSource = DatasourceConfig.DATA_SOURCES.get(configTmp.getDataSourceKey()); + if (srcDataSource == null) { + continue; + } + EtlResult etlRes = RdbEtlService.importData(srcDataSource, dataSource, configTmp, params); + if (!etlRes.getSucceeded()) { + resSucc = false; + resultMsg.append(etlRes.getErrorMessage()).append("\n"); + } else { + resultMsg.append(etlRes.getResultMessage()).append("\n"); + } + } + } + if (resultMsg.length() > 0) { + etlResult.setSucceeded(resSucc); + if (resSucc) { + etlResult.setResultMessage(resultMsg.toString()); + } else { + etlResult.setErrorMessage(resultMsg.toString()); + } + return etlResult; + } + } + etlResult.setSucceeded(false); + etlResult.setErrorMessage("Task not found"); + return etlResult; + } + + @Override + public Map count(String task) { + MappingConfig config = rdbMapping.get(task); + MappingConfig.DbMapping dbMapping = config.getDbMapping(); + String sql = "SELECT COUNT(1) AS cnt FROM " + dbMapping.getTargetTable(); + Connection conn = null; + Map res = new LinkedHashMap<>(); + try { + conn = dataSource.getConnection(); + Util.sqlRS(conn, sql, rs -> { + try { + if (rs.next()) { + Long rowCount = rs.getLong("cnt"); + res.put("count", rowCount); + } + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + }); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } finally { + if (conn != null) { + try { + conn.close(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + } + res.put("targetTable", dbMapping.getTargetTable()); + + return res; + } + + @Override + public String getDestination(String task) { + MappingConfig config = rdbMapping.get(task); + if (config != null) { + return config.getDestination(); + } + return null; + } + + @Override + public void destroy() { + if (rdbConfigMonitor != null) { + rdbConfigMonitor.destroy(); + } + + if (rdbSyncService != null) { + rdbSyncService.close(); + } + + executor.shutdown(); + + if (dataSource != null) { + dataSource.close(); + } + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/config/ConfigLoader.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/config/ConfigLoader.java new file mode 100644 index 00000000..c2fe3339 --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/config/ConfigLoader.java @@ -0,0 +1,46 @@ +package com.alibaba.otter.canal.client.adapter.rdb.config; + +import java.util.LinkedHashMap; +import java.util.Map; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.yaml.snakeyaml.Yaml; + +import com.alibaba.otter.canal.client.adapter.support.MappingConfigsLoader; + +/** + * RDB表映射配置加载器 + * + * @author rewerma 2018-11-07 下午02:41:34 + * @version 1.0.0 + */ +public class ConfigLoader { + + private static Logger logger = LoggerFactory.getLogger(ConfigLoader.class); + + /** + * 加载HBase表映射配置 + * + * @return 配置名/配置文件名--对象 + */ + public static Map load() { + logger.info("## Start loading rdb mapping config ... "); + + Map result = new LinkedHashMap<>(); + + Map configContentMap = MappingConfigsLoader.loadConfigs("rdb"); + configContentMap.forEach((fileName, content) -> { + MappingConfig config = new Yaml().loadAs(content, MappingConfig.class); + try { + config.validate(); + } catch (Exception e) { + throw new RuntimeException("ERROR Config: " + fileName + " " + e.getMessage(), e); + } + result.put(fileName, config); + }); + + logger.info("## Rdb mapping config loaded"); + return result; + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/config/MappingConfig.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/config/MappingConfig.java new file mode 100644 index 00000000..1d32147a --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/config/MappingConfig.java @@ -0,0 +1,182 @@ +package com.alibaba.otter.canal.client.adapter.rdb.config; + +import java.util.LinkedHashSet; +import java.util.Map; +import java.util.Set; + +/** + * RDB表映射配置 + * + * @author rewerma 2018-11-07 下午02:41:34 + * @version 1.0.0 + */ +public class MappingConfig { + + private String dataSourceKey; // 数据源key + + private String destination; // canal实例或MQ的topic + + private String outerAdapterKey; // 对应适配器的key + + private Boolean concurrent; // 是否并行同步 + + private DbMapping dbMapping; // db映射配置 + + public String getDataSourceKey() { + return dataSourceKey; + } + + public void setDataSourceKey(String dataSourceKey) { + this.dataSourceKey = dataSourceKey; + } + + public String getOuterAdapterKey() { + return outerAdapterKey; + } + + public void setOuterAdapterKey(String outerAdapterKey) { + this.outerAdapterKey = outerAdapterKey; + } + + public Boolean getConcurrent() { + return concurrent == null ? false : concurrent; + } + + public void setConcurrent(Boolean concurrent) { + this.concurrent = concurrent; + } + + public DbMapping getDbMapping() { + return dbMapping; + } + + public void setDbMapping(DbMapping dbMapping) { + this.dbMapping = dbMapping; + } + + public String getDestination() { + return destination; + } + + public void setDestination(String destination) { + this.destination = destination; + } + + public void validate() { + if (dbMapping.database == null || dbMapping.database.isEmpty()) { + throw new NullPointerException("dbMapping.database"); + } + if (dbMapping.table == null || dbMapping.table.isEmpty()) { + throw new NullPointerException("dbMapping.table"); + } + if (dbMapping.targetTable == null || dbMapping.targetTable.isEmpty()) { + throw new NullPointerException("dbMapping.targetTable"); + } + } + + public static class DbMapping { + + private String database; // 数据库名或schema名 + private String table; // 表面名 + private Map targetPk; // 目标表主键字段 + private boolean mapAll = false; // 映射所有字段 + private String targetTable; // 目标表名 + private Map targetColumns; // 目标表字段映射 + + private String etlCondition; // etl条件sql + + private Set families = new LinkedHashSet<>(); // column family列表 + private int readBatch = 5000; + private int commitBatch = 5000; // etl等批量提交大小 + + // private volatile Map allColumns; // mapAll为true,自动设置改字段 + + public String getDatabase() { + return database; + } + + public void setDatabase(String database) { + this.database = database; + } + + public String getTable() { + return table; + } + + public void setTable(String table) { + this.table = table; + } + + public Map getTargetPk() { + return targetPk; + } + + public void setTargetPk(Map targetPk) { + this.targetPk = targetPk; + } + + public boolean isMapAll() { + return mapAll; + } + + public void setMapAll(boolean mapAll) { + this.mapAll = mapAll; + } + + public String getTargetTable() { + return targetTable; + } + + public void setTargetTable(String targetTable) { + this.targetTable = targetTable; + } + + public Map getTargetColumns() { + return targetColumns; + } + + public void setTargetColumns(Map targetColumns) { + this.targetColumns = targetColumns; + } + + public String getEtlCondition() { + return etlCondition; + } + + public void setEtlCondition(String etlCondition) { + this.etlCondition = etlCondition; + } + + public Set getFamilies() { + return families; + } + + public void setFamilies(Set families) { + this.families = families; + } + + public int getReadBatch() { + return readBatch; + } + + public void setReadBatch(int readBatch) { + this.readBatch = readBatch; + } + + public int getCommitBatch() { + return commitBatch; + } + + public void setCommitBatch(int commitBatch) { + this.commitBatch = commitBatch; + } + + // public Map getAllColumns() { + // return allColumns; + // } + // + // public void setAllColumns(Map allColumns) { + // this.allColumns = allColumns; + // } + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/monitor/RdbConfigMonitor.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/monitor/RdbConfigMonitor.java new file mode 100644 index 00000000..d74cd884 --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/monitor/RdbConfigMonitor.java @@ -0,0 +1,141 @@ +package com.alibaba.otter.canal.client.adapter.rdb.monitor; + +import java.io.File; +import java.util.HashMap; +import java.util.Map; + +import org.apache.commons.io.filefilter.FileFilterUtils; +import org.apache.commons.io.monitor.FileAlterationListenerAdaptor; +import org.apache.commons.io.monitor.FileAlterationMonitor; +import org.apache.commons.io.monitor.FileAlterationObserver; +import org.apache.commons.lang.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.yaml.snakeyaml.Yaml; + +import com.alibaba.otter.canal.client.adapter.rdb.RdbAdapter; +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.support.MappingConfigsLoader; +import com.alibaba.otter.canal.client.adapter.support.Util; + +public class RdbConfigMonitor { + + private static final Logger logger = LoggerFactory.getLogger(RdbConfigMonitor.class); + + private static final String adapterName = "rdb"; + + private String key; + + private RdbAdapter rdbAdapter; + + private FileAlterationMonitor fileMonitor; + + public void init(String key, RdbAdapter rdbAdapter) { + this.key = key; + this.rdbAdapter = rdbAdapter; + File confDir = Util.getConfDirPath(adapterName); + try { + FileAlterationObserver observer = new FileAlterationObserver(confDir, + FileFilterUtils.and(FileFilterUtils.fileFileFilter(), FileFilterUtils.suffixFileFilter("yml"))); + FileListener listener = new FileListener(); + observer.addListener(listener); + fileMonitor = new FileAlterationMonitor(3000, observer); + fileMonitor.start(); + + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + public void destroy() { + try { + fileMonitor.stop(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private class FileListener extends FileAlterationListenerAdaptor { + + @Override + public void onFileCreate(File file) { + super.onFileCreate(file); + try { + // 加载新增的配置文件 + String configContent = MappingConfigsLoader.loadConfig(adapterName + File.separator + file.getName()); + MappingConfig config = new Yaml().loadAs(configContent, MappingConfig.class); + config.validate(); + if ((key == null && config.getOuterAdapterKey() == null) + || (key != null && key.equals(config.getOuterAdapterKey()))) { + addConfigToCache(file, config); + + logger.info("Add a new rdb mapping config: {} to canal adapter", file.getName()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + @Override + public void onFileChange(File file) { + super.onFileChange(file); + + try { + if (rdbAdapter.getRdbMapping().containsKey(file.getName())) { + // 加载配置文件 + String configContent = MappingConfigsLoader.loadConfig(adapterName + File.separator + file.getName()); + MappingConfig config = new Yaml().loadAs(configContent, MappingConfig.class); + config.validate(); + if ((key == null && config.getOuterAdapterKey() == null) + || (key != null && key.equals(config.getOuterAdapterKey()))) { + if (rdbAdapter.getRdbMapping().containsKey(file.getName())) { + deleteConfigFromCache(file); + } + addConfigToCache(file, config); + } else { + // 不能修改outerAdapterKey + throw new RuntimeException("Outer adapter key not allowed modify"); + } + logger.info("Change a rdb mapping config: {} of canal adapter", file.getName()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + @Override + public void onFileDelete(File file) { + super.onFileDelete(file); + + try { + if (rdbAdapter.getRdbMapping().containsKey(file.getName())) { + deleteConfigFromCache(file); + + logger.info("Delete a rdb mapping config: {} of canal adapter", file.getName()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private void addConfigToCache(File file, MappingConfig config) { + rdbAdapter.getRdbMapping().put(file.getName(), config); + Map configMap = rdbAdapter.getMappingConfigCache() + .computeIfAbsent(StringUtils.trimToEmpty(config.getDestination()) + "." + + config.getDbMapping().getDatabase() + "." + config.getDbMapping().getTable(), + k1 -> new HashMap<>()); + configMap.put(file.getName(), config); + } + + private void deleteConfigFromCache(File file) { + + rdbAdapter.getRdbMapping().remove(file.getName()); + for (Map configMap : rdbAdapter.getMappingConfigCache().values()) { + if (configMap != null) { + configMap.remove(file.getName()); + } + } + + } + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/service/RdbEtlService.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/service/RdbEtlService.java new file mode 100644 index 00000000..a42e5f3c --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/service/RdbEtlService.java @@ -0,0 +1,293 @@ +package com.alibaba.otter.canal.client.adapter.rdb.service; + +import java.sql.*; +import java.util.ArrayList; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; +import java.util.concurrent.atomic.AtomicBoolean; +import java.util.concurrent.atomic.AtomicLong; + +import javax.sql.DataSource; + +import com.alibaba.otter.canal.client.adapter.rdb.support.SyncUtil; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig.DbMapping; +import com.alibaba.otter.canal.client.adapter.support.EtlResult; +import com.alibaba.otter.canal.client.adapter.support.Util; +import com.google.common.base.Joiner; + +/** + * RDB ETL 操作业务类 + * + * @author rewerma @ 2018-11-7 + * @version 1.0.0 + */ +public class RdbEtlService { + + private static final Logger logger = LoggerFactory.getLogger(RdbEtlService.class); + + /** + * 导入数据 + */ + public static EtlResult importData(DataSource srcDS, DataSource targetDS, MappingConfig config, + List params) { + EtlResult etlResult = new EtlResult(); + AtomicLong successCount = new AtomicLong(); + List errMsg = new ArrayList<>(); + String hbaseTable = ""; + try { + if (config == null) { + logger.error("Config is null!"); + etlResult.setSucceeded(false); + etlResult.setErrorMessage("Config is null!"); + return etlResult; + } + DbMapping dbMapping = config.getDbMapping(); + + long start = System.currentTimeMillis(); + + // 拼接sql + StringBuilder sql = new StringBuilder( + "SELECT * FROM " + dbMapping.getDatabase() + "." + dbMapping.getTable()); + + // 拼接条件 + appendCondition(params, dbMapping, srcDS, sql); + + // 获取总数 + String countSql = "SELECT COUNT(1) FROM ( " + sql + ") _CNT "; + long cnt = (Long) Util.sqlRS(srcDS, countSql, rs -> { + Long count = null; + try { + if (rs.next()) { + count = ((Number) rs.getObject(1)).longValue(); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + return count == null ? 0 : count; + }); + + // 当大于1万条记录时开启多线程 + if (cnt >= 10000) { + int threadCount = 3; + long perThreadCnt = cnt / threadCount; + ExecutorService executor = Executors.newFixedThreadPool(threadCount); + List> futures = new ArrayList<>(threadCount); + for (int i = 0; i < threadCount; i++) { + long offset = i * perThreadCnt; + Long size = null; + if (i != threadCount - 1) { + size = perThreadCnt; + } + String sqlFinal; + if (size != null) { + sqlFinal = sql + " LIMIT " + offset + "," + size; + } else { + sqlFinal = sql + " LIMIT " + offset + "," + cnt; + } + Future future = executor + .submit(() -> executeSqlImport(srcDS, targetDS, sqlFinal, dbMapping, successCount, errMsg)); + futures.add(future); + } + + for (Future future : futures) { + future.get(); + } + + executor.shutdown(); + } else { + executeSqlImport(srcDS, targetDS, sql.toString(), dbMapping, successCount, errMsg); + } + + logger.info( + dbMapping.getTable() + " etl completed in: " + (System.currentTimeMillis() - start) / 1000 + "s!"); + + etlResult.setResultMessage("导入目标表 " + dbMapping.getTargetTable() + " 数据:" + successCount.get() + " 条"); + } catch (Exception e) { + logger.error(e.getMessage(), e); + errMsg.add(hbaseTable + " etl failed! ==>" + e.getMessage()); + } + + if (errMsg.isEmpty()) { + etlResult.setSucceeded(true); + } else { + etlResult.setErrorMessage(Joiner.on("\n").join(errMsg)); + } + return etlResult; + } + + private static void appendCondition(List params, DbMapping dbMapping, DataSource ds, + StringBuilder sql) throws SQLException { + if (params != null && params.size() == 1 && dbMapping.getEtlCondition() == null) { + AtomicBoolean stExists = new AtomicBoolean(false); + // 验证是否有SYS_TIME字段 + Util.sqlRS(ds, sql.toString(), rs -> { + try { + ResultSetMetaData rsmd = rs.getMetaData(); + int cnt = rsmd.getColumnCount(); + for (int i = 1; i <= cnt; i++) { + String columnName = rsmd.getColumnName(i); + if ("SYS_TIME".equalsIgnoreCase(columnName)) { + stExists.set(true); + break; + } + } + } catch (Exception e) { + // ignore + } + return null; + }); + if (stExists.get()) { + sql.append(" WHERE SYS_TIME >= '").append(params.get(0)).append("' "); + } + } else if (dbMapping.getEtlCondition() != null && params != null) { + String etlCondition = dbMapping.getEtlCondition(); + int size = params.size(); + for (int i = 0; i < size; i++) { + etlCondition = etlCondition.replace("{" + i + "}", params.get(i)); + } + + sql.append(" ").append(etlCondition); + } + } + + /** + * 执行导入 + */ + private static boolean executeSqlImport(DataSource srcDS, DataSource targetDS, String sql, DbMapping dbMapping, + AtomicLong successCount, List errMsg) { + try { + Util.sqlRS(srcDS, sql, rs -> { + int idx = 1; + + try { + boolean completed = false; + + Map columnType = new LinkedHashMap<>(); + ResultSetMetaData rsd = rs.getMetaData(); + int columnCount = rsd.getColumnCount(); + List columns = new ArrayList<>(); + for (int i = 1; i <= columnCount; i++) { + columnType.put(rsd.getColumnName(i).toLowerCase(), rsd.getColumnType(i)); + columns.add(rsd.getColumnName(i)); + } + + Map columnsMap = SyncUtil.getColumnsMap(dbMapping, columns); + // if (dbMapping.isMapAll()) { + // columnsMap = dbMapping.getAllColumns(); + // } else { + // columnsMap = dbMapping.getTargetColumns(); + // } + + StringBuilder insertSql = new StringBuilder(); + insertSql.append("INSERT INTO ").append(dbMapping.getTargetTable()).append(" ("); + columnsMap + .forEach((targetColumnName, srcColumnName) -> insertSql.append(targetColumnName).append(",")); + + int len = insertSql.length(); + insertSql.delete(len - 1, len).append(") VALUES ("); + int mapLen = columnsMap.size(); + for (int i = 0; i < mapLen; i++) { + insertSql.append("?,"); + } + len = insertSql.length(); + insertSql.delete(len - 1, len).append(")"); + try (Connection connTarget = targetDS.getConnection(); + PreparedStatement pstmt = connTarget.prepareStatement(insertSql.toString())) { + connTarget.setAutoCommit(false); + + while (rs.next()) { + pstmt.clearParameters(); + + // 删除数据 + Map values = new LinkedHashMap<>(); + StringBuilder deleteSql = new StringBuilder( + "DELETE FROM " + dbMapping.getTargetTable() + " WHERE "); + appendCondition(dbMapping, deleteSql, values, rs); + try (PreparedStatement pstmt2 = connTarget.prepareStatement(deleteSql.toString())) { + int k = 1; + for (Object val : values.values()) { + pstmt2.setObject(k++, val); + } + pstmt2.execute(); + } + + int i = 1; + for (Map.Entry entry : columnsMap.entrySet()) { + String targetClolumnName = entry.getKey(); + String srcColumnName = entry.getValue(); + if (srcColumnName == null) { + srcColumnName = targetClolumnName; + } + + Integer type = columnType.get(targetClolumnName.toLowerCase()); + + Object value = rs.getObject(srcColumnName); + if (value != null) { + SyncUtil.setPStmt(type, pstmt, value, i); + } else { + pstmt.setNull(i, type); + } + + i++; + } + + pstmt.execute(); + if (logger.isTraceEnabled()) { + logger.trace("Insert into target table, sql: {}", insertSql); + } + + if (idx % dbMapping.getCommitBatch() == 0) { + connTarget.commit(); + completed = true; + } + idx++; + successCount.incrementAndGet(); + if (logger.isDebugEnabled()) { + logger.debug("successful import count:" + successCount.get()); + } + } + if (!completed) { + connTarget.commit(); + } + } + + } catch (Exception e) { + logger.error(dbMapping.getTable() + " etl failed! ==>" + e.getMessage(), e); + errMsg.add(dbMapping.getTable() + " etl failed! ==>" + e.getMessage()); + } + return idx; + }); + return true; + } catch (Exception e) { + logger.error(e.getMessage(), e); + return false; + } + } + + /** + * 拼接目标表主键where条件 + */ + private static void appendCondition(DbMapping dbMapping, StringBuilder sql, Map values, + ResultSet rs) throws SQLException { + // 拼接主键 + for (Map.Entry entry : dbMapping.getTargetPk().entrySet()) { + String targetColumnName = entry.getKey(); + String srcColumnName = entry.getValue(); + if (srcColumnName == null) { + srcColumnName = targetColumnName; + } + sql.append(targetColumnName).append("=? AND "); + values.put(targetColumnName, rs.getObject(srcColumnName)); + } + int len = sql.length(); + sql.delete(len - 4, len); + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/service/RdbSyncService.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/service/RdbSyncService.java new file mode 100644 index 00000000..02e87cdf --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/service/RdbSyncService.java @@ -0,0 +1,409 @@ +package com.alibaba.otter.canal.client.adapter.rdb.service; + +import java.sql.Connection; +import java.sql.ResultSetMetaData; +import java.sql.SQLException; +import java.util.ArrayList; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; + +import javax.sql.DataSource; + +import org.apache.commons.lang.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.serializer.SerializerFeature; +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig.DbMapping; +import com.alibaba.otter.canal.client.adapter.rdb.support.BatchExecutor; +import com.alibaba.otter.canal.client.adapter.rdb.support.SingleDml; +import com.alibaba.otter.canal.client.adapter.rdb.support.SyncUtil; +import com.alibaba.otter.canal.client.adapter.support.Dml; +import com.alibaba.otter.canal.client.adapter.support.Util; + +/** + * RDB同步操作业务 + * + * @author rewerma 2018-11-7 下午06:45:49 + * @version 1.0.0 + */ +public class RdbSyncService { + + private static final Logger logger = LoggerFactory.getLogger(RdbSyncService.class); + + private final Map> COLUMNS_TYPE_CACHE = new ConcurrentHashMap<>(); + + private Map> mappingConfigCache; // 库名-表名对应配置 + + private int threads = 3; + + private List[] dmlsPartition; + private BatchExecutor[] batchExecutors; + private ExecutorService[] executorThreads; + + @SuppressWarnings("unchecked") + public RdbSyncService(Map> mappingConfigCache, DataSource dataSource, + Integer threads){ + try { + if (threads != null) { + this.threads = threads; + } + this.mappingConfigCache = mappingConfigCache; + this.dmlsPartition = new List[this.threads]; + this.batchExecutors = new BatchExecutor[this.threads]; + this.executorThreads = new ExecutorService[this.threads]; + for (int i = 0; i < this.threads; i++) { + dmlsPartition[i] = new ArrayList<>(); + batchExecutors[i] = new BatchExecutor(dataSource.getConnection()); + executorThreads[i] = Executors.newSingleThreadExecutor(); + } + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + + public void sync(List dmls) { + try { + for (Dml dml : dmls) { + String destination = StringUtils.trimToEmpty(dml.getDestination()); + String database = dml.getDatabase(); + String table = dml.getTable(); + Map configMap = mappingConfigCache + .get(destination + "." + database + "." + table); + + for (MappingConfig config : configMap.values()) { + + if (config.getConcurrent()) { + List singleDmls = SingleDml.dml2SingleDmls(dml); + singleDmls.forEach(singleDml -> { + int hash = pkHash(config.getDbMapping(), singleDml.getData()); + SyncItem syncItem = new SyncItem(config, singleDml); + dmlsPartition[hash].add(syncItem); + }); + } else { + int hash = Math.abs(Math.abs(config.getDbMapping().getTargetTable().hashCode()) % threads); + List singleDmls = SingleDml.dml2SingleDmls(dml); + singleDmls.forEach(singleDml -> { + SyncItem syncItem = new SyncItem(config, singleDml); + dmlsPartition[hash].add(syncItem); + }); + } + } + } + List futures = new ArrayList<>(); + for (int i = 0; i < threads; i++) { + int j = i; + futures.add(executorThreads[i].submit(() -> { + dmlsPartition[j].forEach(syncItem -> sync(batchExecutors[j], syncItem.config, syncItem.singleDml)); + batchExecutors[j].commit(); + return true; + })); + } + + futures.forEach(future -> { + try { + future.get(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + }); + + for (int i = 0; i < threads; i++) { + dmlsPartition[i].clear(); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + private void sync(BatchExecutor batchExecutor, MappingConfig config, SingleDml dml) { + try { + if (config != null) { + String type = dml.getType(); + if (type != null && type.equalsIgnoreCase("INSERT")) { + insert(batchExecutor, config, dml); + } else if (type != null && type.equalsIgnoreCase("UPDATE")) { + update(batchExecutor, config, dml); + } else if (type != null && type.equalsIgnoreCase("DELETE")) { + delete(batchExecutor, config, dml); + } + if (logger.isDebugEnabled()) { + logger.debug("DML: {}", JSON.toJSONString(dml, SerializerFeature.WriteMapNullValue)); + } + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + /** + * 插入操作 + * + * @param config 配置项 + * @param dml DML数据 + */ + private void insert(BatchExecutor batchExecutor, MappingConfig config, SingleDml dml) { + Map data = dml.getData(); + if (data == null || data.isEmpty()) { + return; + } + + DbMapping dbMapping = config.getDbMapping(); + + try { + Map columnsMap = SyncUtil.getColumnsMap(dbMapping, data); + + StringBuilder insertSql = new StringBuilder(); + insertSql.append("INSERT INTO ").append(dbMapping.getTargetTable()).append(" ("); + + columnsMap.forEach((targetColumnName, srcColumnName) -> insertSql.append(targetColumnName).append(",")); + int len = insertSql.length(); + insertSql.delete(len - 1, len).append(") VALUES ("); + int mapLen = columnsMap.size(); + for (int i = 0; i < mapLen; i++) { + insertSql.append("?,"); + } + len = insertSql.length(); + insertSql.delete(len - 1, len).append(")"); + + Map ctype = getTargetColumnType(batchExecutor.getConn(), config); + + List> values = new ArrayList<>(); + for (Map.Entry entry : columnsMap.entrySet()) { + String targetClolumnName = entry.getKey(); + String srcColumnName = entry.getValue(); + if (srcColumnName == null) { + srcColumnName = targetClolumnName; + } + + Integer type = ctype.get(targetClolumnName.toLowerCase()); + + Object value = data.get(srcColumnName); + + BatchExecutor.setValue(values, type, value); + } + + batchExecutor.execute(insertSql.toString(), values); + if (logger.isTraceEnabled()) { + logger.trace("Insert into target table, sql: {}", insertSql); + } + + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + /** + * 更新操作 + * + * @param config 配置项 + * @param dml DML数据 + */ + private void update(BatchExecutor batchExecutor, MappingConfig config, SingleDml dml) { + Map data = dml.getData(); + if (data == null || data.isEmpty()) { + return; + } + + Map old = dml.getOld(); + if (old == null || old.isEmpty()) { + return; + } + + DbMapping dbMapping = config.getDbMapping(); + + try { + Map columnsMap = SyncUtil.getColumnsMap(dbMapping, data); + + Map ctype = getTargetColumnType(batchExecutor.getConn(), config); + + StringBuilder updateSql = new StringBuilder(); + updateSql.append("UPDATE ").append(dbMapping.getTargetTable()).append(" SET "); + List> values = new ArrayList<>(); + for (String srcColumnName : old.keySet()) { + List targetColumnNames = new ArrayList<>(); + columnsMap.forEach((targetColumn, srcColumn) -> { + if (srcColumnName.toLowerCase().equals(srcColumn)) { + targetColumnNames.add(targetColumn); + } + }); + if (!targetColumnNames.isEmpty()) { + + for (String targetColumnName : targetColumnNames) { + updateSql.append(targetColumnName).append("=?, "); + Integer type = ctype.get(targetColumnName.toLowerCase()); + BatchExecutor.setValue(values, type, data.get(srcColumnName)); + } + } + } + int len = updateSql.length(); + updateSql.delete(len - 2, len).append(" WHERE "); + + // 拼接主键 + appendCondition(dbMapping, updateSql, ctype, values, data, old); + + batchExecutor.execute(updateSql.toString(), values); + + if (logger.isTraceEnabled()) { + logger.trace("Update target table, sql: {}", updateSql); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + /** + * 删除操作 + * + * @param config + * @param dml + */ + private void delete(BatchExecutor batchExecutor, MappingConfig config, SingleDml dml) { + Map data = dml.getData(); + if (data == null || data.isEmpty()) { + return; + } + + DbMapping dbMapping = config.getDbMapping(); + + try { + Map ctype = getTargetColumnType(batchExecutor.getConn(), config); + + StringBuilder sql = new StringBuilder(); + sql.append("DELETE FROM ").append(dbMapping.getTargetTable()).append(" WHERE "); + + List> values = new ArrayList<>(); + // 拼接主键 + appendCondition(dbMapping, sql, ctype, values, data); + + batchExecutor.execute(sql.toString(), values); + + if (logger.isTraceEnabled()) { + logger.trace("Delete from target table, sql: {}", sql); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + /** + * 获取目标字段类型 + * + * @param conn sql connection + * @param config 映射配置 + * @return 字段sqlType + */ + private Map getTargetColumnType(Connection conn, MappingConfig config) { + DbMapping dbMapping = config.getDbMapping(); + String cacheKey = config.getDestination() + "." + dbMapping.getDatabase() + "." + dbMapping.getTable(); + Map columnType = COLUMNS_TYPE_CACHE.get(cacheKey); + if (columnType == null) { + synchronized (RdbSyncService.class) { + columnType = COLUMNS_TYPE_CACHE.get(cacheKey); + if (columnType == null) { + columnType = new LinkedHashMap<>(); + final Map columnTypeTmp = columnType; + String sql = "SELECT * FROM " + dbMapping.getTargetTable() + " WHERE 1=2"; + Util.sqlRS(conn, sql, rs -> { + try { + ResultSetMetaData rsd = rs.getMetaData(); + int columnCount = rsd.getColumnCount(); + for (int i = 1; i <= columnCount; i++) { + columnTypeTmp.put(rsd.getColumnName(i).toLowerCase(), rsd.getColumnType(i)); + } + COLUMNS_TYPE_CACHE.put(cacheKey, columnTypeTmp); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + }); + } + } + } + return columnType; + } + + /** + * 拼接主键 where条件 + */ + private void appendCondition(MappingConfig.DbMapping dbMapping, StringBuilder sql, Map ctype, + List> values, Map d) { + appendCondition(dbMapping, sql, ctype, values, d, null); + } + + private void appendCondition(MappingConfig.DbMapping dbMapping, StringBuilder sql, Map ctype, + List> values, Map d, Map o) { + // 拼接主键 + for (Map.Entry entry : dbMapping.getTargetPk().entrySet()) { + String targetColumnName = entry.getKey(); + String srcColumnName = entry.getValue(); + if (srcColumnName == null) { + srcColumnName = targetColumnName; + } + sql.append(targetColumnName).append("=? AND "); + Integer type = ctype.get(targetColumnName.toLowerCase()); + // 如果有修改主键的情况 + if (o != null && o.containsKey(srcColumnName)) { + BatchExecutor.setValue(values, type, o.get(srcColumnName)); + } else { + BatchExecutor.setValue(values, type, d.get(srcColumnName)); + } + } + int len = sql.length(); + sql.delete(len - 4, len); + } + + private class SyncItem { + + private MappingConfig config; + private SingleDml singleDml; + + private SyncItem(MappingConfig config, SingleDml singleDml){ + this.config = config; + this.singleDml = singleDml; + } + } + + /** + * 取主键hash + */ + private int pkHash(DbMapping dbMapping, Map d) { + return pkHash(dbMapping, d, null); + } + + private int pkHash(DbMapping dbMapping, Map d, Map o) { + int hash = 0; + // 取主键 + for (Map.Entry entry : dbMapping.getTargetPk().entrySet()) { + String targetColumnName = entry.getKey(); + String srcColumnName = entry.getValue(); + if (srcColumnName == null) { + srcColumnName = targetColumnName; + } + Object value; + if (o != null && o.containsKey(srcColumnName)) { + value = o.get(srcColumnName); + } else { + value = d.get(srcColumnName); + } + if (value != null) { + hash += value.hashCode(); + } + } + hash = Math.abs(hash) % threads; + return Math.abs(hash); + } + + public void close() { + for (int i = 0; i < threads; i++) { + batchExecutors[i].close(); + executorThreads[i].shutdown(); + } + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/BatchExecutor.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/BatchExecutor.java new file mode 100644 index 00000000..24ac01ba --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/BatchExecutor.java @@ -0,0 +1,91 @@ +package com.alibaba.otter.canal.client.adapter.rdb.support; + +import java.io.Closeable; +import java.sql.Connection; +import java.sql.PreparedStatement; +import java.sql.SQLException; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.concurrent.atomic.AtomicInteger; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +public class BatchExecutor implements Closeable { + + private static final Logger logger = LoggerFactory.getLogger(BatchExecutor.class); + + private Integer key; + private Connection conn; + private AtomicInteger idx = new AtomicInteger(0); + + public BatchExecutor(Connection conn){ + this(1, conn); + } + + public BatchExecutor(Integer key, Connection conn){ + this.key = key; + this.conn = conn; + + try { + this.conn.setAutoCommit(false); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + + public Integer getKey() { + return key; + } + + public Connection getConn() { + return conn; + } + + public static void setValue(List> values, int type, Object value) { + Map valueItem = new HashMap<>(); + valueItem.put("type", type); + valueItem.put("value", value); + values.add(valueItem); + } + + public void execute(String sql, List> values) { + try (PreparedStatement pstmt = conn.prepareStatement(sql)) { + int len = values.size(); + for (int i = 0; i < len; i++) { + int type = (Integer) values.get(i).get("type"); + Object value = values.get(i).get("value"); + SyncUtil.setPStmt(type, pstmt, value, i + 1); + } + + pstmt.execute(); + idx.incrementAndGet(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + + public void commit() { + try { + conn.commit(); + if (logger.isTraceEnabled()) { + logger.trace("Batch executor: " + key + " commit " + idx.get() + " rows"); + } + idx.set(0); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + + @Override + public void close() { + if (conn != null) { + try { + conn.close(); + } catch (SQLException e) { + logger.error(e.getMessage(), e); + } + } + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/SingleDml.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/SingleDml.java new file mode 100644 index 00000000..6e61a15f --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/SingleDml.java @@ -0,0 +1,83 @@ +package com.alibaba.otter.canal.client.adapter.rdb.support; + +import com.alibaba.otter.canal.client.adapter.support.Dml; + +import java.util.ArrayList; +import java.util.List; +import java.util.Map; + +public class SingleDml { + + private String destination; + private String database; + private String table; + private String type; + private Map data; + private Map old; + + public String getDestination() { + return destination; + } + + public void setDestination(String destination) { + this.destination = destination; + } + + public String getDatabase() { + return database; + } + + public void setDatabase(String database) { + this.database = database; + } + + public String getTable() { + return table; + } + + public void setTable(String table) { + this.table = table; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + public Map getData() { + return data; + } + + public void setData(Map data) { + this.data = data; + } + + public Map getOld() { + return old; + } + + public void setOld(Map old) { + this.old = old; + } + + public static List dml2SingleDmls(Dml dml) { + int size = dml.getData().size(); + List singleDmls = new ArrayList<>(size); + for (int i = 0; i < size; i++) { + SingleDml singleDml = new SingleDml(); + singleDml.setDestination(dml.getDestination()); + singleDml.setDatabase(dml.getDatabase()); + singleDml.setTable(dml.getTable()); + singleDml.setType(dml.getType()); + singleDml.setData(dml.getData().get(i)); + if (dml.getOld() != null) { + singleDml.setOld(dml.getOld().get(i)); + } + singleDmls.add(singleDml); + } + return singleDmls; + } +} diff --git a/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/SyncUtil.java b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/SyncUtil.java new file mode 100644 index 00000000..1b2e8e0a --- /dev/null +++ b/client-adapter/rdb/src/main/java/com/alibaba/otter/canal/client/adapter/rdb/support/SyncUtil.java @@ -0,0 +1,252 @@ +package com.alibaba.otter.canal.client.adapter.rdb.support; + +import java.io.Reader; +import java.io.StringReader; +import java.math.BigDecimal; +import java.nio.charset.StandardCharsets; +import java.sql.*; +import java.util.Collection; +import java.util.LinkedHashMap; +import java.util.Map; + +import org.joda.time.DateTime; + +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig; + +public class SyncUtil { + + public static Map getColumnsMap(MappingConfig.DbMapping dbMapping, Map data) { + return getColumnsMap(dbMapping, data.keySet()); + } + + public static Map getColumnsMap(MappingConfig.DbMapping dbMapping, Collection columns) { + Map columnsMap; + if (dbMapping.isMapAll()) { + columnsMap = new LinkedHashMap<>(); + for (String srcColumn : columns) { + boolean flag = true; + if (dbMapping.getTargetColumns() != null) { + for (Map.Entry entry : dbMapping.getTargetColumns().entrySet()) { + if (srcColumn.equals(entry.getValue())) { + columnsMap.put(entry.getKey(), srcColumn); + flag = false; + break; + } + } + } + if (flag) { + columnsMap.put(srcColumn, srcColumn); + } + } + } else { + columnsMap = dbMapping.getTargetColumns(); + } + return columnsMap; + } + + /** + * 设置 preparedStatement + * + * @param type sqlType + * @param pstmt 需要设置的preparedStatement + * @param value 值 + * @param i 索引号 + */ + public static void setPStmt(int type, PreparedStatement pstmt, Object value, int i) throws SQLException { + switch (type) { + case Types.BIT: + case Types.BOOLEAN: + if (value instanceof Boolean) { + pstmt.setBoolean(i, (Boolean) value); + } else if (value instanceof String) { + boolean v = !value.equals("0"); + pstmt.setBoolean(i, v); + } else if (value instanceof Number) { + boolean v = ((Number) value).intValue() != 0; + pstmt.setBoolean(i, v); + } else { + pstmt.setNull(i, type); + } + break; + case Types.CHAR: + case Types.NCHAR: + case Types.VARCHAR: + case Types.LONGVARCHAR: + if (value instanceof String) { + pstmt.setString(i, (String) value); + } else { + pstmt.setString(i, value.toString()); + } + break; + case Types.TINYINT: + if (value instanceof Byte || value instanceof Short || value instanceof Integer) { + pstmt.setByte(i, (byte) value); + } else if (value instanceof Number) { + pstmt.setByte(i, ((Number) value).byteValue()); + } else if (value instanceof String) { + pstmt.setByte(i, Byte.parseByte((String) value)); + } else { + pstmt.setNull(i, type); + } + break; + case Types.SMALLINT: + if (value instanceof Byte || value instanceof Short || value instanceof Integer) { + pstmt.setShort(i, (short) value); + } else if (value instanceof Number) { + pstmt.setShort(i, ((Number) value).shortValue()); + } else if (value instanceof String) { + pstmt.setShort(i, Short.parseShort((String) value)); + } else { + pstmt.setNull(i, type); + } + break; + case Types.INTEGER: + if (value instanceof Byte || value instanceof Short || value instanceof Integer + || value instanceof Long) { + pstmt.setInt(i, (int) value); + } else if (value instanceof Number) { + pstmt.setInt(i, ((Number) value).intValue()); + } else if (value instanceof String) { + pstmt.setInt(i, Integer.parseInt((String) value)); + } else { + pstmt.setNull(i, type); + } + break; + case Types.BIGINT: + if (value instanceof Byte || value instanceof Short || value instanceof Integer + || value instanceof Long) { + pstmt.setLong(i, (long) value); + } else if (value instanceof Number) { + pstmt.setLong(i, ((Number) value).longValue()); + } else if (value instanceof String) { + pstmt.setLong(i, Long.parseLong((String) value)); + } else { + pstmt.setNull(i, type); + } + break; + case Types.DECIMAL: + case Types.NUMERIC: + if (value instanceof BigDecimal) { + pstmt.setBigDecimal(i, (BigDecimal) value); + } else if (value instanceof Byte) { + pstmt.setInt(i, (int) value); + } else if (value instanceof Short) { + pstmt.setInt(i, (int) value); + } else if (value instanceof Integer) { + pstmt.setInt(i, (int) value); + } else if (value instanceof Long) { + pstmt.setLong(i, (long) value); + } else if (value instanceof Float) { + pstmt.setBigDecimal(i, new BigDecimal((float) value)); + } else if (value instanceof Double) { + pstmt.setBigDecimal(i, new BigDecimal((double) value)); + } else { + pstmt.setBigDecimal(i, new BigDecimal(value.toString())); + } + break; + case Types.REAL: + if (value instanceof Byte || value instanceof Short || value instanceof Integer || value instanceof Long + || value instanceof Float || value instanceof Double) { + pstmt.setFloat(i, (float) value); + } else if (value instanceof Number) { + pstmt.setFloat(i, ((Number) value).floatValue()); + } else if (value instanceof String) { + pstmt.setFloat(i, Float.parseFloat((String) value)); + } else { + pstmt.setNull(i, type); + } + break; + case Types.FLOAT: + case Types.DOUBLE: + if (value instanceof Byte || value instanceof Short || value instanceof Integer || value instanceof Long + || value instanceof Float || value instanceof Double) { + pstmt.setDouble(i, (double) value); + } else if (value instanceof Number) { + pstmt.setDouble(i, ((Number) value).doubleValue()); + } else if (value instanceof String) { + pstmt.setDouble(i, Double.parseDouble((String) value)); + } else { + pstmt.setNull(i, type); + } + break; + case Types.BINARY: + case Types.VARBINARY: + case Types.LONGVARBINARY: + case Types.BLOB: + if (value instanceof Blob) { + pstmt.setBlob(i, (Blob) value); + } else if (value instanceof byte[]) { + pstmt.setBytes(i, (byte[]) value); + } else if (value instanceof String) { + pstmt.setBytes(i, ((String) value).getBytes(StandardCharsets.ISO_8859_1)); + } else { + pstmt.setNull(i, type); + } + break; + case Types.CLOB: + if (value instanceof Clob) { + pstmt.setClob(i, (Clob) value); + } else if (value instanceof byte[]) { + pstmt.setBytes(i, (byte[]) value); + } else if (value instanceof String) { + Reader clobReader = new StringReader((String) value); + pstmt.setCharacterStream(i, clobReader); + } else { + pstmt.setNull(i, type); + } + break; + case Types.DATE: + if (value instanceof java.sql.Date) { + pstmt.setDate(i, (java.sql.Date) value); + } else if (value instanceof java.util.Date) { + pstmt.setDate(i, new java.sql.Date(((java.util.Date) value).getTime())); + } else if (value instanceof String) { + String v = (String) value; + if (!v.startsWith("0000-00-00")) { + v = v.trim().replace(" ", "T"); + DateTime dt = new DateTime(v); + pstmt.setDate(i, new Date(dt.toDate().getTime())); + } else { + pstmt.setNull(i, type); + } + } else { + pstmt.setNull(i, type); + } + break; + case Types.TIME: + if (value instanceof java.sql.Time) { + pstmt.setTime(i, (java.sql.Time) value); + } else if (value instanceof java.util.Date) { + pstmt.setTime(i, new java.sql.Time(((java.util.Date) value).getTime())); + } else if (value instanceof String) { + String v = (String) value; + v = "T" + v; + DateTime dt = new DateTime(v); + pstmt.setTime(i, new Time(dt.toDate().getTime())); + } else { + pstmt.setNull(i, type); + } + break; + case Types.TIMESTAMP: + if (value instanceof java.sql.Timestamp) { + pstmt.setTimestamp(i, (java.sql.Timestamp) value); + } else if (value instanceof java.util.Date) { + pstmt.setTimestamp(i, new java.sql.Timestamp(((java.util.Date) value).getTime())); + } else if (value instanceof String) { + String v = (String) value; + if (!v.startsWith("0000-00-00")) { + v = v.trim().replace(" ", "T"); + DateTime dt = new DateTime(v); + pstmt.setTimestamp(i, new Timestamp(dt.toDate().getTime())); + } else { + pstmt.setNull(i, type); + } + } else { + pstmt.setNull(i, type); + } + break; + default: + pstmt.setObject(i, value, type); + } + } +} diff --git a/client-adapter/rdb/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter b/client-adapter/rdb/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter new file mode 100644 index 00000000..0a840275 --- /dev/null +++ b/client-adapter/rdb/src/main/resources/META-INF/canal/com.alibaba.otter.canal.client.adapter.OuterAdapter @@ -0,0 +1 @@ +rdb=com.alibaba.otter.canal.client.adapter.rdb.RdbAdapter \ No newline at end of file diff --git a/client-adapter/rdb/src/main/resources/rdb/mytest_user.yml b/client-adapter/rdb/src/main/resources/rdb/mytest_user.yml new file mode 100644 index 00000000..9b40dd75 --- /dev/null +++ b/client-adapter/rdb/src/main/resources/rdb/mytest_user.yml @@ -0,0 +1,17 @@ +dataSourceKey: defaultDS +destination: example +outerAdapterKey: oracle1 +concurrent: true +dbMapping: + database: mytest + table: user + targetTable: mytest.tb_user + targetPk: + id: id + mapAll: true +# targetColumns: +# id: +# name: +# role_id: +# c_time: +# test1: \ No newline at end of file diff --git a/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/ConfigLoadTest.java b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/ConfigLoadTest.java new file mode 100644 index 00000000..5eeb0878 --- /dev/null +++ b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/ConfigLoadTest.java @@ -0,0 +1,27 @@ +package com.alibaba.otter.canal.client.adapter.rdb.test; + +import java.util.Map; + +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.rdb.config.ConfigLoader; +import com.alibaba.otter.canal.client.adapter.rdb.config.MappingConfig; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; + +public class ConfigLoadTest { + + @Before + public void before() { + // 加载数据源连接池 + DatasourceConfig.DATA_SOURCES.put("defaultDS", TestConstant.dataSource); + } + + @Test + public void testLoad() { + Map configMap = ConfigLoader.load(); + + Assert.assertFalse(configMap.isEmpty()); + } +} diff --git a/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/DBTest.java b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/DBTest.java new file mode 100644 index 00000000..5057765f --- /dev/null +++ b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/DBTest.java @@ -0,0 +1,109 @@ +package com.alibaba.otter.canal.client.adapter.rdb.test; + +import java.io.BufferedReader; +import java.io.Reader; +import java.sql.Clob; +import java.sql.Connection; +import java.sql.PreparedStatement; +import java.sql.SQLException; + +import org.junit.Test; + +import com.alibaba.druid.pool.DruidDataSource; + +public class DBTest { + + @Test + public void test01() throws SQLException { + DruidDataSource dataSource = new DruidDataSource(); + // dataSource.setDriverClassName("oracle.jdbc.OracleDriver"); + // dataSource.setUrl("jdbc:oracle:thin:@127.0.0.1:49161:XE"); + // dataSource.setUsername("mytest"); + // dataSource.setPassword("m121212"); + + dataSource.setDriverClassName("com.mysql.jdbc.Driver"); + dataSource.setUrl("jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true"); + dataSource.setUsername("root"); + dataSource.setPassword("121212"); + + dataSource.setInitialSize(1); + dataSource.setMinIdle(1); + dataSource.setMaxActive(2); + dataSource.setMaxWait(60000); + dataSource.setTimeBetweenEvictionRunsMillis(60000); + dataSource.setMinEvictableIdleTimeMillis(300000); + + dataSource.init(); + + Connection conn = dataSource.getConnection(); + + conn.setAutoCommit(false); + PreparedStatement pstmt = conn + .prepareStatement("insert into user (id,name,role_id,c_time,test1,test2) values (?,?,?,?,?,?)"); + + java.util.Date now = new java.util.Date(); + for (int i = 1; i <= 100000; i++) { + pstmt.clearParameters(); + pstmt.setLong(1, (long) i); + pstmt.setString(2, "test_" + i); + pstmt.setLong(3, (long) i % 4 + 1); + pstmt.setDate(4, new java.sql.Date(now.getTime())); + pstmt.setString(5, null); + pstmt.setBytes(6, null); + + pstmt.execute(); + if (i % 5000 == 0) { + conn.commit(); + } + } + conn.commit(); + + pstmt.close(); + + // Statement stmt = conn.createStatement(); + // ResultSet rs = stmt.executeQuery("select * from user t where 1=2"); + // + // ResultSetMetaData rsm = rs.getMetaData(); + // int cnt = rsm.getColumnCount(); + // for (int i = 1; i <= cnt; i++) { + // System.out.println(rsm.getColumnName(i) + " " + rsm.getColumnType(i)); + // } + + // rs.close(); + // stmt.close(); + + // PreparedStatement pstmt = conn + // .prepareStatement("insert into tb_user (id,name,role_id,c_time,test1,test2) + // values (?,?,?,?,?,?)"); + // pstmt.setBigDecimal(1, new BigDecimal("5")); + // pstmt.setString(2, "test"); + // pstmt.setBigDecimal(3, new BigDecimal("1")); + // pstmt.setDate(4, new Date(new java.util.Date().getTime())); + // byte[] a = { (byte) 1, (byte) 2 }; + // pstmt.setBytes(5, a); + // pstmt.setBytes(6, a); + // pstmt.execute(); + // + // pstmt.close(); + + conn.close(); + dataSource.close(); + } + + private String clob2Str(Clob clob) { + String content = ""; + try { + Reader is = clob.getCharacterStream(); + BufferedReader buff = new BufferedReader(is); + String line = buff.readLine(); + StringBuffer sb = new StringBuffer(); + while (line != null) { + sb.append(line); + line = buff.readLine(); + } + content = sb.toString(); + } catch (Exception e) { + } + return content; + } +} diff --git a/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/TestConstant.java b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/TestConstant.java new file mode 100644 index 00000000..813f0e85 --- /dev/null +++ b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/TestConstant.java @@ -0,0 +1,37 @@ +package com.alibaba.otter.canal.client.adapter.rdb.test; + +import java.sql.SQLException; + +import com.alibaba.druid.pool.DruidDataSource; + +public class TestConstant { + + public final static String jdbcUrl = "jdbc:mysql://127.0.0.1:3306/mytest?useUnicode=true"; + public final static String jdbcUser = "root"; + public final static String jdbcPassword = "121212"; + + public static DruidDataSource dataSource; + + static { + dataSource = new DruidDataSource(); + dataSource.setDriverClassName("com.mysql.jdbc.Driver"); + dataSource.setUrl(jdbcUrl); + dataSource.setUsername(jdbcUser); + dataSource.setPassword(jdbcPassword); + dataSource.setInitialSize(1); + dataSource.setMinIdle(1); + dataSource.setMaxActive(1); + dataSource.setMaxWait(60000); + dataSource.setTimeBetweenEvictionRunsMillis(60000); + dataSource.setMinEvictableIdleTimeMillis(300000); + dataSource.setPoolPreparedStatements(false); + dataSource.setMaxPoolPreparedStatementPerConnectionSize(20); + dataSource.setValidationQuery("select 1"); + try { + dataSource.init(); + } catch (SQLException e) { + e.printStackTrace(); + } + } + +} diff --git a/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/sync/Common.java b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/sync/Common.java new file mode 100644 index 00000000..9d2d117d --- /dev/null +++ b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/sync/Common.java @@ -0,0 +1,30 @@ +package com.alibaba.otter.canal.client.adapter.rdb.test.sync; + +import java.util.HashMap; +import java.util.Map; + +import com.alibaba.otter.canal.client.adapter.rdb.RdbAdapter; +import com.alibaba.otter.canal.client.adapter.rdb.test.TestConstant; +import com.alibaba.otter.canal.client.adapter.support.DatasourceConfig; +import com.alibaba.otter.canal.client.adapter.support.OuterAdapterConfig; + +public class Common { + + public static RdbAdapter init() { + DatasourceConfig.DATA_SOURCES.put("defaultDS", TestConstant.dataSource); + + OuterAdapterConfig outerAdapterConfig = new OuterAdapterConfig(); + outerAdapterConfig.setName("rdb"); + outerAdapterConfig.setKey("oracle1"); + Map properties = new HashMap<>(); + properties.put("jdbc.driveClassName", "oracle.jdbc.OracleDriver"); + properties.put("jdbc.url", "jdbc:oracle:thin:@127.0.0.1:49161:XE"); + properties.put("jdbc.username", "mytest"); + properties.put("jdbc.password", "m121212"); + outerAdapterConfig.setProperties(properties); + + RdbAdapter adapter = new RdbAdapter(); + adapter.init(outerAdapterConfig); + return adapter; + } +} diff --git a/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/sync/OracleSyncTest.java b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/sync/OracleSyncTest.java new file mode 100644 index 00000000..5ea374e2 --- /dev/null +++ b/client-adapter/rdb/src/test/java/com/alibaba/otter/canal/client/adapter/rdb/test/sync/OracleSyncTest.java @@ -0,0 +1,64 @@ +package com.alibaba.otter.canal.client.adapter.rdb.test.sync; + +import java.util.*; + +import org.junit.Before; +import org.junit.Test; + +import com.alibaba.otter.canal.client.adapter.rdb.RdbAdapter; +import com.alibaba.otter.canal.client.adapter.support.Dml; + +public class OracleSyncTest { + + private RdbAdapter rdbAdapter; + + @Before + public void init() { + rdbAdapter = Common.init(); + } + + @Test + public void test01() { + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("INSERT"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("name", "Eric"); + data.put("role_id", 1L); + data.put("c_time", new Date()); + data.put("test1", "sdfasdfawe中国asfwef"); + dml.setData(dataList); + + rdbAdapter.sync(Collections.singletonList(dml)); + } + + @Test + public void test02() { + Dml dml = new Dml(); + dml.setDestination("example"); + dml.setTs(new Date().getTime()); + dml.setType("UPDATE"); + dml.setDatabase("mytest"); + dml.setTable("user"); + List> dataList = new ArrayList<>(); + Map data = new LinkedHashMap<>(); + dataList.add(data); + data.put("id", 1L); + data.put("name", "Eric2"); + dml.setData(dataList); + List> oldList = new ArrayList<>(); + Map old = new LinkedHashMap<>(); + oldList.add(old); + old.put("name", "Eric"); + dml.setOld(oldList); + + rdbAdapter.sync(Collections.singletonList(dml)); + } + +} diff --git a/client-adapter/rdb/src/test/resources/log4j2-test.xml b/client-adapter/rdb/src/test/resources/log4j2-test.xml new file mode 100644 index 00000000..9c3d2ee6 --- /dev/null +++ b/client-adapter/rdb/src/test/resources/log4j2-test.xml @@ -0,0 +1,13 @@ + + + + + + + + + + + + + \ No newline at end of file diff --git a/client-adapter/rdb/src/test/resources/logback-test.xml b/client-adapter/rdb/src/test/resources/logback-test.xml new file mode 100644 index 00000000..91f0de80 --- /dev/null +++ b/client-adapter/rdb/src/test/resources/logback-test.xml @@ -0,0 +1,13 @@ + + + + + %d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{56} - %msg%n + + + + + + + + \ No newline at end of file diff --git a/client-adapter/rdb/src/test/resources/rdb/mytest_user.yml b/client-adapter/rdb/src/test/resources/rdb/mytest_user.yml new file mode 100644 index 00000000..9b40dd75 --- /dev/null +++ b/client-adapter/rdb/src/test/resources/rdb/mytest_user.yml @@ -0,0 +1,17 @@ +dataSourceKey: defaultDS +destination: example +outerAdapterKey: oracle1 +concurrent: true +dbMapping: + database: mytest + table: user + targetTable: mytest.tb_user + targetPk: + id: id + mapAll: true +# targetColumns: +# id: +# name: +# role_id: +# c_time: +# test1: \ No newline at end of file diff --git a/client/pom.xml b/client/pom.xml index c736b141..3d029080 100644 --- a/client/pom.xml +++ b/client/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter @@ -15,15 +15,182 @@ com.alibaba.otter canal.protocol ${project.version} + true + + + + com.google.protobuf + protobuf-java + + + + + io.netty + netty-all + + + + org.apache.zookeeper + zookeeper + + + com.101tec + zkclient + + + + commons-io + commons-io + + + commons-lang + commons-lang + + + commons-codec + commons-codec + + + com.alibaba + fastjson + + + com.google.guava + guava + + + + ch.qos.logback + logback-core + + + ch.qos.logback + logback-classic + + + org.slf4j + jcl-over-slf4j + + + org.slf4j + slf4j-api + + + org.springframework + spring-core + + + org.springframework + spring-aop + + + org.springframework + spring-context + + + org.springframework + spring-jdbc + + + org.springframework + spring-orm + + + org.springframework + spring-test + ${spring_version} + test + + + org.apache.rocketmq + rocketmq-client + + + + org.apache.kafka + kafka-clients + 1.1.1 + provided junit junit + test + + + com.aliyun.openservices + aliware-apache-rocketmq-cloud - + + + + + org.apache.maven.plugins + maven-shade-plugin + 2.4.1 + + false + + + org.apache.zookeeper:zookeeper + com.101tec:zkclient + commons-io:commons-io + commons-lang:commons-lang + commons-codec:commons-codec + com.alibaba:fastjson + ch.qos.logback:logback-core + ch.qos.logback:logback-classic + org.slf4j:jcl-over-slf4j + org.slf4j:slf4j-api + org.springframework:* + org.jboss.netty:netty + commons-logging:commons-logging + aopalliance:aopalliance + com.google.protobuf:protobuf-java + com.google.code.findbugs:jsr305 + io.netty:* + junit:junit + + + + + + package + + shade + + + + + com.google.guava + com.alibaba.google.guava + + + org.joda + com.alibaba.google.joda + + + com.google.common + com.alibaba.google.common + + + com.google.thirdparty + com.alibaba.google.thirdparty + + + + + + + + + + + + dev @@ -91,7 +258,7 @@ ${project.build.directory}/apidocs true scm:git:git@github.com:alibaba/canal.git - gh-pages + gh-pages diff --git a/client/src/main/java/com/alibaba/otter/canal/client/CanalConnector.java b/client/src/main/java/com/alibaba/otter/canal/client/CanalConnector.java index 8e52333d..7f3eeb80 100644 --- a/client/src/main/java/com/alibaba/otter/canal/client/CanalConnector.java +++ b/client/src/main/java/com/alibaba/otter/canal/client/CanalConnector.java @@ -149,11 +149,4 @@ public interface CanalConnector { * @throws CanalClientException */ void rollback() throws CanalClientException; - - /** - * 中断的阻塞,用于优雅停止client - * - * @throws CanalClientException - */ - void stopRunning() throws CanalClientException; } diff --git a/client/src/main/java/com/alibaba/otter/canal/client/CanalMQConnector.java b/client/src/main/java/com/alibaba/otter/canal/client/CanalMQConnector.java new file mode 100644 index 00000000..8ad86022 --- /dev/null +++ b/client/src/main/java/com/alibaba/otter/canal/client/CanalMQConnector.java @@ -0,0 +1,91 @@ +package com.alibaba.otter.canal.client; + +import java.util.List; +import java.util.concurrent.TimeUnit; + +import com.alibaba.otter.canal.protocol.FlatMessage; +import com.alibaba.otter.canal.protocol.Message; +import com.alibaba.otter.canal.protocol.exception.CanalClientException; + +/** + * canal MQ数据操作客户端 + * + *
    + * 1. canal server写入MQ消息,考虑性能会合并多条数据写入为一个MQ消息,一个Message对应一个MQ消息
    + * 2. canal client消费MQ消息,因为client性能会弱于server的写入,MQ数据获取时会拿到堆积的多条MQ消息,会拿到List
    + * 3. client的ack/rollback,都是和MQ直接交互,不存在对应的batchId概念
    + * 
    + * + * @author agapple 2018年10月28日 下午6:42:27 + * @since 1.1.1 + */ +public interface CanalMQConnector extends CanalConnector { + + /** + * 获取数据,自动进行确认,设置timeout时间直到拿到数据为止 + * + *
    +     * 该方法返回的条件:
    +     *  a. 如果timeout=0,有多少取多少,不会阻塞等待
    +     *  b. 如果timeout不为0,尝试阻塞对应的超时时间,直到拿到数据就返回
    +     * 
    + * + * @return + * @throws CanalClientException + */ + List getList(Long timeout, TimeUnit unit) throws CanalClientException; + + /** + * 获取数据,设置timeout时间直到拿到数据为止 + * + *
    +     * 该方法返回的条件:
    +     *  a. 如果timeout=0,有多少取多少,不会阻塞等待
    +     *  b. 如果timeout不为0,尝试阻塞对应的超时时间,直到拿到数据就返回
    +     * 
    + * + * @throws CanalClientException + */ + List getListWithoutAck(Long timeout, TimeUnit unit) throws CanalClientException; + + /** + * 获取数据,自动进行确认,设置timeout时间直到拿到数据为止 + * + *
    +     * 该方法返回的条件:
    +     *  a. 如果timeout=0,有多少取多少,不会阻塞等待
    +     *  b. 如果timeout不为0,尝试阻塞对应的超时时间,直到拿到数据就返回
    +     * 
    + * + * @return + * @throws CanalClientException + */ + List getFlatList(Long timeout, TimeUnit unit) throws CanalClientException; + + /** + * 获取数据,设置timeout时间直到拿到数据为止 + * + *
    +     * 该方法返回的条件:
    +     *  a. 如果timeout=0,有多少取多少,不会阻塞等待
    +     *  b. 如果timeout不为0,尝试阻塞对应的超时时间,直到拿到数据就返回
    +     * 
    + * + * @throws CanalClientException + */ + List getFlatListWithoutAck(Long timeout, TimeUnit unit) throws CanalClientException; + + /** + * 消费确认。 + * + * @throws CanalClientException + */ + void ack() throws CanalClientException; + + /** + * 回滚到未进行 {@link #ack} 的地方,下次fetch的时候,可以从最后一个没有 {@link #ack} 的地方开始拿 + * + * @throws CanalClientException + */ + void rollback() throws CanalClientException; +} diff --git a/client/src/main/java/com/alibaba/otter/canal/client/CanalMessageDeserializer.java b/client/src/main/java/com/alibaba/otter/canal/client/CanalMessageDeserializer.java new file mode 100644 index 00000000..9d24a23b --- /dev/null +++ b/client/src/main/java/com/alibaba/otter/canal/client/CanalMessageDeserializer.java @@ -0,0 +1,57 @@ +package com.alibaba.otter.canal.client; + +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.CanalPacket; +import com.alibaba.otter.canal.protocol.CanalPacket.Ack; +import com.alibaba.otter.canal.protocol.CanalPacket.Compression; +import com.alibaba.otter.canal.protocol.Message; +import com.alibaba.otter.canal.protocol.exception.CanalClientException; +import com.google.protobuf.ByteString; + +public class CanalMessageDeserializer { + + public static Message deserializer(byte[] data) { + return deserializer(data, false); + } + + public static Message deserializer(byte[] data, boolean lazyParseEntry) { + try { + if (data == null) { + return null; + } else { + CanalPacket.Packet p = CanalPacket.Packet.parseFrom(data); + switch (p.getType()) { + case MESSAGES: { + if (!p.getCompression().equals(Compression.NONE) + && !p.getCompression().equals(Compression.COMPRESSIONCOMPATIBLEPROTO2)) { + throw new CanalClientException("compression is not supported in this connector"); + } + + CanalPacket.Messages messages = CanalPacket.Messages.parseFrom(p.getBody()); + Message result = new Message(messages.getBatchId()); + if (lazyParseEntry) { + // byteString + result.setRawEntries(messages.getMessagesList()); + result.setRaw(true); + } else { + for (ByteString byteString : messages.getMessagesList()) { + result.addEntry(CanalEntry.Entry.parseFrom(byteString)); + } + result.setRaw(false); + } + return result; + } + case ACK: { + Ack ack = Ack.parseFrom(p.getBody()); + throw new CanalClientException("something goes wrong with reason: " + ack.getErrorMessage()); + } + default: { + throw new CanalClientException("unexpected packet type: " + p.getType()); + } + } + } + } catch (Exception e) { + throw new CanalClientException("deserializer failed", e); + } + } +} diff --git a/client/src/main/java/com/alibaba/otter/canal/client/impl/ClusterCanalConnector.java b/client/src/main/java/com/alibaba/otter/canal/client/impl/ClusterCanalConnector.java index 6ea3a5cd..3fd9c2c5 100644 --- a/client/src/main/java/com/alibaba/otter/canal/client/impl/ClusterCanalConnector.java +++ b/client/src/main/java/com/alibaba/otter/canal/client/impl/ClusterCanalConnector.java @@ -184,7 +184,7 @@ public class ClusterCanalConnector implements CanalConnector { return msg; } catch (Throwable t) { logger.warn(String.format("something goes wrong when getWithoutAck data from server:%s", - currentConnector.getAddress()), t); + currentConnector != null ? currentConnector.getAddress() : "null"), t); times++; restart(); logger.info("restart the connector for next round retry."); @@ -201,7 +201,7 @@ public class ClusterCanalConnector implements CanalConnector { return msg; } catch (Throwable t) { logger.warn(String.format("something goes wrong when getWithoutAck data from server:%s", - currentConnector.getAddress()), t); + currentConnector != null ? currentConnector.getAddress() : "null"), t); times++; restart(); logger.info("restart the connector for next round retry."); @@ -218,8 +218,7 @@ public class ClusterCanalConnector implements CanalConnector { return; } catch (Throwable t) { logger.warn(String.format("something goes wrong when rollbacking data from server:%s", - currentConnector.getAddress()), - t); + currentConnector != null ? currentConnector.getAddress() : "null"), t); times++; restart(); logger.info("restart the connector for next round retry."); @@ -236,8 +235,7 @@ public class ClusterCanalConnector implements CanalConnector { return; } catch (Throwable t) { logger.warn(String.format("something goes wrong when rollbacking data from server:%s", - currentConnector.getAddress()), - t); + currentConnector != null ? currentConnector.getAddress() : "null"), t); times++; restart(); logger.info("restart the connector for next round retry."); @@ -255,8 +253,7 @@ public class ClusterCanalConnector implements CanalConnector { return; } catch (Throwable t) { logger.warn(String.format("something goes wrong when acking data from server:%s", - currentConnector.getAddress()), - t); + currentConnector != null ? currentConnector.getAddress() : "null"), t); times++; restart(); logger.info("restart the connector for next round retry."); diff --git a/client/src/main/java/com/alibaba/otter/canal/client/impl/SimpleCanalConnector.java b/client/src/main/java/com/alibaba/otter/canal/client/impl/SimpleCanalConnector.java index 0feb3a27..4c2211d2 100644 --- a/client/src/main/java/com/alibaba/otter/canal/client/impl/SimpleCanalConnector.java +++ b/client/src/main/java/com/alibaba/otter/canal/client/impl/SimpleCanalConnector.java @@ -18,13 +18,13 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.alibaba.otter.canal.client.CanalConnector; +import com.alibaba.otter.canal.client.CanalMessageDeserializer; import com.alibaba.otter.canal.client.impl.running.ClientRunningData; import com.alibaba.otter.canal.client.impl.running.ClientRunningListener; import com.alibaba.otter.canal.client.impl.running.ClientRunningMonitor; import com.alibaba.otter.canal.common.utils.AddressUtils; import com.alibaba.otter.canal.common.utils.BooleanMutex; import com.alibaba.otter.canal.common.zookeeper.ZkClientx; -import com.alibaba.otter.canal.protocol.CanalEntry.Entry; import com.alibaba.otter.canal.protocol.CanalPacket.Ack; import com.alibaba.otter.canal.protocol.CanalPacket.ClientAck; import com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth; @@ -32,7 +32,6 @@ import com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback; import com.alibaba.otter.canal.protocol.CanalPacket.Compression; import com.alibaba.otter.canal.protocol.CanalPacket.Get; import com.alibaba.otter.canal.protocol.CanalPacket.Handshake; -import com.alibaba.otter.canal.protocol.CanalPacket.Messages; import com.alibaba.otter.canal.protocol.CanalPacket.Packet; import com.alibaba.otter.canal.protocol.CanalPacket.PacketType; import com.alibaba.otter.canal.protocol.CanalPacket.Sub; @@ -71,7 +70,7 @@ public class SimpleCanalConnector implements CanalConnector { private volatile boolean connected = false; // 代表connected是否已正常执行,因为有HA,不代表在工作中 private boolean rollbackOnConnect = true; // 是否在connect链接成功后,自动执行rollback操作 private boolean rollbackOnDisConnect = false; // 是否在connect链接成功后,自动执行rollback操作 - + private boolean lazyParseEntry = false; // 是否自动化解析Entry对象,如果考虑最大化性能可以延后解析 // 读写数据分别使用不同的锁进行控制,减小锁粒度,读也需要排他锁,并发度容易造成数据包混乱,反序列化失败 private Object readDataLock = new Object(); private Object writeDataLock = new Object(); @@ -134,7 +133,7 @@ public class SimpleCanalConnector implements CanalConnector { runningMonitor.stop(); } } else { - doDisconnnect(); + doDisconnect(); } } @@ -159,7 +158,7 @@ public class SimpleCanalConnector implements CanalConnector { } // Handshake handshake = Handshake.parseFrom(p.getBody()); - supportedCompressions.addAll(handshake.getSupportedCompressionsList()); + supportedCompressions.add(handshake.getSupportedCompressions()); // ClientAuth ca = ClientAuth.newBuilder() .setUsername(username != null ? username : "") @@ -191,7 +190,7 @@ public class SimpleCanalConnector implements CanalConnector { } } - private void doDisconnnect() throws CanalClientException { + private void doDisconnect() throws CanalClientException { if (readableChannel != null) { quietlyClose(readableChannel); readableChannel = null; @@ -319,28 +318,8 @@ public class SimpleCanalConnector implements CanalConnector { } private Message receiveMessages() throws IOException { - Packet p = Packet.parseFrom(readNextPacket()); - switch (p.getType()) { - case MESSAGES: { - if (!p.getCompression().equals(Compression.NONE)) { - throw new CanalClientException("compression is not supported in this connector"); - } - - Messages messages = Messages.parseFrom(p.getBody()); - Message result = new Message(messages.getBatchId()); - for (ByteString byteString : messages.getMessagesList()) { - result.addEntry(Entry.parseFrom(byteString)); - } - return result; - } - case ACK: { - Ack ack = Ack.parseFrom(p.getBody()); - throw new CanalClientException("something goes wrong with reason: " + ack.getErrorMessage()); - } - default: { - throw new CanalClientException("unexpected packet type: " + p.getType()); - } - } + byte[] data = readNextPacket(); + return CanalMessageDeserializer.deserializer(data, lazyParseEntry); } public void ack(long batchId) throws CanalClientException { @@ -455,7 +434,7 @@ public class SimpleCanalConnector implements CanalConnector { public void processActiveExit() { mutex.set(false); - doDisconnnect(); + doDisconnect(); } }); @@ -538,6 +517,14 @@ public class SimpleCanalConnector implements CanalConnector { this.filter = filter; } + public boolean isLazyParseEntry() { + return lazyParseEntry; + } + + public void setLazyParseEntry(boolean lazyParseEntry) { + this.lazyParseEntry = lazyParseEntry; + } + public void stopRunning() { if (running) { running = false; // 设置为非running状态 diff --git a/client/src/main/java/com/alibaba/otter/canal/client/impl/running/ClientRunningMonitor.java b/client/src/main/java/com/alibaba/otter/canal/client/impl/running/ClientRunningMonitor.java index 32202dc1..90a9ad71 100644 --- a/client/src/main/java/com/alibaba/otter/canal/client/impl/running/ClientRunningMonitor.java +++ b/client/src/main/java/com/alibaba/otter/canal/client/impl/running/ClientRunningMonitor.java @@ -98,7 +98,7 @@ public class ClientRunningMonitor extends AbstractCanalLifeCycle { String path = ZookeeperPathUtils.getDestinationClientRunning(this.destination, clientData.getClientId()); zkClient.unsubscribeDataChanges(path, dataListener); releaseRunning(); // 尝试一下release - //Fix issue #697 + // Fix issue #697 if (delayExector != null) { delayExector.shutdown(); } diff --git a/client/src/main/java/com/alibaba/otter/canal/client/kafka/KafkaCanalConnector.java b/client/src/main/java/com/alibaba/otter/canal/client/kafka/KafkaCanalConnector.java new file mode 100644 index 00000000..00403374 --- /dev/null +++ b/client/src/main/java/com/alibaba/otter/canal/client/kafka/KafkaCanalConnector.java @@ -0,0 +1,292 @@ +package com.alibaba.otter.canal.client.kafka; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; +import java.util.Properties; +import java.util.concurrent.TimeUnit; + +import org.apache.kafka.clients.consumer.ConsumerRecord; +import org.apache.kafka.clients.consumer.ConsumerRecords; +import org.apache.kafka.clients.consumer.KafkaConsumer; +import org.apache.kafka.common.TopicPartition; +import org.apache.kafka.common.serialization.StringDeserializer; + +import com.alibaba.fastjson.JSON; +import com.alibaba.otter.canal.client.CanalMQConnector; +import com.alibaba.otter.canal.client.impl.SimpleCanalConnector; +import com.alibaba.otter.canal.protocol.FlatMessage; +import com.alibaba.otter.canal.protocol.Message; +import com.alibaba.otter.canal.protocol.exception.CanalClientException; +import com.google.common.collect.Lists; + +/** + * canal kafka 数据操作客户端 + * + *
    + * 注意点:
    + * 1. 相比于canal {@linkplain SimpleCanalConnector}, 这里get和ack操作不能有并发, 必须是一个线程执行get后,内存里执行完毕ack后再取下一个get
    + * 
    + * + * @author machengyuan @ 2018-6-12 + * @version 1.1.1 + */ +public class KafkaCanalConnector implements CanalMQConnector { + + private KafkaConsumer kafkaConsumer; + private KafkaConsumer kafkaConsumer2; // 用于扁平message的数据消费 + private String topic; + private Integer partition; + private Properties properties; + private volatile boolean connected = false; + private volatile boolean running = false; + private boolean flatMessage; + + public KafkaCanalConnector(String servers, String topic, Integer partition, String groupId, Integer batchSize, + boolean flatMessage){ + this.topic = topic; + this.partition = partition; + this.flatMessage = flatMessage; + + properties = new Properties(); + properties.put("bootstrap.servers", servers); + properties.put("group.id", groupId); + properties.put("enable.auto.commit", false); + properties.put("auto.commit.interval.ms", "1000"); + properties.put("auto.offset.reset", "latest"); // 如果没有offset则从最后的offset开始读 + properties.put("request.timeout.ms", "40000"); // 必须大于session.timeout.ms的设置 + properties.put("session.timeout.ms", "30000"); // 默认为30秒 + if (batchSize == null) { + batchSize = 100; + } + properties.put("max.poll.records", batchSize.toString()); + properties.put("key.deserializer", StringDeserializer.class.getName()); + if (!flatMessage) { + properties.put("value.deserializer", MessageDeserializer.class.getName()); + } else { + properties.put("value.deserializer", StringDeserializer.class.getName()); + } + } + + /** + * 打开连接 + */ + public void connect() { + if (connected) { + return; + } + + connected = true; + if (kafkaConsumer == null && !flatMessage) { + kafkaConsumer = new KafkaConsumer(properties); + } + if (kafkaConsumer2 == null && flatMessage) { + kafkaConsumer2 = new KafkaConsumer(properties); + } + } + + /** + * 关闭链接 + */ + public void disconnect() { + if (kafkaConsumer != null) { + kafkaConsumer.close(); + kafkaConsumer = null; + } + if (kafkaConsumer2 != null) { + kafkaConsumer2.close(); + kafkaConsumer2 = null; + } + + connected = false; + } + + private void waitClientRunning() { + running = true; + } + + public boolean checkValid() { + return true;// 默认都放过 + } + + /** + * 订阅topic + */ + public void subscribe() { + waitClientRunning(); + if (!running) { + return; + } + + if (partition == null) { + if (kafkaConsumer != null) { + kafkaConsumer.subscribe(Collections.singletonList(topic)); + } + if (kafkaConsumer2 != null) { + kafkaConsumer2.subscribe(Collections.singletonList(topic)); + } + } else { + TopicPartition topicPartition = new TopicPartition(topic, partition); + if (kafkaConsumer != null) { + kafkaConsumer.assign(Collections.singletonList(topicPartition)); + } + if (kafkaConsumer2 != null) { + kafkaConsumer2.assign(Collections.singletonList(topicPartition)); + } + } + } + + /** + * 取消订阅 + */ + public void unsubscribe() { + waitClientRunning(); + if (!running) { + return; + } + + if (kafkaConsumer != null) { + kafkaConsumer.unsubscribe(); + } + if (kafkaConsumer2 != null) { + kafkaConsumer2.unsubscribe(); + } + } + + @Override + public List getList(Long timeout, TimeUnit unit) throws CanalClientException { + waitClientRunning(); + if (!running) { + return Lists.newArrayList(); + } + + List messages = getListWithoutAck(timeout, unit); + if (messages != null && !messages.isEmpty()) { + this.ack(); + } + return messages; + } + + @Override + public List getListWithoutAck(Long timeout, TimeUnit unit) throws CanalClientException { + waitClientRunning(); + if (!running) { + return Lists.newArrayList(); + } + + ConsumerRecords records = kafkaConsumer.poll(unit.toMillis(timeout)); + + if (!records.isEmpty()) { + List messages = new ArrayList<>(); + for (ConsumerRecord record : records) { + messages.add(record.value()); + } + return messages; + } + return Lists.newArrayList(); + } + + @Override + public List getFlatList(Long timeout, TimeUnit unit) throws CanalClientException { + waitClientRunning(); + if (!running) { + return Lists.newArrayList(); + } + + List messages = getFlatListWithoutAck(timeout, unit); + if (messages != null && !messages.isEmpty()) { + this.ack(); + } + return messages; + } + + @Override + public List getFlatListWithoutAck(Long timeout, TimeUnit unit) throws CanalClientException { + waitClientRunning(); + if (!running) { + return Lists.newArrayList(); + } + + ConsumerRecords records = kafkaConsumer2.poll(unit.toMillis(timeout)); + if (!records.isEmpty()) { + List flatMessages = new ArrayList<>(); + for (ConsumerRecord record : records) { + String flatMessageJson = record.value(); + FlatMessage flatMessage = JSON.parseObject(flatMessageJson, FlatMessage.class); + flatMessages.add(flatMessage); + } + + return flatMessages; + } + return Lists.newArrayList(); + } + + @Override + public void rollback() throws CanalClientException { + } + + /** + * 提交offset,如果超过 session.timeout.ms 设置的时间没有ack则会抛出异常,ack失败 + */ + public void ack() { + waitClientRunning(); + if (!running) { + return; + } + + if (kafkaConsumer != null) { + kafkaConsumer.commitSync(); + } + if (kafkaConsumer2 != null) { + kafkaConsumer2.commitSync(); + } + } + + @Override + public void subscribe(String filter) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public Message get(int batchSize) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public Message get(int batchSize, Long timeout, TimeUnit unit) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public Message getWithoutAck(int batchSize) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public Message getWithoutAck(int batchSize, Long timeout, TimeUnit unit) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public void ack(long batchId) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public void rollback(long batchId) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + /** + * 重新设置sessionTime + * + * @param timeout + * @param unit + */ + public void setSessionTimeout(Long timeout, TimeUnit unit) { + long t = unit.toMillis(timeout); + properties.put("request.timeout.ms", String.valueOf(t + 60000)); + properties.put("session.timeout.ms", String.valueOf(t)); + } + +} diff --git a/client/src/main/java/com/alibaba/otter/canal/client/kafka/MessageDeserializer.java b/client/src/main/java/com/alibaba/otter/canal/client/kafka/MessageDeserializer.java new file mode 100644 index 00000000..6b78e0e4 --- /dev/null +++ b/client/src/main/java/com/alibaba/otter/canal/client/kafka/MessageDeserializer.java @@ -0,0 +1,31 @@ +package com.alibaba.otter.canal.client.kafka; + +import java.util.Map; + +import org.apache.kafka.common.serialization.Deserializer; + +import com.alibaba.otter.canal.client.CanalMessageDeserializer; +import com.alibaba.otter.canal.protocol.Message; + +/** + * Kafka Message类的反序列化 + * + * @author machengyuan @ 2018-6-12 + * @version 1.0.0 + */ +public class MessageDeserializer implements Deserializer { + + @Override + public void configure(Map configs, boolean isKey) { + } + + @Override + public Message deserialize(String topic1, byte[] data) { + return CanalMessageDeserializer.deserializer(data); + } + + @Override + public void close() { + // nothing to do + } +} diff --git a/client/src/main/java/com/alibaba/otter/canal/client/rocketmq/ConsumerBatchMessage.java b/client/src/main/java/com/alibaba/otter/canal/client/rocketmq/ConsumerBatchMessage.java new file mode 100644 index 00000000..1def9163 --- /dev/null +++ b/client/src/main/java/com/alibaba/otter/canal/client/rocketmq/ConsumerBatchMessage.java @@ -0,0 +1,48 @@ +package com.alibaba.otter.canal.client.rocketmq; + +import java.util.List; +import java.util.concurrent.CountDownLatch; +import java.util.concurrent.TimeUnit; + +public class ConsumerBatchMessage { + + private final List data; + private CountDownLatch latch; + private boolean hasFailure = false; + + public ConsumerBatchMessage(List data){ + this.data = data; + latch = new CountDownLatch(1); + } + + public boolean waitFinish(long timeout) throws InterruptedException { + return latch.await(timeout, TimeUnit.MILLISECONDS); + } + + public boolean isSuccess() { + return !hasFailure; + } + + public List getData() { + return data; + } + + /** + * Countdown if the sub message is successful. + */ + public void ack() { + latch.countDown(); + } + + /** + * Countdown and fail-fast if the sub message is failed. + */ + public void fail() { + hasFailure = true; + // fail fast + long count = latch.getCount(); + for (int i = 0; i < count; i++) { + latch.countDown(); + } + } +} diff --git a/client/src/main/java/com/alibaba/otter/canal/client/rocketmq/RocketMQCanalConnector.java b/client/src/main/java/com/alibaba/otter/canal/client/rocketmq/RocketMQCanalConnector.java new file mode 100644 index 00000000..05849e43 --- /dev/null +++ b/client/src/main/java/com/alibaba/otter/canal/client/rocketmq/RocketMQCanalConnector.java @@ -0,0 +1,293 @@ +package com.alibaba.otter.canal.client.rocketmq; + +import com.aliyun.openservices.apache.api.impl.authority.SessionCredentials; +import com.aliyun.openservices.apache.api.impl.rocketmq.ClientRPCHook; +import java.util.List; +import java.util.concurrent.BlockingQueue; +import java.util.concurrent.LinkedBlockingQueue; +import java.util.concurrent.TimeUnit; + +import org.apache.commons.lang.StringUtils; +import org.apache.rocketmq.client.consumer.DefaultMQPushConsumer; +import org.apache.rocketmq.client.consumer.listener.ConsumeOrderlyContext; +import org.apache.rocketmq.client.consumer.listener.ConsumeOrderlyStatus; +import org.apache.rocketmq.client.consumer.listener.MessageListenerOrderly; +import org.apache.rocketmq.client.consumer.rebalance.AllocateMessageQueueAveragely; +import org.apache.rocketmq.client.exception.MQClientException; +import org.apache.rocketmq.common.message.MessageExt; +import org.apache.rocketmq.remoting.RPCHook; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.fastjson.JSON; +import com.alibaba.otter.canal.client.CanalMQConnector; +import com.alibaba.otter.canal.client.CanalMessageDeserializer; +import com.alibaba.otter.canal.client.impl.SimpleCanalConnector; +import com.alibaba.otter.canal.protocol.FlatMessage; +import com.alibaba.otter.canal.protocol.Message; +import com.alibaba.otter.canal.protocol.exception.CanalClientException; +import com.google.common.collect.Lists; + +/** + * RocketMQ的连接 + * + *
    + * 注意点:
    + * 1. 相比于canal {@linkplain SimpleCanalConnector}, 这里get和ack操作不能有并发, 必须是一个线程执行get后,内存里执行完毕ack后再取下一个get
    + * 
    + * + * @since 1.1.1 + */ +public class RocketMQCanalConnector implements CanalMQConnector { + + private static final Logger logger = LoggerFactory.getLogger(RocketMQCanalConnector.class); + + private String nameServer; + private String topic; + private String groupName; + private volatile boolean connected = false; + private DefaultMQPushConsumer rocketMQConsumer; + private BlockingQueue messageBlockingQueue; + private long batchProcessTimeout = 60 * 1000; + private boolean flatMessage; + private volatile ConsumerBatchMessage lastGetBatchMessage = null; + private String accessKey; + private String secretKey; + + + public RocketMQCanalConnector(String nameServer, String topic, String groupName, boolean flatMessage){ + this.nameServer = nameServer; + this.topic = topic; + this.groupName = groupName; + this.flatMessage = flatMessage; + this.messageBlockingQueue = new LinkedBlockingQueue<>(1024); + } + + public RocketMQCanalConnector(String nameServer, String topic, String groupName, + String accessKey, String secretKey, boolean flatMessage){ + this(nameServer, topic, groupName, flatMessage); + this.accessKey = accessKey; + this.secretKey = secretKey; + } + + public void connect() throws CanalClientException { + + RPCHook rpcHook = null; + if(null != accessKey && accessKey.length() > 0 + && null != secretKey && secretKey.length() > 0){ + SessionCredentials sessionCredentials = new SessionCredentials(); + sessionCredentials.setAccessKey(accessKey); + sessionCredentials.setSecretKey(secretKey); + rpcHook = new ClientRPCHook(sessionCredentials); + } + rocketMQConsumer = new DefaultMQPushConsumer(groupName, rpcHook, new AllocateMessageQueueAveragely()); + rocketMQConsumer.setVipChannelEnabled(false); + if (!StringUtils.isBlank(nameServer)) { + rocketMQConsumer.setNamesrvAddr(nameServer); + } + } + + public void disconnect() throws CanalClientException { + rocketMQConsumer.shutdown(); + connected = false; + } + + public boolean checkValid() throws CanalClientException { + return connected; + } + + public synchronized void subscribe(String filter) throws CanalClientException { + if (connected) { + return; + } + try { + if (rocketMQConsumer == null) { + this.connect(); + } + rocketMQConsumer.subscribe(this.topic, "*"); + rocketMQConsumer.registerMessageListener(new MessageListenerOrderly() { + + @Override + public ConsumeOrderlyStatus consumeMessage(List messageExts, ConsumeOrderlyContext context) { + context.setAutoCommit(true); + boolean isSuccess = process(messageExts); + if (isSuccess) { + return ConsumeOrderlyStatus.SUCCESS; + } else { + return ConsumeOrderlyStatus.SUSPEND_CURRENT_QUEUE_A_MOMENT; + } + } + }); + rocketMQConsumer.start(); + } catch (MQClientException ex) { + connected = false; + logger.error("Start RocketMQ consumer error", ex); + } + connected = true; + } + + private boolean process(List messageExts) { + logger.info("Get Message:{}", messageExts); + List messageList = Lists.newArrayList(); + for (MessageExt messageExt : messageExts) { + byte[] data = messageExt.getBody(); + if (data != null) { + try { + if (!flatMessage) { + Message message = CanalMessageDeserializer.deserializer(data); + messageList.add(message); + } else { + FlatMessage flatMessage = JSON.parseObject(data, FlatMessage.class); + messageList.add(flatMessage); + } + } catch (Exception ex) { + logger.error("Add message error", ex); + throw new CanalClientException(ex); + } + } else { + logger.warn("Received message data is null"); + } + } + ConsumerBatchMessage batchMessage; + if (!flatMessage) { + batchMessage = new ConsumerBatchMessage(messageList); + } else { + batchMessage = new ConsumerBatchMessage(messageList); + } + try { + messageBlockingQueue.put(batchMessage); + } catch (InterruptedException e) { + logger.error("Put message to queue error", e); + throw new RuntimeException(e); + } + boolean isCompleted; + try { + isCompleted = batchMessage.waitFinish(batchProcessTimeout); + } catch (InterruptedException e) { + logger.error("Interrupted when waiting messages to be finished.", e); + throw new RuntimeException(e); + } + boolean isSuccess = batchMessage.isSuccess(); + return isCompleted && isSuccess; + } + + public void subscribe() throws CanalClientException { + this.subscribe(null); + } + + public void unsubscribe() throws CanalClientException { + this.rocketMQConsumer.unsubscribe(this.topic); + } + + @Override + public List getList(Long timeout, TimeUnit unit) throws CanalClientException { + List messages = getListWithoutAck(timeout, unit); + if (messages != null && !messages.isEmpty()) { + ack(); + } + return messages; + } + + @Override + public List getListWithoutAck(Long timeout, TimeUnit unit) throws CanalClientException { + try { + if (this.lastGetBatchMessage != null) { + throw new CanalClientException("mq get/ack not support concurrent & async ack"); + } + + ConsumerBatchMessage batchMessage = messageBlockingQueue.poll(timeout, unit); + if (batchMessage != null) { + this.lastGetBatchMessage = batchMessage; + return batchMessage.getData(); + } + } catch (InterruptedException ex) { + logger.warn("Get message timeout", ex); + throw new CanalClientException("Failed to fetch the data after: " + timeout); + } + return Lists.newArrayList(); + } + + @Override + public List getFlatList(Long timeout, TimeUnit unit) throws CanalClientException { + List messages = getFlatListWithoutAck(timeout, unit); + if (messages != null && !messages.isEmpty()) { + ack(); + } + return messages; + } + + @Override + public List getFlatListWithoutAck(Long timeout, TimeUnit unit) throws CanalClientException { + try { + if (this.lastGetBatchMessage != null) { + throw new CanalClientException("mq get/ack not support concurrent & async ack"); + } + + ConsumerBatchMessage batchMessage = messageBlockingQueue.poll(timeout, unit); + if (batchMessage != null) { + this.lastGetBatchMessage = batchMessage; + return batchMessage.getData(); + } + } catch (InterruptedException ex) { + logger.warn("Get message timeout", ex); + throw new CanalClientException("Failed to fetch the data after: " + timeout); + } + return Lists.newArrayList(); + } + + @Override + public void ack() throws CanalClientException { + try { + if (this.lastGetBatchMessage != null) { + this.lastGetBatchMessage.ack(); + } + } catch (Throwable e) { + if (this.lastGetBatchMessage != null) { + this.lastGetBatchMessage.fail(); + } + } finally { + this.lastGetBatchMessage = null; + } + } + + @Override + public void rollback() throws CanalClientException { + try { + if (this.lastGetBatchMessage != null) { + this.lastGetBatchMessage.fail(); + } + } finally { + this.lastGetBatchMessage = null; + } + } + + public Message get(int batchSize) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public Message get(int batchSize, Long timeout, TimeUnit unit) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public Message getWithoutAck(int batchSize) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public Message getWithoutAck(int batchSize, Long timeout, TimeUnit unit) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public void ack(long batchId) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + + @Override + public void rollback(long batchId) throws CanalClientException { + throw new CanalClientException("mq not support this method"); + } + +} diff --git a/kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/AbstractKafkaTest.java b/client/src/test/java/com/alibaba/otter/canal/client/running/kafka/AbstractKafkaTest.java similarity index 92% rename from kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/AbstractKafkaTest.java rename to client/src/test/java/com/alibaba/otter/canal/client/running/kafka/AbstractKafkaTest.java index 22dda072..473baf67 100644 --- a/kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/AbstractKafkaTest.java +++ b/client/src/test/java/com/alibaba/otter/canal/client/running/kafka/AbstractKafkaTest.java @@ -1,4 +1,4 @@ -package com.alibaba.otter.canal.kafka.client.running; +package com.alibaba.otter.canal.client.running.kafka; import org.junit.Assert; diff --git a/kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/CanalKafkaClientExample.java b/client/src/test/java/com/alibaba/otter/canal/client/running/kafka/CanalKafkaClientExample.java similarity index 59% rename from kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/CanalKafkaClientExample.java rename to client/src/test/java/com/alibaba/otter/canal/client/running/kafka/CanalKafkaClientExample.java index f4a0afc5..c72b229d 100644 --- a/kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/CanalKafkaClientExample.java +++ b/client/src/test/java/com/alibaba/otter/canal/client/running/kafka/CanalKafkaClientExample.java @@ -1,5 +1,6 @@ -package com.alibaba.otter.canal.kafka.client.running; +package com.alibaba.otter.canal.client.running.kafka; +import java.util.List; import java.util.concurrent.TimeUnit; import org.apache.kafka.common.errors.WakeupException; @@ -7,8 +8,7 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.util.Assert; -import com.alibaba.otter.canal.kafka.client.KafkaCanalConnector; -import com.alibaba.otter.canal.kafka.client.KafkaCanalConnectors; +import com.alibaba.otter.canal.client.kafka.KafkaCanalConnector; import com.alibaba.otter.canal.protocol.Message; /** @@ -19,32 +19,33 @@ import com.alibaba.otter.canal.protocol.Message; */ public class CanalKafkaClientExample { - protected final static Logger logger = LoggerFactory.getLogger(CanalKafkaClientExample.class); + protected final static Logger logger = LoggerFactory.getLogger(CanalKafkaClientExample.class); - private KafkaCanalConnector connector; + private KafkaCanalConnector connector; - private static volatile boolean running = false; + private static volatile boolean running = false; - private Thread thread = null; + private Thread thread = null; private Thread.UncaughtExceptionHandler handler = new Thread.UncaughtExceptionHandler() { - public void uncaughtException(Thread t, Throwable e) { - logger.error("parse events has an error", e); - } - }; + public void uncaughtException(Thread t, Throwable e) { + logger.error("parse events has an error", e); + } + }; - public CanalKafkaClientExample(String zkServers, String servers, String topic, Integer partition, String groupId) { - connector = KafkaCanalConnectors.newKafkaConnector(zkServers, servers, topic, partition, groupId); + public CanalKafkaClientExample(String zkServers, String servers, String topic, Integer partition, String groupId){ + connector = new KafkaCanalConnector(servers, topic, partition, groupId, null, false); } public static void main(String[] args) { try { - final CanalKafkaClientExample kafkaCanalClientExample = new CanalKafkaClientExample(AbstractKafkaTest.zkServers, - AbstractKafkaTest.servers, - AbstractKafkaTest.topic, - AbstractKafkaTest.partition, - AbstractKafkaTest.groupId); + final CanalKafkaClientExample kafkaCanalClientExample = new CanalKafkaClientExample( + AbstractKafkaTest.zkServers, + AbstractKafkaTest.servers, + AbstractKafkaTest.topic, + AbstractKafkaTest.partition, + AbstractKafkaTest.groupId); logger.info("## start the kafka consumer: {}-{}", AbstractKafkaTest.topic, AbstractKafkaTest.groupId); kafkaCanalClientExample.start(); logger.info("## the canal kafka consumer is running now ......"); @@ -87,7 +88,6 @@ public class CanalKafkaClientExample { if (!running) { return; } - connector.stopRunning(); running = false; if (thread != null) { try { @@ -107,21 +107,23 @@ public class CanalKafkaClientExample { connector.subscribe(); while (running) { try { - Message message = connector.getWithoutAck(1L, TimeUnit.SECONDS); // 获取message - if (message == null) { + List messages = connector.getListWithoutAck(100L, TimeUnit.MILLISECONDS); // 获取message + if (messages == null) { continue; } - long batchId = message.getId(); - int size = message.getEntries().size(); - if (batchId == -1 || size == 0) { - // try { - // Thread.sleep(1000); - // } catch (InterruptedException e) { - // } - } else { - // printSummary(message, batchId, size); - // printEntry(message.getEntries()); - logger.info(message.toString()); + for (Message message : messages) { + long batchId = message.getId(); + int size = message.getEntries().size(); + if (batchId == -1 || size == 0) { + // try { + // Thread.sleep(1000); + // } catch (InterruptedException e) { + // } + } else { + // printSummary(message, batchId, size); + // printEntry(message.getEntries()); + logger.info(message.toString()); + } } connector.ack(); // 提交确认 @@ -139,6 +141,6 @@ public class CanalKafkaClientExample { } catch (WakeupException e) { // No-op. Continue process } - connector.disconnnect(); + connector.disconnect(); } } diff --git a/kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/KafkaClientRunningTest.java b/client/src/test/java/com/alibaba/otter/canal/client/running/kafka/KafkaClientRunningTest.java similarity index 71% rename from kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/KafkaClientRunningTest.java rename to client/src/test/java/com/alibaba/otter/canal/client/running/kafka/KafkaClientRunningTest.java index d8ff6d30..9133f74c 100644 --- a/kafka-client/src/test/java/com/alibaba/otter/canal/kafka/client/running/KafkaClientRunningTest.java +++ b/client/src/test/java/com/alibaba/otter/canal/client/running/kafka/KafkaClientRunningTest.java @@ -1,5 +1,6 @@ -package com.alibaba.otter.canal.kafka.client.running; +package com.alibaba.otter.canal.client.running.kafka; +import java.util.List; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.TimeUnit; @@ -9,8 +10,7 @@ import org.junit.Test; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import com.alibaba.otter.canal.kafka.client.KafkaCanalConnector; -import com.alibaba.otter.canal.kafka.client.KafkaCanalConnectors; +import com.alibaba.otter.canal.client.kafka.KafkaCanalConnector; import com.alibaba.otter.canal.protocol.Message; /** @@ -29,7 +29,7 @@ public class KafkaClientRunningTest extends AbstractKafkaTest { public void testKafkaConsumer() { final ExecutorService executor = Executors.newFixedThreadPool(1); - final KafkaCanalConnector connector = KafkaCanalConnectors.newKafkaConnector(servers, topic, partition, groupId); + final KafkaCanalConnector connector = new KafkaCanalConnector(servers, topic, partition, groupId, null, false); executor.submit(new Runnable() { @@ -39,9 +39,9 @@ public class KafkaClientRunningTest extends AbstractKafkaTest { connector.subscribe(); while (running) { try { - Message message = connector.getWithoutAck(3L, TimeUnit.SECONDS); - if (message != null) { - System.out.println(message); + List messages = connector.getList(3L, TimeUnit.SECONDS); + if (messages != null) { + System.out.println(messages); } connector.ack(); } catch (WakeupException e) { @@ -49,7 +49,7 @@ public class KafkaClientRunningTest extends AbstractKafkaTest { } } connector.unsubscribe(); - connector.disconnnect(); + connector.disconnect(); } }); diff --git a/client/src/test/java/com/alibaba/otter/canal/client/running/rocketmq/AbstractRocektMQTest.java b/client/src/test/java/com/alibaba/otter/canal/client/running/rocketmq/AbstractRocektMQTest.java new file mode 100644 index 00000000..1b4e35d5 --- /dev/null +++ b/client/src/test/java/com/alibaba/otter/canal/client/running/rocketmq/AbstractRocektMQTest.java @@ -0,0 +1,9 @@ +package com.alibaba.otter.canal.client.running.rocketmq; + +public class AbstractRocektMQTest { + + public static String topic = "example"; + public static String groupId = "group"; + public static String nameServers = "localhost:9876"; + +} diff --git a/client/src/test/java/com/alibaba/otter/canal/client/running/rocketmq/CanalRocketMQClientExample.java b/client/src/test/java/com/alibaba/otter/canal/client/running/rocketmq/CanalRocketMQClientExample.java new file mode 100644 index 00000000..08d53116 --- /dev/null +++ b/client/src/test/java/com/alibaba/otter/canal/client/running/rocketmq/CanalRocketMQClientExample.java @@ -0,0 +1,137 @@ +package com.alibaba.otter.canal.client.running.rocketmq; + +import java.util.List; +import java.util.concurrent.TimeUnit; + +import org.apache.kafka.common.errors.WakeupException; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.util.Assert; + +import com.alibaba.otter.canal.client.rocketmq.RocketMQCanalConnector; +import com.alibaba.otter.canal.client.running.kafka.AbstractKafkaTest; +import com.alibaba.otter.canal.protocol.Message; + +/** + * Kafka client example + * + * @author machengyuan @ 2018-6-12 + * @version 1.0.0 + */ +public class CanalRocketMQClientExample extends AbstractRocektMQTest { + + protected final static Logger logger = LoggerFactory.getLogger(CanalRocketMQClientExample.class); + + private RocketMQCanalConnector connector; + + private static volatile boolean running = false; + + private Thread thread = null; + + private Thread.UncaughtExceptionHandler handler = new Thread.UncaughtExceptionHandler() { + + public void uncaughtException(Thread t, Throwable e) { + logger.error("parse events has an error", e); + } + }; + + public CanalRocketMQClientExample(String nameServers, String topic, String groupId){ + connector = new RocketMQCanalConnector(nameServers, topic, groupId, false); + } + + public static void main(String[] args) { + try { + final CanalRocketMQClientExample rocketMQClientExample = new CanalRocketMQClientExample(nameServers, + topic, + groupId); + logger.info("## Start the rocketmq consumer: {}-{}", AbstractKafkaTest.topic, AbstractKafkaTest.groupId); + rocketMQClientExample.start(); + logger.info("## The canal rocketmq consumer is running now ......"); + Runtime.getRuntime().addShutdownHook(new Thread() { + + public void run() { + try { + logger.info("## Stop the rocketmq consumer"); + rocketMQClientExample.stop(); + } catch (Throwable e) { + logger.warn("## Something goes wrong when stopping rocketmq consumer:", e); + } finally { + logger.info("## Rocketmq consumer is down."); + } + } + + }); + while (running) + ; + } catch (Throwable e) { + logger.error("## Something going wrong when starting up the rocketmq consumer:", e); + System.exit(0); + } + } + + public void start() { + Assert.notNull(connector, "connector is null"); + thread = new Thread(new Runnable() { + + public void run() { + process(); + } + }); + thread.setUncaughtExceptionHandler(handler); + thread.start(); + running = true; + } + + public void stop() { + if (!running) { + return; + } + running = false; + if (thread != null) { + try { + thread.join(); + } catch (InterruptedException e) { + // ignore + } + } + } + + private void process() { + while (!running) + ; + while (running) { + try { + connector.connect(); + connector.subscribe(); + while (running) { + List messages = connector.getListWithoutAck(100L, TimeUnit.MILLISECONDS); // 获取message + for (Message message : messages) { + long batchId = message.getId(); + int size = message.getEntries().size(); + if (batchId == -1 || size == 0) { + // try { + // Thread.sleep(1000); + // } catch (InterruptedException e) { + // } + } else { + // printSummary(message, batchId, size); + // printEntry(message.getEntries()); + logger.info(message.toString()); + } + } + + connector.ack(); // 提交确认 + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + + try { + connector.unsubscribe(); + } catch (WakeupException e) { + // No-op. Continue process + } +// connector.stopRunning(); + } +} diff --git a/common/pom.xml b/common/pom.xml index 9c57c560..9d6777b3 100644 --- a/common/pom.xml +++ b/common/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml canal.common @@ -83,6 +83,10 @@ org.springframework spring-orm + + com.google.code.findbugs + jsr305 + org.springframework spring-test diff --git a/common/src/main/java/com/alibaba/otter/canal/common/utils/BooleanMutex.java b/common/src/main/java/com/alibaba/otter/canal/common/utils/BooleanMutex.java index d729ad01..3a2ee258 100644 --- a/common/src/main/java/com/alibaba/otter/canal/common/utils/BooleanMutex.java +++ b/common/src/main/java/com/alibaba/otter/canal/common/utils/BooleanMutex.java @@ -5,7 +5,7 @@ import java.util.concurrent.TimeoutException; import java.util.concurrent.locks.AbstractQueuedSynchronizer; /** - * 实现一个互斥实现,基于Cocurrent中的{@linkplain AbstractQueuedSynchronizer}实现了自己的sync
    + * 实现一个互斥实现,基于Cocurrent中的AQS实现了自己的sync
    * 应用场景:系统初始化/授权控制,没权限时阻塞等待。有权限时所有线程都可以快速通过 * *
    diff --git a/common/src/main/java/com/alibaba/otter/canal/common/utils/NamedThreadFactory.java b/common/src/main/java/com/alibaba/otter/canal/common/utils/NamedThreadFactory.java
    index 866664a1..eeb94c4a 100644
    --- a/common/src/main/java/com/alibaba/otter/canal/common/utils/NamedThreadFactory.java
    +++ b/common/src/main/java/com/alibaba/otter/canal/common/utils/NamedThreadFactory.java
    @@ -23,6 +23,11 @@ public class NamedThreadFactory implements ThreadFactory {
     
                                                                            public void uncaughtException(Thread t,
                                                                                                          Throwable e) {
    +                                                                           if (e instanceof InterruptedException
    +                                                                               || (e.getCause() != null && e.getCause() instanceof InterruptedException)) {
    +                                                                               return;
    +                                                                           }
    +
                                                                                logger.error("from " + t.getName(), e);
                                                                            }
                                                                        };
    diff --git a/dbsync/pom.xml b/dbsync/pom.xml
    index 1f274e82..4b027523 100644
    --- a/dbsync/pom.xml
    +++ b/dbsync/pom.xml
    @@ -3,7 +3,7 @@
     	
     		com.alibaba.otter
     		canal
    -		1.0.26-SNAPSHOT
    +		1.1.3-SNAPSHOT
     		../pom.xml
     	
     	com.alibaba.otter
    @@ -11,6 +11,11 @@
     	jar
     	canal dbsync module for otter ${project.version}
     	
    +		
    +			com.alibaba.otter
    +			canal.parse.driver
    +			${project.version}
    +		
     		
     		
     			ch.qos.logback
    diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/FileLogFetcher.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/FileLogFetcher.java
    index 0d586cd4..cdb1f685 100644
    --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/FileLogFetcher.java
    +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/FileLogFetcher.java
    @@ -168,7 +168,9 @@ public final class FileLogFetcher extends LogFetcher {
          * @see com.taobao.tddl.dbsync.binlog.LogFetcher#close()
          */
         public void close() throws IOException {
    -        if (fin != null) fin.close();
    +        if (fin != null) {
    +            fin.close();
    +        }
     
             fin = null;
         }
    diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/JsonConversion.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/JsonConversion.java
    index 020591f7..e61b6645 100644
    --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/JsonConversion.java
    +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/JsonConversion.java
    @@ -1,5 +1,9 @@
     package com.taobao.tddl.dbsync.binlog;
     
    +import static com.taobao.tddl.dbsync.binlog.event.RowsLogBuffer.appendNumber2;
    +import static com.taobao.tddl.dbsync.binlog.event.RowsLogBuffer.appendNumber4;
    +import static com.taobao.tddl.dbsync.binlog.event.RowsLogBuffer.usecondsToStr;
    +
     /**
      * 处理下MySQL json二进制转化为可读的字符串
      * 
    @@ -330,12 +334,30 @@ public class JsonConversion {
                                 long ultime = Math.abs(packed_value);
                                 long intpart = ultime >> 24;
                                 int frac = (int) (ultime % (1L << 24));
    -                            text = String.format("%s%02d:%02d:%02d",
    -                                packed_value >= 0 ? "" : "-",
    -                                (int) ((intpart >> 12) % (1 << 10)),
    -                                (int) ((intpart >> 6) % (1 << 6)),
    -                                (int) (intpart % (1 << 6)));
    -                            text = text + "." + usecondsToStr(frac, 6);
    +                            // text = String.format("%s%02d:%02d:%02d",
    +                            // packed_value >= 0 ? "" : "-",
    +                            // (int) ((intpart >> 12) % (1 << 10)),
    +                            // (int) ((intpart >> 6) % (1 << 6)),
    +                            // (int) (intpart % (1 << 6)));
    +                            // text = text + "." + usecondsToStr(frac, 6);
    +                            StringBuilder builder = new StringBuilder(17);
    +                            if (packed_value < 0) {
    +                                builder.append('-');
    +                            }
    +
    +                            int d = (int) ((intpart >> 12) % (1 << 10));
    +                            if (d > 100) {
    +                                builder.append(String.valueOf(d));
    +                            } else {
    +                                appendNumber2(builder, d);
    +                            }
    +                            builder.append(':');
    +                            appendNumber2(builder, (int) ((intpart >> 6) % (1 << 6)));
    +                            builder.append(':');
    +                            appendNumber2(builder, (int) (intpart % (1 << 6)));
    +
    +                            builder.append('.').append(usecondsToStr(frac, 6));
    +                            text = builder.toString();
                             }
                             buf.append('"').append(text).append('"');
                         } else if (m_field_type == LogEvent.MYSQL_TYPE_DATE || m_field_type == LogEvent.MYSQL_TYPE_DATETIME
    @@ -351,14 +373,28 @@ public class JsonConversion {
                                 long ymd = intpart >> 17;
                                 long ym = ymd >> 5;
                                 long hms = intpart % (1 << 17);
    -                            text = String.format("%04d-%02d-%02d %02d:%02d:%02d",
    -                                (int) (ym / 13),
    -                                (int) (ym % 13),
    -                                (int) (ymd % (1 << 5)),
    -                                (int) (hms >> 12),
    -                                (int) ((hms >> 6) % (1 << 6)),
    -                                (int) (hms % (1 << 6)));
    -                            text = text + "." + usecondsToStr(frac, 6);
    +                            // text =
    +                            // String.format("%04d-%02d-%02d %02d:%02d:%02d",
    +                            // (int) (ym / 13),
    +                            // (int) (ym % 13),
    +                            // (int) (ymd % (1 << 5)),
    +                            // (int) (hms >> 12),
    +                            // (int) ((hms >> 6) % (1 << 6)),
    +                            // (int) (hms % (1 << 6)));
    +                            StringBuilder builder = new StringBuilder(26);
    +                            appendNumber4(builder, (int) (ym / 13));
    +                            builder.append('-');
    +                            appendNumber2(builder, (int) (ym % 13));
    +                            builder.append('-');
    +                            appendNumber2(builder, (int) (ymd % (1 << 5)));
    +                            builder.append(' ');
    +                            appendNumber2(builder, (int) (hms >> 12));
    +                            builder.append(':');
    +                            appendNumber2(builder, (int) ((hms >> 6) % (1 << 6)));
    +                            builder.append(':');
    +                            appendNumber2(builder, (int) (hms % (1 << 6)));
    +                            builder.append('.').append(usecondsToStr(frac, 6));
    +                            text = builder.toString();
                             }
                             buf.append('"').append(text).append('"');
                         } else {
    @@ -397,22 +433,4 @@ public class JsonConversion {
             OBJECT, ARRAY, STRING, INT, UINT, DOUBLE, LITERAL_NULL, LITERAL_TRUE, LITERAL_FALSE, OPAQUE, ERROR
         }
     
    -    private static String usecondsToStr(int frac, int meta) {
    -        String sec = String.valueOf(frac);
    -        if (meta > 6) {
    -            throw new IllegalArgumentException("unknow useconds meta : " + meta);
    -        }
    -
    -        if (sec.length() < 6) {
    -            StringBuilder result = new StringBuilder(6);
    -            int len = 6 - sec.length();
    -            for (; len > 0; len--) {
    -                result.append('0');
    -            }
    -            result.append(sec);
    -            sec = result.toString();
    -        }
    -
    -        return sec.substring(0, meta);
    -    }
     }
    diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/JsonDiffConversion.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/JsonDiffConversion.java
    new file mode 100644
    index 00000000..223b5d9c
    --- /dev/null
    +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/JsonDiffConversion.java
    @@ -0,0 +1,154 @@
    +package com.taobao.tddl.dbsync.binlog;
    +
    +import java.util.ArrayList;
    +import java.util.List;
    +
    +import com.taobao.tddl.dbsync.binlog.JsonConversion.Json_Value;
    +import com.taobao.tddl.dbsync.binlog.JsonConversion.Json_enum_type;
    +
    +/**
    + * 处理mysql8.0 parital json diff解析
    + * 
    + * @author agapple 2018年11月4日 下午3:53:46
    + * @since 1.1.2
    + */
    +public class JsonDiffConversion {
    +
    +    /**
    +     * The JSON value in the given path is replaced with a new value. It has the
    +     * same effect as `JSON_REPLACE(col, path, value)`.
    +     */
    +    public static final int DIFF_OPERATION_REPLACE    = 0;
    +    /**
    +     * Add a new element at the given path. If the path specifies an array
    +     * element, it has the same effect as `JSON_ARRAY_INSERT(col, path, value)`.
    +     * If the path specifies an object member, it has the same effect as
    +     * `JSON_INSERT(col, path, value)`.
    +     */
    +    public static final int DIFF_OPERATION_INSERT     = 1;
    +    /**
    +     * The JSON value at the given path is removed from an array or object. It
    +     * has the same effect as `JSON_REMOVE(col, path)`.
    +     */
    +    public static final int DIFF_OPERATION_REMOVE     = 2;
    +
    +    public static final int JSON_DIFF_OPERATION_COUNT = 3;
    +
    +    public static StringBuilder print_json_diff(LogBuffer buffer, long len, String columnName, int columnIndex,
    +                                                String charsetName) {
    +        int position = buffer.position();
    +        List operation_names = new ArrayList();
    +        while (buffer.hasRemaining()) {
    +            int operation_int = buffer.getUint8();
    +            if (operation_int >= JSON_DIFF_OPERATION_COUNT) {
    +                throw new IllegalArgumentException("reading operation type (invalid operation code)");
    +            }
    +
    +            // skip path
    +            long path_length = buffer.getPackedLong();
    +            if (path_length > len) {
    +                throw new IllegalArgumentException("skipping path");
    +            }
    +
    +            // compute operation name
    +            byte[] lastP = buffer.getData(buffer.position() + (int) path_length - 1, 1);
    +            String operation_name = json_diff_operation_name(operation_int, lastP[0]);
    +            operation_names.add(operation_name);
    +
    +            buffer.forward((int) path_length);
    +            // skip value
    +            if (operation_int != DIFF_OPERATION_REMOVE) {
    +                long value_length = buffer.getPackedLong();
    +                if (value_length > len) {
    +                    throw new IllegalArgumentException("skipping path");
    +                }
    +
    +                buffer.forward((int) value_length);
    +            }
    +        }
    +
    +        // Print function names in reverse order.
    +        StringBuilder builder = new StringBuilder();
    +        for (int i = operation_names.size() - 1; i >= 0; i--) {
    +            if (i == 0 || operation_names.get(i - 1) != operation_names.get(i)) {
    +                builder.append(operation_names.get(i)).append("(");
    +            }
    +        }
    +
    +        // Print column id
    +        if (columnName != null) {
    +            builder.append(columnName);
    +        } else {
    +            builder.append("@").append(columnIndex);
    +        }
    +
    +        // In case this vector is empty (a no-op), make an early return
    +        // after printing only the column name
    +        if (operation_names.size() == 0) {
    +            return builder;
    +        }
    +
    +        // Print comma between column name and next function argument
    +        builder.append(", ");
    +        // Print paths and values.
    +        buffer.position(position);
    +        int diff_i = 0;
    +        while (buffer.hasRemaining()) {
    +            // Read operation
    +            int operation_int = buffer.getUint8();
    +
    +            // Read path length
    +            long path_length = buffer.getPackedLong();
    +            // Print path
    +            builder.append('\'').append(buffer.getFixString((int) path_length)).append('\'');
    +
    +            if (operation_int != DIFF_OPERATION_REMOVE) {
    +                // Print comma between path and value
    +                builder.append(", ");
    +                // Read value length
    +                long value_length = buffer.getPackedLong();
    +
    +                Json_Value jsonValue = JsonConversion.parse_value(buffer.getUint8(),
    +                    buffer,
    +                    value_length - 1,
    +                    charsetName);
    +                buffer.forward((int) value_length - 1);
    +                // Read value
    +                if (jsonValue.m_type == Json_enum_type.ERROR) {
    +                    throw new IllegalArgumentException("parsing json value");
    +                }
    +                StringBuilder jsonBuilder = new StringBuilder();
    +                jsonValue.toJsonString(jsonBuilder, charsetName);
    +                builder.append(jsonBuilder);
    +            }
    +
    +            // Print closing parenthesis
    +            if (!buffer.hasRemaining() || operation_names.get(diff_i + 1) != operation_names.get(diff_i)) {
    +                builder.append(")");
    +            }
    +
    +            if (buffer.hasRemaining()) {
    +                builder.append(", ");
    +            }
    +            diff_i++;
    +        }
    +
    +        return builder;
    +    }
    +
    +    private static String json_diff_operation_name(int operationType, int last_path_char) {
    +        switch (operationType) {
    +            case DIFF_OPERATION_REPLACE:
    +                return "JSON_REPLACE";
    +            case DIFF_OPERATION_INSERT:
    +                if (last_path_char == ']') {
    +                    return "JSON_ARRAY_INSERT";
    +                } else {
    +                    return "JSON_INSERT";
    +                }
    +            case DIFF_OPERATION_REMOVE:
    +                return "JSON_REMOVE";
    +        }
    +        throw new IllegalArgumentException("illeagal operationType : " + operationType);
    +    }
    +}
    diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogBuffer.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogBuffer.java
    index be61c99f..408eaa4e 100644
    --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogBuffer.java
    +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogBuffer.java
    @@ -1484,7 +1484,9 @@ public class LogBuffer {
     
             for (int bit = 0; bit < len; bit += 8) {
                 int flag = ((int) buf[pos++]) & 0xff;
    -            if (flag == 0) continue;
    +            if (flag == 0) {
    +                continue;
    +            }
                 if ((flag & 0x01) != 0) bitmap.set(bit);
                 if ((flag & 0x02) != 0) bitmap.set(bit + 1);
                 if ((flag & 0x04) != 0) bitmap.set(bit + 2);
    diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogContext.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogContext.java
    index 8d88d00d..0668ac4e 100644
    --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogContext.java
    +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogContext.java
    @@ -3,7 +3,9 @@ package com.taobao.tddl.dbsync.binlog;
     import java.util.HashMap;
     import java.util.Map;
     
    +import com.alibaba.otter.canal.parse.driver.mysql.packets.GTIDSet;
     import com.taobao.tddl.dbsync.binlog.event.FormatDescriptionLogEvent;
    +import com.taobao.tddl.dbsync.binlog.event.GtidLogEvent;
     import com.taobao.tddl.dbsync.binlog.event.TableMapLogEvent;
     
     /**
    @@ -20,6 +22,10 @@ public final class LogContext {
     
         private LogPosition                       logPosition;
     
    +    private GTIDSet                           gtidSet;
    +
    +    private GtidLogEvent                      gtidLogEvent; // save current gtid log event
    +
         public LogContext(){
             this.formatDescription = FormatDescriptionLogEvent.FORMAT_DESCRIPTION_EVENT_5_x;
         }
    @@ -60,4 +66,20 @@ public final class LogContext {
             formatDescription = FormatDescriptionLogEvent.FORMAT_DESCRIPTION_EVENT_5_x;
             mapOfTable.clear();
         }
    +
    +    public GTIDSet getGtidSet() {
    +        return gtidSet;
    +    }
    +
    +    public void setGtidSet(GTIDSet gtidSet) {
    +        this.gtidSet = gtidSet;
    +    }
    +
    +    public GtidLogEvent getGtidLogEvent() {
    +        return gtidLogEvent;
    +    }
    +
    +    public void setGtidLogEvent(GtidLogEvent gtidLogEvent) {
    +        this.gtidLogEvent = gtidLogEvent;
    +    }
     }
    diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogDecoder.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogDecoder.java
    index bbb358b7..3c1bff17 100644
    --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogDecoder.java
    +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogDecoder.java
    @@ -6,6 +6,7 @@ import java.util.BitSet;
     import org.apache.commons.logging.Log;
     import org.apache.commons.logging.LogFactory;
     
    +import com.alibaba.otter.canal.parse.driver.mysql.packets.GTIDSet;
     import com.taobao.tddl.dbsync.binlog.event.AppendBlockLogEvent;
     import com.taobao.tddl.dbsync.binlog.event.BeginLoadQueryLogEvent;
     import com.taobao.tddl.dbsync.binlog.event.CreateFileLogEvent;
    @@ -46,7 +47,7 @@ import com.taobao.tddl.dbsync.binlog.event.mariadb.StartEncryptionLogEvent;
     
     /**
      * Implements a binary-log decoder.
    - * 
    + *
      * 
      * LogDecoder decoder = new LogDecoder();
      * decoder.handle(...);
    @@ -61,7 +62,7 @@ import com.taobao.tddl.dbsync.binlog.event.mariadb.StartEncryptionLogEvent;
      * while (event != null);
      * // no more events in buffer.
      * 
    - * + * * @author Changyuan.lh * @version 1.0 */ @@ -88,7 +89,7 @@ public final class LogDecoder { /** * Decoding an event from binary-log buffer. - * + * * @return UknownLogEvent if event type is unknown or skipped, * null if buffer is not including a full event. */ @@ -108,11 +109,6 @@ public final class LogDecoder { try { /* Decoding binary-log to event */ event = decode(buffer, header, context); - if (event != null) { - // set logFileName - event.getHeader().setLogFileName(context.getLogPosition().getFileName()); - event.setSemival(buffer.semival); - } } catch (IOException e) { if (logger.isWarnEnabled()) { logger.warn("Decoding " + LogEvent.getTypeName(header.getType()) + " failed from: " @@ -127,6 +123,12 @@ public final class LogDecoder { event = new UnknownLogEvent(header); } + if (event != null) { + // set logFileName + event.getHeader().setLogFileName(context.getLogPosition().getFileName()); + event.setSemival(buffer.semival); + } + /* consume this binary-log. */ buffer.consume(len); return event; @@ -140,7 +142,7 @@ public final class LogDecoder { /** * Deserialize an event from buffer. - * + * * @return UknownLogEvent if event type is unknown or skipped. */ public static LogEvent decode(LogBuffer buffer, LogHeader header, LogContext context) throws IOException { @@ -159,18 +161,21 @@ public final class LogDecoder { // remove checksum bytes buffer.limit(header.getEventLen() - LogEvent.BINLOG_CHECKSUM_LEN); } - + GTIDSet gtidSet = context.getGtidSet(); + GtidLogEvent gtidLogEvent = context.getGtidLogEvent(); switch (header.getType()) { case LogEvent.QUERY_EVENT: { QueryLogEvent event = new QueryLogEvent(header, buffer, descriptionEvent); /* updating position in context */ logPosition.position = header.getLogPos(); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.XID_EVENT: { XidLogEvent event = new XidLogEvent(header, buffer, descriptionEvent); /* updating position in context */ logPosition.position = header.getLogPos(); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.TABLE_MAP_EVENT: { @@ -185,6 +190,7 @@ public final class LogDecoder { /* updating position in context */ logPosition.position = header.getLogPos(); event.fillTable(context); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.UPDATE_ROWS_EVENT_V1: { @@ -192,6 +198,7 @@ public final class LogDecoder { /* updating position in context */ logPosition.position = header.getLogPos(); event.fillTable(context); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.DELETE_ROWS_EVENT_V1: { @@ -199,6 +206,7 @@ public final class LogDecoder { /* updating position in context */ logPosition.position = header.getLogPos(); event.fillTable(context); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.ROTATE_EVENT: { @@ -268,12 +276,14 @@ public final class LogDecoder { RandLogEvent event = new RandLogEvent(header, buffer, descriptionEvent); /* updating position in context */ logPosition.position = header.getLogPos(); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.USER_VAR_EVENT: { UserVarLogEvent event = new UserVarLogEvent(header, buffer, descriptionEvent); /* updating position in context */ logPosition.position = header.getLogPos(); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.FORMAT_DESCRIPTION_EVENT: { @@ -336,6 +346,7 @@ public final class LogDecoder { RowsQueryLogEvent event = new RowsQueryLogEvent(header, buffer, descriptionEvent); /* updating position in context */ logPosition.position = header.getLogPos(); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.WRITE_ROWS_EVENT: { @@ -343,6 +354,7 @@ public final class LogDecoder { /* updating position in context */ logPosition.position = header.getLogPos(); event.fillTable(context); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.UPDATE_ROWS_EVENT: { @@ -350,6 +362,7 @@ public final class LogDecoder { /* updating position in context */ logPosition.position = header.getLogPos(); event.fillTable(context); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.DELETE_ROWS_EVENT: { @@ -357,6 +370,15 @@ public final class LogDecoder { /* updating position in context */ logPosition.position = header.getLogPos(); event.fillTable(context); + header.putGtid(context.getGtidSet(), gtidLogEvent); + return event; + } + case LogEvent.PARTIAL_UPDATE_ROWS_EVENT: { + RowsLogEvent event = new UpdateRowsLogEvent(header, buffer, descriptionEvent, true); + /* updating position in context */ + logPosition.position = header.getLogPos(); + event.fillTable(context); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.GTID_LOG_EVENT: @@ -364,6 +386,13 @@ public final class LogDecoder { GtidLogEvent event = new GtidLogEvent(header, buffer, descriptionEvent); /* updating position in context */ logPosition.position = header.getLogPos(); + if (gtidSet != null) { + gtidSet.update(event.getGtidStr()); + // update latest gtid + header.putGtid(gtidSet, event); + } + // update current gtid event to context + context.setGtidLogEvent(event); return event; } case LogEvent.PREVIOUS_GTIDS_LOG_EVENT: { @@ -394,6 +423,7 @@ public final class LogDecoder { AnnotateRowsEvent event = new AnnotateRowsEvent(header, buffer, descriptionEvent); /* updating position in context */ logPosition.position = header.getLogPos(); + header.putGtid(context.getGtidSet(), gtidLogEvent); return event; } case LogEvent.BINLOG_CHECKPOINT_EVENT: { diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogEvent.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogEvent.java index 8a5957d0..41208516 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogEvent.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/LogEvent.java @@ -169,9 +169,15 @@ public abstract class LogEvent { /* Prepared XA transaction terminal event similar to Xid */ public static final int XA_PREPARE_LOG_EVENT = 38; + /** + * Extension of UPDATE_ROWS_EVENT, allowing partial values according to + * binlog_row_value_options. + */ + public static final int PARTIAL_UPDATE_ROWS_EVENT = 39; + // mariaDb 5.5.34 /* New MySQL/Sun events are to be added right above this comment */ - public static final int MYSQL_EVENTS_END = 39; + public static final int MYSQL_EVENTS_END = 49; public static final int MARIA_EVENTS_BEGIN = 160; /* New Maria event numbers start from here */ @@ -361,6 +367,8 @@ public abstract class LogEvent { return "Anonymous_Gtid"; case PREVIOUS_GTIDS_LOG_EVENT: return "Previous_gtids"; + case PARTIAL_UPDATE_ROWS_EVENT: + return "Update_rows_partial"; default: return "Unknown"; /* impossible */ } diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/FormatDescriptionLogEvent.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/FormatDescriptionLogEvent.java index 8492e2d7..a14b9111 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/FormatDescriptionLogEvent.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/FormatDescriptionLogEvent.java @@ -211,6 +211,7 @@ public final class FormatDescriptionLogEvent extends StartLogEventV3 { postHeaderLen[TRANSACTION_CONTEXT_EVENT - 1] = TRANSACTION_CONTEXT_HEADER_LEN; postHeaderLen[VIEW_CHANGE_EVENT - 1] = VIEW_CHANGE_HEADER_LEN; postHeaderLen[XA_PREPARE_LOG_EVENT - 1] = XA_PREPARE_HEADER_LEN; + postHeaderLen[PARTIAL_UPDATE_ROWS_EVENT - 1] = ROWS_HEADER_LEN_V2; // mariadb 10 postHeaderLen[ANNOTATE_ROWS_EVENT - 1] = ANNOTATE_ROWS_HEADER_LEN; diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/GtidLogEvent.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/GtidLogEvent.java index 064f60bf..49557fc6 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/GtidLogEvent.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/GtidLogEvent.java @@ -14,13 +14,16 @@ import com.taobao.tddl.dbsync.binlog.LogEvent; public class GtidLogEvent extends LogEvent { // / Length of the commit_flag in event encoding - public static final int ENCODED_FLAG_LENGTH = 1; + public static final int ENCODED_FLAG_LENGTH = 1; // / Length of SID in event encoding - public static final int ENCODED_SID_LENGTH = 16; + public static final int ENCODED_SID_LENGTH = 16; + public static final int LOGICAL_TIMESTAMP_TYPE_CODE = 2; private boolean commitFlag; private UUID sid; private long gno; + private Long lastCommitted; + private Long sequenceNumber; public GtidLogEvent(LogHeader header, LogBuffer buffer, FormatDescriptionLogEvent descriptionEvent){ super(header); @@ -40,6 +43,13 @@ public class GtidLogEvent extends LogEvent { gno = buffer.getLong64(); + // support gtid lastCommitted and sequenceNumber + // fix bug #776 + if (buffer.hasRemaining() && buffer.remaining() > 16 && buffer.getUint8() == LOGICAL_TIMESTAMP_TYPE_CODE) { + lastCommitted = buffer.getLong64(); + sequenceNumber = buffer.getLong64(); + } + // ignore gtid info read // sid.copy_from((uchar *)ptr_buffer); // ptr_buffer+= ENCODED_SID_LENGTH; @@ -62,4 +72,19 @@ public class GtidLogEvent extends LogEvent { public long getGno() { return gno; } + + public Long getLastCommitted() { + return lastCommitted; + } + + public Long getSequenceNumber() { + return sequenceNumber; + } + + public String getGtidStr() { + StringBuilder sb = new StringBuilder(); + sb.append(sid.toString()).append(":"); + sb.append(gno); + return sb.toString(); + } } diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/LogHeader.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/LogHeader.java index 229693a2..ab273f1b 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/LogHeader.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/LogHeader.java @@ -1,8 +1,12 @@ package com.taobao.tddl.dbsync.binlog.event; +import com.alibaba.otter.canal.parse.driver.mysql.packets.GTIDSet; import com.taobao.tddl.dbsync.binlog.LogBuffer; import com.taobao.tddl.dbsync.binlog.LogEvent; +import java.util.HashMap; +import java.util.Map; + /** * The Common-Header, documented in the table @ref Table_common_header "below", * always has the same form and length within one version of MySQL. Each event @@ -120,6 +124,13 @@ public final class LogHeader { */ protected String logFileName; + protected Map gtidMap = new HashMap<>(); + + private static final String CURRENT_GTID_STRING = "curt_gtid"; + private static final String CURRENT_GTID_SN = "curt_gtid_sn"; + private static final String CURRENT_GTID_LAST_COMMIT = "curt_gtid_lct"; + private static final String GTID_SET_STRING = "gtid_str"; + /* for Start_event_v3 */ public LogHeader(final int type){ this.type = type; @@ -288,4 +299,31 @@ public final class LogHeader { crc = buffer.getUint32(eventLen - LogEvent.BINLOG_CHECKSUM_LEN); } } + + public String getGtidSetStr() { + return gtidMap.get(GTID_SET_STRING); + } + + public String getCurrentGtid() { + return gtidMap.get(CURRENT_GTID_STRING); + } + + public String getCurrentGtidSn() { + return gtidMap.get(CURRENT_GTID_SN); + } + + public String getCurrentGtidLastCommit() { + return gtidMap.get(CURRENT_GTID_LAST_COMMIT); + } + + public void putGtid(GTIDSet gtidSet, GtidLogEvent event) { + if (gtidSet != null) { + gtidMap.put(GTID_SET_STRING, gtidSet.toString()); + if (event != null) { + gtidMap.put(CURRENT_GTID_STRING, event.getGtidStr()); + gtidMap.put(CURRENT_GTID_SN, String.valueOf(event.getSequenceNumber())); + gtidMap.put(CURRENT_GTID_LAST_COMMIT, String.valueOf(event.getLastCommitted())); + } + } + } } diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/QueryLogEvent.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/QueryLogEvent.java index f6e0459c..c732da99 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/QueryLogEvent.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/QueryLogEvent.java @@ -1,6 +1,7 @@ package com.taobao.tddl.dbsync.binlog.event; import java.io.IOException; +import java.math.BigInteger; import java.nio.charset.Charset; import com.taobao.tddl.dbsync.binlog.CharsetConversion; @@ -285,12 +286,12 @@ public class QueryLogEvent extends LogEvent { * type, * sql_mode */ - + 1 + 1 + 255 /* - * type, - * length - * , - * catalog - */ + + 1 + 1 + 255/* + * type, + * length + * , + * catalog + */ + 1 + 4 /* * type, * auto_increment @@ -330,14 +331,32 @@ public class QueryLogEvent extends LogEvent { * MariaDb type, * sec_part of NOW() */ - + 1 + (MAX_DBS_IN_EVENT_MTS * (1 + NAME_LEN)) + 3 + 1 + 32 * 3 - + 1 + 60/* - * type , - * user_len , - * user , - * host_len , - * host - */); + + 1 + (MAX_DBS_IN_EVENT_MTS * (1 + NAME_LEN)) + 3 /* + * type + * , + * microseconds + */+ 1 + 32 + * 3 + 1 + 60/* + * type , + * user_len + * , user , + * host_len + * , host + */) + + 1 + 1 /* + * type, + * explicit_def + * ..ts + */+ 1 + 8 /* + * type, + * xid + * of + * DDL + */+ 1 + 2 /* + * type + * , + * default_collation_for_utf8mb4_number + */+ 1 /* sql_require_primary_key */; /** * Fixed data part: *
      @@ -394,7 +413,7 @@ public class QueryLogEvent extends LogEvent { // inspection by the DBA private final long execTime; private final int errorCode; - private final long sessionId; /* thread_id */ + private final long sessionId; /* thread_id */ /** * 'flags2' is a second set of flags (on top of those in Log_event), for @@ -412,6 +431,8 @@ public class QueryLogEvent extends LogEvent { private int clientCharset = -1; private int clientCollation = -1; private int serverCollation = -1; + private int tvSec = -1; + private BigInteger ddlXid = BigInteger.valueOf(-1L); private String charsetName; private String timezone; @@ -562,6 +583,21 @@ public class QueryLogEvent extends LogEvent { */ public static final int Q_EXPLICIT_DEFAULTS_FOR_TIMESTAMP = 16; + /** + * The variable carries xid info of 2pc-aware (recoverable) DDL queries. + */ + public static final int Q_DDL_LOGGED_WITH_XID = 17; + /** + * This variable stores the default collation for the utf8mb4 character set. + * Used to support cross-version replication. + */ + public static final int Q_DEFAULT_COLLATION_FOR_UTF8MB4 = 18; + + /** + * Replicate sql_require_primary_key. + */ + public static final int Q_SQL_REQUIRE_PRIMARY_KEY = 19; + /** * FROM MariaDB 5.5.34 */ @@ -625,7 +661,7 @@ public class QueryLogEvent extends LogEvent { break; case Q_MICROSECONDS: // when.tv_usec= uint3korr(pos); - buffer.forward(3); + tvSec = buffer.getInt24(); break; case Q_UPDATED_DB_NAMES: int mtsAccessedDbs = buffer.getUint8(); @@ -646,6 +682,19 @@ public class QueryLogEvent extends LogEvent { } break; case Q_EXPLICIT_DEFAULTS_FOR_TIMESTAMP: + // thd->variables.explicit_defaults_for_timestamp + buffer.forward(1); + break; + case Q_DDL_LOGGED_WITH_XID: + ddlXid = buffer.getUlong64(); + break; + case Q_DEFAULT_COLLATION_FOR_UTF8MB4: + // int2store(start, + // default_collation_for_utf8mb4_number); + buffer.forward(2); + break; + case Q_SQL_REQUIRE_PRIMARY_KEY: + // *start++ = thd->variables.sql_require_primary_key; buffer.forward(1); break; case Q_HRNOW: @@ -657,8 +706,10 @@ public class QueryLogEvent extends LogEvent { * That's why you must write status vars in growing * order of code */ - if (logger.isDebugEnabled()) logger.debug("Query_log_event has unknown status vars (first has code: " - + code + "), skipping the rest of them"); + if (logger.isDebugEnabled()) { + logger.debug("Query_log_event has unknown status vars (first has code: " + code + + "), skipping the rest of them"); + } break; // Break loop } } @@ -695,6 +746,12 @@ public class QueryLogEvent extends LogEvent { return "Q_UPDATED_DB_NAMES"; case Q_MICROSECONDS: return "Q_MICROSECONDS"; + case Q_DDL_LOGGED_WITH_XID: + return "Q_DDL_LOGGED_WITH_XID"; + case Q_DEFAULT_COLLATION_FOR_UTF8MB4: + return "Q_DEFAULT_COLLATION_FOR_UTF8MB4"; + case Q_SQL_REQUIRE_PRIMARY_KEY: + return "Q_SQL_REQUIRE_PRIMARY_KEY"; } return "CODE#" + code; } @@ -777,6 +834,14 @@ public class QueryLogEvent extends LogEvent { return serverCollation; } + public int getTvSec() { + return tvSec; + } + + public BigInteger getDdlXid() { + return ddlXid; + } + /** * Returns the sql_mode value. *

      diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogBuffer.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogBuffer.java index fdfb3ebc..013494d5 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogBuffer.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogBuffer.java @@ -10,6 +10,7 @@ import org.apache.commons.logging.LogFactory; import com.taobao.tddl.dbsync.binlog.JsonConversion; import com.taobao.tddl.dbsync.binlog.JsonConversion.Json_Value; +import com.taobao.tddl.dbsync.binlog.JsonDiffConversion; import com.taobao.tddl.dbsync.binlog.LogBuffer; import com.taobao.tddl.dbsync.binlog.LogEvent; @@ -31,22 +32,33 @@ public final class RowsLogBuffer { private final LogBuffer buffer; private final int columnLen; + private final int jsonColumnCount; private final String charsetName; - // private Calendar cal; private final BitSet nullBits; private int nullBitIndex; + // Read value_options if this is AI for PARTIAL_UPDATE_ROWS_EVENT + private final boolean partial; + private final BitSet partialBits; + private boolean fNull; private int javaType; private int length; private Serializable value; - public RowsLogBuffer(LogBuffer buffer, final int columnLen, String charsetName){ + public RowsLogBuffer(LogBuffer buffer, final int columnLen, String charsetName, int jsonColumnCount, boolean partial){ this.buffer = buffer; this.columnLen = columnLen; this.charsetName = charsetName; + this.partial = partial; + this.jsonColumnCount = jsonColumnCount; this.nullBits = new BitSet(columnLen); + this.partialBits = new BitSet(1); + } + + public final boolean nextOneRow(BitSet columns) { + return nextOneRow(columns, false); } /** @@ -55,18 +67,30 @@ public final class RowsLogBuffer { * @see mysql-5.1.60/sql/log_event.cc - * Rows_log_event::print_verbose_one_row */ - public final boolean nextOneRow(BitSet columns) { + public final boolean nextOneRow(BitSet columns, boolean after) { final boolean hasOneRow = buffer.hasRemaining(); if (hasOneRow) { int column = 0; for (int i = 0; i < columnLen; i++) - if (columns.get(i)) column++; + if (columns.get(i)) { + column++; + } + if (after && partial) { + partialBits.clear(); + long valueOptions = buffer.getPackedLong(); + int PARTIAL_JSON_UPDATES = 1; + if ((valueOptions & PARTIAL_JSON_UPDATES) != 0) { + partialBits.set(1); + buffer.forward((jsonColumnCount + 7) / 8); + } + } nullBitIndex = 0; nullBits.clear(); buffer.fillBitmap(nullBits, column); + } return hasOneRow; } @@ -77,8 +101,8 @@ public final class RowsLogBuffer { * @see mysql-5.1.60/sql/log_event.cc - * Rows_log_event::print_verbose_one_row */ - public final Serializable nextValue(final int type, final int meta) { - return nextValue(type, meta, false); + public final Serializable nextValue(final String columName, final int columnIndex, final int type, final int meta) { + return nextValue(columName, columnIndex, type, meta, false); } /** @@ -87,7 +111,8 @@ public final class RowsLogBuffer { * @see mysql-5.1.60/sql/log_event.cc - * Rows_log_event::print_verbose_one_row */ - public final Serializable nextValue(final int type, final int meta, boolean isBinary) { + public final Serializable nextValue(final String columName, final int columnIndex, final int type, final int meta, + boolean isBinary) { fNull = nullBits.get(nullBitIndex++); if (fNull) { @@ -97,7 +122,7 @@ public final class RowsLogBuffer { return null; } else { // Extracting field value from packed buffer. - return fetchValue(type, meta, isBinary); + return fetchValue(columName, columnIndex, type, meta, isBinary); } } @@ -248,7 +273,7 @@ public final class RowsLogBuffer { * * @see mysql-5.1.60/sql/log_event.cc - log_event_print_value */ - final Serializable fetchValue(int type, final int meta, boolean isBinary) { + final Serializable fetchValue(String columnName, int columnIndex, int type, final int meta, boolean isBinary) { int len = 0; if (type == LogEvent.MYSQL_TYPE_STRING) { @@ -367,7 +392,7 @@ public final class RowsLogBuffer { // 转化为unsign long switch (len) { case 1: - value = buffer.getInt8(); + value = buffer.getUint8(); break; case 2: value = buffer.getBeUint16(); @@ -490,7 +515,6 @@ public final class RowsLogBuffer { // t % 100); StringBuilder builder = new StringBuilder(); - builder.append(26); appendNumber4(builder, d / 10000); builder.append('-'); appendNumber2(builder, (d % 10000) / 100); @@ -611,11 +635,17 @@ public final class RowsLogBuffer { // (u32 % 10000) / 100, // u32 % 100); - StringBuilder builder = new StringBuilder(12); + StringBuilder builder = new StringBuilder(17); if (i32 < 0) { builder.append('-'); } - appendNumber2(builder, u32 / 10000); + + int d = u32 / 10000; + if (d > 100) { + builder.append(String.valueOf(d)); + } else { + appendNumber2(builder, d); + } builder.append(':'); appendNumber2(builder, (u32 % 10000) / 100); builder.append(':'); @@ -724,7 +754,13 @@ public final class RowsLogBuffer { if (ltime < 0) { builder.append('-'); } - appendNumber2(builder, (int) ((intpart >> 12) % (1 << 10))); + + int d = (int) ((intpart >> 12) % (1 << 10)); + if (d > 100) { + builder.append(String.valueOf(d)); + } else { + appendNumber2(builder, d); + } builder.append(':'); appendNumber2(builder, (int) ((intpart >> 6) % (1 << 6))); builder.append(':'); @@ -848,7 +884,7 @@ public final class RowsLogBuffer { // 转化为unsign long switch (len) { case 1: - value = buffer.getInt8(); + value = buffer.getUint8(); break; case 2: value = buffer.getUint16(); @@ -1030,17 +1066,34 @@ public final class RowsLogBuffer { default: throw new IllegalArgumentException("!! Unknown JSON packlen = " + meta); } - if (0 == len) { - // fixed issue #1 by lava, json column of zero length has no - // value, value parsing should be skipped - value = ""; - } else { + + if (partialBits.get(1)) { + // print_json_diff int position = buffer.position(); - Json_Value jsonValue = JsonConversion.parse_value(buffer.getUint8(), buffer, len - 1, charsetName); - StringBuilder builder = new StringBuilder(); - jsonValue.toJsonString(builder, charsetName); + StringBuilder builder = JsonDiffConversion.print_json_diff(buffer, + len, + columnName, + columnIndex, + charsetName); value = builder.toString(); buffer.position(position + len); + } else { + if (0 == len) { + // fixed issue #1 by lava, json column of zero length + // has no + // value, value parsing should be skipped + value = ""; + } else { + int position = buffer.position(); + Json_Value jsonValue = JsonConversion.parse_value(buffer.getUint8(), + buffer, + len - 1, + charsetName); + StringBuilder builder = new StringBuilder(); + jsonValue.toJsonString(builder, charsetName); + value = builder.toString(); + buffer.position(position + len); + } } javaType = Types.VARCHAR; length = len; @@ -1071,10 +1124,10 @@ public final class RowsLogBuffer { buffer.fillBytes(binary, 0, len); /* Warning unsupport cloumn type */ - logger.warn(String.format("!! Unsupport column type MYSQL_TYPE_GEOMETRY: meta=%d (%04X), len = %d", - meta, - meta, - len)); + // logger.warn(String.format("!! Unsupport column type MYSQL_TYPE_GEOMETRY: meta=%d (%04X), len = %d", + // meta, + // meta, + // len)); javaType = Types.BINARY; value = binary; length = len; @@ -1109,7 +1162,7 @@ public final class RowsLogBuffer { return length; } - private String usecondsToStr(int frac, int meta) { + public static String usecondsToStr(int frac, int meta) { String sec = String.valueOf(frac); if (meta > 6) { throw new IllegalArgumentException("unknow useconds meta : " + meta); @@ -1128,30 +1181,28 @@ public final class RowsLogBuffer { return sec.substring(0, meta); } - private void appendNumber4(StringBuilder builder, int d) { + public static void appendNumber4(StringBuilder builder, int d) { if (d >= 1000) { builder.append(digits[d / 1000]) .append(digits[(d / 100) % 10]) .append(digits[(d / 10) % 10]) .append(digits[d % 10]); - } else if (d >= 100) { + } else { builder.append('0'); appendNumber3(builder, d); } } - private void appendNumber3(StringBuilder builder, int d) { + public static void appendNumber3(StringBuilder builder, int d) { if (d >= 100) { - builder.append(digits[d / 100]) - .append(digits[(d / 10) % 10]) - .append(digits[d % 10]); + builder.append(digits[d / 100]).append(digits[(d / 10) % 10]).append(digits[d % 10]); } else { builder.append('0'); appendNumber2(builder, d); } } - private void appendNumber2(StringBuilder builder, int d) { + public static void appendNumber2(StringBuilder builder, int d) { if (d >= 10) { builder.append(digits[(d / 10) % 10]).append(digits[d % 10]); } else { diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogEvent.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogEvent.java index f2ce79b0..f11b0734 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogEvent.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/RowsLogEvent.java @@ -5,6 +5,7 @@ import java.util.BitSet; import com.taobao.tddl.dbsync.binlog.LogBuffer; import com.taobao.tddl.dbsync.binlog.LogContext; import com.taobao.tddl.dbsync.binlog.LogEvent; +import com.taobao.tddl.dbsync.binlog.event.TableMapLogEvent.ColumnInfo; /** * Common base class for all row-containing log events. @@ -61,6 +62,7 @@ public abstract class RowsLogEvent extends LogEvent { /** Bitmap denoting columns available */ protected final int columnLen; + protected final boolean partial; protected final BitSet columns; /** @@ -71,6 +73,8 @@ public abstract class RowsLogEvent extends LogEvent { */ protected final BitSet changeColumns; + protected int jsonColumnCount = 0; + /** XXX: Don't handle buffer in another thread. */ private final LogBuffer rowsBuf; /* * The rows in @@ -109,6 +113,10 @@ public abstract class RowsLogEvent extends LogEvent { public static final int RW_V_EXTRAINFO_TAG = 0; public RowsLogEvent(LogHeader header, LogBuffer buffer, FormatDescriptionLogEvent descriptionEvent){ + this(header, buffer, descriptionEvent, false); + } + + public RowsLogEvent(LogHeader header, LogBuffer buffer, FormatDescriptionLogEvent descriptionEvent, boolean partial){ super(header); final int commonHeaderLen = descriptionEvent.commonHeaderLen; @@ -153,9 +161,11 @@ public abstract class RowsLogEvent extends LogEvent { buffer.position(commonHeaderLen + postHeaderLen + headerLen); columnLen = (int) buffer.getPackedLong(); + this.partial = partial; columns = buffer.getBitmap(columnLen); - if (header.type == UPDATE_ROWS_EVENT_V1 || header.type == UPDATE_ROWS_EVENT) { + if (header.type == UPDATE_ROWS_EVENT_V1 || header.type == UPDATE_ROWS_EVENT + || header.type == PARTIAL_UPDATE_ROWS_EVENT) { changeColumns = buffer.getBitmap(columnLen); } else { changeColumns = columns; @@ -175,6 +185,17 @@ public abstract class RowsLogEvent extends LogEvent { // delete original table map events stored in the map). context.clearAllTables(); } + + int jsonColumnCount = 0; + int columnCnt = table.getColumnCnt(); + ColumnInfo[] columnInfo = table.getColumnInfo(); + for (int i = 0; i < columnCnt; i++) { + ColumnInfo info = columnInfo[i]; + if (info.type == LogEvent.MYSQL_TYPE_JSON) { + jsonColumnCount++; + } + } + this.jsonColumnCount = jsonColumnCount; } public final long getTableId() { @@ -194,7 +215,7 @@ public abstract class RowsLogEvent extends LogEvent { } public final RowsLogBuffer getRowsBuf(String charsetName) { - return new RowsLogBuffer(rowsBuf, columnLen, charsetName); + return new RowsLogBuffer(rowsBuf, columnLen, charsetName, jsonColumnCount, partial); } public final int getFlags(final int flags) { diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/TableMapLogEvent.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/TableMapLogEvent.java index e6550b27..18201ea9 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/TableMapLogEvent.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/TableMapLogEvent.java @@ -1,6 +1,8 @@ package com.taobao.tddl.dbsync.binlog.event; +import java.util.ArrayList; import java.util.BitSet; +import java.util.List; import com.taobao.tddl.dbsync.binlog.LogBuffer; import com.taobao.tddl.dbsync.binlog.LogEvent; @@ -88,6 +90,17 @@ import com.taobao.tddl.dbsync.binlog.LogEvent; * first byte, the ninth is in the least significant bit of the second byte, and * so on. * + * + * optional metadata fields + * optional metadata fields are stored in Type, Length, Value(TLV) format. + * Type takes 1 byte. Length is a packed integer value. Values takes Length + * bytes. + * There are some optional metadata defined. They are listed in the table + * + * @ref Table_table_map_event_optional_metadata. Optional metadata fields follow + * null_bits. Whether binlogging an optional metadata is decided by the server. + * The order is not defined, so they can be binlogged in any order. + * * * The table below lists all column types, along with the numerical identifier * for it and the size and interpretation of meta-data used to describe the @@ -284,7 +297,6 @@ import com.taobao.tddl.dbsync.binlog.LogEvent; * of the geometry: 1, 2, 3, or 4. * * - * * @author Changyuan.lh * @version 1.0 */ @@ -322,20 +334,63 @@ public final class TableMapLogEvent extends LogEvent { */ public static final class ColumnInfo { - public int type; - public int meta; + public int type; + public int meta; + public String name; + public boolean unsigned; + public boolean pk; + public List set_enum_values; + public int charset; // 可以通过CharsetUtil进行转化 + public int geoType; + public boolean nullable; + + @Override + public String toString() { + return "ColumnInfo [type=" + type + ", meta=" + meta + ", name=" + name + ", unsigned=" + unsigned + + ", pk=" + pk + ", set_enum_values=" + set_enum_values + ", charset=" + charset + ", geoType=" + + geoType + ", nullable=" + nullable + "]"; + } } protected final int columnCnt; - protected final ColumnInfo[] columnInfo; // buffer for field - // metadata + protected final ColumnInfo[] columnInfo; // buffer + // for + // field + // metadata protected final long tableId; protected BitSet nullBits; /** TM = "Table Map" */ - public static final int TM_MAPID_OFFSET = 0; - public static final int TM_FLAGS_OFFSET = 6; + public static final int TM_MAPID_OFFSET = 0; + public static final int TM_FLAGS_OFFSET = 6; + + // UNSIGNED flag of numeric columns + public static final int SIGNEDNESS = 1; + // Default character set of string columns + public static final int DEFAULT_CHARSET = 2; + // Character set of string columns + public static final int COLUMN_CHARSET = 3; + public static final int COLUMN_NAME = 4; + // String value of SET columns + public static final int SET_STR_VALUE = 5; + // String value of ENUM columns + public static final int ENUM_STR_VALUE = 6; + // Real type of geometry columns + public static final int GEOMETRY_TYPE = 7; + // Primary key without prefix + public static final int SIMPLE_PRIMARY_KEY = 8; + // Primary key with prefix + public static final int PRIMARY_KEY_WITH_PREFIX = 9; + + private int default_charset; + private boolean existOptionalMetaData = false; + + private static final class Pair { + + public int col_index; + public int col_charset; + } /** * Constructor used by slave to read the event from the binary log. @@ -379,7 +434,91 @@ public final class TableMapLogEvent extends LogEvent { final int fieldSize = (int) buffer.getPackedLong(); decodeFields(buffer, fieldSize); nullBits = buffer.getBitmap(columnCnt); + + for (int i = 0; i < columnCnt; i++) { + if (nullBits.get(i)) { + columnInfo[i].nullable = true; + } + } + /* + * After null_bits field, there are some new fields for extra + * metadata. + */ + existOptionalMetaData = false; + List defaultCharsetPairs = null; + List columnCharsets = null; + while (buffer.hasRemaining()) { + // optional metadata fields + int type = buffer.getUint8(); + int len = (int) buffer.getPackedLong(); + + switch (type) { + case SIGNEDNESS: + parse_signedness(buffer, len); + break; + case DEFAULT_CHARSET: + defaultCharsetPairs = parse_default_charset(buffer, len); + break; + case COLUMN_CHARSET: + columnCharsets = parse_column_charset(buffer, len); + break; + case COLUMN_NAME: + // set @@global.binlog_row_metadata='FULL' + // 主要是补充列名相关信息 + existOptionalMetaData = true; + parse_column_name(buffer, len); + break; + case SET_STR_VALUE: + parse_set_str_value(buffer, len, true); + break; + case ENUM_STR_VALUE: + parse_set_str_value(buffer, len, false); + break; + case GEOMETRY_TYPE: + parse_geometry_type(buffer, len); + break; + case SIMPLE_PRIMARY_KEY: + parse_simple_pk(buffer, len); + break; + case PRIMARY_KEY_WITH_PREFIX: + parse_pk_with_prefix(buffer, len); + break; + default: + throw new IllegalArgumentException("unknow type : " + type); + } + } + + if (existOptionalMetaData) { + int index = 0; + int char_col_index = 0; + for (int i = 0; i < columnCnt; i++) { + int cs = -1; + int type = getRealType(columnInfo[i].type, columnInfo[i].meta); + if (is_character_type(type)) { + if (defaultCharsetPairs != null && !defaultCharsetPairs.isEmpty()) { + if (index < defaultCharsetPairs.size() + && char_col_index == defaultCharsetPairs.get(index).col_index) { + cs = defaultCharsetPairs.get(index).col_charset; + index++; + } else { + cs = default_charset; + } + + char_col_index++; + } else if (columnCharsets != null) { + cs = columnCharsets.get(index); + index++; + } + + columnInfo[i].charset = cs; + } + } + } } + + // for (int i = 0; i < columnCnt; i++) { + // System.out.println(columnInfo[i]); + // } } /** @@ -459,6 +598,192 @@ public final class TableMapLogEvent extends LogEvent { buffer.limit(limit); } + private void parse_signedness(LogBuffer buffer, int length) { + // stores the signedness flags extracted from field + List datas = new ArrayList(); + for (int i = 0; i < length; i++) { + int ut = buffer.getUint8(); + for (int c = 0x80; c != 0; c >>= 1) { + datas.add((ut & c) > 0); + } + } + + int index = 0; + for (int i = 0; i < columnCnt; i++) { + if (is_numeric_type(columnInfo[i].type)) { + columnInfo[i].unsigned = datas.get(index); + index++; + } + } + } + + private List parse_default_charset(LogBuffer buffer, int length) { + // stores collation numbers extracted from field. + int limit = buffer.position() + length; + this.default_charset = (int) buffer.getPackedLong(); + List datas = new ArrayList(); + while (buffer.hasRemaining() && buffer.position() < limit) { + int col_index = (int) buffer.getPackedLong(); + int col_charset = (int) buffer.getPackedLong(); + + Pair pair = new Pair(); + pair.col_index = col_index; + pair.col_charset = col_charset; + datas.add(pair); + } + + return datas; + } + + private List parse_column_charset(LogBuffer buffer, int length) { + // stores collation numbers extracted from field. + int limit = buffer.position() + length; + List datas = new ArrayList(); + while (buffer.hasRemaining() && buffer.position() < limit) { + int col_charset = (int) buffer.getPackedLong(); + datas.add(col_charset); + } + + return datas; + } + + private void parse_column_name(LogBuffer buffer, int length) { + // stores column names extracted from field + int limit = buffer.position() + length; + int index = 0; + while (buffer.hasRemaining() && buffer.position() < limit) { + int len = (int) buffer.getPackedLong(); + columnInfo[index++].name = buffer.getFixString(len); + } + } + + private void parse_set_str_value(LogBuffer buffer, int length, boolean set) { + // stores SET/ENUM column's string values extracted from + // field. Each SET/ENUM column's string values are stored + // into a string separate vector. All of them are stored + // in 'vec'. + int limit = buffer.position() + length; + List> datas = new ArrayList>(); + while (buffer.hasRemaining() && buffer.position() < limit) { + int count = (int) buffer.getPackedLong(); + List data = new ArrayList(count); + for (int i = 0; i < count; i++) { + int len1 = (int) buffer.getPackedLong(); + data.add(buffer.getFixString(len1)); + } + + datas.add(data); + } + + int index = 0; + for (int i = 0; i < columnCnt; i++) { + if (set && getRealType(columnInfo[i].type, columnInfo[i].meta) == LogEvent.MYSQL_TYPE_SET) { + columnInfo[i].set_enum_values = datas.get(index); + index++; + } + + if (!set && getRealType(columnInfo[i].type, columnInfo[i].meta) == LogEvent.MYSQL_TYPE_ENUM) { + columnInfo[i].set_enum_values = datas.get(index); + index++; + } + } + } + + private void parse_geometry_type(LogBuffer buffer, int length) { + // stores geometry column's types extracted from field. + int limit = buffer.position() + length; + + List datas = new ArrayList(); + while (buffer.hasRemaining() && buffer.position() < limit) { + int col_type = (int) buffer.getPackedLong(); + datas.add(col_type); + } + + int index = 0; + for (int i = 0; i < columnCnt; i++) { + if (columnInfo[i].type == LogEvent.MYSQL_TYPE_GEOMETRY) { + columnInfo[i].geoType = datas.get(index); + index++; + } + } + } + + private void parse_simple_pk(LogBuffer buffer, int length) { + // stores primary key's column information extracted from + // field. Each column has an index and a prefix which are + // stored as a unit_pair. prefix is always 0 for + // SIMPLE_PRIMARY_KEY field. + + int limit = buffer.position() + length; + while (buffer.hasRemaining() && buffer.position() < limit) { + int col_index = (int) buffer.getPackedLong(); + columnInfo[col_index].pk = true; + } + } + + private void parse_pk_with_prefix(LogBuffer buffer, int length) { + // stores primary key's column information extracted from + // field. Each column has an index and a prefix which are + // stored as a unit_pair. + int limit = buffer.position() + length; + while (buffer.hasRemaining() && buffer.position() < limit) { + int col_index = (int) buffer.getPackedLong(); + // prefix length, 比如 char(32) + @SuppressWarnings("unused") + int col_prefix = (int) buffer.getPackedLong(); + columnInfo[col_index].pk = true; + } + } + + private boolean is_numeric_type(int type) { + switch (type) { + case MYSQL_TYPE_TINY: + case MYSQL_TYPE_SHORT: + case MYSQL_TYPE_INT24: + case MYSQL_TYPE_LONG: + case MYSQL_TYPE_LONGLONG: + case MYSQL_TYPE_NEWDECIMAL: + case MYSQL_TYPE_FLOAT: + case MYSQL_TYPE_DOUBLE: + return true; + default: + return false; + } + } + + private boolean is_character_type(int type) { + switch (type) { + case MYSQL_TYPE_STRING: + case MYSQL_TYPE_VAR_STRING: + case MYSQL_TYPE_VARCHAR: + case MYSQL_TYPE_BLOB: + return true; + default: + return false; + } + } + + private int getRealType(int type, int meta) { + if (type == LogEvent.MYSQL_TYPE_STRING) { + if (meta >= 256) { + int byte0 = meta >> 8; + if ((byte0 & 0x30) != 0x30) { + /* a long CHAR() field: see #37426 */ + type = byte0 | 0x30; + } else { + switch (byte0) { + case LogEvent.MYSQL_TYPE_SET: + case LogEvent.MYSQL_TYPE_ENUM: + case LogEvent.MYSQL_TYPE_STRING: + type = byte0; + } + } + } + } + + return type; + } + public final String getDbName() { return dbname; } @@ -478,4 +803,13 @@ public final class TableMapLogEvent extends LogEvent { public final long getTableId() { return tableId; } + + public boolean isExistOptionalMetaData() { + return existOptionalMetaData; + } + + public void setExistOptionalMetaData(boolean existOptional) { + this.existOptionalMetaData = existOptional; + } + } diff --git a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/UpdateRowsLogEvent.java b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/UpdateRowsLogEvent.java index f5e5866e..b604e04d 100644 --- a/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/UpdateRowsLogEvent.java +++ b/dbsync/src/main/java/com/taobao/tddl/dbsync/binlog/event/UpdateRowsLogEvent.java @@ -14,6 +14,11 @@ import com.taobao.tddl.dbsync.binlog.LogBuffer; public final class UpdateRowsLogEvent extends RowsLogEvent { public UpdateRowsLogEvent(LogHeader header, LogBuffer buffer, FormatDescriptionLogEvent descriptionEvent){ - super(header, buffer, descriptionEvent); + super(header, buffer, descriptionEvent, false); + } + + public UpdateRowsLogEvent(LogHeader header, LogBuffer buffer, FormatDescriptionLogEvent descriptionEvent, + boolean partial){ + super(header, buffer, descriptionEvent, partial); } } diff --git a/dbsync/src/test/java/com/taobao/tddl/dbsync/FetcherPerformanceTest.java b/dbsync/src/test/java/com/taobao/tddl/dbsync/FetcherPerformanceTest.java new file mode 100644 index 00000000..d9b6355b --- /dev/null +++ b/dbsync/src/test/java/com/taobao/tddl/dbsync/FetcherPerformanceTest.java @@ -0,0 +1,50 @@ +package com.taobao.tddl.dbsync; + +import java.io.IOException; +import java.sql.Connection; +import java.sql.DriverManager; +import java.sql.Statement; +import java.util.concurrent.atomic.AtomicLong; + +import com.taobao.tddl.dbsync.binlog.DirectLogFetcher; +import com.taobao.tddl.dbsync.binlog.LogEvent; + +public class FetcherPerformanceTest { + + public static void main(String args[]) { + DirectLogFetcher fetcher = new DirectLogFetcher(); + try { + Class.forName("com.mysql.jdbc.Driver"); + Connection connection = DriverManager.getConnection("jdbc:mysql://127.0.0.1:3306", "root", "hello"); + Statement statement = connection.createStatement(); + statement.execute("SET @master_binlog_checksum='@@global.binlog_checksum'"); + statement.execute("SET @mariadb_slave_capability='" + LogEvent.MARIA_SLAVE_CAPABILITY_MINE + "'"); + + fetcher.open(connection, "mysql-bin.000006", 120L, 2); + + AtomicLong sum = new AtomicLong(0); + long start = System.currentTimeMillis(); + long last = 0; + long end = 0; + + while (fetcher.fetch()) { + sum.incrementAndGet(); + long current = sum.get(); + if (current - last >= 100000) { + end = System.currentTimeMillis(); + long tps = ((current - last) * 1000) / (end - start); + System.out.println(" total : " + sum + " , cost : " + (end - start) + " , tps : " + tps); + last = current; + start = end; + } + } + } catch (Exception e) { + e.printStackTrace(); + } finally { + try { + fetcher.close(); + } catch (IOException e) { + } + } + } +} diff --git a/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/BaseLogFetcherTest.java b/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/BaseLogFetcherTest.java index d0c6746d..27ecf3db 100644 --- a/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/BaseLogFetcherTest.java +++ b/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/BaseLogFetcherTest.java @@ -68,7 +68,7 @@ public class BaseLogFetcherTest { // update需要处理before/after System.out.println("-------> before"); parseOneRow(event, buffer, columns, false); - if (!buffer.nextOneRow(changeColumns)) { + if (!buffer.nextOneRow(changeColumns, true)) { break; } System.out.println("-------> after"); @@ -97,7 +97,7 @@ public class BaseLogFetcherTest { } ColumnInfo info = columnInfo[i]; - buffer.nextValue(info.type, info.meta); + buffer.nextValue(null , i ,info.type, info.meta); if (buffer.isNull()) { // diff --git a/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/DirectLogFetcherTest.java b/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/DirectLogFetcherTest.java index 23a10f01..3648da68 100644 --- a/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/DirectLogFetcherTest.java +++ b/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/DirectLogFetcherTest.java @@ -29,19 +29,12 @@ public class DirectLogFetcherTest extends BaseLogFetcherTest { statement.execute("SET @master_binlog_checksum='@@global.binlog_checksum'"); statement.execute("SET @mariadb_slave_capability='" + LogEvent.MARIA_SLAVE_CAPABILITY_MINE + "'"); - fecther.open(connection, "mysql-bin.000001", 4L, 2); + fecther.open(connection, "mysql-bin.000007", 89797036L, 2); LogDecoder decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); LogContext context = new LogContext(); while (fecther.fetch()) { - LogEvent event = null; - event = decoder.decode(fecther, context); - - if (event == null) { - continue; - // throw new RuntimeException("parse failed"); - } - + LogEvent event = decoder.decode(fecther, context); int eventType = event.getHeader().getType(); switch (eventType) { case LogEvent.ROTATE_EVENT: @@ -52,6 +45,7 @@ public class DirectLogFetcherTest extends BaseLogFetcherTest { parseRowsEvent((WriteRowsLogEvent) event); break; case LogEvent.UPDATE_ROWS_EVENT_V1: + case LogEvent.PARTIAL_UPDATE_ROWS_EVENT: case LogEvent.UPDATE_ROWS_EVENT: parseRowsEvent((UpdateRowsLogEvent) event); break; diff --git a/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/FileLogFetcherTest.java b/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/FileLogFetcherTest.java index 7673f71b..aada3de8 100644 --- a/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/FileLogFetcherTest.java +++ b/dbsync/src/test/java/com/taobao/tddl/dbsync/binlog/FileLogFetcherTest.java @@ -53,6 +53,7 @@ public class FileLogFetcherTest extends BaseLogFetcherTest { parseRowsEvent((WriteRowsLogEvent) event); break; case LogEvent.UPDATE_ROWS_EVENT_V1: + case LogEvent.PARTIAL_UPDATE_ROWS_EVENT: case LogEvent.UPDATE_ROWS_EVENT: parseRowsEvent((UpdateRowsLogEvent) event); break; diff --git a/deployer/pom.xml b/deployer/pom.xml index 5fa2efc8..d7de9395 100644 --- a/deployer/pom.xml +++ b/deployer/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter @@ -16,6 +16,14 @@ canal.server ${project.version} + + + + com.alibaba.otter + canal.prometheus + ${project.version} + runtime + @@ -32,6 +40,7 @@ **/canal.properties **/spring/** **/example/** + **/mq.yml diff --git a/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalConstants.java b/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalConstants.java index b328feb7..ba39bde0 100644 --- a/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalConstants.java +++ b/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalConstants.java @@ -15,6 +15,7 @@ public class CanalConstants { public static final String CANAL_ID = ROOT + "." + "id"; public static final String CANAL_IP = ROOT + "." + "ip"; public static final String CANAL_PORT = ROOT + "." + "port"; + public static final String CANAL_METRICS_PULL_PORT = ROOT + "." + "metrics.pull.port"; public static final String CANAL_ZKSERVERS = ROOT + "." + "zkServers"; public static final String CANAL_WITHOUT_NETTY = ROOT + "." + "withoutNetty"; @@ -22,6 +23,7 @@ public class CanalConstants { public static final String CANAL_AUTO_SCAN = ROOT + "." + "auto.scan"; public static final String CANAL_AUTO_SCAN_INTERVAL = ROOT + "." + "auto.scan.interval"; public static final String CANAL_CONF_DIR = ROOT + "." + "conf.dir"; + public static final String CANAL_SERVER_MODE = ROOT + "." + "serverMode"; public static final String CANAL_DESTINATION_SPLIT = ","; public static final String GLOBAL_NAME = "global"; @@ -35,6 +37,20 @@ public class CanalConstants { public static final String CANAL_SOCKETCHANNEL = ROOT + "." + "socketChannel"; + public static final String CANAL_MQ_SERVERS = ROOT + "." + "mq.servers"; + public static final String CANAL_MQ_RETRIES = ROOT + "." + "mq.retries"; + public static final String CANAL_MQ_BATCHSIZE = ROOT + "." + "mq.batchSize"; + public static final String CANAL_MQ_LINGERMS = ROOT + "." + "mq.lingerMs"; + public static final String CANAL_MQ_MAXREQUESTSIZE = ROOT + "." + "mq.maxRequestSize"; + public static final String CANAL_MQ_BUFFERMEMORY = ROOT + "." + "mq.bufferMemory"; + public static final String CANAL_MQ_CANALBATCHSIZE = ROOT + "." + "mq.canalBatchSize"; + public static final String CANAL_MQ_CANALGETTIMEOUT = ROOT + "." + "mq.canalGetTimeout"; + public static final String CANAL_MQ_FLATMESSAGE = ROOT + "." + "mq.flatMessage"; + public static final String CANAL_MQ_COMPRESSION_TYPE = ROOT + "." + "mq.compressionType"; + public static final String CANAL_MQ_ACKS = ROOT + "." + "mq.acks"; + public static final String CANAL_ALIYUN_ACCESSKEY = ROOT + "." + "aliyun.accessKey"; + public static final String CANAL_ALIYUN_SECRETKEY = ROOT + "." + "aliyun.secretKey"; + public static String getInstanceModeKey(String destination) { return MessageFormat.format(INSTANCE_MODE_TEMPLATE, destination); } diff --git a/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalController.java b/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalController.java index 88f6e9a3..dbc5938e 100644 --- a/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalController.java +++ b/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalController.java @@ -34,6 +34,8 @@ import com.alibaba.otter.canal.instance.core.CanalInstanceGenerator; import com.alibaba.otter.canal.instance.manager.CanalConfigClient; import com.alibaba.otter.canal.instance.manager.ManagerCanalInstanceGenerator; import com.alibaba.otter.canal.instance.spring.SpringCanalInstanceGenerator; +import com.alibaba.otter.canal.parse.CanalEventParser; +import com.alibaba.otter.canal.server.CanalMQStarter; import com.alibaba.otter.canal.server.embedded.CanalServerWithEmbedded; import com.alibaba.otter.canal.server.exception.CanalServerException; import com.alibaba.otter.canal.server.netty.CanalServerWithNetty; @@ -67,6 +69,8 @@ public class CanalController { private CanalInstanceGenerator instanceGenerator; private ZkClientx zkclientx; + private CanalMQStarter canalMQStarter; + public CanalController(){ this(System.getProperties()); } @@ -91,12 +95,30 @@ public class CanalController { System.setProperty(CanalConstants.CANAL_SOCKETCHANNEL, socketChannel); } + // 兼容1.1.0版本的ak/sk参数名 + String accesskey = getProperty(properties, "canal.instance.rds.accesskey"); + String secretkey = getProperty(properties, "canal.instance.rds.secretkey"); + if (StringUtils.isNotEmpty(accesskey)) { + System.setProperty(CanalConstants.CANAL_ALIYUN_ACCESSKEY, accesskey); + } + if (StringUtils.isNotEmpty(secretkey)) { + System.setProperty(CanalConstants.CANAL_ALIYUN_SECRETKEY, secretkey); + } + // 准备canal server cid = Long.valueOf(getProperty(properties, CanalConstants.CANAL_ID)); ip = getProperty(properties, CanalConstants.CANAL_IP); port = Integer.valueOf(getProperty(properties, CanalConstants.CANAL_PORT)); embededCanalServer = CanalServerWithEmbedded.instance(); embededCanalServer.setCanalInstanceGenerator(instanceGenerator);// 设置自定义的instanceGenerator + try { + int metricsPort = Integer.valueOf(getProperty(properties, CanalConstants.CANAL_METRICS_PULL_PORT)); + embededCanalServer.setMetricsPort(metricsPort); + } catch (NumberFormatException e) { + logger.info("No valid metrics server port found, use default 11112."); + embededCanalServer.setMetricsPort(11112); + } + String canalWithoutNetty = getProperty(properties, CanalConstants.CANAL_WITHOUT_NETTY); if (canalWithoutNetty == null || "false".equals(canalWithoutNetty)) { canalServer = CanalServerWithNetty.instance(); @@ -211,6 +233,9 @@ public class CanalController { ServerRunningMonitor runningMonitor = ServerRunningMonitors.getRunningMonitor(destination); if (!config.getLazy() && !runningMonitor.isStart()) { runningMonitor.start(); + if (canalMQStarter != null) { + canalMQStarter.startDestination(destination); + } } } } @@ -219,6 +244,9 @@ public class CanalController { // 此处的stop,代表强制退出,非HA机制,所以需要退出HA的monitor和配置信息 InstanceConfig config = instanceConfigs.remove(destination); if (config != null) { + if (canalMQStarter != null) { + canalMQStarter.stopDestination(destination); + } embededCanalServer.stop(destination); ServerRunningMonitor runningMonitor = ServerRunningMonitors.getRunningMonitor(destination); if (runningMonitor.isStart()) { @@ -303,7 +331,7 @@ public class CanalController { return instanceGenerator.generate(destination); } else if (config.getMode().isSpring()) { SpringCanalInstanceGenerator instanceGenerator = new SpringCanalInstanceGenerator(); - synchronized (this) { + synchronized (CanalEventParser.class) { try { // 设置当前正在加载的通道,加载spring查找文件时会用到该变量 System.setProperty(CanalConstants.CANAL_DESTINATION_PROPERTY, destination); @@ -345,8 +373,7 @@ public class CanalController { InstanceConfig oldConfig = instanceConfigs.put(destination, config); if (oldConfig != null) { - logger.warn("destination:{} old config:{} has replace by new config:{}", new Object[] { destination, - oldConfig, config }); + logger.warn("destination:{} old config:{} has replace by new config:{}", destination, oldConfig, config); } } } @@ -378,8 +405,19 @@ public class CanalController { return config; } - private String getProperty(Properties properties, String key) { - return StringUtils.trim(properties.getProperty(StringUtils.trim(key))); + public static String getProperty(Properties properties, String key) { + key = StringUtils.trim(key); + String value = System.getProperty(key); + + if (value == null) { + value = System.getenv(key); + } + + if (value == null) { + value = properties.getProperty(key); + } + + return StringUtils.trim(value); } public void start() throws Throwable { @@ -494,4 +532,11 @@ public class CanalController { } } + public CanalMQStarter getCanalMQStarter() { + return canalMQStarter; + } + + public void setCanalMQStarter(CanalMQStarter canalMQStarter) { + this.canalMQStarter = canalMQStarter; + } } diff --git a/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalLauncher.java b/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalLauncher.java index 828f49e2..aa7f53b0 100644 --- a/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalLauncher.java +++ b/deployer/src/main/java/com/alibaba/otter/canal/deployer/CanalLauncher.java @@ -7,9 +7,15 @@ import org.apache.commons.lang.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import com.alibaba.otter.canal.common.MQProperties; +import com.alibaba.otter.canal.kafka.CanalKafkaProducer; +import com.alibaba.otter.canal.rocketmq.CanalRocketMQProducer; +import com.alibaba.otter.canal.server.CanalMQStarter; +import com.alibaba.otter.canal.spi.CanalMQProducer; + /** * canal独立版本启动的入口类 - * + * * @author jianghang 2012-11-6 下午05:20:49 * @version 1.0.0 */ @@ -33,6 +39,19 @@ public class CanalLauncher { properties.load(new FileInputStream(conf)); } + CanalMQProducer canalMQProducer = null; + String serverMode = CanalController.getProperty(properties, CanalConstants.CANAL_SERVER_MODE); + if (serverMode.equalsIgnoreCase("kafka")) { + canalMQProducer = new CanalKafkaProducer(); + } else if (serverMode.equalsIgnoreCase("rocketmq")) { + canalMQProducer = new CanalRocketMQProducer(); + } + + if (canalMQProducer != null) { + // disable netty + System.setProperty(CanalConstants.CANAL_WITHOUT_NETTY, "true"); + } + logger.info("## start the canal server."); final CanalController controller = new CanalController(properties); controller.start(); @@ -51,12 +70,77 @@ public class CanalLauncher { } }); + + if (canalMQProducer != null) { + CanalMQStarter canalMQStarter = new CanalMQStarter(canalMQProducer); + MQProperties mqProperties = buildMQPosition(properties); + canalMQStarter.start(mqProperties); + controller.setCanalMQStarter(canalMQStarter); + } } catch (Throwable e) { logger.error("## Something goes wrong when starting up the canal Server:", e); System.exit(0); } } + private static MQProperties buildMQPosition(Properties properties) { + MQProperties mqProperties = new MQProperties(); + String servers = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_SERVERS); + if (!StringUtils.isEmpty(servers)) { + mqProperties.setServers(servers); + } + String retires = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_RETRIES); + if (!StringUtils.isEmpty(retires)) { + mqProperties.setRetries(Integer.valueOf(retires)); + } + String batchSize = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_BATCHSIZE); + if (!StringUtils.isEmpty(batchSize)) { + mqProperties.setBatchSize(Integer.valueOf(batchSize)); + } + String lingerMs = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_LINGERMS); + if (!StringUtils.isEmpty(lingerMs)) { + mqProperties.setLingerMs(Integer.valueOf(lingerMs)); + } + String maxRequestSize = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_MAXREQUESTSIZE); + if (!StringUtils.isEmpty(maxRequestSize)) { + mqProperties.setMaxRequestSize(Integer.valueOf(maxRequestSize)); + } + String bufferMemory = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_BUFFERMEMORY); + if (!StringUtils.isEmpty(bufferMemory)) { + mqProperties.setBufferMemory(Long.valueOf(bufferMemory)); + } + String canalBatchSize = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_CANALBATCHSIZE); + if (!StringUtils.isEmpty(canalBatchSize)) { + mqProperties.setCanalBatchSize(Integer.valueOf(canalBatchSize)); + } + String canalGetTimeout = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_CANALGETTIMEOUT); + if (!StringUtils.isEmpty(canalGetTimeout)) { + mqProperties.setCanalGetTimeout(Long.valueOf(canalGetTimeout)); + } + String flatMessage = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_FLATMESSAGE); + if (!StringUtils.isEmpty(flatMessage)) { + mqProperties.setFlatMessage(Boolean.valueOf(flatMessage)); + } + String compressionType = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_COMPRESSION_TYPE); + if (!StringUtils.isEmpty(compressionType)) { + mqProperties.setCompressionType(compressionType); + } + String acks = CanalController.getProperty(properties, CanalConstants.CANAL_MQ_ACKS); + if (!StringUtils.isEmpty(acks)) { + mqProperties.setAcks(acks); + } + + String aliyunAccessKey = CanalController.getProperty(properties, CanalConstants.CANAL_ALIYUN_ACCESSKEY); + if (!StringUtils.isEmpty(aliyunAccessKey)) { + mqProperties.setAliyunAccessKey(aliyunAccessKey); + } + String aliyunSecretKey = CanalController.getProperty(properties, CanalConstants.CANAL_ALIYUN_SECRETKEY); + if (!StringUtils.isEmpty(aliyunSecretKey)) { + mqProperties.setAliyunSecretKey(aliyunSecretKey); + } + return mqProperties; + } + private static void setGlobalUncaughtExceptionHandler() { Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() { diff --git a/deployer/src/main/resources/canal.properties b/deployer/src/main/resources/canal.properties index 23ec03a1..5d7b9d06 100644 --- a/deployer/src/main/resources/canal.properties +++ b/deployer/src/main/resources/canal.properties @@ -1,13 +1,16 @@ ################################################# ######### common argument ############# ################################################# -canal.id= 1 -canal.ip= -canal.port= 11111 -canal.zkServers= +canal.id = 1 +canal.ip = +canal.port = 11111 +canal.metrics.pull.port = 11112 +canal.zkServers = # flush data to zk canal.zookeeper.flush.period = 1000 canal.withoutNetty = false +# tcp, kafka, RocketMQ +canal.serverMode = tcp # flush meta cursor/parse position to file canal.file.data.dir = ${canal.conf.dir} canal.file.flush.period = 1000 @@ -17,6 +20,7 @@ canal.instance.memory.buffer.size = 16384 canal.instance.memory.buffer.memunit = 1024 ## meory store gets mode used MEMSIZE or ITEMSIZE canal.instance.memory.batch.mode = MEMSIZE +canal.instance.memory.rawEntry = true ## detecing config canal.instance.detecting.enable = false @@ -43,6 +47,7 @@ canal.instance.filter.query.dml = false canal.instance.filter.query.ddl = false canal.instance.filter.table.error = false canal.instance.filter.rows = false +canal.instance.filter.transaction.entry = false # binlog format/image check canal.instance.binlog.format = ROW,STATEMENT,MIXED @@ -58,23 +63,52 @@ canal.instance.parser.parallel = true ## disruptor ringbuffer size, must be power of 2 canal.instance.parser.parallelBufferSize = 256 +# table meta tsdb info +canal.instance.tsdb.enable = true +canal.instance.tsdb.dir = ${canal.file.data.dir:../conf}/${canal.instance.destination:} +canal.instance.tsdb.url = jdbc:h2:${canal.instance.tsdb.dir}/h2;CACHE_SIZE=1000;MODE=MYSQL; +canal.instance.tsdb.dbUsername = canal +canal.instance.tsdb.dbPassword = canal +# dump snapshot interval, default 24 hour +canal.instance.tsdb.snapshot.interval = 24 +# purge snapshot expire , default 360 hour(15 days) +canal.instance.tsdb.snapshot.expire = 360 + +# aliyun ak/sk , support rds/mq +canal.aliyun.accesskey = +canal.aliyun.secretkey = + ################################################# ######### destinations ############# ################################################# -canal.destinations= example +canal.destinations = example # conf root dir canal.conf.dir = ../conf # auto scan instance dir add/remove and start/stop instance canal.auto.scan = true canal.auto.scan.interval = 5 -canal.instance.tsdb.spring.xml=classpath:spring/tsdb/h2-tsdb.xml -#canal.instance.tsdb.spring.xml=classpath:spring/tsdb/mysql-tsdb.xml +canal.instance.tsdb.spring.xml = classpath:spring/tsdb/h2-tsdb.xml +#canal.instance.tsdb.spring.xml = classpath:spring/tsdb/mysql-tsdb.xml -canal.instance.global.mode = spring +canal.instance.global.mode = spring canal.instance.global.lazy = false #canal.instance.global.manager.address = 127.0.0.1:1099 -#canal.instance.global.spring.xml = classpath:spring/local-instance.xml #canal.instance.global.spring.xml = classpath:spring/memory-instance.xml canal.instance.global.spring.xml = classpath:spring/file-instance.xml #canal.instance.global.spring.xml = classpath:spring/default-instance.xml + +################################################## +######### MQ ############# +################################################## +canal.mq.servers = 127.0.0.1:6667 +canal.mq.retries = 0 +canal.mq.batchSize = 16384 +canal.mq.maxRequestSize = 1048576 +canal.mq.lingerMs = 1 +canal.mq.bufferMemory = 33554432 +canal.mq.canalBatchSize = 50 +canal.mq.canalGetTimeout = 100 +canal.mq.flatMessage = true +canal.mq.compressionType = none +canal.mq.acks = all diff --git a/deployer/src/main/resources/example/instance.properties b/deployer/src/main/resources/example/instance.properties index a3703b86..3a9ac883 100644 --- a/deployer/src/main/resources/example/instance.properties +++ b/deployer/src/main/resources/example/instance.properties @@ -1,37 +1,52 @@ ################################################# -## mysql serverId -canal.instance.mysql.slaveId=0 +## mysql serverId , v1.0.26+ will autoGen +# canal.instance.mysql.slaveId=0 + +# enable gtid use true/false +canal.instance.gtidon=false # position info canal.instance.master.address=127.0.0.1:3306 -# enable gtid use true/false -canal.instance.gtidon=false canal.instance.master.journal.name= canal.instance.master.position= canal.instance.master.timestamp= canal.instance.master.gtid= +# rds oss binlog +canal.instance.rds.accesskey= +canal.instance.rds.secretkey= +canal.instance.rds.instanceId= + # table meta tsdb info canal.instance.tsdb.enable=true -canal.instance.tsdb.dir=${canal.file.data.dir:../conf}/${canal.instance.destination:} -canal.instance.tsdb.url=jdbc:h2:${canal.instance.tsdb.dir}/h2;CACHE_SIZE=1000;MODE=MYSQL; #canal.instance.tsdb.url=jdbc:mysql://127.0.0.1:3306/canal_tsdb -canal.instance.tsdb.dbUsername=canal -canal.instance.tsdb.dbPassword=canal - +#canal.instance.tsdb.dbUsername=canal +#canal.instance.tsdb.dbPassword=canal #canal.instance.standby.address = #canal.instance.standby.journal.name = -#canal.instance.standby.position = +#canal.instance.standby.position = #canal.instance.standby.timestamp = #canal.instance.standby.gtid= + # username/password canal.instance.dbUsername=canal canal.instance.dbPassword=canal -canal.instance.defaultDatabaseName=test -canal.instance.connectionCharset=UTF-8 +canal.instance.connectionCharset = UTF-8 +canal.instance.defaultDatabaseName =test +# enable druid Decrypt database password +canal.instance.enableDruid=false +#canal.instance.pwdPublicKey=MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBALK4BUxdDltRRE5/zXpVEVPUgunvscYFtEip3pmLlhrWpacX7y7GCMo2/JM6LeHmiiNdH1FWgGCpUfircSwlWKUCAwEAAQ== + # table regex canal.instance.filter.regex=.*\\..* # table black regex canal.instance.filter.black.regex= + +# mq config +canal.mq.topic=example +canal.mq.partition=0 +# hash partition config +#canal.mq.partitionsNum=3 +#canal.mq.partitionHash=mytest.person:id,mytest.role:id ################################################# \ No newline at end of file diff --git a/deployer/src/main/resources/example/rds_instance.properties b/deployer/src/main/resources/example/rds_instance.properties deleted file mode 100644 index f04b3832..00000000 --- a/deployer/src/main/resources/example/rds_instance.properties +++ /dev/null @@ -1,32 +0,0 @@ -################################################# -# rds openapi binlog -canal.instance.rds.open.url=https://rds.aliyuncs.com/ -canal.instance.rds.open.accesskey= -canal.instance.rds.open.secretkey= -canal.instance.rds.instanceId= -canal.instance.rds.startTime= -canal.instance.rds.endTime= - -# local binlog dir -canal.instance.parser.directory=${canal.file.data.dir:../conf}/${canal.instance.destination:}/binlog -# position info -canal.instance.master.address=127.0.0.1:3306 - -# table meta tsdb info -canal.instance.tsdb.enable=true -canal.instance.tsdb.dir=${canal.file.data.dir:../conf}/${canal.instance.destination:} -canal.instance.tsdb.url=jdbc:h2:${canal.instance.tsdb.dir}/h2;CACHE_SIZE=1000;MODE=MYSQL; -#canal.instance.tsdb.url=jdbc:mysql://127.0.0.1:3306/canal_tsdb -#canal.instance.tsdb.dbUsername=canal -#canal.instance.tsdb.dbPassword=canal - -# username/password -canal.instance.dbUsername=canal -canal.instance.dbPassword=canal -canal.instance.defaultDatabaseName=test -canal.instance.connectionCharset=UTF-8 -# table regex -canal.instance.filter.regex=test\\..* -# table black regex -canal.instance.filter.black.regex= -################################################# \ No newline at end of file diff --git a/deployer/src/main/resources/logback.xml b/deployer/src/main/resources/logback.xml index f1c0e93b..aaaefac7 100644 --- a/deployer/src/main/resources/logback.xml +++ b/deployer/src/main/resources/logback.xml @@ -6,7 +6,7 @@ - + destination @@ -16,7 +16,7 @@ ../logs/${destination}/${destination}.log + class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy"> ../logs/${destination}/%d{yyyy-MM-dd}/${destination}-%d{yyyy-MM-dd}-%i.log.gz @@ -33,7 +33,7 @@ - + destination @@ -43,7 +43,7 @@ ../logs/${destination}/meta.log + class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy"> ../logs/${destination}/%d{yyyy-MM-dd}/meta-%d{yyyy-MM-dd}-%i.log.gz @@ -60,24 +60,24 @@ - - - - - - - - - - - - - + + + + + + + + + + + + + - + diff --git a/deployer/src/main/resources/metrics/Canal_instances_tmpl.json b/deployer/src/main/resources/metrics/Canal_instances_tmpl.json new file mode 100644 index 00000000..141810c0 --- /dev/null +++ b/deployer/src/main/resources/metrics/Canal_instances_tmpl.json @@ -0,0 +1,1375 @@ +{ + "__inputs": [ + { + "name": "DS_PROMETHEUS", + "label": "prometheus", + "description": "", + "type": "datasource", + "pluginId": "prometheus", + "pluginName": "Prometheus" + } + ], + "__requires": [ + { + "type": "grafana", + "id": "grafana", + "name": "Grafana", + "version": "5.2.2" + }, + { + "type": "panel", + "id": "graph", + "name": "Graph", + "version": "5.0.0" + }, + { + "type": "datasource", + "id": "prometheus", + "name": "Prometheus", + "version": "5.0.0" + } + ], + "annotations": { + "list": [ + { + "builtIn": 1, + "datasource": "-- Grafana --", + "enable": true, + "hide": true, + "iconColor": "rgba(0, 211, 255, 1)", + "name": "Annotations & Alerts", + "type": "dashboard" + } + ] + }, + "editable": true, + "gnetId": null, + "graphTooltip": 0, + "id": null, + "iteration": 1536989235272, + "links": [], + "panels": [ + { + "collapsed": false, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 0 + }, + "id": 30, + "panels": [], + "title": "Instance status", + "type": "row" + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Canal instance 基本信息。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 0, + "y": 1 + }, + "id": 24, + "legend": { + "alignAsTable": true, + "avg": false, + "current": false, + "hideEmpty": false, + "hideZero": false, + "max": false, + "min": false, + "rightSide": true, + "show": true, + "sideWidth": 500, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "repeat": null, + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "canal_instance{destination=~\"$destination\"}", + "format": "time_series", + "instant": true, + "intervalFactor": 1, + "legendFormat": "Destination: {{destination}}", + "refId": "A" + }, + { + "expr": "canal_instance_parser_mode{destination=~\"$destination\"}", + "format": "time_series", + "instant": true, + "intervalFactor": 1, + "legendFormat": "Parallel parser: {{parallel}}", + "refId": "B" + }, + { + "expr": "canal_instance_store{destination=~\"$destination\"}", + "format": "time_series", + "instant": true, + "intervalFactor": 1, + "legendFormat": "Batch mode: {{batchMode}}", + "refId": "C" + }, + { + "expr": "canal_instance_store{destination=~\"$destination\"}", + "format": "time_series", + "instant": true, + "intervalFactor": 1, + "legendFormat": "Buffer size: {{size}}", + "refId": "D" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Basic", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "transparent": true, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": false, + "values": [] + }, + "yaxes": [ + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": false + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": false + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": { + "inbound": "#bf1b00" + }, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Canal instance 网络带宽占用。\ninbound: 读取MySQL binlog.\noutbound: 对Client端传输格式化binlog.", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 6, + "y": 1 + }, + "id": 6, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "rate(canal_instance_received_binlog_bytes{destination=~\"$destination\", parser=\"0\"}[2m]) / 1024", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "inbound", + "refId": "A" + }, + { + "expr": "rate(canal_instance_client_bytes{destination=~\"$destination\"}[2m]) / 1024", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "outbound", + "refId": "B" + }, + { + "expr": "rate(canal_instance_received_binlog_bytes{destination=~\"$destination\", parser=\"1\"}[2m]) / 1024", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "inbound-1", + "refId": "C" + }, + { + "expr": "rate(canal_instance_received_binlog_bytes{destination=~\"$destination\", parser=\"2\"}[2m]) / 1024", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "inbound-2", + "refId": "D" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Network bandwith", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "KBs", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": { + "ack": "#f29191", + "get": "#cca300", + "put": "#1f78c1" + }, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "master: Canal server相对于MySQL master的延时。通过master heartbeat机制能刷新idle状态下的延时。\nput: store put操作的时间点为基准。\nget: client get操作的时间点为基准。\nack: client ack操作的时间点为基准。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 12, + "y": 1 + }, + "id": 4, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "canal_instance_traffic_delay{destination=~\"$destination\"} / 1000", + "format": "time_series", + "hide": false, + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "master", + "refId": "D" + }, + { + "expr": "canal_instance_put_delay{destination=~\"$destination\"} / 1000", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "put", + "refId": "A" + }, + { + "expr": "canal_instance_get_delay{destination=~\"$destination\"} / 1000", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "get", + "refId": "B" + }, + { + "expr": "canal_instance_ack_delay{destination=~\"$destination\"} / 1000", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "ack", + "refId": "C" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Delay", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "s", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "sink线程blocking占比;dump线程blocking占比(仅parallel mode)。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 18, + "y": 1 + }, + "hideTimeOverride": false, + "id": 2, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "clamp_max(rate(canal_instance_publish_blocking_time{destination=~\"$destination\", parser=\"0\"}[2m]), 1000) / 10", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "dump", + "refId": "B" + }, + { + "expr": "clamp_max(rate(canal_instance_sink_blocking_time{destination=~\"$destination\"}[2m]), 1000) / 10", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "sink", + "refId": "A" + }, + { + "expr": "clamp_max(rate(canal_instance_publish_blocking_time{destination=~\"$destination\", parser=\"1\"}[2m]), 1000) / 10", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "dump-1", + "refId": "C" + }, + { + "expr": "clamp_max(rate(canal_instance_publish_blocking_time{destination=~\"$destination\", parser=\"2\"}[2m]), 1000) / 10", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "dump-2", + "refId": "D" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Blocking", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "percent", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "collapsed": false, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 6 + }, + "id": 32, + "panels": [], + "title": "Throughput", + "type": "row" + }, + { + "aliasColors": { + "rowDatas": "#7eb26d", + "tableRows": "#c15c17" + }, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Instance处理binlog的TPS(以master变更行数table rows为基准计算)。\nput: put操作TPS。\nget: get操作TPS。\nack: ack操作TPS。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 0, + "y": 7 + }, + "id": 14, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "rate(canal_instance_put_rows{destination=~\"$destination\"}[2m])", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "put", + "refId": "A" + }, + { + "expr": "rate(canal_instance_get_rows{destination=~\"$destination\"}[2m])", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "get", + "refId": "B" + }, + { + "expr": "rate(canal_instance_ack_rows{destination=~\"$destination\"}[2m])", + "format": "time_series", + "intervalFactor": 1, + "legendFormat": "ack", + "refId": "C" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "TPS(table rows)", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "iops", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": { + "transactions": "#f9ba8f" + }, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Canal instance 处理binlog的TPS,以MySQL transaction为单位计算。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 6, + "y": 7 + }, + "id": 12, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "rate(canal_instance_transactions{destination=~\"$destination\"}[2m])", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "transactions", + "refId": "A" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "TPS(MySQL transaction)", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "iops", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "collapsed": false, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 12 + }, + "id": 34, + "panels": [], + "title": "Client", + "type": "row" + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Canal instance接收到的请求统计,结果按packet type分类。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 0, + "y": 13 + }, + "id": 16, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "canal_instance_client_packets{destination=~\"$destination\"}", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "{{packetType}}", + "refId": "A" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Client requests", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "none", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "${DS_PROMETHEUS}", + "description": "client 请求的GET与ACK包的QPS。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 6, + "y": 13 + }, + "id": 38, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "rate(canal_instance_client_packets{destination=~\"$destination\",packetType=\"GET\"}[2m])", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "GET", + "refId": "A" + }, + { + "expr": "rate(canal_instance_client_packets{destination=~\"$destination\",packetType=\"CLIENTACK\"}[2m])", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "ACK", + "refId": "B" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Client QPS", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "server响应GET请求,但返回空包的占比。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 12, + "y": 13 + }, + "id": 26, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "rate(canal_instance_client_empty_batches{destination=~\"$destination\"}[2m])", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "empty", + "refId": "A" + }, + { + "expr": "rate(canal_instance_client_packets{destination=~\"$destination\", packetType=\"GET\"}[2m])", + "format": "time_series", + "intervalFactor": 1, + "legendFormat": "nonempty", + "refId": "B" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Empty packets", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "wps", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Canal client 请求响应时间的概况。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 18, + "y": 13 + }, + "id": 18, + "legend": { + "alignAsTable": false, + "avg": false, + "current": false, + "max": false, + "min": false, + "rightSide": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [ + { + "alias": "25.0", + "yaxis": 1 + }, + { + "alias": "100.0", + "yaxis": 1 + } + ], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "rate(canal_instance_client_request_latency_bucket{destination=~\"$destination\"}[2m])", + "format": "time_series", + "hide": false, + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "{{le}}ms", + "refId": "A" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Response time", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "transparent": false, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "collapsed": false, + "gridPos": { + "h": 1, + "w": 24, + "x": 0, + "y": 18 + }, + "id": 36, + "panels": [], + "title": "Store", + "type": "row" + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Canal instance ringbuffer内未释放的events数量。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 0, + "y": 19 + }, + "id": 20, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "canal_instance_store_produce_seq{destination=~\"$destination\"} - canal_instance_store_consume_seq{destination=~\"$destination\"}", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "events", + "refId": "A" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Store remain events", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "decimals": null, + "format": "none", + "label": "", + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "decimals": null, + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + }, + { + "aliasColors": {}, + "bars": false, + "dashLength": 10, + "dashes": false, + "datasource": "$datasource", + "description": "Canal instance ringbuffer 内未释放events占用内存。", + "fill": 1, + "gridPos": { + "h": 5, + "w": 6, + "x": 6, + "y": 19 + }, + "id": 22, + "legend": { + "avg": false, + "current": false, + "max": false, + "min": false, + "show": true, + "total": false, + "values": false + }, + "lines": true, + "linewidth": 1, + "links": [], + "nullPointMode": "null", + "percentage": false, + "pointradius": 5, + "points": false, + "renderer": "flot", + "seriesOverrides": [], + "spaceLength": 10, + "stack": false, + "steppedLine": false, + "targets": [ + { + "expr": "(canal_instance_store_produce_mem{destination=~\"$destination\"} - canal_instance_store_consume_mem{destination=~\"$destination\"}) / 1024", + "format": "time_series", + "interval": "15s", + "intervalFactor": 2, + "legendFormat": "memsize", + "refId": "A" + } + ], + "thresholds": [], + "timeFrom": null, + "timeShift": null, + "title": "Store remain mem", + "tooltip": { + "shared": true, + "sort": 0, + "value_type": "individual" + }, + "type": "graph", + "xaxis": { + "buckets": null, + "mode": "time", + "name": null, + "show": true, + "values": [] + }, + "yaxes": [ + { + "format": "deckbytes", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + }, + { + "format": "short", + "label": null, + "logBase": 1, + "max": null, + "min": null, + "show": true + } + ], + "yaxis": { + "align": false, + "alignLevel": null + } + } + ], + "refresh": false, + "schemaVersion": 16, + "style": "dark", + "tags": [ + "canal" + ], + "templating": { + "list": [ + { + "current": { + "text": "prometheus", + "value": "prometheus" + }, + "hide": 0, + "label": "datasource", + "name": "datasource", + "options": [], + "query": "prometheus", + "refresh": 1, + "regex": "", + "type": "datasource" + }, + { + "allValue": null, + "current": {}, + "datasource": "$datasource", + "hide": 0, + "includeAll": false, + "label": "destination", + "multi": false, + "name": "destination", + "options": [], + "query": "label_values(canal_instance, destination)", + "refresh": 1, + "regex": "", + "sort": 0, + "tagValuesQuery": "", + "tags": [], + "tagsQuery": "", + "type": "query", + "useTags": false + } + ] + }, + "time": { + "from": "now-6h", + "to": "now" + }, + "timepicker": { + "refresh_intervals": [ + "5s", + "10s", + "30s", + "1m", + "5m", + "15m", + "30m", + "1h", + "2h", + "1d" + ], + "time_options": [ + "5m", + "15m", + "1h", + "6h", + "12h", + "24h", + "2d", + "7d", + "30d" + ] + }, + "timezone": "", + "title": "Canal instances", + "uid": "8vh8NGpiz", + "version": 103 +} \ No newline at end of file diff --git a/deployer/src/main/resources/spring/base-instance.xml b/deployer/src/main/resources/spring/base-instance.xml new file mode 100644 index 00000000..a89b7400 --- /dev/null +++ b/deployer/src/main/resources/spring/base-instance.xml @@ -0,0 +1,39 @@ + + + + + + + + + + classpath:canal.properties + classpath:${canal.instance.destination:}/instance.properties + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/deployer/src/main/resources/spring/default-instance.xml b/deployer/src/main/resources/spring/default-instance.xml index c4465df1..f312b1ce 100644 --- a/deployer/src/main/resources/spring/default-instance.xml +++ b/deployer/src/main/resources/spring/default-instance.xml @@ -10,26 +10,7 @@ http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd" default-autowire="byName"> - - - - - - - classpath:canal.properties - classpath:${canal.instance.destination:}/instance.properties - - - - - - - - - - - - + @@ -48,6 +29,9 @@ + + + @@ -77,13 +61,15 @@ + + - + @@ -144,19 +130,23 @@ - + - + + + - + - + + + @@ -189,6 +179,8 @@ + + @@ -198,4 +190,11 @@ + + + + + + + diff --git a/deployer/src/main/resources/spring/file-instance.xml b/deployer/src/main/resources/spring/file-instance.xml index 340a8158..3b6d6a8d 100644 --- a/deployer/src/main/resources/spring/file-instance.xml +++ b/deployer/src/main/resources/spring/file-instance.xml @@ -10,26 +10,7 @@ http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd" default-autowire="byName"> - - - - - - - classpath:canal.properties - classpath:${canal.instance.destination:}/instance.properties - - - - - - - - - - - - + @@ -48,6 +29,9 @@ + + + @@ -63,13 +47,15 @@ + + - + @@ -129,22 +115,26 @@ - + - + + + - + - + + + - + @@ -174,6 +164,8 @@ + + @@ -183,4 +175,11 @@ + + + + + + + diff --git a/deployer/src/main/resources/spring/group-instance.xml b/deployer/src/main/resources/spring/group-instance.xml index 60d069dc..d9c61fb8 100644 --- a/deployer/src/main/resources/spring/group-instance.xml +++ b/deployer/src/main/resources/spring/group-instance.xml @@ -10,26 +10,7 @@ http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd" default-autowire="byName"> - - - - - - - classpath:canal.properties - classpath:${canal.instance.destination:}/instance.properties - - - - - - - - - - - - + @@ -48,6 +29,9 @@ + + + @@ -60,10 +44,12 @@ + + @@ -75,7 +61,7 @@ - + @@ -126,19 +112,23 @@ - + - + + + - + - + + + @@ -173,7 +163,7 @@ - + @@ -224,19 +214,23 @@ - + - + + + - + - + + + @@ -271,4 +265,11 @@ + + + + + + + diff --git a/deployer/src/main/resources/spring/local-instance.xml b/deployer/src/main/resources/spring/local-instance.xml deleted file mode 100644 index 0b2f96aa..00000000 --- a/deployer/src/main/resources/spring/local-instance.xml +++ /dev/null @@ -1,146 +0,0 @@ - - - - - - - - - - classpath:canal.properties - classpath:${canal.instance.destination:}/instance.properties - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/deployer/src/main/resources/spring/memory-instance.xml b/deployer/src/main/resources/spring/memory-instance.xml index 8fec8918..9260c166 100644 --- a/deployer/src/main/resources/spring/memory-instance.xml +++ b/deployer/src/main/resources/spring/memory-instance.xml @@ -10,26 +10,7 @@ http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd" default-autowire="byName"> - - - - - - - classpath:canal.properties - classpath:${canal.instance.destination:}/instance.properties - - - - - - - - - - - - + @@ -48,6 +29,9 @@ + + + @@ -60,13 +44,15 @@ + + - + @@ -114,22 +100,26 @@ - + - + - + + + - + - + + + @@ -162,6 +152,8 @@ + + @@ -171,4 +163,11 @@ + + + + + + + diff --git a/deployer/src/main/resources/spring/tsdb/h2-tsdb.xml b/deployer/src/main/resources/spring/tsdb/h2-tsdb.xml index 6f8ba05d..c05b5200 100644 --- a/deployer/src/main/resources/spring/tsdb/h2-tsdb.xml +++ b/deployer/src/main/resources/spring/tsdb/h2-tsdb.xml @@ -23,7 +23,7 @@ - + @@ -31,8 +31,8 @@ - - + + diff --git a/deployer/src/main/resources/spring/tsdb/mysql-tsdb.xml b/deployer/src/main/resources/spring/tsdb/mysql-tsdb.xml index 555eec44..87f407b3 100644 --- a/deployer/src/main/resources/spring/tsdb/mysql-tsdb.xml +++ b/deployer/src/main/resources/spring/tsdb/mysql-tsdb.xml @@ -23,7 +23,7 @@ - + @@ -31,8 +31,8 @@ - - + + diff --git a/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_history.xml b/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_history.xml index 7445bf69..58957c28 100644 --- a/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_history.xml +++ b/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_history.xml @@ -36,10 +36,10 @@ - + \ No newline at end of file diff --git a/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_snapshot.xml b/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_snapshot.xml index 79aa25fe..2ee0f8f4 100644 --- a/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_snapshot.xml +++ b/deployer/src/main/resources/spring/tsdb/sql-map/sqlmap_snapshot.xml @@ -42,10 +42,10 @@ where destination=#destination# - + 0 ]]> \ No newline at end of file diff --git a/deployer/src/main/resources/spring/tsdb/sql/create_table.sql b/deployer/src/main/resources/spring/tsdb/sql/create_table.sql index e5d6dbf4..322bc2b6 100644 --- a/deployer/src/main/resources/spring/tsdb/sql/create_table.sql +++ b/deployer/src/main/resources/spring/tsdb/sql/create_table.sql @@ -26,10 +26,10 @@ CREATE TABLE IF NOT EXISTS `meta_history` ( `binlog_master_id` varchar(64) DEFAULT NULL COMMENT 'binlog节点id', `binlog_timestamp` bigint(20) DEFAULT NULL COMMENT 'binlog应用的时间戳', `use_schema` varchar(1024) DEFAULT NULL COMMENT '执行sql时对应的schema', - `schema` varchar(1024) DEFAULT NULL COMMENT '对应的schema', - `table` varchar(1024) DEFAULT NULL COMMENT '对应的table', - `sql` longtext DEFAULT NULL COMMENT '执行的sql', - `type` varchar(256) DEFAULT NULL COMMENT 'sql类型', + `sql_schema` varchar(1024) DEFAULT NULL COMMENT '对应的schema', + `sql_table` varchar(1024) DEFAULT NULL COMMENT '对应的table', + `sql_text` longtext DEFAULT NULL COMMENT '执行的sql', + `sql_type` varchar(256) DEFAULT NULL COMMENT 'sql类型', `extra` text DEFAULT NULL COMMENT '额外的扩展信息', PRIMARY KEY (`id`), UNIQUE KEY binlog_file_offest(`destination`,`binlog_master_id`,`binlog_file`,`binlog_offest`), diff --git a/docker/Dockerfile b/docker/Dockerfile new file mode 100644 index 00000000..44655560 --- /dev/null +++ b/docker/Dockerfile @@ -0,0 +1,33 @@ +FROM canal/osbase:v1 + +MAINTAINER agapple (jianghang115@gmail.com) + +# install canal +COPY image/ /tmp/docker/ +COPY canal.deployer-*.tar.gz /home/admin/ + +RUN \ + cp -R /tmp/docker/alidata /alidata && \ + chmod +x /alidata/bin/* && \ + mkdir -p /home/admin && \ + cp -R /tmp/docker/admin/* /home/admin/ && \ + /bin/cp -f alidata/bin/lark-wait /usr/bin/lark-wait && \ + + mkdir -p /home/admin/canal-server && \ + tar -xzvf /home/admin/canal.deployer-*.tar.gz -C /home/admin/canal-server && \ + /bin/rm -f /home/admin/canal.deployer-*.tar.gz && \ + + mkdir -p home/admin/canal-server/logs && \ + chmod +x /home/admin/*.sh && \ + chmod +x /home/admin/bin/*.sh && \ + chown admin: -R /home/admin && \ + yum clean all && \ + true + +# 2222 sys , 8000 debug , 11111 canal , 11112 metrics +EXPOSE 2222 11111 8000 11112 + +WORKDIR /home/admin + +ENTRYPOINT [ "/alidata/bin/main.sh" ] +CMD [ "/home/admin/app.sh" ] diff --git a/docker/base/Dockerfile b/docker/base/Dockerfile new file mode 100644 index 00000000..010b97e0 --- /dev/null +++ b/docker/base/Dockerfile @@ -0,0 +1,41 @@ +FROM centos:centos6.10 + +MAINTAINER agapple (jianghang115@gmail.com) + +env DOWNLOAD_LINK="http://download.oracle.com/otn-pub/java/jdk/8u181-b13/96a7b8442fe848ef90c96a2fad6ed6d1/jdk-8u181-linux-x64.rpm" +# install system +RUN \ + /bin/cp -f /usr/share/zoneinfo/Asia/Shanghai /etc/localtime && \ + echo 'root:Hello1234' | chpasswd && \ + groupadd -r admin && useradd -g admin admin && \ + yum install -y man && \ + yum install -y dstat && \ + yum install -y unzip && \ + yum install -y nc && \ + yum install -y openssh-server && \ + yum install -y tar && \ + yum install -y which && \ + yum install -y wget && \ + yum install -y perl && \ + yum install -y file && \ + ssh-keygen -q -N "" -t dsa -f /etc/ssh/ssh_host_dsa_key && \ + ssh-keygen -q -N "" -t rsa -f /etc/ssh/ssh_host_rsa_key && \ + sed -ri 's/session required pam_loginuid.so/#session required pam_loginuid.so/g' /etc/pam.d/sshd && \ + sed -i -e 's/^#Port 22$/Port 2222/' /etc/ssh/sshd_config && \ + mkdir -p /root/.ssh && chown root.root /root && chmod 700 /root/.ssh && \ + yum install -y cronie && \ + sed -i '/session required pam_loginuid.so/d' /etc/pam.d/crond && \ + true + +RUN \ + touch /var/lib/rpm/* && \ + wget --no-cookies --no-check-certificate --header "Cookie: gpw_e24=xxx; oraclelicense=accept-securebackup-cookie" "$DOWNLOAD_LINK" -O /tmp/jdk-8-linux-x64.rpm && \ + yum -y install /tmp/jdk-8-linux-x64.rpm && \ + /bin/rm -f /tmp/jdk-8-linux-x64.rpm && \ + + echo "export JAVA_HOME=/usr/java/latest" >> /etc/profile && \ + echo "export PATH=\$JAVA_HOME/bin:\$PATH" >> /etc/profile && \ + yum clean all && \ + true + +CMD ["/bin/bash"] diff --git a/docker/build.sh b/docker/build.sh new file mode 100644 index 00000000..6b42e3a4 --- /dev/null +++ b/docker/build.sh @@ -0,0 +1,29 @@ +#!/bin/bash + +current_path=`pwd` +case "`uname`" in + Darwin) + bin_abs_path=`cd $(dirname $0); pwd` + ;; + Linux) + bin_abs_path=$(readlink -f $(dirname $0)) + ;; + *) + bin_abs_path=`cd $(dirname $0); pwd` + ;; +esac +BASE=${bin_abs_path} + +if [ "$1" == "base" ] ; then + docker build --no-cache -t canal/osbase $BASE/base +else + rm -rf $BASE/canal.*.tar.gz ; + cd $BASE/../ && mvn clean package -Dmaven.test.skip -Denv=release && cd $current_path ; + if [ "$1" == "kafka" ] ; then + cp $BASE/../target/canal-kafka-*.tar.gz $BASE/ + docker build --no-cache -t canal/canal-server $BASE/ + else + cp $BASE/../target/canal.deployer-*.tar.gz $BASE/ + docker build --no-cache -t canal/canal-server $BASE/ + fi +fi diff --git a/docker/image/admin/app.sh b/docker/image/admin/app.sh new file mode 100755 index 00000000..413378c8 --- /dev/null +++ b/docker/image/admin/app.sh @@ -0,0 +1,121 @@ +#!/bin/bash +set -e + +source /etc/profile +export JAVA_HOME=/usr/java/latest +export PATH=$JAVA_HOME/bin:$PATH +touch /tmp/start.log +chown admin: /tmp/start.log +chown -R admin: /home/admin/canal-server +host=`hostname -i` + +# waitterm +# wait TERM/INT signal. +# see: http://veithen.github.io/2014/11/16/sigterm-propagation.html +waitterm() { + local PID + # any process to block + tail -f /dev/null & + PID="$!" + # setup trap, could do nothing, or just kill the blocker + trap "kill -TERM ${PID}" TERM INT + # wait for signal, ignore wait exit code + wait "${PID}" || true + # clear trap + trap - TERM INT + # wait blocker, ignore blocker exit code + wait "${PID}" 2>/dev/null || true +} + +# waittermpid "${PIDFILE}". +# monitor process by pidfile && wait TERM/INT signal. +# if the process disappeared, return 1, means exit with ERROR. +# if TERM or INT signal received, return 0, means OK to exit. +waittermpid() { + local PIDFILE PID do_run error + PIDFILE="${1?}" + do_run=true + error=0 + trap "do_run=false" TERM INT + while "${do_run}" ; do + PID="$(cat "${PIDFILE}")" + if ! ps -p "${PID}" >/dev/null 2>&1 ; then + do_run=false + error=1 + else + sleep 1 + fi + done + trap - TERM INT + return "${error}" +} + + +function checkStart() { + local name=$1 + local cmd=$2 + local timeout=$3 + cost=5 + while [ $timeout -gt 0 ]; do + ST=`eval $cmd` + if [ "$ST" == "0" ]; then + sleep 1 + let timeout=timeout-1 + let cost=cost+1 + elif [ "$ST" == "" ]; then + sleep 1 + let timeout=timeout-1 + let cost=cost+1 + else + break + fi + done + echo "start $name successful" +} + + +function start_canal() { + echo "start canal ..." + metricsPort=`perl -le 'print $ENV{"canal.metrics.pull.port"}'` + if [ -z "$metricsPort" ] ; then + metricsPort=11112 + fi + + destination=`perl -le 'print $ENV{"canal.destinations"}'` + if [[ "$destination" =~ ',' ]]; then + echo "multi destination:$destination is not support" + exit 1; + else + if [ "$destination" != "" ] && [ "$destination" != "example" ] ; then + if [ -d /home/admin/canal-server/conf/example ]; then + mv /home/admin/canal-server/conf/example /home/admin/canal-server/conf/$destination + fi + fi + fi + su admin -c 'cd /home/admin/canal-server/bin/ && sh restart.sh 1>>/tmp/start.log 2>&1' + sleep 5 + #check start + checkStart "canal" "nc 127.0.0.1 $metricsPort -w 1 -z | wc -l" 30 +} + +function stop_canal() { + echo "stop canal" + su admin -c 'cd /home/admin/canal-server/bin/ && sh stop.sh 1>>/tmp/start.log 2>&1' + echo "stop canal successful ..." +} + +echo "==> START ..." + +start_canal + +echo "==> START SUCCESSFUL ..." + +tail -f /dev/null & +# wait TERM signal +waitterm + +echo "==> STOP" + +stop_canal + +echo "==> STOP SUCCESSFUL ..." diff --git a/docker/image/admin/bin/clean_log b/docker/image/admin/bin/clean_log new file mode 100644 index 00000000..df183614 --- /dev/null +++ b/docker/image/admin/bin/clean_log @@ -0,0 +1,2 @@ +# cron clean log once per minute +*/2 * * * * admin /home/admin/bin/clean_log.sh >>/tmp/clean_log.log 2>&1 diff --git a/docker/image/admin/bin/clean_log.sh b/docker/image/admin/bin/clean_log.sh new file mode 100755 index 00000000..9d0a0bef --- /dev/null +++ b/docker/image/admin/bin/clean_log.sh @@ -0,0 +1,45 @@ +#!/bin/bash + +# Global Settings +PATH="$HOME/bin:/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin:/usr/X11R6/bin:/root/bin" +export PATH + +CUTOFF="85" +#获取磁盘使用率最高的分区 +USAGE=$(df -h|awk 'NR>1 {gsub(/%$/,"",$5);print $5 }'|sort -nr|head -1) +before=$USAGE + +baseClean(){ + #删除tmp目录15天前的文件。 + #更新文档时间戳 + if [ -d /tmp/hsperfdata_admin ] + then + touch /tmp/hsperfdata_admin + touch /tmp/hsperfdata_admin/* + fi + + find /tmp/ -type f -mtime +15 | xargs -t rm -rf >/dev/null 2>&1 + + + now=$(df -h|awk 'NR>1 {gsub(/%$/,"",$5);print $5 }'|sort -nr|head -1) + echo "before:$before; now:$now" +} + +CANAL_DIR="/home/admin/canal-server/logs" +if [[ -d $CANAL_DIR ]]; then + USAGE=$(df -h|awk 'NR>1 {gsub(/%$/,"",$5);print $5 }'|sort -nr|head -1) + if [[ $USAGE -ge 90 ]]; then + find $CANAL_DIR -type f -mtime +7 | xargs rm -rf {} + fi + USAGE=$(df -h|awk 'NR>1 {gsub(/%$/,"",$5);print $5 }'|sort -nr|head -1) + if [[ $USAGE -ge 80 ]]; then + find $CANAL_DIR -type f -mtime +3 | xargs rm -rf {} + fi + USAGE=$(df -h|awk 'NR>1 {gsub(/%$/,"",$5);print $5 }'|sort -nr|head -1) + if [[ $USAGE -ge 80 ]]; then + find $CANAL_DIR -type d -empty -mtime +3 | grep -v canal | xargs rm -rf {} + find $CANAL_DIR -type f -iname '*.tmp' | xargs rm -rf {} + fi + baseClean + exit 0 +fi \ No newline at end of file diff --git a/docker/image/admin/health.sh b/docker/image/admin/health.sh new file mode 100755 index 00000000..c48e6d9d --- /dev/null +++ b/docker/image/admin/health.sh @@ -0,0 +1,18 @@ +#!/bin/sh +metrics_port=`perl -le 'print $ENV{"canal.metrics.pull.port"}'` +if [ "$metrics_port" == "" ]; then + metrics_port="11112" +fi + +CHECK_URL="http://127.0.0.1:$metrics_port/metrics" +CHECK_POINT="canal" +CHECK_COUNT=`curl -s --connect-timeout 7 --max-time 7 $CHECK_URL | grep -c $CHECK_POINT` +if [ $CHECK_COUNT -eq 0 ]; then + echo "[FAILED]" + status=0 + error=1 +else + echo "[ OK ]" + status=1 + error=0 +fi \ No newline at end of file diff --git a/docker/image/alidata/bin/exec_rc_local.sh b/docker/image/alidata/bin/exec_rc_local.sh new file mode 100755 index 00000000..7cc8aa3f --- /dev/null +++ b/docker/image/alidata/bin/exec_rc_local.sh @@ -0,0 +1,11 @@ +#!/bin/bash + +if [ "${SKIP_EXEC_RC_LOCAL}" = "YES" ] ; then + echo "skip /etc/rc.local: SKIP_EXEC_RC_LOCAL=${SKIP_EXEC_RC_LOCAL}" + exit +fi + +if [ "${DOCKER_DEPLOY_TYPE}" = "HOST" ] ; then + echo "skip /etc/rc.local: DOCKER_DEPLOY_TYPE=${DOCKER_DEPLOY_TYPE}" + exit +fi \ No newline at end of file diff --git a/docker/image/alidata/bin/lark-wait b/docker/image/alidata/bin/lark-wait new file mode 100755 index 00000000..db7be708 --- /dev/null +++ b/docker/image/alidata/bin/lark-wait @@ -0,0 +1,6 @@ +#!/bin/bash +set -e + +chown admin: -R /home/admin/ +source /alidata/lib/proc.sh +waitterm diff --git a/docker/image/alidata/bin/main.sh b/docker/image/alidata/bin/main.sh new file mode 100755 index 00000000..a57551a7 --- /dev/null +++ b/docker/image/alidata/bin/main.sh @@ -0,0 +1,27 @@ +#!/bin/bash + +[ -n "${DOCKER_DEPLOY_TYPE}" ] || DOCKER_DEPLOY_TYPE="VM" +echo "DOCKER_DEPLOY_TYPE=${DOCKER_DEPLOY_TYPE}" + +# run init scripts +for e in $(ls /alidata/init/*) ; do + [ -x "${e}" ] || continue + echo "==> INIT $e" + $e + echo "==> EXIT CODE: $?" +done + +echo "==> INIT DEFAULT" +service sshd start +service crond start + +#echo "check hostname -i: `hostname -i`" +#hti_num=`hostname -i|awk '{print NF}'` +#if [ $hti_num -gt 1 ];then +# echo "hostname -i result error:`hostname -i`" +# exit 120 +#fi + +echo "==> INIT DONE" +echo "==> RUN ${*}" +exec "${@}" \ No newline at end of file diff --git a/docker/image/alidata/init/02init-sshd.sh b/docker/image/alidata/init/02init-sshd.sh new file mode 100755 index 00000000..118ee553 --- /dev/null +++ b/docker/image/alidata/init/02init-sshd.sh @@ -0,0 +1,19 @@ +#!/bin/bash + +# set port +if [ -z "${SSHD_PORT}" ] ; then + SSHD_PORT=22 + [ "${DOCKER_DEPLOY_TYPE}" = "HOST" ] && SSHD_PORT=2222 +fi + +sed -r -i '/^OPTIONS=/ d' /etc/sysconfig/sshd +echo 'OPTIONS="-p '"${SSHD_PORT}"'"' >> /etc/sysconfig/sshd + +# set admin ssh pulic key +if [ "${USE_ADMIN_PASSAGE}" = "YES" ] ; then + echo "set admin passage" + mkdir -p /home/admin/.ssh + chown admin:admin /home/admin/.ssh + chown admin:admin /home/admin/.ssh/authorized_keys + chmod 644 /home/admin/.ssh/authorized_keys +fi diff --git a/docker/image/alidata/init/fix-hosts.py b/docker/image/alidata/init/fix-hosts.py new file mode 100755 index 00000000..4ee8abb5 --- /dev/null +++ b/docker/image/alidata/init/fix-hosts.py @@ -0,0 +1,66 @@ +#!/usr/bin/python +# -*- coding: utf-8 -*- +#****************************************************************# +# Create Date: 2017-01-06 17:58 +#***************************************************************# + +import socket +import shutil +from time import gmtime, strftime + +# get host_name +host_name = socket.gethostname() +tmp_file = "/tmp/.lark-fix-host.hosts" +host_file = "/etc/hosts" +bak_file_name = "/tmp/hosts-fix-bak.%s" % ( strftime("%Y-%m-%d_%H-%M-%S", gmtime()) ) + +# load /etc/hosts file context +FH = open(host_file,"r") +file_lines = [ i.rstrip() for i in FH.readlines()] +FH.close() +file_lines_reverse = file_lines[::-1] +new_lines = [] +bad_lines = [] +last_match_line = "" + +for line in file_lines_reverse: + if line.find(host_name) < 0: # 不匹配的行直接跳过 + new_lines.append(line + "\n") + continue + + cols = line.split() + new_cols = [] + if cols[0].startswith("#"): # 跳过已经注释掉的行 + new_lines.append(line + "\n") + continue + for col in cols: + if not col == host_name: # 跳过不匹配的列 + new_cols.append(col) + continue + + if cols[0] == "127.0.0.1": # 如果第一列是 127.0.0.1 就跳过匹配的列, 防止 hostname -i 返回 127.0.0.1 + continue + + # 如果已经发现过匹配的列, 就丢掉重复的列 + if not len(last_match_line) == 0: + continue + + new_cols.append(col) + last_match_line = line + + # 跳过 xx.xx.xx.xx hostname 这样的重复列 + if len(new_cols) == 1: + continue + + new_l = "%s\n" % " ".join(new_cols) + new_lines.append(new_l) + +# save tmp hosts + +FH2=file(tmp_file,"w+") +FH2.writelines( new_lines[::-1]) +FH2.close() + +# mv to /etc/hosts +shutil.copy(host_file, bak_file_name) +shutil.move(tmp_file, host_file) diff --git a/docker/image/alidata/lib/proc.sh b/docker/image/alidata/lib/proc.sh new file mode 100644 index 00000000..40ddff93 --- /dev/null +++ b/docker/image/alidata/lib/proc.sh @@ -0,0 +1,40 @@ +# waitterm +# wait TERM/INT signal. +# see: http://veithen.github.io/2014/11/16/sigterm-propagation.html +waitterm() { + local PID + # any process to block + tail -f /dev/null & + PID="$!" + # setup trap, could do nothing, or just kill the blocker + trap "kill -TERM ${PID}" TERM INT + # wait for signal, ignore wait exit code + wait "${PID}" || true + # clear trap + trap - TERM INT + # wait blocker, ignore blocker exit code + wait "${PID}" 2>/dev/null || true +} + +# waittermpid "${PIDFILE}". +# monitor process by pidfile && wait TERM/INT signal. +# if the process disappeared, return 1, means exit with ERROR. +# if TERM or INT signal received, return 0, means OK to exit. +waittermpid() { + local PIDFILE PID do_run error + PIDFILE="${1?}" + do_run=true + error=0 + trap "do_run=false" TERM INT + while "${do_run}" ; do + PID="$(cat "${PIDFILE}")" + if ! ps -p "${PID}" >/dev/null 2>&1 ; then + do_run=false + error=1 + else + sleep 1 + fi + done + trap - TERM INT + return "${error}" +} diff --git a/docker/run.sh b/docker/run.sh new file mode 100644 index 00000000..28f32411 --- /dev/null +++ b/docker/run.sh @@ -0,0 +1,92 @@ +#!/bin/bash + +function usage() { + echo "Usage:" + echo " run.sh [CONFIG]" + echo "example:" + echo " run.sh -e canal.instance.master.address=127.0.0.1:3306 \\" + echo " -e canal.instance.dbUsername=canal \\" + echo " -e canal.instance.dbPassword=canal \\" + echo " -e canal.instance.connectionCharset=UTF-8 \\" + echo " -e canal.instance.tsdb.enable=true \\" + echo " -e canal.instance.gtidon=false \\" + echo " -e canal.instance.filter.regex=.*\\\\\\..* " + exit +} + +function check_port() { + local port=$1 + local TL=$(which telnet) + if [ -f $TL ]; then + data=`echo quit | telnet 127.0.0.1 $port| grep -ic connected` + echo $data + return + fi + + local NC=$(which nc) + if [ -f $NC ]; then + data=`nc -z -w 1 127.0.0.1 $port | grep -ic succeeded` + echo $data + return + fi + echo "0" + return +} + +function getMyIp() { + case "`uname`" in + Darwin) + myip=`echo "show State:/Network/Global/IPv4" | scutil | grep PrimaryInterface | awk '{print $3}' | xargs ifconfig | grep inet | grep -v inet6 | awk '{print $2}'` + ;; + *) + myip=`ip route get 1 | awk '{print $NF;exit}'` + ;; + esac + echo $myip +} + +NET_MODE="" +case "`uname`" in + Darwin) + bin_abs_path=`cd $(dirname $0); pwd` + ;; + Linux) + bin_abs_path=$(readlink -f $(dirname $0)) + NET_MODE="--net=host" + ;; + *) + NET_MODE="--net=host" + bin_abs_path=`cd $(dirname $0); pwd` + ;; +esac +BASE=${bin_abs_path} +if [ $# -eq 0 ]; then + usage +elif [ "$1" == "-h" ] ; then + usage +elif [ "$1" == "help" ] ; then + usage +fi + +DATA="$BASE/data" +mkdir -p $DATA +CONFIG=${@:1} +#VOLUMNS="-v $DATA:/home/admin/canal-server/logs" +PORTLIST="8000 2222 11111 11112" +PORTS="" +for PORT in $PORTLIST ; do + #exist=`check_port $PORT` + exist="0" + if [ "$exist" == "0" ]; then + PORTS="$PORTS -p $PORT:$PORT" + else + echo "port $PORT is used , pls check" + exit 1 + fi +done + +MEMORY="-m 4096m" +LOCALHOST=`getMyIp` +cmd="docker run -it -h $LOCALHOST $CONFIG --name=canal-server $VOLUMNS $NET_MODE $PORTS $MEMORY canal/canal-server" +echo $cmd +eval $cmd diff --git a/driver/pom.xml b/driver/pom.xml index edd24e57..05baa5ac 100644 --- a/driver/pom.xml +++ b/driver/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter diff --git a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/MysqlConnector.java b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/MysqlConnector.java index 29b96852..0f01cbd5 100644 --- a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/MysqlConnector.java +++ b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/MysqlConnector.java @@ -32,7 +32,7 @@ public class MysqlConnector { private String password; private byte charsetNumber = 33; - private String defaultSchema = "retl"; + private String defaultSchema = "test"; private int soTimeout = 30 * 1000; private int connTimeout = 5 * 1000; private int receiveBufferSize = 16 * 1024; diff --git a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/MysqlGTIDSet.java b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/MysqlGTIDSet.java index 35872370..f5128e23 100644 --- a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/MysqlGTIDSet.java +++ b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/MysqlGTIDSet.java @@ -86,7 +86,8 @@ public class MysqlGTIDSet implements GTIDSet { if (gtidData == null || gtidData.length() < 1) { m = new HashMap(); } else { - String[] uuidStrs = gtidData.split(","); + // 存在多个GTID时会有回车符 + String[] uuidStrs = gtidData.replaceAll("\n", "").split(","); m = new HashMap(uuidStrs.length); for (int i = 0; i < uuidStrs.length; i++) { UUIDSet uuidSet = UUIDSet.parse(uuidStrs[i]); diff --git a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/client/BinlogDumpCommandPacket.java b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/client/BinlogDumpCommandPacket.java index 70624549..f0fba11a 100644 --- a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/client/BinlogDumpCommandPacket.java +++ b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/packets/client/BinlogDumpCommandPacket.java @@ -54,7 +54,7 @@ public class BinlogDumpCommandPacket extends CommandPacket { // 1. write 4 bytes bin-log position to start at ByteHelper.writeUnsignedIntLittleEndian(binlogPosition, out); // 2. write 2 bytes bin-log flags - int binlog_flags = BINLOG_DUMP_NON_BLOCK; + int binlog_flags = 0; binlog_flags |= BINLOG_SEND_ANNOTATE_ROWS_EVENT; out.write(binlog_flags); out.write(0x00); diff --git a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/BioSocketChannel.java b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/BioSocketChannel.java index 2ed318e8..dfa2783f 100644 --- a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/BioSocketChannel.java +++ b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/BioSocketChannel.java @@ -1,5 +1,6 @@ package com.alibaba.otter.canal.parse.driver.mysql.socket; +import java.io.BufferedInputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; @@ -24,7 +25,7 @@ public class BioSocketChannel implements SocketChannel { BioSocketChannel(Socket socket) throws IOException{ this.socket = socket; - this.input = socket.getInputStream(); + this.input = new BufferedInputStream(socket.getInputStream(), 16384); this.output = socket.getOutputStream(); } @@ -87,8 +88,9 @@ public class BioSocketChannel implements SocketChannel { } } if (remain > 0 && accTimeout >= timeout) { - throw new SocketTimeoutException("Timeout occurred, failed to read " + readSize + " bytes in " + timeout - + " milliseconds."); + throw new SocketTimeoutException("Timeout occurred, failed to read total " + readSize + " bytes in " + + timeout + " milliseconds, actual read only " + (readSize - remain) + + " bytes"); } return data; } @@ -119,8 +121,8 @@ public class BioSocketChannel implements SocketChannel { } if (n < len && accTimeout >= timeout) { - throw new SocketTimeoutException("Timeout occurred, failed to read " + len + " bytes in " + timeout - + " milliseconds."); + throw new SocketTimeoutException("Timeout occurred, failed to read total " + len + " bytes in " + timeout + + " milliseconds, actual read only " + n + " bytes"); } } @@ -137,6 +139,16 @@ public class BioSocketChannel implements SocketChannel { if (socket != null) { return socket.getRemoteSocketAddress(); } + + return null; + } + + public SocketAddress getLocalSocketAddress() { + Socket socket = this.socket; + if (socket != null) { + return socket.getLocalSocketAddress(); + } + return null; } @@ -164,5 +176,4 @@ public class BioSocketChannel implements SocketChannel { this.socket = null; } - } diff --git a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/NettySocketChannel.java b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/NettySocketChannel.java index 782af21e..878dc605 100644 --- a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/NettySocketChannel.java +++ b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/NettySocketChannel.java @@ -216,6 +216,10 @@ public class NettySocketChannel implements SocketChannel { return channel != null ? channel.remoteAddress() : null; } + public SocketAddress getLocalSocketAddress() { + return channel != null ? channel.localAddress() : null; + } + public void close() { if (channel != null) { channel.close(); diff --git a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/SocketChannel.java b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/SocketChannel.java index 67f967ab..b67702ae 100644 --- a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/SocketChannel.java +++ b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/socket/SocketChannel.java @@ -21,5 +21,7 @@ public interface SocketChannel { public SocketAddress getRemoteSocketAddress(); + public SocketAddress getLocalSocketAddress(); + public void close(); } diff --git a/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/utils/CharsetUtil.java b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/utils/CharsetUtil.java new file mode 100644 index 00000000..ba98a87f --- /dev/null +++ b/driver/src/main/java/com/alibaba/otter/canal/parse/driver/mysql/utils/CharsetUtil.java @@ -0,0 +1,258 @@ +package com.alibaba.otter.canal.parse.driver.mysql.utils; + +import java.util.HashMap; +import java.util.Map; + +import org.apache.commons.lang.StringUtils; + +/** + * mysql collation转换mapping关系表 + * + * @author agapple 2018年11月5日 下午1:01:15 + * @since 1.1.2 + */ +public class CharsetUtil { + + private static final String[] INDEX_TO_CHARSET = new String[2048]; + private static final Map CHARSET_TO_INDEX = new HashMap(); + static { + INDEX_TO_CHARSET[1] = "big5"; + INDEX_TO_CHARSET[84] = "big5"; + + INDEX_TO_CHARSET[3] = "dec8"; + INDEX_TO_CHARSET[69] = "dec8"; + + INDEX_TO_CHARSET[4] = "cp850"; + INDEX_TO_CHARSET[80] = "cp850"; + + INDEX_TO_CHARSET[6] = "hp8"; + INDEX_TO_CHARSET[72] = "hp8"; + + INDEX_TO_CHARSET[7] = "koi8r"; + INDEX_TO_CHARSET[74] = "koi8r"; + + INDEX_TO_CHARSET[5] = "latin1"; + INDEX_TO_CHARSET[8] = "latin1"; + INDEX_TO_CHARSET[15] = "latin1"; + INDEX_TO_CHARSET[31] = "latin1"; + INDEX_TO_CHARSET[47] = "latin1"; + INDEX_TO_CHARSET[48] = "latin1"; + INDEX_TO_CHARSET[49] = "latin1"; + INDEX_TO_CHARSET[94] = "latin1"; + + INDEX_TO_CHARSET[9] = "latin2"; + INDEX_TO_CHARSET[21] = "latin2"; + INDEX_TO_CHARSET[27] = "latin2"; + INDEX_TO_CHARSET[77] = "latin2"; + + INDEX_TO_CHARSET[10] = "swe7"; + INDEX_TO_CHARSET[82] = "swe7"; + + INDEX_TO_CHARSET[11] = "ascii"; + INDEX_TO_CHARSET[65] = "ascii"; + + INDEX_TO_CHARSET[12] = "ujis"; + INDEX_TO_CHARSET[91] = "ujis"; + + INDEX_TO_CHARSET[13] = "sjis"; + INDEX_TO_CHARSET[88] = "sjis"; + + INDEX_TO_CHARSET[16] = "hebrew"; + INDEX_TO_CHARSET[71] = "hebrew"; + + INDEX_TO_CHARSET[18] = "tis620"; + INDEX_TO_CHARSET[69] = "tis620"; + + INDEX_TO_CHARSET[19] = "euckr"; + INDEX_TO_CHARSET[85] = "euckr"; + + INDEX_TO_CHARSET[22] = "koi8u"; + INDEX_TO_CHARSET[75] = "koi8u"; + + INDEX_TO_CHARSET[24] = "gb2312"; + INDEX_TO_CHARSET[86] = "gb2312"; + + INDEX_TO_CHARSET[25] = "greek"; + INDEX_TO_CHARSET[70] = "greek"; + + INDEX_TO_CHARSET[26] = "cp1250"; + INDEX_TO_CHARSET[34] = "cp1250"; + INDEX_TO_CHARSET[44] = "cp1250"; + INDEX_TO_CHARSET[66] = "cp1250"; + INDEX_TO_CHARSET[99] = "cp1250"; + + INDEX_TO_CHARSET[28] = "gbk"; + INDEX_TO_CHARSET[87] = "gbk"; + + INDEX_TO_CHARSET[30] = "latin5"; + INDEX_TO_CHARSET[78] = "latin5"; + + INDEX_TO_CHARSET[32] = "armscii8"; + INDEX_TO_CHARSET[64] = "armscii8"; + + INDEX_TO_CHARSET[33] = "utf8"; + INDEX_TO_CHARSET[83] = "utf8"; + for (int i = 192; i <= 223; i++) { + INDEX_TO_CHARSET[i] = "utf8"; + } + for (int i = 336; i <= 337; i++) { + INDEX_TO_CHARSET[i] = "utf8"; + } + for (int i = 352; i <= 357; i++) { + INDEX_TO_CHARSET[i] = "utf8"; + } + INDEX_TO_CHARSET[368] = "utf8"; + INDEX_TO_CHARSET[2047] = "utf8"; + + INDEX_TO_CHARSET[35] = "ucs2"; + INDEX_TO_CHARSET[90] = "ucs2"; + for (int i = 128; i <= 151; i++) { + INDEX_TO_CHARSET[i] = "ucs2"; + } + INDEX_TO_CHARSET[159] = "ucs2"; + for (int i = 358; i <= 360; i++) { + INDEX_TO_CHARSET[i] = "ucs2"; + } + + INDEX_TO_CHARSET[36] = "cp866"; + INDEX_TO_CHARSET[68] = "cp866"; + + INDEX_TO_CHARSET[37] = "keybcs2"; + INDEX_TO_CHARSET[73] = "keybcs2"; + + INDEX_TO_CHARSET[38] = "macce"; + INDEX_TO_CHARSET[43] = "macce"; + + INDEX_TO_CHARSET[39] = "macroman"; + INDEX_TO_CHARSET[53] = "macroman"; + + INDEX_TO_CHARSET[40] = "cp852"; + INDEX_TO_CHARSET[81] = "cp852"; + + INDEX_TO_CHARSET[20] = "latin7"; + INDEX_TO_CHARSET[41] = "latin7"; + INDEX_TO_CHARSET[42] = "latin7"; + INDEX_TO_CHARSET[79] = "latin7"; + + INDEX_TO_CHARSET[45] = "utf8mb4"; + INDEX_TO_CHARSET[46] = "utf8mb4"; + for (int i = 224; i <= 247; i++) { + INDEX_TO_CHARSET[i] = "utf8mb4"; + } + for (int i = 255; i <= 271; i++) { + INDEX_TO_CHARSET[i] = "utf8mb4"; + } + for (int i = 273; i <= 275; i++) { + INDEX_TO_CHARSET[i] = "utf8mb4"; + } + for (int i = 277; i <= 294; i++) { + INDEX_TO_CHARSET[i] = "utf8mb4"; + } + for (int i = 296; i <= 298; i++) { + INDEX_TO_CHARSET[i] = "utf8mb4"; + } + INDEX_TO_CHARSET[300] = "utf8mb4"; + for (int i = 303; i <= 307; i++) { + INDEX_TO_CHARSET[i] = "utf8mb4"; + } + INDEX_TO_CHARSET[326] = "utf8mb4"; + INDEX_TO_CHARSET[328] = "utf8mb4"; + + INDEX_TO_CHARSET[14] = "cp1251"; + INDEX_TO_CHARSET[23] = "cp1251"; + INDEX_TO_CHARSET[50] = "cp1251"; + INDEX_TO_CHARSET[51] = "cp1251"; + INDEX_TO_CHARSET[52] = "cp1251"; + + INDEX_TO_CHARSET[54] = "utf16"; + INDEX_TO_CHARSET[55] = "utf16"; + for (int i = 101; i <= 124; i++) { + INDEX_TO_CHARSET[i] = "utf16"; + } + INDEX_TO_CHARSET[327] = "utf16"; + + INDEX_TO_CHARSET[56] = "utf16le"; + INDEX_TO_CHARSET[62] = "utf16le"; + + INDEX_TO_CHARSET[57] = "cp1256"; + INDEX_TO_CHARSET[67] = "cp1256"; + + INDEX_TO_CHARSET[29] = "cp1257"; + INDEX_TO_CHARSET[58] = "cp1257"; + INDEX_TO_CHARSET[59] = "cp1257"; + + INDEX_TO_CHARSET[60] = "utf32"; + INDEX_TO_CHARSET[61] = "utf32"; + for (int i = 160; i <= 183; i++) { + INDEX_TO_CHARSET[i] = "utf32"; + } + INDEX_TO_CHARSET[391] = "utf32"; + + INDEX_TO_CHARSET[63] = "binary"; + + INDEX_TO_CHARSET[92] = "geostd8"; + INDEX_TO_CHARSET[93] = "geostd8"; + + INDEX_TO_CHARSET[95] = "cp932"; + INDEX_TO_CHARSET[96] = "cp932"; + + INDEX_TO_CHARSET[97] = "eucjpms"; + INDEX_TO_CHARSET[98] = "eucjpms"; + + for (int i = 248; i <= 250; i++) { + INDEX_TO_CHARSET[i] = "gb18030"; + } + + // charset --> index + for (int i = 0; i < 2048; i++) { + String charset = INDEX_TO_CHARSET[i]; + if (charset != null && CHARSET_TO_INDEX.get(charset) == null) { + CHARSET_TO_INDEX.put(charset, i); + } + } + CHARSET_TO_INDEX.put("iso-8859-1", 14); + CHARSET_TO_INDEX.put("iso_8859_1", 14); + CHARSET_TO_INDEX.put("utf-8", 33); + CHARSET_TO_INDEX.put("utf8mb4", 45); + } + + public static final String getCharset(int index) { + return INDEX_TO_CHARSET[index]; + } + + public static final int getIndex(String charset) { + if (charset == null || charset.length() == 0) { + return 0; + } else { + Integer i = CHARSET_TO_INDEX.get(charset.toLowerCase()); + return (i == null) ? 0 : i.intValue(); + } + } + + /** + * 'utf8' COLLATE 'utf8_general_ci' + * + * @param charset + * @return + */ + public static final String collateCharset(String charset) { + String[] output = StringUtils.split(charset, "COLLATE"); + return output[0].replace('\'', ' ').trim(); + } + + public static String getJavaCharset(String charset) { + if ("utf8".equals(charset)) { + return charset; + } + + if (StringUtils.endsWithIgnoreCase(charset, "utf8mb4")) { + return "utf-8"; + } + + if (StringUtils.endsWithIgnoreCase(charset, "binary")) { + return "iso_8859_1"; + } + + return charset; + } +} diff --git a/driver/src/test/java/com/alibaba/otter/canal/parse/driver/mysql/CharsetUtilTest.java b/driver/src/test/java/com/alibaba/otter/canal/parse/driver/mysql/CharsetUtilTest.java new file mode 100644 index 00000000..09837d09 --- /dev/null +++ b/driver/src/test/java/com/alibaba/otter/canal/parse/driver/mysql/CharsetUtilTest.java @@ -0,0 +1,51 @@ +package com.alibaba.otter.canal.parse.driver.mysql; + +import org.junit.Assert; +import org.junit.Test; + +import com.alibaba.otter.canal.parse.driver.mysql.utils.CharsetUtil; + +public class CharsetUtilTest { + + @Test + public void testLatin1() { + int charsetIndex = 5; + String charset = "latin1"; + Assert.assertTrue(charset.equals(CharsetUtil.getCharset(charsetIndex))); + } + + @Test + public void testGbk() { + int charsetIndex = 87; + String charset = "gbk"; + Assert.assertTrue(charset.equals(CharsetUtil.getCharset(charsetIndex))); + } + + @Test + public void testGb2312() { + int charsetIndex = 24; + String charset = "gb2312"; + Assert.assertTrue(charset.equals(CharsetUtil.getCharset(charsetIndex))); + } + + @Test + public void testUtf8() { + int charsetIndex = 213; + String charset = "utf8"; + Assert.assertTrue(charset.equals(CharsetUtil.getCharset(charsetIndex))); + } + + @Test + public void testUtf8mb4() { + int charsetIndex = 235; + String charset = "utf8mb4"; + Assert.assertTrue(charset.equals(CharsetUtil.getCharset(charsetIndex))); + } + + @Test + public void testBinary() { + int charsetIndex = 63; + String charset = "binary"; + Assert.assertTrue(charset.equals(CharsetUtil.getCharset(charsetIndex))); + } +} diff --git a/example/pom.xml b/example/pom.xml index 1f60bc01..819b4b12 100644 --- a/example/pom.xml +++ b/example/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter @@ -21,6 +21,82 @@ canal.protocol ${project.version} + + com.alibaba + druid + + + mysql + mysql-connector-java + + + org.apache.ddlutils + ddlutils + 1.0 + + + commons-beanutils + commons-beanutils-core + + + commons-lang + commons-lang + + + commons-dbcp + commons-dbcp + + + commons-pool + commons-pool + + + commons-logging + commons-logging-api + + + dom4j + dom4j + + + stax + stax-api + + + commons-collections + commons-collections + + + commons-digester + commons-digester + + + commons-betwixt + commons-betwixt + + + + + org.apache.commons + commons-pool2 + 2.5.0 + + + commons-beanutils + commons-beanutils + 1.8.2 + + + org.apache.commons + commons-lang3 + 3.7 + + + commons-collections + commons-collections + 3.2 + + junit diff --git a/example/src/main/java/com/alibaba/otter/canal/example/AbstractCanalClientTest.java b/example/src/main/java/com/alibaba/otter/canal/example/AbstractCanalClientTest.java index 1b84463b..552f19da 100644 --- a/example/src/main/java/com/alibaba/otter/canal/example/AbstractCanalClientTest.java +++ b/example/src/main/java/com/alibaba/otter/canal/example/AbstractCanalClientTest.java @@ -1,9 +1,11 @@ package com.alibaba.otter.canal.example; +import java.io.UnsupportedEncodingException; import java.text.SimpleDateFormat; import java.util.Date; import java.util.List; +import com.alibaba.otter.canal.protocol.CanalEntry; import org.apache.commons.lang.StringUtils; import org.apache.commons.lang.SystemUtils; import org.slf4j.Logger; @@ -94,7 +96,6 @@ public class AbstractCanalClientTest { if (!running) { return; } - connector.stopRunning(); running = false; if (thread != null) { try { @@ -253,7 +254,17 @@ public class AbstractCanalClientTest { protected void printColumn(List columns) { for (Column column : columns) { StringBuilder builder = new StringBuilder(); - builder.append(column.getName() + " : " + column.getValue()); + try { + if (StringUtils.containsIgnoreCase(column.getMysqlType(), "BLOB") + || StringUtils.containsIgnoreCase(column.getMysqlType(), "BINARY")) { + // get value bytes + builder.append(column.getName() + " : " + + new String(column.getValue().getBytes("ISO-8859-1"), "UTF-8")); + } else { + builder.append(column.getName() + " : " + column.getValue()); + } + } catch (UnsupportedEncodingException e) { + } builder.append(" type=" + column.getMysqlType()); if (column.getUpdated()) { builder.append(" update=" + column.getUpdated()); @@ -288,4 +299,55 @@ public class AbstractCanalClientTest { this.connector = connector; } + /** + * 获取当前Entry的 GTID信息示例 + * @param header + * @return + */ + public static String getCurrentGtid(CanalEntry.Header header) { + List props = header.getPropsList(); + if (props != null && props.size() > 0) { + for (CanalEntry.Pair pair : props) { + if ("curtGtid".equals(pair.getKey())) { + return pair.getValue(); + } + } + } + return ""; + } + + /** + * 获取当前Entry的 GTID Sequence No信息示例 + * @param header + * @return + */ + public static String getCurrentGtidSn(CanalEntry.Header header) { + List props = header.getPropsList(); + if (props != null && props.size() > 0) { + for (CanalEntry.Pair pair : props) { + if ("curtGtidSn".equals(pair.getKey())) { + return pair.getValue(); + } + } + } + return ""; + } + + /** + * 获取当前Entry的 GTID Last Committed信息示例 + * @param header + * @return + */ + public static String getCurrentGtidLct(CanalEntry.Header header) { + List props = header.getPropsList(); + if (props != null && props.size() > 0) { + for (CanalEntry.Pair pair : props) { + if ("curtGtidLct".equals(pair.getKey())) { + return pair.getValue(); + } + } + } + return ""; + } + } diff --git a/example/src/main/java/com/alibaba/otter/canal/example/SimpleCanalClientPermanceTest.java b/example/src/main/java/com/alibaba/otter/canal/example/SimpleCanalClientPermanceTest.java new file mode 100644 index 00000000..6b1f1800 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/SimpleCanalClientPermanceTest.java @@ -0,0 +1,72 @@ +package com.alibaba.otter.canal.example; + +import java.net.InetSocketAddress; +import java.util.concurrent.ArrayBlockingQueue; +import java.util.concurrent.TimeUnit; + +import com.alibaba.otter.canal.client.CanalConnector; +import com.alibaba.otter.canal.client.CanalConnectors; +import com.alibaba.otter.canal.client.impl.SimpleCanalConnector; +import com.alibaba.otter.canal.protocol.Message; + +public class SimpleCanalClientPermanceTest { + + public static void main(String args[]) { + String destination = "example"; + String ip = "127.0.0.1"; + int batchSize = 1024; + int count = 0; + int sum = 0; + int perSum = 0; + long start = System.currentTimeMillis(); + long end = 0; + final ArrayBlockingQueue queue = new ArrayBlockingQueue(100); + try { + final CanalConnector connector = CanalConnectors.newSingleConnector(new InetSocketAddress(ip, 11111), + destination, + "", + ""); + + Thread ackThread = new Thread(new Runnable() { + + @Override + public void run() { + while (true) { + try { + long batchId = queue.take(); + connector.ack(batchId); + } catch (InterruptedException e) { + } + } + } + }); + ackThread.start(); + + ((SimpleCanalConnector) connector).setLazyParseEntry(true); + connector.connect(); + connector.subscribe(); + while (true) { + Message message = connector.getWithoutAck(batchSize, 100L, TimeUnit.MILLISECONDS); + long batchId = message.getId(); + int size = message.getRawEntries().size(); + sum += size; + perSum += size; + count++; + queue.add(batchId); + if (count % 10 == 0) { + end = System.currentTimeMillis(); + if (end - start != 0) { + long tps = (perSum * 1000) / (end - start); + System.out.println(" total : " + sum + " , current : " + perSum + " , cost : " + (end - start) + + " , tps : " + tps); + start = end; + perSum = 0; + } + } + } + } catch (Throwable e) { + e.printStackTrace(); + } + } + +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/AbstractDbClient.java b/example/src/main/java/com/alibaba/otter/canal/example/db/AbstractDbClient.java new file mode 100644 index 00000000..ec998e55 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/AbstractDbClient.java @@ -0,0 +1,144 @@ +package com.alibaba.otter.canal.example.db; + +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.Message; +import org.slf4j.MDC; + +import java.util.Date; +import java.util.List; + +public abstract class AbstractDbClient extends CanalConnectorClient { + + + public abstract void insert(CanalEntry.Header header, List afterColumns); + + public abstract void update(CanalEntry.Header header, List afterColumns); + + public abstract void delete(CanalEntry.Header header, List beforeColumns); + + + @Override + public synchronized void start() { + if (running) { + return; + } + super.start(); + } + + @Override + public synchronized void stop() { + if (!running) { + return; + } + super.stop(); + MDC.remove("destination"); + } + + @Override + protected void processMessage(Message message) { + long batchId = message.getId(); + //遍历每条消息 + for (CanalEntry.Entry entry : message.getEntries()) { + session(entry);//no exception + } + //ack all the time。 + connector.ack(batchId); + } + + private void session(CanalEntry.Entry entry) { + CanalEntry.EntryType entryType = entry.getEntryType(); + int times = 0; + boolean success = false; + while (!success) { + if (times > 0) { + /** + * 1:retry,重试,重试默认为3次,由retryTimes参数决定,如果重试次数达到阈值,则跳过,并且记录日志。 + * 2:ignore,直接忽略,不重试,记录日志。 + */ + if (exceptionStrategy == ExceptionStrategy.RETRY.code) { + if (times >= retryTimes) { + break; + } + } else { + break; + } + } + try { + switch (entryType) { + case TRANSACTIONBEGIN: + transactionBegin(entry); + break; + case TRANSACTIONEND: + transactionEnd(entry); + break; + case ROWDATA: + rowData(entry); + break; + default: + break; + } + success = true; + } catch (Exception e) { + times++; + logger.error("parse event has an error ,times: + " + times + ", data:" + entry.toString(), e); + } + + } + } + + private void rowData(CanalEntry.Entry entry) throws Exception { + CanalEntry.RowChange rowChange = CanalEntry.RowChange.parseFrom(entry.getStoreValue()); + CanalEntry.EventType eventType = rowChange.getEventType(); + CanalEntry.Header header = entry.getHeader(); + long executeTime = header.getExecuteTime(); + long delayTime = new Date().getTime() - executeTime; + String sql = rowChange.getSql(); + + try { + if (!isDML(eventType) || rowChange.getIsDdl()) { + processDDL(header, eventType, sql); + return; + } + //处理DML数据 + processDML(header, eventType, rowChange, sql); + } catch (Exception e) { + logger.error("process event error ,", e); + logger.error(rowFormat, + new Object[]{header.getLogfileName(), String.valueOf(header.getLogfileOffset()), + header.getSchemaName(), header.getTableName(), eventType, + String.valueOf(executeTime), String.valueOf(delayTime)}); + throw e;//重新抛出 + } + } + + /** + * 处理 dml 数据 + * + * @param header + * @param eventType + * @param rowChange + * @param sql + */ + protected void processDML(CanalEntry.Header header, CanalEntry.EventType eventType, CanalEntry.RowChange rowChange, String sql) { + for (CanalEntry.RowData rowData : rowChange.getRowDatasList()) { + switch (eventType) { + case DELETE: + delete(header, rowData.getBeforeColumnsList()); + break; + case INSERT: + insert(header, rowData.getAfterColumnsList()); + break; + case UPDATE: + update(header, rowData.getAfterColumnsList()); + break; + default: + whenOthers(header, sql); + } + } + } + +} + + + + diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/CanalConnectorClient.java b/example/src/main/java/com/alibaba/otter/canal/example/db/CanalConnectorClient.java new file mode 100644 index 00000000..247f9e1f --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/CanalConnectorClient.java @@ -0,0 +1,488 @@ +package com.alibaba.otter.canal.example.db; + +import com.alibaba.otter.canal.client.CanalConnector; +import com.alibaba.otter.canal.client.CanalConnectors; +import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.Message; +import org.apache.commons.lang.SystemUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.slf4j.MDC; +import org.springframework.beans.factory.InitializingBean; +import org.springframework.util.CollectionUtils; + +import java.net.InetSocketAddress; +import java.net.SocketAddress; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.List; + +public abstract class CanalConnectorClient extends AbstractCanalLifeCycle implements InitializingBean { + + protected static final Logger logger = LoggerFactory.getLogger(CanalConnectorClient.class); + protected static final String SEP = SystemUtils.LINE_SEPARATOR; + protected static String contextFormat; + protected static String rowFormat; + protected static String transactionFormat; + protected static final String DATE_FORMAT = "yyyy-MM-dd HH:mm:ss"; + + static { + StringBuilder sb = new StringBuilder(); + sb.append(SEP) + .append("-------------Batch-------------") + .append(SEP) + .append("* Batch Id: [{}] ,count : [{}] , Mem size : [{}] , Time : {}") + .append(SEP) + .append("* Start : [{}] ") + .append(SEP) + .append("* End : [{}] ") + .append(SEP) + .append("-------------------------------") + .append(SEP); + contextFormat = sb.toString(); + + sb = new StringBuilder(); + sb.append(SEP) + .append("+++++++++++++Row+++++++++++++>>>") + .append("binlog[{}:{}] , name[{},{}] , eventType : {} , executeTime : {} , delay : {}ms") + .append(SEP); + rowFormat = sb.toString(); + + sb = new StringBuilder(); + sb.append(SEP) + .append("===========Transaction {} : {}=======>>>") + .append("binlog[{}:{}] , executeTime : {} , delay : {}ms") + .append(SEP); + transactionFormat = sb.toString(); + } + + private String zkServers;//cluster + private String address;//single,ip:port + private String destination; + private String username; + private String password; + private int batchSize = 5 * 1024; + private String filter = "";//同canal filter,用于过滤database或者table的相关数据。 + protected boolean debug = false;//开启debug,会把每条消息的详情打印 + + //1:retry,重试,重试默认为3次,由retryTimes参数决定,如果重试次数达到阈值,则跳过,并且记录日志。 + //2:ignore,直接忽略,不重试,记录日志。 + protected int exceptionStrategy = 1; + protected int retryTimes = 3; + protected int waitingTime = 100;//当binlog没有数据时,主线程等待的时间,单位ms,大于0 + + + protected CanalConnector connector; + protected Thread thread; + + protected Thread.UncaughtExceptionHandler handler = new Thread.UncaughtExceptionHandler() { + + public void uncaughtException(Thread t, Throwable e) { + logger.error("process message has an error", e); + } + }; + + @Override + public void afterPropertiesSet() { + if (waitingTime <= 0) { + throw new IllegalArgumentException("waitingTime must be greater than 0"); + } + if (ExceptionStrategy.codeOf(exceptionStrategy) == null) { + throw new IllegalArgumentException("exceptionStrategy is not valid,1 or 2"); + } + start(); + } + + @Override + public void start() { + if (running) { + return; + } + super.start(); + initConnector(); + + thread = new Thread(new Runnable() { + + public void run() { + process(); + } + }); + + thread.setUncaughtExceptionHandler(handler); + thread.start(); + } + + @Override + public void stop() { + if (!running) { + return; + } + super.stop(); + quietlyStop(thread); + } + + protected void quietlyStop(Thread task) { + if (task != null) { + task.interrupt(); + try { + task.join(); + } catch (InterruptedException e) { + // ignore + } + } + } + + public void process() { + int times = 0; + while (running) { + try { + sleepWhenFailed(times); + //after block, should check the status of thread. + if (!running) { + break; + } + MDC.put("destination", destination); + connector.connect(); + connector.subscribe(filter); + connector.rollback(); + times = 0;//reset; + + while (running) { + // 获取指定数量的数据,不确认 + Message message = connector.getWithoutAck(batchSize); + + long batchId = message.getId(); + int size = message.getEntries().size(); + + if (batchId == -1 || size == 0) { + try { + Thread.sleep(waitingTime); + } catch (InterruptedException e) { + // + } + continue; + } + //logger + printBatch(message, batchId); + + processMessage(message); + + } + } catch (Exception e) { + logger.error("process error!", e); + if (times > 20) { + times = 0; + } + times++; + } finally { + connector.disconnect(); + MDC.remove("destination"); + } + } + } + + protected abstract void processMessage(Message message); + + + private void initConnector() { + if (zkServers != null && zkServers.length() > 0) { + connector = CanalConnectors.newClusterConnector(zkServers, destination, username, password); + } else if (address != null) { + String[] segments = address.split(":"); + SocketAddress socketAddress = new InetSocketAddress(segments[0], Integer.valueOf(segments[1])); + connector = CanalConnectors.newSingleConnector(socketAddress, destination, username, password); + } else { + throw new IllegalArgumentException("zkServers or address cant be null at same time,you should specify one of them!"); + } + + } + + /** + * 用于控制当连接异常时,重试的策略,我们不应该每次都是立即重试,否则将可能导致大量的错误,在空转时导致CPU过高的问题 + * sleep策略基于简单的累加 + * + * @param times + */ + private void sleepWhenFailed(int times) { + if (times <= 0) { + return; + } + try { + int sleepTime = 1000 + times * 100;//最大sleep 3s。 + Thread.sleep(sleepTime); + } catch (Exception ex) { + // + } + } + + /** + * 打印当前batch的摘要信息 + * + * @param message + * @param batchId + */ + protected void printBatch(Message message, long batchId) { + if (!debug) { + return; + } + List entries = message.getEntries(); + if (CollectionUtils.isEmpty(entries)) { + return; + } + + long memSize = 0; + for (CanalEntry.Entry entry : entries) { + memSize += entry.getHeader().getEventLength(); + } + int size = entries.size(); + String startPosition = buildPosition(entries.get(0)); + String endPosition = buildPosition(message.getEntries().get(size - 1)); + + SimpleDateFormat format = new SimpleDateFormat(DATE_FORMAT); + logger.info(contextFormat, new Object[]{batchId, size, memSize, format.format(new Date()), startPosition, endPosition}); + } + + protected String buildPosition(CanalEntry.Entry entry) { + CanalEntry.Header header = entry.getHeader(); + long time = header.getExecuteTime(); + Date date = new Date(time); + SimpleDateFormat format = new SimpleDateFormat(DATE_FORMAT); + StringBuilder sb = new StringBuilder(); + sb.append(header.getLogfileName()) + .append(":") + .append(header.getLogfileOffset()) + .append(":") + .append(header.getExecuteTime()) + .append("(") + .append(format.format(date)) + .append(")"); + return sb.toString(); + } + + /** + * default,only logging information + * + * @param entry + */ + protected void transactionBegin(CanalEntry.Entry entry) { + if (!debug) { + return; + } + try { + CanalEntry.TransactionBegin begin = CanalEntry.TransactionBegin.parseFrom(entry.getStoreValue()); + // 打印事务头信息,执行的线程id,事务耗时 + CanalEntry.Header header = entry.getHeader(); + long executeTime = header.getExecuteTime(); + long delayTime = new Date().getTime() - executeTime; + logger.info(transactionFormat, + new Object[]{"begin", begin.getTransactionId(), header.getLogfileName(), + String.valueOf(header.getLogfileOffset()), + String.valueOf(header.getExecuteTime()), String.valueOf(delayTime)}); + } catch (Exception e) { + logger.error("parse event has an error , data:" + entry.toString(), e); + } + } + + protected void transactionEnd(CanalEntry.Entry entry) { + if (!debug) { + return; + } + try { + CanalEntry.TransactionEnd end = CanalEntry.TransactionEnd.parseFrom(entry.getStoreValue()); + // 打印事务提交信息,事务id + CanalEntry.Header header = entry.getHeader(); + long executeTime = header.getExecuteTime(); + long delayTime = new Date().getTime() - executeTime; + + logger.info(transactionFormat, + new Object[]{"end", end.getTransactionId(), header.getLogfileName(), + String.valueOf(header.getLogfileOffset()), + String.valueOf(header.getExecuteTime()), String.valueOf(delayTime)}); + } catch (Exception e) { + logger.error("parse event has an error , data:" + entry.toString(), e); + } + } + + /** + * 判断事件类型为DML 数据 + * + * @param eventType + * @return + */ + protected boolean isDML(CanalEntry.EventType eventType) { + switch (eventType) { + case INSERT: + case UPDATE: + case DELETE: + return true; + default: + return false; + } + } + + /** + * 处理 DDL数据 + * + * @param header + * @param eventType + * @param sql + */ + + protected void processDDL(CanalEntry.Header header, CanalEntry.EventType eventType, String sql) { + if (!debug) { + return; + } + String table = header.getSchemaName() + "." + header.getTableName(); + //对于DDL,直接执行,因为没有行变更数据 + switch (eventType) { + case CREATE: + logger.warn("parse create table event, table: {}, sql: {}", table, sql); + return; + case ALTER: + logger.warn("parse alter table event, table: {}, sql: {}", table, sql); + return; + case TRUNCATE: + logger.warn("parse truncate table event, table: {}, sql: {}", table, sql); + return; + case ERASE: + case QUERY: + logger.warn("parse event : {}, sql: {} . ignored!", eventType.name(), sql); + return; + case RENAME: + logger.warn("parse rename table event, table: {}, sql: {}", table, sql); + return; + case CINDEX: + logger.warn("parse create index event, table: {}, sql: {}", table, sql); + return; + case DINDEX: + logger.warn("parse delete index event, table: {}, sql: {}", table, sql); + return; + default: + logger.warn("parse unknown event: {}, table: {}, sql: {}", eventType.name(), table, sql); + break; + } + } + + /** + * 强烈建议捕获异常,非上述已列出的其他操作,非核心 + * 除了“insert”、“update”、“delete”操作之外的,其他类型的操作. + * 默认实现为“无操作” + * + * @param header 可以从header中获得schema、table的名称 + * @param sql + */ + public void whenOthers(CanalEntry.Header header, String sql) { + String schema = header.getSchemaName(); + String table = header.getTableName(); + logger.error("ignore event,schema: {},table: {},SQL: {}", schema, table, sql); + } + + public enum ExceptionStrategy { + RETRY(1), IGNORE(2); + public int code; + + ExceptionStrategy(int code) { + this.code = code; + } + + public static ExceptionStrategy codeOf(Integer code) { + if (code != null) { + for (ExceptionStrategy e : ExceptionStrategy.values()) { + if (e.code == code) { + return e; + } + } + } + return null; + } + } + + public String getZkServers() { + return zkServers; + } + + public void setZkServers(String zkServers) { + this.zkServers = zkServers; + } + + public String getAddress() { + return address; + } + + public void setAddress(String address) { + this.address = address; + } + + public String getDestination() { + return destination; + } + + public void setDestination(String destination) { + this.destination = destination; + } + + public String getUsername() { + return username; + } + + public void setUsername(String username) { + this.username = username; + } + + public String getPassword() { + return password; + } + + public void setPassword(String password) { + this.password = password; + } + + public int getBatchSize() { + return batchSize; + } + + public void setBatchSize(int batchSize) { + this.batchSize = batchSize; + } + + public String getFilter() { + return filter; + } + + public void setFilter(String filter) { + this.filter = filter; + } + + public boolean isDebug() { + return debug; + } + + public void setDebug(boolean debug) { + this.debug = debug; + } + + public int getExceptionStrategy() { + return exceptionStrategy; + } + + public void setExceptionStrategy(int exceptionStrategy) { + this.exceptionStrategy = exceptionStrategy; + } + + public int getRetryTimes() { + return retryTimes; + } + + public void setRetryTimes(int retryTimes) { + this.retryTimes = retryTimes; + } + + public int getWaitingTime() { + return waitingTime; + } + + public void setWaitingTime(int waitingTime) { + this.waitingTime = waitingTime; + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/MysqlLoadLauncher.java b/example/src/main/java/com/alibaba/otter/canal/example/db/MysqlLoadLauncher.java new file mode 100644 index 00000000..b9936106 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/MysqlLoadLauncher.java @@ -0,0 +1,35 @@ +package com.alibaba.otter.canal.example.db; + +import com.alibaba.otter.canal.example.db.mysql.MysqlClient; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +public class MysqlLoadLauncher { + private static final Logger logger = LoggerFactory.getLogger(MysqlLoadLauncher.class); + + public static void main(String[] args) { + try { + logger.info("## start the canal mysql client."); + final MysqlClient client = ServiceLocator.getMysqlClient(); + logger.info("## the canal consumer is running now ......"); + client.start(); + Runtime.getRuntime().addShutdownHook(new Thread() { + + public void run() { + try { + logger.info("## stop the canal consumer"); + client.stop(); + } catch (Throwable e) { + logger.warn("##something goes wrong when stopping canal consumer:\n{}", e); + } finally { + logger.info("## canal consumer is down."); + } + } + + }); + } catch (Throwable e) { + logger.error("## Something goes wrong when starting up the canal consumer:\n{}", e); + System.exit(0); + } + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/PropertyPlaceholderConfigurer.java b/example/src/main/java/com/alibaba/otter/canal/example/db/PropertyPlaceholderConfigurer.java new file mode 100644 index 00000000..65b4827c --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/PropertyPlaceholderConfigurer.java @@ -0,0 +1,169 @@ +package com.alibaba.otter.canal.example.db; + +import org.springframework.beans.factory.InitializingBean; +import org.springframework.context.ResourceLoaderAware; +import org.springframework.core.io.Resource; +import org.springframework.core.io.ResourceLoader; +import org.springframework.util.Assert; + +import java.util.ArrayList; +import java.util.List; +import java.util.Properties; + +/** + * 扩展Spring的 + * {@linkplain org.springframework.beans.factory.config.PropertyPlaceholderConfigurer} + * ,增加默认值的功能。 例如:${placeholder:defaultValue},假如placeholder的值不存在,则默认取得 + * defaultValue。 + * + * @author jianghang 2013-1-24 下午03:37:56 + * @version 1.0.0 + */ +public class PropertyPlaceholderConfigurer extends org.springframework.beans.factory.config.PropertyPlaceholderConfigurer implements ResourceLoaderAware, InitializingBean { + + private static final String PLACEHOLDER_PREFIX = "${"; + private static final String PLACEHOLDER_SUFFIX = "}"; + private ResourceLoader loader; + private String[] locationNames; + + public PropertyPlaceholderConfigurer(){ + setIgnoreUnresolvablePlaceholders(true); + } + + public void setResourceLoader(ResourceLoader loader) { + this.loader = loader; + } + + public void setLocationNames(String[] locations) { + this.locationNames = locations; + } + + public void afterPropertiesSet() throws Exception { + Assert.notNull(loader, "no resourceLoader"); + + if (locationNames != null) { + for (int i = 0; i < locationNames.length; i++) { + locationNames[i] = resolveSystemPropertyPlaceholders(locationNames[i]); + } + } + + if (locationNames != null) { + List resources = new ArrayList(locationNames.length); + + for (String location : locationNames) { + location = trimToNull(location); + + if (location != null) { + resources.add(loader.getResource(location)); + } + } + + super.setLocations(resources.toArray(new Resource[resources.size()])); + } + } + + private String resolveSystemPropertyPlaceholders(String text) { + StringBuilder buf = new StringBuilder(text); + + for (int startIndex = buf.indexOf(PLACEHOLDER_PREFIX); startIndex >= 0;) { + int endIndex = buf.indexOf(PLACEHOLDER_SUFFIX, startIndex + PLACEHOLDER_PREFIX.length()); + + if (endIndex != -1) { + String placeholder = buf.substring(startIndex + PLACEHOLDER_PREFIX.length(), endIndex); + int nextIndex = endIndex + PLACEHOLDER_SUFFIX.length(); + + try { + String value = resolveSystemPropertyPlaceholder(placeholder); + + if (value != null) { + buf.replace(startIndex, endIndex + PLACEHOLDER_SUFFIX.length(), value); + nextIndex = startIndex + value.length(); + } else { + System.err.println("Could not resolve placeholder '" + + placeholder + + "' in [" + + text + + "] as system property: neither system property nor environment variable found"); + } + } catch (Throwable ex) { + System.err.println("Could not resolve placeholder '" + placeholder + "' in [" + text + + "] as system property: " + ex); + } + + startIndex = buf.indexOf(PLACEHOLDER_PREFIX, nextIndex); + } else { + startIndex = -1; + } + } + + return buf.toString(); + } + + private String resolveSystemPropertyPlaceholder(String placeholder) { + DefaultablePlaceholder dp = new DefaultablePlaceholder(placeholder); + String value = System.getProperty(dp.placeholder); + + if (value == null) { + value = System.getenv(dp.placeholder); + } + + if (value == null) { + value = dp.defaultValue; + } + + return value; + } + + @Override + protected String resolvePlaceholder(String placeholder, Properties props, int systemPropertiesMode) { + DefaultablePlaceholder dp = new DefaultablePlaceholder(placeholder); + String value = super.resolvePlaceholder(dp.placeholder, props, systemPropertiesMode); + + if (value == null) { + value = dp.defaultValue; + } + + return trimToEmpty(value); + } + + private static class DefaultablePlaceholder { + + private final String defaultValue; + private final String placeholder; + + public DefaultablePlaceholder(String placeholder){ + int commaIndex = placeholder.indexOf(":"); + String defaultValue = null; + + if (commaIndex >= 0) { + defaultValue = trimToEmpty(placeholder.substring(commaIndex + 1)); + placeholder = trimToEmpty(placeholder.substring(0, commaIndex)); + } + + this.placeholder = placeholder; + this.defaultValue = defaultValue; + } + } + + private String trimToNull(String str) { + if (str == null) { + return null; + } + + String result = str.trim(); + + if (result == null || result.length() == 0) { + return null; + } + + return result; + } + + public static String trimToEmpty(String str) { + if (str == null) { + return ""; + } + + return str.trim(); + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/ServiceLocator.java b/example/src/main/java/com/alibaba/otter/canal/example/db/ServiceLocator.java new file mode 100644 index 00000000..39ad4c62 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/ServiceLocator.java @@ -0,0 +1,44 @@ +package com.alibaba.otter.canal.example.db; + +import com.alibaba.otter.canal.example.db.mysql.MysqlClient; +import org.springframework.beans.factory.DisposableBean; +import org.springframework.context.ApplicationContext; +import org.springframework.context.support.ClassPathXmlApplicationContext; +import org.springframework.util.Assert; + +public class ServiceLocator implements DisposableBean { + + private static ApplicationContext applicationContext = null; + + static { + try { + applicationContext = new ClassPathXmlApplicationContext("classpath:client-spring.xml"); + } catch (RuntimeException e) { + throw e; + } + } + + private static T getBean(String name) { + assertContextInjected(); + return (T) applicationContext.getBean(name); + } + + + private static void clearHolder() { + ServiceLocator.applicationContext = null; + } + + @Override + public void destroy() throws Exception { + ServiceLocator.clearHolder(); + } + + private static void assertContextInjected() { + Assert.state(applicationContext != null, "ApplicationContext not set"); + } + + + public static MysqlClient getMysqlClient() { + return getBean("mysqlClient"); + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/AbstractDbDialect.java b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/AbstractDbDialect.java new file mode 100644 index 00000000..ec99b316 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/AbstractDbDialect.java @@ -0,0 +1,121 @@ +/* + * Copyright (C) 2010-2101 Alibaba Group Holding Limited. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.alibaba.otter.canal.example.db.dialect; + +import com.alibaba.otter.canal.example.db.utils.DdlUtils; +import com.google.common.base.Function; +import com.google.common.collect.MigrateMap; +import org.apache.commons.lang.exception.NestableRuntimeException; +import org.apache.ddlutils.model.Table; +import org.springframework.dao.DataAccessException; +import org.springframework.jdbc.core.ConnectionCallback; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.jdbc.datasource.DataSourceTransactionManager; +import org.springframework.jdbc.support.lob.LobHandler; +import org.springframework.transaction.TransactionDefinition; +import org.springframework.transaction.support.TransactionTemplate; +import org.springframework.util.Assert; + +import java.sql.Connection; +import java.sql.DatabaseMetaData; +import java.sql.SQLException; +import java.util.Arrays; +import java.util.List; +import java.util.Map; + +public abstract class AbstractDbDialect implements DbDialect { + + protected int databaseMajorVersion; + protected int databaseMinorVersion; + protected String databaseName; + protected JdbcTemplate jdbcTemplate; + protected TransactionTemplate transactionTemplate; + protected LobHandler lobHandler; + protected Map, Table> tables; + + public AbstractDbDialect(final JdbcTemplate jdbcTemplate, LobHandler lobHandler) { + this.jdbcTemplate = jdbcTemplate; + this.lobHandler = lobHandler; + // 初始化transction + this.transactionTemplate = new TransactionTemplate(); + transactionTemplate.setTransactionManager(new DataSourceTransactionManager(jdbcTemplate.getDataSource())); + transactionTemplate.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRES_NEW); + + // 初始化一些数据 + jdbcTemplate.execute(new ConnectionCallback() { + + public Object doInConnection(Connection c) throws SQLException, DataAccessException { + DatabaseMetaData meta = c.getMetaData(); + databaseName = meta.getDatabaseProductName(); + databaseMajorVersion = meta.getDatabaseMajorVersion(); + databaseMinorVersion = meta.getDatabaseMinorVersion(); + + return null; + } + }); + + initTables(jdbcTemplate); + } + + public Table findTable(String schema, String table, boolean useCache) { + List key = Arrays.asList(schema, table); + if (useCache == false) { + tables.remove(key); + } + + return tables.get(key); + } + + public Table findTable(String schema, String table) { + return findTable(schema, table, true); + } + + public LobHandler getLobHandler() { + return lobHandler; + } + + public JdbcTemplate getJdbcTemplate() { + return jdbcTemplate; + } + + public TransactionTemplate getTransactionTemplate() { + return transactionTemplate; + } + + private void initTables(final JdbcTemplate jdbcTemplate) { + this.tables = MigrateMap.makeComputingMap(new Function, Table>() { + + public Table apply(List names) { + Assert.isTrue(names.size() == 2); + try { + Table table = DdlUtils.findTable(jdbcTemplate, names.get(0), names.get(0), names.get(1)); + if (table == null) { + throw new NestableRuntimeException("no found table [" + names.get(0) + "." + names.get(1) + + "] , pls check"); + } else { + return table; + } + } catch (Exception e) { + throw new NestableRuntimeException("find table [" + names.get(0) + "." + names.get(1) + "] error", + e); + } + } + }); + } + + +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/AbstractSqlTemplate.java b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/AbstractSqlTemplate.java new file mode 100644 index 00000000..fbbecabe --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/AbstractSqlTemplate.java @@ -0,0 +1,105 @@ +/* + * Copyright (C) 2010-2101 Alibaba Group Holding Limited. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.alibaba.otter.canal.example.db.dialect; + +/** + * 默认的基于标准SQL实现的CRUD sql封装 + * + * @author jianghang 2011-10-27 下午01:37:00 + * @version 4.0.0 + */ +public abstract class AbstractSqlTemplate implements SqlTemplate { + + private static final String DOT = "."; + + public String getSelectSql(String schemaName, String tableName, String[] pkNames, String[] columnNames) { + StringBuilder sql = new StringBuilder("select "); + int size = columnNames.length; + for (int i = 0; i < size; i++) { + sql.append(appendEscape(columnNames[i])).append((i + 1 < size) ? " , " : ""); + } + + sql.append(" from ").append(getFullName(schemaName, tableName)).append(" where ( "); + appendColumnEquals(sql, pkNames, "and"); + sql.append(" ) "); + return sql.toString().intern();// 不使用intern,避免方法区内存消耗过多 + } + + public String getUpdateSql(String schemaName, String tableName, String[] pkNames, String[] columnNames) { + StringBuilder sql = new StringBuilder("update " + getFullName(schemaName, tableName) + " set "); + appendColumnEquals(sql, columnNames, ","); + sql.append(" where ("); + appendColumnEquals(sql, pkNames, "and"); + sql.append(")"); + return sql.toString().intern(); // 不使用intern,避免方法区内存消耗过多 + } + + public String getInsertSql(String schemaName, String tableName, String[] pkNames, String[] columnNames) { + StringBuilder sql = new StringBuilder("insert into " + getFullName(schemaName, tableName) + "("); + String[] allColumns = new String[pkNames.length + columnNames.length]; + System.arraycopy(columnNames, 0, allColumns, 0, columnNames.length); + System.arraycopy(pkNames, 0, allColumns, columnNames.length, pkNames.length); + + int size = allColumns.length; + for (int i = 0; i < size; i++) { + sql.append(appendEscape(allColumns[i])).append((i + 1 < size) ? "," : ""); + } + + sql.append(") values ("); + appendColumnQuestions(sql, allColumns); + sql.append(")"); + return sql.toString().intern();// intern优化,避免出现大量相同的字符串 + } + + public String getDeleteSql(String schemaName, String tableName, String[] pkNames) { + StringBuilder sql = new StringBuilder("delete from " + getFullName(schemaName, tableName) + " where "); + appendColumnEquals(sql, pkNames, "and"); + return sql.toString().intern();// intern优化,避免出现大量相同的字符串 + } + + protected String getFullName(String schemaName, String tableName) { + StringBuilder sb = new StringBuilder(); + if (schemaName != null) { + sb.append(appendEscape(schemaName)).append(DOT); + } + sb.append(appendEscape(tableName)); + return sb.toString().intern(); + } + + // ================ helper method ============ + + protected String appendEscape(String columnName) { + return columnName; + } + + protected void appendColumnQuestions(StringBuilder sql, String[] columns) { + int size = columns.length; + for (int i = 0; i < size; i++) { + sql.append("?").append((i + 1 < size) ? " , " : ""); + } + } + + protected void appendColumnEquals(StringBuilder sql, String[] columns, String separator) { + int size = columns.length; + for (int i = 0; i < size; i++) { + sql.append(" ").append(appendEscape(columns[i])).append(" = ").append("? "); + if (i != size - 1) { + sql.append(separator); + } + } + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/DbDialect.java b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/DbDialect.java new file mode 100644 index 00000000..060f476d --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/DbDialect.java @@ -0,0 +1,20 @@ +package com.alibaba.otter.canal.example.db.dialect; + +import org.apache.ddlutils.model.Table; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.jdbc.support.lob.LobHandler; +import org.springframework.transaction.support.TransactionTemplate; + +public interface DbDialect { + + LobHandler getLobHandler(); + + JdbcTemplate getJdbcTemplate(); + + TransactionTemplate getTransactionTemplate(); + + Table findTable(String schema, String table); + + Table findTable(String schema, String table, boolean useCache); + +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/SqlTemplate.java b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/SqlTemplate.java new file mode 100644 index 00000000..a90bd5ce --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/SqlTemplate.java @@ -0,0 +1,40 @@ +/* + * Copyright (C) 2010-2101 Alibaba Group Holding Limited. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.alibaba.otter.canal.example.db.dialect; + +/** + * sql构造模板操作 + * + * @author jianghang 2011-10-27 下午01:31:15 + * @version 4.0.0 + */ +public interface SqlTemplate { + + public String getSelectSql(String schemaName, String tableName, String[] pkNames, String[] columnNames); + + public String getUpdateSql(String schemaName, String tableName, String[] pkNames, String[] columnNames); + + public String getDeleteSql(String schemaName, String tableName, String[] pkNames); + + public String getInsertSql(String schemaName, String tableName, String[] pkNames, String[] columnNames); + + /** + * 获取对应的mergeSql + */ + public String getMergeSql(String schemaName, String tableName, String[] pkNames, String[] columnNames, + String[] viewColumnNames, boolean updatePks); +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/TableType.java b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/TableType.java new file mode 100644 index 00000000..58cf662a --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/TableType.java @@ -0,0 +1,93 @@ +package com.alibaba.otter.canal.example.db.dialect; + +import java.util.ArrayList; +import java.util.List; +import java.util.Locale; + +/** + * An enumeration wrapper around JDBC table types. + */ +public enum TableType { + + /** + * Unknown + */ + unknown, + + /** + * System table + */ + system_table, + + /** + * Global temporary + */ + global_temporary, + + /** + * Local temporary + */ + local_temporary, + + /** + * Table + */ + table, + + /** + * View + */ + view, + + /** + * Alias + */ + alias, + + /** + * Synonym + */ + synonym,; + + /** + * Converts an array of table types to an array of their corresponding string values. + * + * @param tableTypes Array of table types + * @return Array of string table types + */ + public static String[] toStrings(final TableType[] tableTypes) { + if ((tableTypes == null) || (tableTypes.length == 0)) { + return new String[0]; + } + + final List tableTypeStrings = new ArrayList(tableTypes.length); + + for (final TableType tableType : tableTypes) { + if (tableType != null) { + tableTypeStrings.add(tableType.toString().toUpperCase(Locale.ENGLISH)); + } + } + + return tableTypeStrings.toArray(new String[tableTypeStrings.size()]); + } + + /** + * Converts an array of string table types to an array of their corresponding enumeration values. + * + * @param tableTypeStrings Array of string table types + * @return Array of table types + */ + public static TableType[] valueOf(final String[] tableTypeStrings) { + if ((tableTypeStrings == null) || (tableTypeStrings.length == 0)) { + return new TableType[0]; + } + + final List tableTypes = new ArrayList(tableTypeStrings.length); + + for (final String tableTypeString : tableTypeStrings) { + tableTypes.add(valueOf(tableTypeString.toLowerCase(Locale.ENGLISH))); + } + + return tableTypes.toArray(new TableType[tableTypes.size()]); + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/mysql/MysqlDialect.java b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/mysql/MysqlDialect.java new file mode 100644 index 00000000..7bdfe1df --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/mysql/MysqlDialect.java @@ -0,0 +1,32 @@ +/* + * Copyright (C) 2010-2101 Alibaba Group Holding Limited. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.alibaba.otter.canal.example.db.dialect.mysql; + +import com.alibaba.otter.canal.example.db.dialect.AbstractDbDialect; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.jdbc.support.lob.LobHandler; + +public class MysqlDialect extends AbstractDbDialect { + + public MysqlDialect(JdbcTemplate jdbcTemplate, LobHandler lobHandler) { + super(jdbcTemplate, lobHandler); + } + + public boolean isEmptyStringNulled() { + return false; + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/mysql/MysqlSqlTemplate.java b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/mysql/MysqlSqlTemplate.java new file mode 100644 index 00000000..0cf987ff --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/dialect/mysql/MysqlSqlTemplate.java @@ -0,0 +1,84 @@ +/* + * Copyright (C) 2010-2101 Alibaba Group Holding Limited. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.alibaba.otter.canal.example.db.dialect.mysql; + +import com.alibaba.otter.canal.example.db.dialect.AbstractSqlTemplate; + +/** + * mysql sql生成模板 + * + * @author jianghang 2011-10-27 下午01:41:20 + * @version 4.0.0 + */ +public class MysqlSqlTemplate extends AbstractSqlTemplate { + + private static final String ESCAPE = "`"; + + public String getMergeSql(String schemaName, String tableName, String[] pkNames, String[] columnNames, + String[] viewColumnNames, boolean includePks) { + StringBuilder sql = new StringBuilder("insert into " + getFullName(schemaName, tableName) + "("); + int size = columnNames.length; + for (int i = 0; i < size; i++) { + sql.append(appendEscape(columnNames[i])).append(" , "); + } + size = pkNames.length; + for (int i = 0; i < size; i++) { + sql.append(appendEscape(pkNames[i])).append((i + 1 < size) ? " , " : ""); + } + + sql.append(") values ("); + size = columnNames.length; + for (int i = 0; i < size; i++) { + sql.append("?").append(" , "); + } + size = pkNames.length; + for (int i = 0; i < size; i++) { + sql.append("?").append((i + 1 < size) ? " , " : ""); + } + sql.append(")"); + sql.append(" on duplicate key update "); + + size = columnNames.length; + for (int i = 0; i < size; i++) { + sql.append(appendEscape(columnNames[i])) + .append("=values(") + .append(appendEscape(columnNames[i])) + .append(")"); + if (includePks) { + sql.append(" , "); + } else { + sql.append((i + 1 < size) ? " , " : ""); + } + } + + if (includePks) { + // mysql merge sql匹配了uniqe / primary key时都会执行update,所以需要更新pk信息 + size = pkNames.length; + for (int i = 0; i < size; i++) { + sql.append(appendEscape(pkNames[i])).append("=values(").append(appendEscape(pkNames[i])).append(")"); + sql.append((i + 1 < size) ? " , " : ""); + } + } + + return sql.toString().intern();// intern优化,避免出现大量相同的字符串 + } + + protected String appendEscape(String columnName) { + return ESCAPE + columnName + ESCAPE; + } + +} \ No newline at end of file diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/mysql/AbstractMysqlClient.java b/example/src/main/java/com/alibaba/otter/canal/example/db/mysql/AbstractMysqlClient.java new file mode 100644 index 00000000..608b81e6 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/mysql/AbstractMysqlClient.java @@ -0,0 +1,207 @@ +package com.alibaba.otter.canal.example.db.mysql; + +import com.alibaba.fastjson.JSON; +import com.alibaba.otter.canal.example.db.AbstractDbClient; +import com.alibaba.otter.canal.example.db.dialect.DbDialect; +import com.alibaba.otter.canal.example.db.dialect.mysql.MysqlDialect; +import com.alibaba.otter.canal.example.db.dialect.mysql.MysqlSqlTemplate; +import com.alibaba.otter.canal.example.db.dialect.SqlTemplate; +import com.alibaba.otter.canal.example.db.utils.SqlUtils; +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.exception.CanalClientException; +import org.apache.commons.lang.StringUtils; +import org.apache.ddlutils.model.Column; +import org.apache.ddlutils.model.Table; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.jdbc.core.PreparedStatementSetter; +import org.springframework.jdbc.core.StatementCreatorUtils; +import org.springframework.jdbc.support.lob.DefaultLobHandler; +import org.springframework.jdbc.support.lob.LobCreator; +import org.springframework.transaction.TransactionStatus; +import org.springframework.transaction.support.TransactionCallback; + +import javax.sql.DataSource; +import java.sql.PreparedStatement; +import java.sql.SQLException; +import java.sql.Types; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + + +public abstract class AbstractMysqlClient extends AbstractDbClient { + + private DataSource dataSource; + + private DbDialect dbDialect; + private SqlTemplate sqlTemplate; + + protected Integer execute(final CanalEntry.Header header, final List columns) { + final String sql = getSql(header, columns); + final LobCreator lobCreator = dbDialect.getLobHandler().getLobCreator(); + dbDialect.getTransactionTemplate().execute(new TransactionCallback() { + + public Object doInTransaction(TransactionStatus status) { + try { + JdbcTemplate template = dbDialect.getJdbcTemplate(); + int affect = template.update(sql, new PreparedStatementSetter() { + + public void setValues(PreparedStatement ps) throws SQLException { + doPreparedStatement(ps, dbDialect, lobCreator, header, columns); + } + }); + return affect; + } finally { + lobCreator.close(); + } + } + }); + return 0; + } + + private String getSql(CanalEntry.Header header, List columns) { + List pkNames = new ArrayList<>(); + List colNames = new ArrayList<>(); + for (CanalEntry.Column column : columns) { + if (column.getIsKey()) { + pkNames.add(column.getName()); + } else { + colNames.add(column.getName()); + } + } + String sql = ""; + CanalEntry.EventType eventType = header.getEventType(); + switch (eventType) { + case INSERT: + sql = sqlTemplate.getInsertSql(header.getSchemaName(), header.getTableName(), pkNames.toArray(new String[]{}), colNames.toArray(new String[]{})); + break; + case UPDATE: + sql = sqlTemplate.getUpdateSql(header.getSchemaName(), header.getTableName(), pkNames.toArray(new String[]{}), colNames.toArray(new String[]{})); + break; + case DELETE: + sql = sqlTemplate.getDeleteSql(header.getSchemaName(), header.getTableName(), pkNames.toArray(new String[]{})); + } + logger.info("Execute sql: {}", sql); + return sql; + } + + private void doPreparedStatement(PreparedStatement ps, DbDialect dbDialect, LobCreator lobCreator, + CanalEntry.Header header, List columns) throws SQLException { + + List rebuildColumns = new ArrayList<>(columns.size()); + + List keyColumns = new ArrayList<>(columns.size()); + List notKeyColumns = new ArrayList<>(columns.size()); + for (CanalEntry.Column column : columns) { + if (column.getIsKey()) { + keyColumns.add(column); + } else { + notKeyColumns.add(column); + } + } + CanalEntry.EventType eventType = header.getEventType(); + switch (eventType) { + case INSERT: + case UPDATE: + // insert/update语句对应的字段数序都是将主键排在后面 + rebuildColumns.addAll(notKeyColumns); + rebuildColumns.addAll(keyColumns); + break; + case DELETE: + rebuildColumns.addAll(keyColumns); + } + + // 获取一下当前字段名的数据是否必填 + Table table = dbDialect.findTable(header.getSchemaName(), header.getTableName()); + Map isRequiredMap = new HashMap(); + for (Column tableColumn : table.getColumns()) { + isRequiredMap.put(StringUtils.lowerCase(tableColumn.getName()), tableColumn.isRequired()); + } + + List values = new ArrayList<>(rebuildColumns.size()); + for (int i = 0; i < rebuildColumns.size(); i++) { + int paramIndex = i + 1; + CanalEntry.Column column = rebuildColumns.get(i); + int sqlType = column.getSqlType(); + + Boolean isRequired = isRequiredMap.get(StringUtils.lowerCase(column.getName())); + if (isRequired == null) { + // 清理一下目标库的表结构,二次检查一下 + table = dbDialect.findTable(header.getSchemaName(), header.getTableName()); + + isRequiredMap = new HashMap<>(); + for (Column tableColumn : table.getColumns()) { + isRequiredMap.put(StringUtils.lowerCase(tableColumn.getName()), tableColumn.isRequired()); + } + + isRequired = isRequiredMap.get(StringUtils.lowerCase(column.getName())); + if (isRequired == null) { + throw new CanalClientException(String.format("column name %s is not found in Table[%s]", + column.getName(), + table.toString())); + } + } + + Object param; + if (sqlType == Types.TIME || sqlType == Types.TIMESTAMP || sqlType == Types.DATE) { + // 解决mysql的0000-00-00 00:00:00问题,直接依赖mysql + // driver进行处理,如果转化为Timestamp会出错 + param = column.getValue(); + if (param instanceof String && StringUtils.isEmpty(String.valueOf(param))) { + param = null; + } + } else { + param = SqlUtils.stringToSqlValue(column.getValue(), + sqlType, + isRequired, + column.getIsNull()); + } + + try { + switch (sqlType) { + case Types.CLOB: + lobCreator.setClobAsString(ps, paramIndex, (String) param); + break; + case Types.BLOB: + lobCreator.setBlobAsBytes(ps, paramIndex, (byte[]) param); + break; + case Types.TIME: + case Types.TIMESTAMP: + case Types.DATE: + ps.setObject(paramIndex, param); + break; + case Types.BIT: + StatementCreatorUtils.setParameterValue(ps, paramIndex, Types.DECIMAL, null, param); + break; + default: + StatementCreatorUtils.setParameterValue(ps, paramIndex, sqlType, null, param); + break; + } + values.add(param); + } catch (SQLException ex) { + logger.error("## SetParam error , [sqltype={}, value={}]", + new Object[]{sqlType, param}); + throw ex; + } + } + logger.info("## sql values: {}", JSON.toJSONString(values)); + } + + @Override + public void afterPropertiesSet() { + JdbcTemplate jdbcTemplate = new JdbcTemplate(dataSource); + DefaultLobHandler lobHandler = new DefaultLobHandler(); + lobHandler.setStreamAsLob(true); + dbDialect = new MysqlDialect(jdbcTemplate, lobHandler); + sqlTemplate = new MysqlSqlTemplate(); + } + + public DataSource getDataSource() { + return dataSource; + } + + public void setDataSource(DataSource dataSource) { + this.dataSource = dataSource; + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/mysql/MysqlClient.java b/example/src/main/java/com/alibaba/otter/canal/example/db/mysql/MysqlClient.java new file mode 100644 index 00000000..f16b6146 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/mysql/MysqlClient.java @@ -0,0 +1,23 @@ +package com.alibaba.otter.canal.example.db.mysql; + +import com.alibaba.otter.canal.protocol.CanalEntry; + +import java.util.List; + +public class MysqlClient extends AbstractMysqlClient { + + @Override + public void insert(CanalEntry.Header header, List afterColumns) { + execute(header, afterColumns); + } + + @Override + public void update(CanalEntry.Header header, List afterColumns) { + execute(header, afterColumns); + } + + @Override + public void delete(CanalEntry.Header header, List beforeColumns) { + execute(header, beforeColumns); + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/utils/ByteArrayConverter.java b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/ByteArrayConverter.java new file mode 100644 index 00000000..6bd33686 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/ByteArrayConverter.java @@ -0,0 +1,50 @@ +package com.alibaba.otter.canal.example.db.utils; + +import org.apache.commons.beanutils.ConversionException; +import org.apache.commons.beanutils.Converter; +import org.apache.commons.beanutils.converters.ArrayConverter; +import org.apache.commons.beanutils.converters.ByteConverter; + +public class ByteArrayConverter implements Converter { + + public static final Converter SQL_BYTES = new ByteArrayConverter(null); + private static final Converter converter = new ArrayConverter(byte[].class, new ByteConverter()); + + protected final Object defaultValue; + protected final boolean useDefault; + + public ByteArrayConverter() { + this.defaultValue = null; + this.useDefault = false; + } + + public ByteArrayConverter(Object defaultValue) { + this.defaultValue = defaultValue; + this.useDefault = true; + } + + public Object convert(Class type, Object value) { + if (value == null) { + if (useDefault) { + return (defaultValue); + } else { + throw new ConversionException("No value specified"); + } + } + + if (value instanceof byte[]) { + return (value); + } + + // BLOB类型,canal直接存储为String("ISO-8859-1") + if (value instanceof String) { + try { + return ((String) value).getBytes("ISO-8859-1"); + } catch (Exception e) { + throw new ConversionException(e); + } + } + + return converter.convert(type, value); // byteConvertor进行转化 + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/utils/DdlUtils.java b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/DdlUtils.java new file mode 100644 index 00000000..7964b18d --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/DdlUtils.java @@ -0,0 +1,326 @@ +package com.alibaba.otter.canal.example.db.utils; + +import com.alibaba.otter.canal.example.db.dialect.TableType; +import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang.builder.ToStringBuilder; +import org.apache.commons.lang.builder.ToStringStyle; +import org.apache.commons.lang.math.NumberUtils; +import org.apache.ddlutils.model.Column; +import org.apache.ddlutils.model.Table; +import org.apache.ddlutils.platform.DatabaseMetaDataWrapper; +import org.apache.ddlutils.platform.MetaDataColumnDescriptor; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.dao.DataAccessException; +import org.springframework.jdbc.core.ConnectionCallback; +import org.springframework.jdbc.core.JdbcTemplate; +import org.springframework.jdbc.support.JdbcUtils; + +import java.sql.*; +import java.util.*; + + +public class DdlUtils { + + private static final Logger logger = LoggerFactory.getLogger(DdlUtils.class); + private static TableType[] SUPPORTED_TABLE_TYPES = new TableType[]{TableType.view, TableType.table}; + private final static Map _defaultSizes = new HashMap(); + + static { + _defaultSizes.put(new Integer(1), "254"); + _defaultSizes.put(new Integer(12), "254"); + _defaultSizes.put(new Integer(-1), "254"); + _defaultSizes.put(new Integer(-2), "254"); + _defaultSizes.put(new Integer(-3), "254"); + _defaultSizes.put(new Integer(-4), "254"); + _defaultSizes.put(new Integer(4), "32"); + _defaultSizes.put(new Integer(-5), "64"); + _defaultSizes.put(new Integer(7), "7,0"); + _defaultSizes.put(new Integer(6), "15,0"); + _defaultSizes.put(new Integer(8), "15,0"); + _defaultSizes.put(new Integer(3), "15,15"); + _defaultSizes.put(new Integer(2), "15,15"); + } + + + public static Table findTable(final JdbcTemplate jdbcTemplate, final String catalogName, final String schemaName, + final String tableName) { + return (Table) jdbcTemplate.execute(new ConnectionCallback() { + + public Object doInConnection(Connection con) throws SQLException, DataAccessException { + Table table = null; + DatabaseMetaDataWrapper metaData = new DatabaseMetaDataWrapper(); + try { + + DatabaseMetaData databaseMetaData = con.getMetaData(); + + metaData.setMetaData(databaseMetaData); + metaData.setTableTypes(TableType.toStrings(SUPPORTED_TABLE_TYPES)); + metaData.setCatalog(catalogName); + metaData.setSchemaPattern(schemaName); + + String convertTableName = tableName; + if (databaseMetaData.storesUpperCaseIdentifiers()) { + metaData.setCatalog(catalogName.toUpperCase()); + metaData.setSchemaPattern(schemaName.toUpperCase()); + convertTableName = tableName.toUpperCase(); + } + if (databaseMetaData.storesLowerCaseIdentifiers()) { + metaData.setCatalog(catalogName.toLowerCase()); + metaData.setSchemaPattern(schemaName.toLowerCase()); + convertTableName = tableName.toLowerCase(); + } + + ResultSet tableData = null; + try { + tableData = metaData.getTables(convertTableName); + + while ((tableData != null) && tableData.next()) { + Map values = readColumns(tableData, initColumnsForTable()); + + table = readTable(metaData, values); + if (table.getName().equalsIgnoreCase(tableName)) { + break; + } + } + } finally { + JdbcUtils.closeResultSet(tableData); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + + makeAllColumnsPrimaryKeysIfNoPrimaryKeysFound(table); + return table; + } + }); + } + + /** + * Treat tables with no primary keys as a table with all primary keys. + */ + private static void makeAllColumnsPrimaryKeysIfNoPrimaryKeysFound(Table table) { + if ((table != null) && (table.getPrimaryKeyColumns() != null) && (table.getPrimaryKeyColumns().length == 0)) { + Column[] allCoumns = table.getColumns(); + + for (Column column : allCoumns) { + column.setPrimaryKey(true); + } + } + } + + private static Table readTable(DatabaseMetaDataWrapper metaData, Map values) throws SQLException { + String tableName = (String) values.get("TABLE_NAME"); + Table table = null; + + if ((tableName != null) && (tableName.length() > 0)) { + table = new Table(); + table.setName(tableName); + table.setType((String) values.get("TABLE_TYPE")); + table.setCatalog((String) values.get("TABLE_CAT")); + table.setSchema((String) values.get("TABLE_SCHEM")); + table.setDescription((String) values.get("REMARKS")); + table.addColumns(readColumns(metaData, tableName)); + + Collection primaryKeys = readPrimaryKeyNames(metaData, tableName); + + for (Object key : primaryKeys) { + Column col = table.findColumn((String) key, true); + + if (col != null) { + col.setPrimaryKey(true); + } else { + throw new NullPointerException(String.format("%s pk %s is null - %s %s", + tableName, + key, + ToStringBuilder.reflectionToString(metaData, ToStringStyle.SIMPLE_STYLE), + ToStringBuilder.reflectionToString(values, ToStringStyle.SIMPLE_STYLE))); + } + } + } + + return table; + } + + private static List initColumnsForTable() { + List result = new ArrayList(); + + result.add(new MetaDataColumnDescriptor("TABLE_NAME", Types.VARCHAR)); + result.add(new MetaDataColumnDescriptor("TABLE_TYPE", Types.VARCHAR, "UNKNOWN")); + result.add(new MetaDataColumnDescriptor("TABLE_CAT", Types.VARCHAR)); + result.add(new MetaDataColumnDescriptor("TABLE_SCHEM", Types.VARCHAR)); + result.add(new MetaDataColumnDescriptor("REMARKS", Types.VARCHAR)); + + return result; + } + + private static List initColumnsForColumn() { + List result = new ArrayList(); + + // As suggested by Alexandre Borgoltz, we're reading the COLUMN_DEF + // first because Oracle + // has problems otherwise (it seemingly requires a LONG column to be the + // first to be read) + // See also DDLUTILS-29 + result.add(new MetaDataColumnDescriptor("COLUMN_DEF", Types.VARCHAR)); + + // we're also reading the table name so that a model reader impl can + // filter manually + result.add(new MetaDataColumnDescriptor("TABLE_NAME", Types.VARCHAR)); + result.add(new MetaDataColumnDescriptor("COLUMN_NAME", Types.VARCHAR)); + result.add(new MetaDataColumnDescriptor("TYPE_NAME", Types.VARCHAR)); + result.add(new MetaDataColumnDescriptor("DATA_TYPE", Types.INTEGER, new Integer(Types.OTHER))); + result.add(new MetaDataColumnDescriptor("NUM_PREC_RADIX", Types.INTEGER, new Integer(10))); + result.add(new MetaDataColumnDescriptor("DECIMAL_DIGITS", Types.INTEGER, new Integer(0))); + result.add(new MetaDataColumnDescriptor("COLUMN_SIZE", Types.VARCHAR)); + result.add(new MetaDataColumnDescriptor("IS_NULLABLE", Types.VARCHAR, "YES")); + result.add(new MetaDataColumnDescriptor("REMARKS", Types.VARCHAR)); + + return result; + } + + private static List initColumnsForPK() { + List result = new ArrayList(); + + result.add(new MetaDataColumnDescriptor("COLUMN_NAME", Types.VARCHAR)); + + // we're also reading the table name so that a model reader impl can + // filter manually + result.add(new MetaDataColumnDescriptor("TABLE_NAME", Types.VARCHAR)); + + // the name of the primary key is currently only interesting to the pk + // index name resolution + result.add(new MetaDataColumnDescriptor("PK_NAME", Types.VARCHAR)); + + return result; + } + + private static List readColumns(DatabaseMetaDataWrapper metaData, String tableName) throws SQLException { + ResultSet columnData = null; + + try { + columnData = metaData.getColumns(tableName, null); + + List columns = new ArrayList(); + Map values; + + for (; columnData.next(); columns.add(readColumn(metaData, values))) { + Map tmp = readColumns(columnData, initColumnsForColumn()); + if (tableName.equalsIgnoreCase((String) tmp.get("TABLE_NAME"))) { + values = tmp; + } else { + break; + } + } + + return columns; + } finally { + JdbcUtils.closeResultSet(columnData); + } + } + + private static Column readColumn(DatabaseMetaDataWrapper metaData, Map values) throws SQLException { + Column column = new Column(); + + column.setName((String) values.get("COLUMN_NAME")); + column.setDefaultValue((String) values.get("COLUMN_DEF")); + column.setTypeCode(((Integer) values.get("DATA_TYPE")).intValue()); + + String typeName = (String) values.get("TYPE_NAME"); + // column.setType(typeName); + + if ((typeName != null) && typeName.startsWith("TIMESTAMP")) { + column.setTypeCode(Types.TIMESTAMP); + } + // modify 2013-09-25,处理下unsigned + if ((typeName != null) && StringUtils.containsIgnoreCase(typeName, "UNSIGNED")) { + // 如果为unsigned,往上调大一个量级,避免数据溢出 + switch (column.getTypeCode()) { + case Types.TINYINT: + column.setTypeCode(Types.SMALLINT); + break; + case Types.SMALLINT: + column.setTypeCode(Types.INTEGER); + break; + case Types.INTEGER: + column.setTypeCode(Types.BIGINT); + break; + case Types.BIGINT: + column.setTypeCode(Types.DECIMAL); + break; + default: + break; + } + } + + Integer precision = (Integer) values.get("NUM_PREC_RADIX"); + + if (precision != null) { + column.setPrecisionRadix(precision.intValue()); + } + + String size = (String) values.get("COLUMN_SIZE"); + + if (size == null) { + size = (String) _defaultSizes.get(new Integer(column.getTypeCode())); + } + + // we're setting the size after the precision and radix in case + // the database prefers to return them in the size value + column.setSize(size); + + int scale = 0; + Object dec_digits = values.get("DECIMAL_DIGITS"); + + if (dec_digits instanceof String) { + scale = (dec_digits == null) ? 0 : NumberUtils.toInt(dec_digits.toString()); + } else if (dec_digits instanceof Integer) { + scale = (dec_digits == null) ? 0 : (Integer) dec_digits; + } + + if (scale != 0) { + column.setScale(scale); + } + + column.setRequired("NO".equalsIgnoreCase(((String) values.get("IS_NULLABLE")).trim())); + column.setDescription((String) values.get("REMARKS")); + return column; + } + + private static Map readColumns(ResultSet resultSet, List columnDescriptors) + throws SQLException { + Map values = new HashMap(); + MetaDataColumnDescriptor descriptor; + + for (Iterator it = columnDescriptors.iterator(); it.hasNext(); values.put(descriptor.getName(), + descriptor.readColumn(resultSet))) { + descriptor = (MetaDataColumnDescriptor) it.next(); + } + + return values; + } + + private static Collection readPrimaryKeyNames(DatabaseMetaDataWrapper metaData, String tableName) + throws SQLException { + ResultSet pkData = null; + + try { + List pks = new ArrayList(); + Map values; + + for (pkData = metaData.getPrimaryKeys(tableName); pkData.next(); pks.add(readPrimaryKeyName(metaData, + values))) { + values = readColumns(pkData, initColumnsForPK()); + } + + return pks; + } finally { + JdbcUtils.closeResultSet(pkData); + } + } + + private static String readPrimaryKeyName(DatabaseMetaDataWrapper metaData, Map values) + throws SQLException { + return (String) values.get("COLUMN_NAME"); + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/utils/SqlTimestampConverter.java b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/SqlTimestampConverter.java new file mode 100644 index 00000000..5743106d --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/SqlTimestampConverter.java @@ -0,0 +1,140 @@ +package com.alibaba.otter.canal.example.db.utils; + +import org.apache.commons.beanutils.ConversionException; +import org.apache.commons.beanutils.Converter; +import org.apache.commons.lang.time.DateFormatUtils; + +import java.sql.Timestamp; +import java.text.ParseException; +import java.text.ParsePosition; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.Locale; + +public class SqlTimestampConverter implements Converter { + + /** + * Field description + */ + public static final String[] DATE_FORMATS = new String[]{"yyyy-MM-dd", "HH:mm:ss", "yyyy-MM-dd HH:mm:ss", + "yyyy-MM-dd hh:mm:ss.fffffffff", "EEE MMM dd HH:mm:ss zzz yyyy", + DateFormatUtils.ISO_DATETIME_FORMAT.getPattern(), + DateFormatUtils.ISO_DATETIME_TIME_ZONE_FORMAT.getPattern(), + DateFormatUtils.SMTP_DATETIME_FORMAT.getPattern(),}; + + public static final Converter SQL_TIMESTAMP = new SqlTimestampConverter(null); + + /** + * The default value specified to our Constructor, if any. + */ + private final Object defaultValue; + + /** + * Should we return the default value on conversion errors? + */ + private final boolean useDefault; + + /** + * Create a {@link Converter} that will throw a {@link ConversionException} if a conversion error occurs. + */ + public SqlTimestampConverter() { + this.defaultValue = null; + this.useDefault = false; + } + + /** + * Create a {@link Converter} that will return the specified default value if a conversion error occurs. + * + * @param defaultValue The default value to be returned + */ + public SqlTimestampConverter(Object defaultValue) { + this.defaultValue = defaultValue; + this.useDefault = true; + } + + /** + * Convert the specified input object into an output object of the specified type. + * + * @param type Data type to which this value should be converted + * @param value The input value to be converted + * @throws ConversionException if conversion cannot be performed successfully + */ + public Object convert(Class type, Object value) { + if (value == null) { + if (useDefault) { + return (defaultValue); + } else { + throw new ConversionException("No value specified"); + } + } + + if (value instanceof java.sql.Date && java.sql.Date.class.equals(type)) { + return value; + } else if (value instanceof java.sql.Time && java.sql.Time.class.equals(type)) { + return value; + } else if (value instanceof Timestamp && Timestamp.class.equals(type)) { + return value; + } else { + try { + if (java.sql.Date.class.equals(type)) { + return new java.sql.Date(convertTimestamp2TimeMillis(value.toString())); + } else if (java.sql.Time.class.equals(type)) { + return new java.sql.Time(convertTimestamp2TimeMillis(value.toString())); + } else if (Timestamp.class.equals(type)) { + return new Timestamp(convertTimestamp2TimeMillis(value.toString())); + } else { + return new Timestamp(convertTimestamp2TimeMillis(value.toString())); + } + } catch (Exception e) { + throw new ConversionException("Value format invalid: " + e.getMessage(), e); + } + } + + } + + private Long convertTimestamp2TimeMillis(String input) { + if (input == null) { + return null; + } + + try { + // 先处理Timestamp类型 + return Timestamp.valueOf(input).getTime(); + } catch (Exception nfe) { + try { + try { + return parseDate(input, DATE_FORMATS, Locale.ENGLISH).getTime(); + } catch (Exception err) { + return parseDate(input, DATE_FORMATS, Locale.getDefault()).getTime(); + } + } catch (Exception err) { + // 最后处理long time的情况 + return Long.parseLong(input); + } + } + } + + private Date parseDate(String str, String[] parsePatterns, Locale locale) throws ParseException { + if ((str == null) || (parsePatterns == null)) { + throw new IllegalArgumentException("Date and Patterns must not be null"); + } + + SimpleDateFormat parser = null; + ParsePosition pos = new ParsePosition(0); + + for (int i = 0; i < parsePatterns.length; i++) { + if (i == 0) { + parser = new SimpleDateFormat(parsePatterns[0], locale); + } else { + parser.applyPattern(parsePatterns[i]); + } + pos.setIndex(0); + Date date = parser.parse(str, pos); + if ((date != null) && (pos.getIndex() == str.length())) { + return date; + } + } + + throw new ParseException("Unable to parse the date: " + str, -1); + } +} diff --git a/example/src/main/java/com/alibaba/otter/canal/example/db/utils/SqlUtils.java b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/SqlUtils.java new file mode 100644 index 00000000..565d5730 --- /dev/null +++ b/example/src/main/java/com/alibaba/otter/canal/example/db/utils/SqlUtils.java @@ -0,0 +1,315 @@ +package com.alibaba.otter.canal.example.db.utils; + +import org.apache.commons.beanutils.ConvertUtilsBean; +import org.apache.commons.lang.StringUtils; + +import java.io.UnsupportedEncodingException; +import java.math.BigDecimal; +import java.math.BigInteger; +import java.sql.*; +import java.util.HashMap; +import java.util.Map; + +public class SqlUtils { + + public static final String REQUIRED_FIELD_NULL_SUBSTITUTE = " "; + public static final String SQLDATE_FORMAT = "yyyy-MM-dd"; + public static final String TIMESTAMP_FORMAT = "yyyy-MM-dd HH:mm:ss"; + private static final Map> sqlTypeToJavaTypeMap = new HashMap>(); + private static final ConvertUtilsBean convertUtilsBean = new ConvertUtilsBean(); + + static { + // regist Converter + convertUtilsBean.register(SqlTimestampConverter.SQL_TIMESTAMP, Date.class); + convertUtilsBean.register(SqlTimestampConverter.SQL_TIMESTAMP, Time.class); + convertUtilsBean.register(SqlTimestampConverter.SQL_TIMESTAMP, Timestamp.class); + convertUtilsBean.register(ByteArrayConverter.SQL_BYTES, byte[].class); + + // bool + sqlTypeToJavaTypeMap.put(Types.BOOLEAN, Boolean.class); + + // int + sqlTypeToJavaTypeMap.put(Types.TINYINT, Integer.class); + sqlTypeToJavaTypeMap.put(Types.SMALLINT, Integer.class); + sqlTypeToJavaTypeMap.put(Types.INTEGER, Integer.class); + + // long + sqlTypeToJavaTypeMap.put(Types.BIGINT, Long.class); + // mysql bit最多64位,无符号 + sqlTypeToJavaTypeMap.put(Types.BIT, BigInteger.class); + + // decimal + sqlTypeToJavaTypeMap.put(Types.REAL, Float.class); + sqlTypeToJavaTypeMap.put(Types.FLOAT, Float.class); + sqlTypeToJavaTypeMap.put(Types.DOUBLE, Double.class); + sqlTypeToJavaTypeMap.put(Types.NUMERIC, BigDecimal.class); + sqlTypeToJavaTypeMap.put(Types.DECIMAL, BigDecimal.class); + + // date + sqlTypeToJavaTypeMap.put(Types.DATE, Date.class); + sqlTypeToJavaTypeMap.put(Types.TIME, Time.class); + sqlTypeToJavaTypeMap.put(Types.TIMESTAMP, Timestamp.class); + + // blob + sqlTypeToJavaTypeMap.put(Types.BLOB, byte[].class); + + // byte[] + sqlTypeToJavaTypeMap.put(Types.REF, byte[].class); + sqlTypeToJavaTypeMap.put(Types.OTHER, byte[].class); + sqlTypeToJavaTypeMap.put(Types.ARRAY, byte[].class); + sqlTypeToJavaTypeMap.put(Types.STRUCT, byte[].class); + sqlTypeToJavaTypeMap.put(Types.SQLXML, byte[].class); + sqlTypeToJavaTypeMap.put(Types.BINARY, byte[].class); + sqlTypeToJavaTypeMap.put(Types.DATALINK, byte[].class); + sqlTypeToJavaTypeMap.put(Types.DISTINCT, byte[].class); + sqlTypeToJavaTypeMap.put(Types.VARBINARY, byte[].class); + sqlTypeToJavaTypeMap.put(Types.JAVA_OBJECT, byte[].class); + sqlTypeToJavaTypeMap.put(Types.LONGVARBINARY, byte[].class); + + // String + sqlTypeToJavaTypeMap.put(Types.CHAR, String.class); + sqlTypeToJavaTypeMap.put(Types.VARCHAR, String.class); + sqlTypeToJavaTypeMap.put(Types.LONGVARCHAR, String.class); + sqlTypeToJavaTypeMap.put(Types.LONGNVARCHAR, String.class); + sqlTypeToJavaTypeMap.put(Types.NCHAR, String.class); + sqlTypeToJavaTypeMap.put(Types.NVARCHAR, String.class); + sqlTypeToJavaTypeMap.put(Types.NCLOB, String.class); + sqlTypeToJavaTypeMap.put(Types.CLOB, String.class); + } + + /** + * 将指定java.sql.Types的ResultSet value转换成相应的String + * + * @param rs + * @param index + * @param sqlType + * @return + * @throws SQLException + */ + public static String sqlValueToString(ResultSet rs, int index, int sqlType) throws SQLException { + Class requiredType = sqlTypeToJavaTypeMap.get(sqlType); + if (requiredType == null) { + throw new IllegalArgumentException("unknow java.sql.Types - " + sqlType); + } + + return getResultSetValue(rs, index, requiredType); + } + + /** + * sqlValueToString方法的逆向过程 + * + * @param value + * @param sqlType + * @param isTextRequired + * @param isEmptyStringNulled + * @return + */ + public static Object stringToSqlValue(String value, int sqlType, boolean isRequired, boolean isEmptyStringNulled) { + // 设置变量 + String sourceValue = value; + if (SqlUtils.isTextType(sqlType)) { + if ((sourceValue == null) || (StringUtils.isEmpty(sourceValue) && isEmptyStringNulled)) { + return isRequired ? REQUIRED_FIELD_NULL_SUBSTITUTE : null; + } else { + return sourceValue; + } + } else { + if (StringUtils.isEmpty(sourceValue)) { + return null; + } else { + Class requiredType = sqlTypeToJavaTypeMap.get(sqlType); + if (requiredType == null) { + throw new IllegalArgumentException("unknow java.sql.Types - " + sqlType); + } else if (requiredType.equals(String.class)) { + return sourceValue; + } else if (isNumeric(sqlType)) { + return convertUtilsBean.convert(sourceValue.trim(), requiredType); + } else { + return convertUtilsBean.convert(sourceValue, requiredType); + } + } + } + } + + public static String encoding(String source, int sqlType, String sourceEncoding, String targetEncoding) { + switch (sqlType) { + case Types.CHAR: + case Types.VARCHAR: + case Types.LONGVARCHAR: + case Types.NCHAR: + case Types.NVARCHAR: + case Types.LONGNVARCHAR: + case Types.CLOB: + case Types.NCLOB: + if (false == StringUtils.isEmpty(source)) { + String fromEncoding = StringUtils.isBlank(sourceEncoding) ? "UTF-8" : sourceEncoding; + String toEncoding = StringUtils.isBlank(targetEncoding) ? "UTF-8" : targetEncoding; + + // if (false == StringUtils.equalsIgnoreCase(fromEncoding, + // toEncoding)) { + try { + return new String(source.getBytes(fromEncoding), toEncoding); + } catch (UnsupportedEncodingException e) { + throw new IllegalArgumentException(e.getMessage(), e); + } + // } + } + } + + return source; + } + + /** + * Retrieve a JDBC column value from a ResultSet, using the specified value + * type. + *

      + * Uses the specifically typed ResultSet accessor methods, falling back to + * {@link #getResultSetValue(ResultSet, int)} for unknown types. + *

      + * Note that the returned value may not be assignable to the specified + * required type, in case of an unknown type. Calling code needs to deal + * with this case appropriately, e.g. throwing a corresponding exception. + * + * @param rs is the ResultSet holding the data + * @param index is the column index + * @param requiredType the required value type (may be null) + * @return the value object + * @throws SQLException if thrown by the JDBC API + */ + private static String getResultSetValue(ResultSet rs, int index, Class requiredType) throws SQLException { + if (requiredType == null) { + return getResultSetValue(rs, index); + } + + Object value = null; + boolean wasNullCheck = false; + + // Explicitly extract typed value, as far as possible. + if (String.class.equals(requiredType)) { + value = rs.getString(index); + } else if (boolean.class.equals(requiredType) || Boolean.class.equals(requiredType)) { + value = Boolean.valueOf(rs.getBoolean(index)); + wasNullCheck = true; + } else if (byte.class.equals(requiredType) || Byte.class.equals(requiredType)) { + value = new Byte(rs.getByte(index)); + wasNullCheck = true; + } else if (short.class.equals(requiredType) || Short.class.equals(requiredType)) { + value = new Short(rs.getShort(index)); + wasNullCheck = true; + } else if (int.class.equals(requiredType) || Integer.class.equals(requiredType)) { + value = new Long(rs.getLong(index)); + wasNullCheck = true; + } else if (long.class.equals(requiredType) || Long.class.equals(requiredType)) { + value = rs.getBigDecimal(index); + wasNullCheck = true; + } else if (float.class.equals(requiredType) || Float.class.equals(requiredType)) { + value = new Float(rs.getFloat(index)); + wasNullCheck = true; + } else if (double.class.equals(requiredType) || Double.class.equals(requiredType) + || Number.class.equals(requiredType)) { + value = new Double(rs.getDouble(index)); + wasNullCheck = true; + } else if (Time.class.equals(requiredType)) { + // try { + // value = rs.getTime(index); + // } catch (SQLException e) { + value = rs.getString(index);// 尝试拿为string对象,0000无法用Time表示 + // if (value == null && !rs.wasNull()) { + // value = "00:00:00"; // + // mysql设置了zeroDateTimeBehavior=convertToNull,出现0值时返回为null + // } + // } + } else if (Timestamp.class.equals(requiredType) || Date.class.equals(requiredType)) { + // try { + // value = convertTimestamp(rs.getTimestamp(index)); + // } catch (SQLException e) { + // 尝试拿为string对象,0000-00-00 00:00:00无法用Timestamp 表示 + value = rs.getString(index); + // if (value == null && !rs.wasNull()) { + // value = "0000:00:00 00:00:00"; // + // mysql设置了zeroDateTimeBehavior=convertToNull,出现0值时返回为null + // } + // } + } else if (BigDecimal.class.equals(requiredType)) { + value = rs.getBigDecimal(index); + } else if (BigInteger.class.equals(requiredType)) { + value = rs.getBigDecimal(index); + } else if (Blob.class.equals(requiredType)) { + value = rs.getBlob(index); + } else if (Clob.class.equals(requiredType)) { + value = rs.getClob(index); + } else if (byte[].class.equals(requiredType)) { + try { + byte[] bytes = rs.getBytes(index); + if (bytes == null) { + value = null; + } else { + value = new String(bytes, "ISO-8859-1");// 将binary转化为iso-8859-1的字符串 + } + } catch (UnsupportedEncodingException e) { + throw new SQLException(e); + } + } else { + // Some unknown type desired -> rely on getObject. + value = getResultSetValue(rs, index); + } + + // Perform was-null check if demanded (for results that the + // JDBC driver returns as primitives). + if (wasNullCheck && (value != null) && rs.wasNull()) { + value = null; + } + + return (value == null) ? null : convertUtilsBean.convert(value); + } + + /** + * Retrieve a JDBC column value from a ResultSet, using the most appropriate + * value type. The returned value should be a detached value object, not + * having any ties to the active ResultSet: in particular, it should not be + * a Blob or Clob object but rather a byte array respectively String + * representation. + *

      + * Uses the getObject(index) method, but includes additional + * "hacks" to get around Oracle 10g returning a non-standard object for its + * TIMESTAMP datatype and a java.sql.Date for DATE columns + * leaving out the time portion: These columns will explicitly be extracted + * as standard java.sql.Timestamp object. + * + * @param rs is the ResultSet holding the data + * @param index is the column index + * @return the value object + * @throws SQLException if thrown by the JDBC API + * @see Blob + * @see Clob + * @see Timestamp + */ + private static String getResultSetValue(ResultSet rs, int index) throws SQLException { + Object obj = rs.getObject(index); + return (obj == null) ? null : convertUtilsBean.convert(obj); + } + + // private static Object convertTimestamp(Timestamp timestamp) { + // return (timestamp == null) ? null : timestamp.getTime(); + // } + + /** + * Check whether the given SQL type is numeric. + */ + public static boolean isNumeric(int sqlType) { + return (Types.BIT == sqlType) || (Types.BIGINT == sqlType) || (Types.DECIMAL == sqlType) + || (Types.DOUBLE == sqlType) || (Types.FLOAT == sqlType) || (Types.INTEGER == sqlType) + || (Types.NUMERIC == sqlType) || (Types.REAL == sqlType) || (Types.SMALLINT == sqlType) + || (Types.TINYINT == sqlType); + } + + public static boolean isTextType(int sqlType) { + if (sqlType == Types.CHAR || sqlType == Types.VARCHAR || sqlType == Types.CLOB || sqlType == Types.LONGVARCHAR + || sqlType == Types.NCHAR || sqlType == Types.NVARCHAR || sqlType == Types.NCLOB + || sqlType == Types.LONGNVARCHAR) { + return true; + } else { + return false; + } + } +} diff --git a/example/src/main/resources/client-spring.xml b/example/src/main/resources/client-spring.xml new file mode 100644 index 00000000..29eba1af --- /dev/null +++ b/example/src/main/resources/client-spring.xml @@ -0,0 +1,53 @@ + + + + + + + + + classpath:client.properties + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/example/src/main/resources/client.properties b/example/src/main/resources/client.properties new file mode 100644 index 00000000..c5142912 --- /dev/null +++ b/example/src/main/resources/client.properties @@ -0,0 +1,16 @@ +# client 配置 +zk.servers=127.0.0.1:2181 +# 5 * 1024 +client.batch.size=5120 +client.debug=false +client.destination=example +client.username=canal +client.password=canal +client.exceptionstrategy=1 +client.retrytimes=3 +client.filter=.*\\..* + +# 同步目标: mysql 配置 +target.mysql.url=jdbc:mysql://127.0.0.1:4306 +target.mysql.username=root +target.mysql.password=123456 diff --git a/filter/pom.xml b/filter/pom.xml index 30b53e28..6fc6ba88 100644 --- a/filter/pom.xml +++ b/filter/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter diff --git a/images/QPS.PNG b/images/QPS.PNG new file mode 100644 index 00000000..e646ce40 Binary files /dev/null and b/images/QPS.PNG differ diff --git a/images/TPS.PNG b/images/TPS.PNG new file mode 100644 index 00000000..7559e2ed Binary files /dev/null and b/images/TPS.PNG differ diff --git a/images/basic.PNG b/images/basic.PNG new file mode 100644 index 00000000..21773a57 Binary files /dev/null and b/images/basic.PNG differ diff --git a/images/clients.PNG b/images/clients.PNG new file mode 100644 index 00000000..9131f321 Binary files /dev/null and b/images/clients.PNG differ diff --git a/images/delay.PNG b/images/delay.PNG new file mode 100644 index 00000000..9f236a7c Binary files /dev/null and b/images/delay.PNG differ diff --git a/images/empty.PNG b/images/empty.PNG new file mode 100644 index 00000000..6c98b62d Binary files /dev/null and b/images/empty.PNG differ diff --git a/images/idle.PNG b/images/idle.PNG new file mode 100644 index 00000000..a2d3a9ff Binary files /dev/null and b/images/idle.PNG differ diff --git a/images/instance.PNG b/images/instance.PNG new file mode 100644 index 00000000..fb7b0e79 Binary files /dev/null and b/images/instance.PNG differ diff --git a/images/latency.PNG b/images/latency.PNG new file mode 100644 index 00000000..be701be9 Binary files /dev/null and b/images/latency.PNG differ diff --git a/images/network.PNG b/images/network.PNG new file mode 100644 index 00000000..06a5b6e1 Binary files /dev/null and b/images/network.PNG differ diff --git a/images/overview.PNG b/images/overview.PNG new file mode 100644 index 00000000..4df00557 Binary files /dev/null and b/images/overview.PNG differ diff --git a/images/remain_events.PNG b/images/remain_events.PNG new file mode 100644 index 00000000..7aa05883 Binary files /dev/null and b/images/remain_events.PNG differ diff --git a/images/remain_mem.PNG b/images/remain_mem.PNG new file mode 100644 index 00000000..7f749be1 Binary files /dev/null and b/images/remain_mem.PNG differ diff --git a/images/reqs.PNG b/images/reqs.PNG new file mode 100644 index 00000000..6897c9b3 Binary files /dev/null and b/images/reqs.PNG differ diff --git a/images/rows.PNG b/images/rows.PNG new file mode 100644 index 00000000..5934ae42 Binary files /dev/null and b/images/rows.PNG differ diff --git a/images/store.PNG b/images/store.PNG new file mode 100644 index 00000000..f5b2b66e Binary files /dev/null and b/images/store.PNG differ diff --git a/images/throughput.PNG b/images/throughput.PNG new file mode 100644 index 00000000..d0c54607 Binary files /dev/null and b/images/throughput.PNG differ diff --git a/images/transactions.PNG b/images/transactions.PNG new file mode 100644 index 00000000..a8e1943c Binary files /dev/null and b/images/transactions.PNG differ diff --git a/instance/core/pom.xml b/instance/core/pom.xml index cbfab2fd..a7346fc8 100644 --- a/instance/core/pom.xml +++ b/instance/core/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../../pom.xml canal.instance.core diff --git a/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/AbstractCanalInstance.java b/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/AbstractCanalInstance.java index 9143a626..b1b64d5b 100644 --- a/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/AbstractCanalInstance.java +++ b/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/AbstractCanalInstance.java @@ -38,6 +38,9 @@ public class AbstractCanalInstance extends AbstractCanalLifeCycle implements Can protected CanalEventSink> eventSink; // 链接parse和store的桥接器 protected CanalMetaManager metaManager; // 消费信息管理器 protected CanalAlarmHandler alarmHandler; // alarm报警机制 + protected CanalMQConfig mqConfig; // mq的配置 + + @Override public boolean subscribeChange(ClientIdentity identity) { @@ -241,4 +244,9 @@ public class AbstractCanalInstance extends AbstractCanalLifeCycle implements Can public CanalAlarmHandler getAlarmHandler() { return alarmHandler; } + + @Override + public CanalMQConfig getMqConfig() { + return mqConfig; + } } diff --git a/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/CanalInstance.java b/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/CanalInstance.java index 3bd0464b..3d1a08c2 100644 --- a/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/CanalInstance.java +++ b/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/CanalInstance.java @@ -32,4 +32,6 @@ public interface CanalInstance extends CanalLifeCycle { * 客户端发生订阅/取消订阅行为 */ boolean subscribeChange(ClientIdentity identity); + + CanalMQConfig getMqConfig(); } diff --git a/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/CanalMQConfig.java b/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/CanalMQConfig.java new file mode 100644 index 00000000..c275f150 --- /dev/null +++ b/instance/core/src/main/java/com/alibaba/otter/canal/instance/core/CanalMQConfig.java @@ -0,0 +1,68 @@ +package com.alibaba.otter.canal.instance.core; + +import java.util.LinkedHashMap; +import java.util.Map; + +public class CanalMQConfig { + + private String topic; + private Integer partition; + private Integer partitionsNum; + private String partitionHash; + + private volatile Map partitionHashProperties; + + public String getTopic() { + return topic; + } + + public void setTopic(String topic) { + this.topic = topic; + } + + public Integer getPartition() { + return partition; + } + + public void setPartition(Integer partition) { + this.partition = partition; + } + + public Integer getPartitionsNum() { + return partitionsNum; + } + + public void setPartitionsNum(Integer partitionsNum) { + this.partitionsNum = partitionsNum; + } + + public String getPartitionHash() { + return partitionHash; + } + + public void setPartitionHash(String partitionHash) { + this.partitionHash = partitionHash; + } + + public Map getPartitionHashProperties() { + if (partitionHashProperties == null) { + synchronized (CanalMQConfig.class) { + if (partitionHashProperties == null) { + if (partitionHash != null) { + partitionHashProperties = new LinkedHashMap<>(); + String[] items = partitionHash.split(","); + for (String item : items) { + int i = item.indexOf(":"); + if (i > -1) { + String dbTable = item.substring(0, i).trim(); + String pk = item.substring(i + 1).trim(); + partitionHashProperties.put(dbTable, pk); + } + } + } + } + } + } + return partitionHashProperties; + } +} diff --git a/instance/manager/pom.xml b/instance/manager/pom.xml index 10f01e43..ef5c987e 100644 --- a/instance/manager/pom.xml +++ b/instance/manager/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../../pom.xml com.alibaba.otter diff --git a/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/CanalInstanceWithManager.java b/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/CanalInstanceWithManager.java index bca5ba13..11091695 100644 --- a/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/CanalInstanceWithManager.java +++ b/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/CanalInstanceWithManager.java @@ -6,6 +6,7 @@ import java.util.ArrayList; import java.util.Collections; import java.util.List; +import org.apache.commons.lang.BooleanUtils; import org.apache.commons.lang.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -27,6 +28,7 @@ import com.alibaba.otter.canal.instance.manager.model.CanalParameter.MetaMode; import com.alibaba.otter.canal.instance.manager.model.CanalParameter.SourcingType; import com.alibaba.otter.canal.instance.manager.model.CanalParameter.StorageMode; import com.alibaba.otter.canal.instance.manager.model.CanalParameter.StorageScavengeMode; +import com.alibaba.otter.canal.meta.FileMixedMetaManager; import com.alibaba.otter.canal.meta.MemoryMetaManager; import com.alibaba.otter.canal.meta.PeriodMixedMetaManager; import com.alibaba.otter.canal.meta.ZooKeeperMetaManager; @@ -37,6 +39,10 @@ import com.alibaba.otter.canal.parse.inbound.AbstractEventParser; import com.alibaba.otter.canal.parse.inbound.group.GroupEventParser; import com.alibaba.otter.canal.parse.inbound.mysql.LocalBinlogEventParser; import com.alibaba.otter.canal.parse.inbound.mysql.MysqlEventParser; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.RdsBinlogEventParserProxy; +import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.DefaultTableMetaTSDBFactory; +import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.TableMetaTSDB; +import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.TableMetaTSDBBuilder; import com.alibaba.otter.canal.parse.index.CanalLogPositionManager; import com.alibaba.otter.canal.parse.index.FailbackLogPositionManager; import com.alibaba.otter.canal.parse.index.MemoryLogPositionManager; @@ -120,6 +126,11 @@ public class CanalInstanceWithManager extends AbstractCanalInstance { ZooKeeperMetaManager zooKeeperMetaManager = new ZooKeeperMetaManager(); zooKeeperMetaManager.setZkClientx(getZkclientx()); ((PeriodMixedMetaManager) metaManager).setZooKeeperMetaManager(zooKeeperMetaManager); + } else if (mode.isLocalFile()) { + FileMixedMetaManager fileMixedMetaManager = new FileMixedMetaManager(); + fileMixedMetaManager.setDataDir(parameters.getDataDir()); + fileMixedMetaManager.setPeriod(parameters.getMetaFileFlushPeriod()); + metaManager = fileMixedMetaManager; } else { throw new CanalException("unsupport MetaMode for " + mode); } @@ -136,6 +147,7 @@ public class CanalInstanceWithManager extends AbstractCanalInstance { memoryEventStore.setBufferMemUnit(parameters.getMemoryStorageBufferMemUnit()); memoryEventStore.setBatchMode(BatchMode.valueOf(parameters.getStorageBatchMode().name())); memoryEventStore.setDdlIsolation(parameters.getDdlIsolation()); + memoryEventStore.setRaw(parameters.getMemoryStorageRawEntry()); eventStore = memoryEventStore; } else if (mode.isFile()) { // 后续版本支持 @@ -227,7 +239,18 @@ public class CanalInstanceWithManager extends AbstractCanalInstance { private CanalEventParser doInitEventParser(SourcingType type, List dbAddresses) { CanalEventParser eventParser; if (type.isMysql()) { - MysqlEventParser mysqlEventParser = new MysqlEventParser(); + MysqlEventParser mysqlEventParser = null; + if (StringUtils.isNotEmpty(parameters.getRdsAccesskey()) + && StringUtils.isNotEmpty(parameters.getRdsSecretkey()) + && StringUtils.isNotEmpty(parameters.getRdsInstanceId())) { + + mysqlEventParser = new RdsBinlogEventParserProxy(); + ((RdsBinlogEventParserProxy) mysqlEventParser).setAccesskey(parameters.getRdsAccesskey()); + ((RdsBinlogEventParserProxy) mysqlEventParser).setSecretkey(parameters.getRdsSecretkey()); + ((RdsBinlogEventParserProxy) mysqlEventParser).setInstanceId(parameters.getRdsInstanceId()); + } else { + mysqlEventParser = new MysqlEventParser(); + } mysqlEventParser.setDestination(destination); // 编码参数 mysqlEventParser.setConnectionCharset(Charset.forName(parameters.getConnectionCharset())); @@ -271,6 +294,40 @@ public class CanalInstanceWithManager extends AbstractCanalInstance { mysqlEventParser.setFallbackIntervalInSeconds(parameters.getFallbackIntervalInSeconds()); mysqlEventParser.setProfilingEnabled(false); mysqlEventParser.setFilterTableError(parameters.getFilterTableError()); + mysqlEventParser.setIsGTIDMode(BooleanUtils.toBoolean(parameters.getGtidEnable())); + // tsdb + if (parameters.getTsdbSnapshotInterval() != null) { + mysqlEventParser.setTsdbSnapshotInterval(parameters.getTsdbSnapshotInterval()); + } + if (parameters.getTsdbSnapshotExpire() != null) { + mysqlEventParser.setTsdbSnapshotExpire(parameters.getTsdbSnapshotExpire()); + } + boolean tsdbEnable = BooleanUtils.toBoolean(parameters.getTsdbEnable()); + if (tsdbEnable) { + mysqlEventParser.setTableMetaTSDBFactory(new DefaultTableMetaTSDBFactory() { + + @Override + public void destory(String destination) { + TableMetaTSDBBuilder.destory(destination); + } + + @Override + public TableMetaTSDB build(String destination, String springXml) { + try { + System.setProperty("canal.instance.tsdb.url", parameters.getTsdbJdbcUrl()); + System.setProperty("canal.instance.tsdb.dbUsername", parameters.getTsdbJdbcUserName()); + System.setProperty("canal.instance.tsdb.dbPassword", parameters.getTsdbJdbcPassword()); + + return TableMetaTSDBBuilder.build(destination, "classpath:spring/tsdb/mysql-tsdb.xml"); + } finally { + System.setProperty("canal.instance.tsdb.url", ""); + System.setProperty("canal.instance.tsdb.dbUsername", ""); + System.setProperty("canal.instance.tsdb.dbPassword", ""); + } + } + }); + mysqlEventParser.setEnableTsdb(tsdbEnable); + } eventParser = mysqlEventParser; } else if (type.isLocalBinlog()) { LocalBinlogEventParser localBinlogEventParser = new LocalBinlogEventParser(); @@ -289,8 +346,8 @@ public class CanalInstanceWithManager extends AbstractCanalInstance { parameters.getDbUsername(), parameters.getDbPassword(), parameters.getDefaultDatabaseName())); - } + eventParser = localBinlogEventParser; } else if (type.isOracle()) { throw new CanalException("unsupport SourcingType for " + type); diff --git a/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/model/CanalParameter.java b/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/model/CanalParameter.java index 16c929ca..af3841dd 100644 --- a/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/model/CanalParameter.java +++ b/instance/manager/src/main/java/com/alibaba/otter/canal/instance/manager/model/CanalParameter.java @@ -28,8 +28,10 @@ public class CanalParameter implements Serializable { private Long zkClusterId; // zk集群id,为管理方便 private List zkClusters; // zk集群地址 + private String dataDir = "../conf"; // 默认本地文件数据的目录默认是conf // meta相关参数 private MetaMode metaMode = MetaMode.MEMORY; // meta机制 + private Integer metaFileFlushPeriod = 1000; // meta刷新间隔 // storage存储 private Integer transactionSize = 1024; // 支持处理的transaction事务大小 @@ -37,6 +39,7 @@ public class CanalParameter implements Serializable { private BatchMode storageBatchMode = BatchMode.MEMSIZE; // 基于大小返回结果 private Integer memoryStorageBufferSize = 16 * 1024; // 内存存储的buffer大小 private Integer memoryStorageBufferMemUnit = 1024; // 内存存储的buffer内存占用单位,默认为1kb + private Boolean memoryStorageRawEntry = Boolean.TRUE; // 内存存储的对象是否启用raw的ByteString模式 private String fileStorageDirectory; // 文件存储的目录位置 private Integer fileStorageStoreCount; // 每个文件store存储的记录数 private Integer fileStorageRollverCount; // store文件的个数 @@ -91,6 +94,16 @@ public class CanalParameter implements Serializable { private Boolean filterTableError = Boolean.FALSE; // 是否忽略表解析异常 private String blackFilter = null; // 匹配黑名单,忽略解析 + private Boolean tsdbEnable = Boolean.FALSE; // 是否开启tableMetaTSDB + private String tsdbJdbcUrl; + private String tsdbJdbcUserName; + private String tsdbJdbcPassword; + private Integer tsdbSnapshotInterval = 24; + private Integer tsdbSnapshotExpire = 360; + private String rdsAccesskey; + private String rdsSecretkey; + private String rdsInstanceId; + private Boolean gtidEnable = Boolean.FALSE; // 是否开启gtid // ================================== 兼容字段处理 private InetSocketAddress masterAddress; // 主库信息 private String masterUsername; // 帐号 @@ -243,7 +256,9 @@ public class CanalParameter implements Serializable { /** 文件存储模式 */ ZOOKEEPER, /** 混合模式,内存+文件 */ - MIXED; + MIXED, + /** 本地文件存储模式 */ + LOCAL_FILE; public boolean isMemory() { return this.equals(MetaMode.MEMORY); @@ -256,6 +271,10 @@ public class CanalParameter implements Serializable { public boolean isMixed() { return this.equals(MetaMode.MIXED); } + + public boolean isLocalFile() { + return this.equals(MetaMode.LOCAL_FILE); + } } public static enum IndexMode { @@ -390,6 +409,22 @@ public class CanalParameter implements Serializable { return storageMode; } + public String getDataDir() { + return dataDir; + } + + public void setDataDir(String dataDir) { + this.dataDir = dataDir; + } + + public Integer getMetaFileFlushPeriod() { + return metaFileFlushPeriod; + } + + public void setMetaFileFlushPeriod(Integer metaFileFlushPeriod) { + this.metaFileFlushPeriod = metaFileFlushPeriod; + } + public void setStorageMode(StorageMode storageMode) { this.storageMode = storageMode; } @@ -859,6 +894,94 @@ public class CanalParameter implements Serializable { this.blackFilter = blackFilter; } + public Boolean getTsdbEnable() { + return tsdbEnable; + } + + public void setTsdbEnable(Boolean tsdbEnable) { + this.tsdbEnable = tsdbEnable; + } + + public String getTsdbJdbcUrl() { + return tsdbJdbcUrl; + } + + public void setTsdbJdbcUrl(String tsdbJdbcUrl) { + this.tsdbJdbcUrl = tsdbJdbcUrl; + } + + public String getTsdbJdbcUserName() { + return tsdbJdbcUserName; + } + + public void setTsdbJdbcUserName(String tsdbJdbcUserName) { + this.tsdbJdbcUserName = tsdbJdbcUserName; + } + + public String getTsdbJdbcPassword() { + return tsdbJdbcPassword; + } + + public void setTsdbJdbcPassword(String tsdbJdbcPassword) { + this.tsdbJdbcPassword = tsdbJdbcPassword; + } + + public String getRdsAccesskey() { + return rdsAccesskey; + } + + public void setRdsAccesskey(String rdsAccesskey) { + this.rdsAccesskey = rdsAccesskey; + } + + public String getRdsSecretkey() { + return rdsSecretkey; + } + + public void setRdsSecretkey(String rdsSecretkey) { + this.rdsSecretkey = rdsSecretkey; + } + + public String getRdsInstanceId() { + return rdsInstanceId; + } + + public void setRdsInstanceId(String rdsInstanceId) { + this.rdsInstanceId = rdsInstanceId; + } + + public Boolean getGtidEnable() { + return gtidEnable; + } + + public void setGtidEnable(Boolean gtidEnable) { + this.gtidEnable = gtidEnable; + } + + public Boolean getMemoryStorageRawEntry() { + return memoryStorageRawEntry; + } + + public void setMemoryStorageRawEntry(Boolean memoryStorageRawEntry) { + this.memoryStorageRawEntry = memoryStorageRawEntry; + } + + public Integer getTsdbSnapshotInterval() { + return tsdbSnapshotInterval; + } + + public void setTsdbSnapshotInterval(Integer tsdbSnapshotInterval) { + this.tsdbSnapshotInterval = tsdbSnapshotInterval; + } + + public Integer getTsdbSnapshotExpire() { + return tsdbSnapshotExpire; + } + + public void setTsdbSnapshotExpire(Integer tsdbSnapshotExpire) { + this.tsdbSnapshotExpire = tsdbSnapshotExpire; + } + public String toString() { return ToStringBuilder.reflectionToString(this, CanalToStringStyle.DEFAULT_STYLE); } diff --git a/instance/pom.xml b/instance/pom.xml index aeec17cb..2a4da45c 100644 --- a/instance/pom.xml +++ b/instance/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter diff --git a/instance/spring/pom.xml b/instance/spring/pom.xml index 6a8f172a..bea5d37d 100644 --- a/instance/spring/pom.xml +++ b/instance/spring/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../../pom.xml com.alibaba.otter diff --git a/instance/spring/src/main/java/com/alibaba/otter/canal/instance/spring/CanalInstanceWithSpring.java b/instance/spring/src/main/java/com/alibaba/otter/canal/instance/spring/CanalInstanceWithSpring.java index 79693c4c..69672a6c 100644 --- a/instance/spring/src/main/java/com/alibaba/otter/canal/instance/spring/CanalInstanceWithSpring.java +++ b/instance/spring/src/main/java/com/alibaba/otter/canal/instance/spring/CanalInstanceWithSpring.java @@ -2,6 +2,8 @@ package com.alibaba.otter.canal.instance.spring; import java.util.List; +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.instance.core.CanalMQConfig; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -56,4 +58,8 @@ public class CanalInstanceWithSpring extends AbstractCanalInstance { this.alarmHandler = alarmHandler; } + public void setMqConfig(CanalMQConfig mqConfig){ + this.mqConfig = mqConfig; + } + } diff --git a/instance/spring/src/test/resources/retl/instance.properties b/instance/spring/src/test/resources/retl/instance.properties index 62ba5c4c..afc34305 100644 --- a/instance/spring/src/test/resources/retl/instance.properties +++ b/instance/spring/src/test/resources/retl/instance.properties @@ -27,9 +27,12 @@ canal.instance.master2.timestamp = # username/password canal.instance.dbUsername = xxxxx -canal.instance.dbPassword = xxxxx +canal.instance.dbPassword=cZozNf1mzW6EQLGO2q9u99619xbZLO0fbua3EX08r4BWNXb8lAt1aHrTEOBttd6UY8Vnuc0easlVXZDdLtt8BQ== +canal.instance.pwdPublicKey=MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBALK4BUxdDltRRE5/zXpVEVPUgunvscYFtEip3pmLlhrWpacX7y7GCMo2/JM6LeHmiiNdH1FWgGCpUfircSwlWKUCAwEAAQ== canal.instance.defaultDatabaseName = canal.instance.connectionCharset = UTF-8 +# enable druid Decrypt database password +canal.instance.enableDruid=true # table regex canal.instance.filter.regex = .*\\..* diff --git a/kafka-client/pom.xml b/kafka-client/pom.xml deleted file mode 100644 index d814be52..00000000 --- a/kafka-client/pom.xml +++ /dev/null @@ -1,111 +0,0 @@ - - - 4.0.0 - - canal - com.alibaba.otter - 1.0.26-SNAPSHOT - ../pom.xml - - com.alibaba.otter - canal.kafka.client - jar - canal kafka client module for otter ${project.version} - - - - - com.alibaba.otter - canal.protocol - ${project.version} - - - org.apache.kafka - kafka-clients - 0.9.0.1 - - - - - junit - junit - - - - - - dev - - true - - env - !javadoc - - - - - - javadoc - - - env - javadoc - - - - - - org.apache.maven.plugins - maven-javadoc-plugin - 2.9.1 - - - attach-javadocs - package - - jar - - - - - true - public - true -

      ${project.artifactId}-${project.version}
      -
      ${project.artifactId}-${project.version}
      - ${project.artifactId}-${project.version} - - https://github.com/alibaba/canal - - ${project.build.directory}/apidocs/apidocs/${project.version} - - - - org.apache.maven.plugins - maven-scm-publish-plugin - 1.0-beta-2 - - - attach-javadocs - package - - publish-scm - - - - - ${project.build.directory}/scmpublish - Publishing javadoc for ${project.artifactId}:${project.version} - ${project.build.directory}/apidocs - true - scm:git:git@github.com:alibaba/canal.git - gh-pages - - - - - - - \ No newline at end of file diff --git a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/KafkaCanalConnector.java b/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/KafkaCanalConnector.java deleted file mode 100644 index 3e997e27..00000000 --- a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/KafkaCanalConnector.java +++ /dev/null @@ -1,242 +0,0 @@ -package com.alibaba.otter.canal.kafka.client; - -import com.alibaba.otter.canal.common.utils.AddressUtils; -import com.alibaba.otter.canal.common.utils.BooleanMutex; -import com.alibaba.otter.canal.common.zookeeper.ZkClientx; -import com.alibaba.otter.canal.kafka.client.running.ClientRunningData; -import com.alibaba.otter.canal.kafka.client.running.ClientRunningListener; -import com.alibaba.otter.canal.kafka.client.running.ClientRunningMonitor; -import com.alibaba.otter.canal.protocol.Message; -import com.alibaba.otter.canal.protocol.exception.CanalClientException; -import org.apache.kafka.clients.consumer.ConsumerRecords; -import org.apache.kafka.clients.consumer.KafkaConsumer; -import org.apache.kafka.common.TopicPartition; -import org.apache.kafka.common.serialization.StringDeserializer; - -import java.util.Collections; -import java.util.Properties; -import java.util.concurrent.TimeUnit; - -/** - * canal kafka 数据操作客户端 - * - * @author machengyuan @ 2018-6-12 - * @version 1.0.0 - */ -public class KafkaCanalConnector { - - private KafkaConsumer kafkaConsumer; - private String topic; - private Integer partition; - private Properties properties; - private ClientRunningMonitor runningMonitor; // 运行控制 - private ZkClientx zkClientx; - private BooleanMutex mutex = new BooleanMutex(false); - private volatile boolean connected = false; - private volatile boolean running = false; - - public KafkaCanalConnector(String zkServers, String servers, String topic, Integer partition, String groupId) { - this.topic = topic; - this.partition = partition; - - properties = new Properties(); - properties.put("bootstrap.servers", servers); - properties.put("group.id", groupId); - properties.put("enable.auto.commit", false); - properties.put("auto.commit.interval.ms", "1000"); - properties.put("auto.offset.reset", "latest"); //如果没有offset则从最后的offset开始读 - properties.put("request.timeout.ms", "40000"); // 必须大于session.timeout.ms的设置 - properties.put("session.timeout.ms", "30000"); // 默认为30秒 - properties.put("max.poll.records", "1"); // 所以一次只取一条数据 - properties.put("key.deserializer", StringDeserializer.class.getName()); - properties.put("value.deserializer", MessageDeserializer.class.getName()); - - if (zkServers != null) { - zkClientx = new ZkClientx(zkServers); - - ClientRunningData clientData = new ClientRunningData(); - clientData.setGroupId(groupId); - clientData.setAddress(AddressUtils.getHostIp()); - - runningMonitor = new ClientRunningMonitor(); - runningMonitor.setTopic(topic); - runningMonitor.setZkClient(zkClientx); - runningMonitor.setClientData(clientData); - runningMonitor.setListener(new ClientRunningListener() { - public void processActiveEnter() { - mutex.set(true); - } - - public void processActiveExit() { - mutex.set(false); - } - }); - } - - } - - /** - * 重新设置sessionTime - * - * @param timeout - * @param unit - */ - public void setSessionTimeout(Long timeout, TimeUnit unit) { - long t = unit.toMillis(timeout); - properties.put("request.timeout.ms", String.valueOf(t + 60000)); - properties.put("session.timeout.ms", String.valueOf(t)); - } - - /** - * 打开连接 - */ - public void connect() { - if (connected) { - return; - } - - if (runningMonitor != null) { - if (!runningMonitor.isStart()) { - runningMonitor.start(); - } - } - - connected = true; - - if (kafkaConsumer == null) { - kafkaConsumer = new KafkaConsumer(properties); - } - } - - /** - * 关闭链接 - */ - public void disconnnect() { - kafkaConsumer.close(); - - connected = false; - if (runningMonitor.isStart()) { - runningMonitor.stop(); - } - } - - private void waitClientRunning() { - try { - if (zkClientx != null) { - if (!connected) {// 未调用connect - throw new CanalClientException("should connect first"); - } - - running = true; - mutex.get();// 阻塞等待 - } else { - // 单机模式直接设置为running - running = true; - } - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - throw new CanalClientException(e); - } - } - - public boolean checkValid() { - if (zkClientx != null) { - return mutex.state(); - } else { - return true;// 默认都放过 - } - } - - /** - * 订阅topic - */ - public void subscribe() { - waitClientRunning(); - if (!running) { - return; - } - - if (partition == null) { - kafkaConsumer.subscribe(Collections.singletonList(topic)); - } else { - TopicPartition topicPartition = new TopicPartition(topic, partition); - kafkaConsumer.assign(Collections.singletonList(topicPartition)); - } - } - - /** - * 取消订阅 - */ - public void unsubscribe() { - waitClientRunning(); - if (!running) { - return; - } - - kafkaConsumer.unsubscribe(); - } - - /** - * 获取数据,自动进行确认 - * - * @return - */ - public Message get() { - return get(100L, TimeUnit.MILLISECONDS); - } - - public Message get(Long timeout, TimeUnit unit) { - waitClientRunning(); - if (!running) { - return null; - } - - Message message = getWithoutAck(timeout, unit); - this.ack(); - return message; - } - - public Message getWithoutAck() { - return getWithoutAck(100L, TimeUnit.MILLISECONDS); - } - - /** - * 获取数据,不进行确认,等待处理完成手工确认 - * - * @return - */ - public Message getWithoutAck(Long timeout, TimeUnit unit) { - waitClientRunning(); - if (!running) { - return null; - } - - ConsumerRecords records = kafkaConsumer.poll(unit.toMillis(timeout)); // 基于配置,最多只能poll到一条数据 - - if (!records.isEmpty()) { - return records.iterator().next().value(); - } - return null; - } - - /** - * 提交offset,如果超过 session.timeout.ms 设置的时间没有ack则会抛出异常,ack失败 - */ - public void ack() { - waitClientRunning(); - if (!running) { - return; - } - - kafkaConsumer.commitSync(); - } - - public void stopRunning() { - if (running) { - running = false; // 设置为非running状态 - if (!mutex.state()) { - mutex.set(true); // 中断阻塞 - } - } - } -} diff --git a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/KafkaCanalConnectors.java b/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/KafkaCanalConnectors.java deleted file mode 100644 index 1a2942ab..00000000 --- a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/KafkaCanalConnectors.java +++ /dev/null @@ -1,62 +0,0 @@ -package com.alibaba.otter.canal.kafka.client; - -/** - * canal kafka connectors创建工具类 - * - * @author machengyuan @ 2018-6-12 - * @version 1.0.0 - */ -public class KafkaCanalConnectors { - - /** - * 创建kafka客户端链接,独立运行不注册zk信息 - * - * @param servers - * @param topic - * @param partition - * @param groupId - * @return - */ - public static KafkaCanalConnector newKafkaConnector(String servers, String topic, Integer partition, String groupId) { - return new KafkaCanalConnector(null, servers, topic, partition, groupId); - } - - /** - * 创建kafka客户端链接,独立运行不注册zk信息 - * - * @param servers - * @param topic - * @param groupId - * @return - */ - public static KafkaCanalConnector newKafkaConnector(String servers, String topic, String groupId) { - return new KafkaCanalConnector(null, servers, topic, null, groupId); - } - - /** - * 创建kafka客户端链接 - * - * @param zkServers - * @param servers - * @param topic - * @param partition - * @param groupId - * @return - */ - public static KafkaCanalConnector newKafkaConnector(String zkServers, String servers, String topic, Integer partition, String groupId) { - return new KafkaCanalConnector(zkServers, servers, topic, partition, groupId); - } - - /** - * 创建kafka客户端链接 - * - * @param zkServers - * @param servers - * @param topic - * @param groupId - * @return - */ - public static KafkaCanalConnector newKafkaConnector(String zkServers, String servers, String topic, String groupId) { - return new KafkaCanalConnector(zkServers, servers, topic, null, groupId); - } -} diff --git a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/MessageDeserializer.java b/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/MessageDeserializer.java deleted file mode 100644 index 1cb3daba..00000000 --- a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/MessageDeserializer.java +++ /dev/null @@ -1,62 +0,0 @@ -package com.alibaba.otter.canal.kafka.client; - -import java.util.Map; - -import org.apache.kafka.common.serialization.Deserializer; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import com.alibaba.otter.canal.protocol.CanalEntry; -import com.alibaba.otter.canal.protocol.CanalPacket; -import com.alibaba.otter.canal.protocol.Message; -import com.alibaba.otter.canal.protocol.exception.CanalClientException; -import com.google.protobuf.ByteString; - -/** - * Kafka Message类的反序列化 - * - * @author machengyuan @ 2018-6-12 - * @version 1.0.0 - */ -public class MessageDeserializer implements Deserializer { - - private static Logger logger = LoggerFactory.getLogger(MessageDeserializer.class); - - @Override - public void configure(Map configs, boolean isKey) { - } - - @Override - public Message deserialize(String topic, byte[] data) { - try { - if (data == null) return null; - else { - CanalPacket.Packet p = CanalPacket.Packet.parseFrom(data); - switch (p.getType()) { - case MESSAGES: { - if (!p.getCompression().equals(CanalPacket.Compression.NONE)) { - throw new CanalClientException("compression is not supported in this connector"); - } - - CanalPacket.Messages messages = CanalPacket.Messages.parseFrom(p.getBody()); - Message result = new Message(messages.getBatchId()); - for (ByteString byteString : messages.getMessagesList()) { - result.addEntry(CanalEntry.Entry.parseFrom(byteString)); - } - return result; - } - default: - break; - } - } - } catch (Exception e) { - logger.error("Error when deserializing byte[] to message "); - } - return null; - } - - @Override - public void close() { - // nothing to do - } -} diff --git a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningData.java b/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningData.java deleted file mode 100644 index 3eab85ed..00000000 --- a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningData.java +++ /dev/null @@ -1,39 +0,0 @@ -package com.alibaba.otter.canal.kafka.client.running; - -/** - * client running状态信息 - * - * @author machengyuan 2018-06-20 下午04:10:12 - * @version 1.0.0 - */ -public class ClientRunningData { - - private String groupId; - private String address; - private boolean active = true; - - public String getGroupId() { - return groupId; - } - - public void setGroupId(String groupId) { - this.groupId = groupId; - } - - public String getAddress() { - return address; - } - - public void setAddress(String address) { - this.address = address; - } - - public boolean isActive() { - return active; - } - - public void setActive(boolean active) { - this.active = active; - } - -} diff --git a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningListener.java b/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningListener.java deleted file mode 100644 index d49cf79f..00000000 --- a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningListener.java +++ /dev/null @@ -1,21 +0,0 @@ -package com.alibaba.otter.canal.kafka.client.running; - -/** - * client running状态信息 - * - * @author machengyuan 2018-06-20 下午04:10:12 - * @version 1.0.0 - */ -public interface ClientRunningListener { - - /** - * 触发现在轮到自己做为active - */ - public void processActiveEnter(); - - /** - * 触发一下当前active模式失败 - */ - public void processActiveExit(); - -} diff --git a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningMonitor.java b/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningMonitor.java deleted file mode 100644 index 3bdbfe6e..00000000 --- a/kafka-client/src/main/java/com/alibaba/otter/canal/kafka/client/running/ClientRunningMonitor.java +++ /dev/null @@ -1,275 +0,0 @@ -package com.alibaba.otter.canal.kafka.client.running; - -import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; -import com.alibaba.otter.canal.common.utils.AddressUtils; -import com.alibaba.otter.canal.common.utils.BooleanMutex; -import com.alibaba.otter.canal.common.utils.JsonUtils; -import com.alibaba.otter.canal.common.zookeeper.ZkClientx; -import com.alibaba.otter.canal.common.zookeeper.ZookeeperPathUtils; -import com.alibaba.otter.canal.protocol.exception.CanalClientException; -import org.I0Itec.zkclient.IZkDataListener; -import org.I0Itec.zkclient.exception.ZkException; -import org.I0Itec.zkclient.exception.ZkInterruptedException; -import org.I0Itec.zkclient.exception.ZkNoNodeException; -import org.I0Itec.zkclient.exception.ZkNodeExistsException; -import org.apache.zookeeper.CreateMode; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.slf4j.MDC; - -import java.text.MessageFormat; -import java.util.Random; -import java.util.concurrent.Executors; -import java.util.concurrent.ScheduledExecutorService; -import java.util.concurrent.TimeUnit; - -/** - * kafka client running状态信息 - * - * @author machengyuan 2018-06-20 下午04:10:12 - * @version 1.0.0 - */ -public class ClientRunningMonitor extends AbstractCanalLifeCycle { - - private static final String TOPIC_ROOT_NODE = ZookeeperPathUtils.CANAL_ROOT_NODE + ZookeeperPathUtils.ZOOKEEPER_SEPARATOR + "topics"; - - private static final String TOPIC_NODE = TOPIC_ROOT_NODE + ZookeeperPathUtils.ZOOKEEPER_SEPARATOR + "{0}"; - - private static final String TOPIC_CLIENTID_NODE = TOPIC_NODE + ZookeeperPathUtils.ZOOKEEPER_SEPARATOR + "{1}"; - - private static final String TOPIC_CLIENTID_RUNNING_NODE = TOPIC_CLIENTID_NODE + ZookeeperPathUtils.ZOOKEEPER_SEPARATOR + ZookeeperPathUtils.RUNNING_NODE; - - private static String getTopicClientRunning(String topic, String groupId) { - return MessageFormat.format(TOPIC_CLIENTID_RUNNING_NODE, topic, groupId); - } - - private static String getClientIdNodePath(String topic, String groupId) { - return MessageFormat.format(TOPIC_CLIENTID_NODE, topic, groupId); - } - - private static final Logger logger = LoggerFactory.getLogger(ClientRunningMonitor.class); - private ZkClientx zkClient; - private String topic; - private ClientRunningData clientData; - private IZkDataListener dataListener; - private BooleanMutex mutex = new BooleanMutex(false); - private volatile boolean release = false; - private volatile ClientRunningData activeData; - private ScheduledExecutorService delayExector = Executors.newScheduledThreadPool(1); - private ClientRunningListener listener; - private int delayTime = 5; - - private static Integer virtualPort; - - public ClientRunningMonitor() { - if (virtualPort == null) { - Random rand = new Random(); - virtualPort = rand.nextInt(9000) + 1000; - } - - dataListener = new IZkDataListener() { - - public void handleDataChange(String dataPath, Object data) throws Exception { - MDC.put("kafkaTopic", topic); - ClientRunningData runningData = JsonUtils.unmarshalFromByte((byte[]) data, ClientRunningData.class); - if (!isMine(runningData.getAddress())) { - mutex.set(false); - } - - if (!runningData.isActive() && isMine(runningData.getAddress())) { // 说明出现了主动释放的操作,并且本机之前是active - release = true; - releaseRunning();// 彻底释放mainstem - } - - activeData = (ClientRunningData) runningData; - } - - public void handleDataDeleted(String dataPath) throws Exception { - MDC.put("kafkaTopic", topic); - - mutex.set(false); - // 触发一下退出,可能是人为干预的释放操作或者网络闪断引起的session expired timeout - processActiveExit(); - if (!release && activeData != null && isMine(activeData.getAddress())) { - // 如果上一次active的状态就是本机,则即时触发一下active抢占 - initRunning(); - } else { - // 否则就是等待delayTime,避免因网络瞬端或者zk异常,导致出现频繁的切换操作 - delayExector.schedule(new Runnable() { - - public void run() { - initRunning(); - } - }, delayTime, TimeUnit.SECONDS); - } - } - - }; - - } - - - public void start() { - super.start(); - - String path = getTopicClientRunning(this.topic, clientData.getGroupId()); - - zkClient.subscribeDataChanges(path, dataListener); - initRunning(); - } - - public void stop() { - super.stop(); - String path = getTopicClientRunning(this.topic, clientData.getGroupId()); - zkClient.unsubscribeDataChanges(path, dataListener); - releaseRunning(); // 尝试一下release - //Fix issue #697 - if (delayExector != null) { - delayExector.shutdown(); - } - } - - // 改动记录: - // 1,在方法上加synchronized关键字,保证同步顺序执行; - // 2,判断Zk上已经存在的activeData是否是本机,是的话把mutex重置为true,否则会导致死锁 - // 3,增加异常处理,保证出现异常时,running节点能被删除,否则会导致死锁 - public synchronized void initRunning() { - if (!isStart()) { - return; - } - - String path = getTopicClientRunning(this.topic, clientData.getGroupId()); - // 序列化 - byte[] bytes = JsonUtils.marshalToByte(clientData); - try { - mutex.set(false); - zkClient.create(path, bytes, CreateMode.EPHEMERAL); - processActiveEnter();// 触发一下事件 - activeData = clientData; - mutex.set(true); - } catch (ZkNodeExistsException e) { - bytes = zkClient.readData(path, true); - if (bytes == null) {// 如果不存在节点,立即尝试一次 - initRunning(); - } else { - activeData = JsonUtils.unmarshalFromByte(bytes, ClientRunningData.class); - // 如果发现已经存在,判断一下是否自己,避免活锁 - if (activeData.getAddress().contains(":") && isMine(activeData.getAddress())) { - mutex.set(true); - } - } - } catch (ZkNoNodeException e) { - zkClient.createPersistent(getClientIdNodePath(this.topic, clientData.getGroupId()), - true); // 尝试创建父节点 - initRunning(); - } catch (Throwable t) { - logger.error(MessageFormat.format("There is an error when execute initRunning method, with destination [{0}].", - topic), - t); - // 出现任何异常尝试release - releaseRunning(); - throw new CanalClientException("something goes wrong in initRunning method. ", t); - } - } - - /** - * 阻塞等待自己成为active,如果自己成为active,立马返回 - * - * @throws InterruptedException - */ - public void waitForActive() throws InterruptedException { - initRunning(); - mutex.get(); - } - - /** - * 检查当前的状态 - */ - public boolean check() { - String path = getTopicClientRunning(this.topic, clientData.getGroupId()); - //ZookeeperPathUtils.getDestinationClientRunning(this.destination, clientData.getClientId()); - try { - byte[] bytes = zkClient.readData(path); - ClientRunningData eventData = JsonUtils.unmarshalFromByte(bytes, ClientRunningData.class); - activeData = eventData;// 更新下为最新值 - // 检查下nid是否为自己 - boolean result = isMine(activeData.getAddress()); - if (!result) { - logger.warn("canal is running in [{}] , but not in [{}]", - activeData.getAddress(), - clientData.getAddress()); - } - return result; - } catch (ZkNoNodeException e) { - logger.warn("canal is not run any in node"); - return false; - } catch (ZkInterruptedException e) { - logger.warn("canal check is interrupt"); - Thread.interrupted();// 清除interrupt标记 - return check(); - } catch (ZkException e) { - logger.warn("canal check is failed"); - return false; - } - } - - public boolean releaseRunning() { - if (check()) { - String path = getTopicClientRunning(this.topic, clientData.getGroupId()); - zkClient.delete(path); - mutex.set(false); - processActiveExit(); - return true; - } - - return false; - } - - // ====================== helper method ====================== - - private boolean isMine(String address) { - return address.equals(clientData.getAddress()); - } - - private void processActiveEnter() { - if (listener != null) { - // 触发回调 - listener.processActiveEnter(); - this.clientData.setAddress(/*address*/AddressUtils.getHostIp() + ":" + virtualPort); - - String path = getTopicClientRunning(this.topic, clientData.getGroupId()); - // 序列化 - byte[] bytes = JsonUtils.marshalToByte(clientData); - zkClient.writeData(path, bytes); - } - } - - private void processActiveExit() { - if (listener != null) { - listener.processActiveExit(); - } - } - - public void setListener(ClientRunningListener listener) { - this.listener = listener; - } - - // ===================== setter / getter ======================= - - public void setTopic(String topic) { - this.topic = topic; - } - - public void setClientData(ClientRunningData clientData) { - this.clientData = clientData; - } - - public void setDelayTime(int delayTime) { - this.delayTime = delayTime; - } - - public void setZkClient(ZkClientx zkClient) { - this.zkClient = zkClient; - } - -} diff --git a/kafka/pom.xml b/kafka/pom.xml deleted file mode 100644 index 8d3b35d7..00000000 --- a/kafka/pom.xml +++ /dev/null @@ -1,140 +0,0 @@ - - - 4.0.0 - - canal - com.alibaba.otter - 1.0.26-SNAPSHOT - ../pom.xml - - com.alibaba.otter - canal.kafka - jar - canal kafka module for otter ${project.version} - - - com.alibaba.otter - canal.deployer - ${project.version} - - - - org.yaml - snakeyaml - 1.17 - - - - org.apache.kafka - kafka_2.11 - 0.9.0.1 - - - org.slf4j - slf4j-log4j12 - - - - - - - - - - maven-jar-plugin - - - true - - - **/logback.xml - **/canal.properties - **/spring/** - **/example/** - **/kafka.yml - - - - - - org.apache.maven.plugins - maven-assembly-plugin - - 2.2.1 - - - assemble - - single - - package - - - - false - false - - - - - - - - dev - - true - - env - !release - - - - - - - maven-assembly-plugin - - - - ${basedir}/src/main/assembly/dev.xml - - canal - ${project.build.directory} - - - - - - - - - release - - - env - release - - - - - - - maven-assembly-plugin - - - - ${basedir}/src/main/assembly/release.xml - - - ${project.artifactId}-${project.version} - - ${project.parent.build.directory} - - - - - - - \ No newline at end of file diff --git a/kafka/src/main/assembly/dev.xml b/kafka/src/main/assembly/dev.xml deleted file mode 100644 index 2c3e3fff..00000000 --- a/kafka/src/main/assembly/dev.xml +++ /dev/null @@ -1,64 +0,0 @@ - - dist - - dir - - false - - - . - / - - README* - - - - ./src/main/bin - bin - - **/* - - 0755 - - - ../deployer/src/main/conf - /conf - - **/* - - - - ../deployer/src/main/resources - /conf - - **/* - - - logback.xml - - - - ./src/main/resources - /conf - - **/* - - - - target - logs - - **/* - - - - - - lib - - junit:junit - - - - diff --git a/kafka/src/main/assembly/release.xml b/kafka/src/main/assembly/release.xml deleted file mode 100644 index 0b103620..00000000 --- a/kafka/src/main/assembly/release.xml +++ /dev/null @@ -1,64 +0,0 @@ - - dist - - tar.gz - - false - - - . - / - - README* - - - - ./src/main/bin - bin - - **/* - - 0755 - - - ../deployer/src/main/conf - /conf - - **/* - - - - ../deployer/src/main/resources - /conf - - **/* - - - logback.xml - - - - ./src/main/resources - /conf - - **/* - - - - target - logs - - **/* - - - - - - lib - - junit:junit - - - - diff --git a/kafka/src/main/bin/startup.bat b/kafka/src/main/bin/startup.bat deleted file mode 100755 index 429cc653..00000000 --- a/kafka/src/main/bin/startup.bat +++ /dev/null @@ -1,25 +0,0 @@ -@echo off -@if not "%ECHO%" == "" echo %ECHO% -@if "%OS%" == "Windows_NT" setlocal - -set ENV_PATH=.\ -if "%OS%" == "Windows_NT" set ENV_PATH=%~dp0% - -set conf_dir=%ENV_PATH%\..\conf -set canal_conf=%conf_dir%\canal.properties -set logback_configurationFile=%conf_dir%\logback.xml - -set CLASSPATH=%conf_dir% -set CLASSPATH=%conf_dir%\..\lib\*;%CLASSPATH% - -set JAVA_MEM_OPTS= -Xms128m -Xmx512m -XX:PermSize=128m -set JAVA_OPTS_EXT= -Djava.awt.headless=true -Djava.net.preferIPv4Stack=true -Dapplication.codeset=UTF-8 -Dfile.encoding=UTF-8 -set JAVA_DEBUG_OPT= -server -Xdebug -Xnoagent -Djava.compiler=NONE -Xrunjdwp:transport=dt_socket,address=9099,server=y,suspend=n -set CANAL_OPTS= -DappName=otter-canal -Dlogback.configurationFile="%logback_configurationFile%" -Dcanal.conf="%canal_conf%" - -set JAVA_OPTS= %JAVA_MEM_OPTS% %JAVA_OPTS_EXT% %JAVA_DEBUG_OPT% %CANAL_OPTS% - -set CMD_STR= java %JAVA_OPTS% -classpath "%CLASSPATH%" java %JAVA_OPTS% -classpath "%CLASSPATH%" com.alibaba.otter.canal.kafka.CanalLauncher -echo start cmd : %CMD_STR% - -java %JAVA_OPTS% -classpath "%CLASSPATH%" com.alibaba.otter.canal.kafka.CanalLauncher \ No newline at end of file diff --git a/kafka/src/main/bin/startup.sh b/kafka/src/main/bin/startup.sh deleted file mode 100644 index 184c4b3f..00000000 --- a/kafka/src/main/bin/startup.sh +++ /dev/null @@ -1,104 +0,0 @@ -#!/bin/bash - -current_path=`pwd` -case "`uname`" in - Linux) - bin_abs_path=$(readlink -f $(dirname $0)) - ;; - *) - bin_abs_path=`cd $(dirname $0); pwd` - ;; -esac -base=${bin_abs_path}/.. -canal_conf=$base/conf/canal.properties -logback_configurationFile=$base/conf/logback.xml -export LANG=en_US.UTF-8 -export BASE=$base - -if [ -f $base/bin/canal.pid ] ; then - echo "found canal.pid , Please run stop.sh first ,then startup.sh" 2>&2 - exit 1 -fi - -if [ ! -d $base/logs/canal ] ; then - mkdir -p $base/logs/canal -fi - -## set java path -if [ -z "$JAVA" ] ; then - JAVA=$(which java) -fi - -ALIBABA_JAVA="/usr/alibaba/java/bin/java" -TAOBAO_JAVA="/opt/taobao/java/bin/java" -if [ -z "$JAVA" ]; then - if [ -f $ALIBABA_JAVA ] ; then - JAVA=$ALIBABA_JAVA - elif [ -f $TAOBAO_JAVA ] ; then - JAVA=$TAOBAO_JAVA - else - echo "Cannot find a Java JDK. Please set either set JAVA or put java (>=1.5) in your PATH." 2>&2 - exit 1 - fi -fi - -case "$#" -in -0 ) - ;; -1 ) - var=$* - if [ -f $var ] ; then - canal_conf=$var - else - echo "THE PARAMETER IS NOT CORRECT.PLEASE CHECK AGAIN." - exit - fi;; -2 ) - var=$1 - if [ -f $var ] ; then - canal_conf=$var - else - if [ "$1" = "debug" ]; then - DEBUG_PORT=$2 - DEBUG_SUSPEND="n" - JAVA_DEBUG_OPT="-Xdebug -Xnoagent -Djava.compiler=NONE -Xrunjdwp:transport=dt_socket,address=$DEBUG_PORT,server=y,suspend=$DEBUG_SUSPEND" - fi - fi;; -* ) - echo "THE PARAMETERS MUST BE TWO OR LESS.PLEASE CHECK AGAIN." - exit;; -esac - -str=`file -L $JAVA | grep 64-bit` -if [ -n "$str" ]; then - JAVA_OPTS="-server -Xms2048m -Xmx3072m -Xmn1024m -XX:SurvivorRatio=2 -XX:PermSize=96m -XX:MaxPermSize=256m -Xss256k -XX:-UseAdaptiveSizePolicy -XX:MaxTenuringThreshold=15 -XX:+DisableExplicitGC -XX:+UseConcMarkSweepGC -XX:+CMSParallelRemarkEnabled -XX:+UseCMSCompactAtFullCollection -XX:+UseFastAccessorMethods -XX:+UseCMSInitiatingOccupancyOnly -XX:+HeapDumpOnOutOfMemoryError" -else - JAVA_OPTS="-server -Xms1024m -Xmx1024m -XX:NewSize=256m -XX:MaxNewSize=256m -XX:MaxPermSize=128m " -fi - -JAVA_OPTS=" $JAVA_OPTS -Djava.awt.headless=true -Djava.net.preferIPv4Stack=true -Dfile.encoding=UTF-8" -CANAL_OPTS="-DappName=otter-canal -Dlogback.configurationFile=$logback_configurationFile -Dcanal.conf=$canal_conf" - -if [ -e $canal_conf -a -e $logback_configurationFile ] -then - - for i in $base/lib/*; - do CLASSPATH=$i:"$CLASSPATH"; - done - CLASSPATH="$base/conf:$CLASSPATH"; - - echo "cd to $bin_abs_path for workaround relative path" - cd $bin_abs_path - - echo LOG CONFIGURATION : $logback_configurationFile - echo canal conf : $canal_conf - echo CLASSPATH :$CLASSPATH - $JAVA $JAVA_OPTS $JAVA_DEBUG_OPT $CANAL_OPTS -classpath .:$CLASSPATH com.alibaba.otter.canal.kafka.CanalLauncher 1>>$base/logs/canal/canal.log 2>&1 & - echo $! > $base/bin/canal.pid - - echo "cd to $current_path for continue" - cd $current_path -else - echo "canal conf("$canal_conf") OR log configration file($logback_configurationFile) is not exist,please create then first!" -fi diff --git a/kafka/src/main/java/com/alibaba/otter/canal/kafka/CanalLauncher.java b/kafka/src/main/java/com/alibaba/otter/canal/kafka/CanalLauncher.java deleted file mode 100644 index 3212733c..00000000 --- a/kafka/src/main/java/com/alibaba/otter/canal/kafka/CanalLauncher.java +++ /dev/null @@ -1,17 +0,0 @@ -package com.alibaba.otter.canal.kafka; - -import com.alibaba.otter.canal.kafka.producer.CanalKafkaStarter; - -/** - * canal-kafka独立版本启动的入口类 - * - * @author machengyuan 2018-6-11 下午05:30:49 - * @version 1.0.0 - */ -public class CanalLauncher { - - public static void main(String[] args) { - CanalServerStarter.init(); - CanalKafkaStarter.init(); - } -} diff --git a/kafka/src/main/java/com/alibaba/otter/canal/kafka/CanalServerStarter.java b/kafka/src/main/java/com/alibaba/otter/canal/kafka/CanalServerStarter.java deleted file mode 100644 index e0b2d1d8..00000000 --- a/kafka/src/main/java/com/alibaba/otter/canal/kafka/CanalServerStarter.java +++ /dev/null @@ -1,78 +0,0 @@ -package com.alibaba.otter.canal.kafka; - -import java.io.FileInputStream; -import java.util.Properties; - -import org.apache.commons.lang.StringUtils; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import com.alibaba.otter.canal.deployer.CanalController; - -/** - * canal server 启动类 - * - * @author machengyuan 2018-6-11 下午05:30:49 - * @version 1.0.0 - */ -public class CanalServerStarter { - - private static final String CLASSPATH_URL_PREFIX = "classpath:"; - private static final Logger logger = LoggerFactory.getLogger(CanalServerStarter.class); - private volatile static boolean running = false; - - public static void init() { - try { - logger.info("## set default uncaught exception handler"); - setGlobalUncaughtExceptionHandler(); - - logger.info("## load canal configurations"); - String conf = System.getProperty("canal.conf", "classpath:canal.properties"); - Properties properties = new Properties(); - if (conf.startsWith(CLASSPATH_URL_PREFIX)) { - conf = StringUtils.substringAfter(conf, CLASSPATH_URL_PREFIX); - properties.load(CanalLauncher.class.getClassLoader().getResourceAsStream(conf)); - } else { - properties.load(new FileInputStream(conf)); - } - - logger.info("## start the canal server."); - final CanalController controller = new CanalController(properties); - controller.start(); - running = true; - logger.info("## the canal server is running now ......"); - Runtime.getRuntime().addShutdownHook(new Thread() { - - public void run() { - try { - logger.info("## stop the canal server"); - running = false; - controller.stop(); - } catch (Throwable e) { - logger.warn("##something goes wrong when stopping canal Server:", e); - } finally { - logger.info("## canal server is down."); - } - } - - }); - } catch (Throwable e) { - logger.error("## Something goes wrong when starting up the canal Server:", e); - System.exit(0); - } - } - - public static boolean isRunning() { - return running; - } - - private static void setGlobalUncaughtExceptionHandler() { - Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() { - - @Override - public void uncaughtException(Thread t, Throwable e) { - logger.error("UnCaughtException", e); - } - }); - } -} diff --git a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/CanalKafkaProducer.java b/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/CanalKafkaProducer.java deleted file mode 100644 index 1543abf9..00000000 --- a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/CanalKafkaProducer.java +++ /dev/null @@ -1,76 +0,0 @@ -package com.alibaba.otter.canal.kafka.producer; - -import java.util.Properties; - -import org.apache.kafka.clients.producer.KafkaProducer; -import org.apache.kafka.clients.producer.Producer; -import org.apache.kafka.clients.producer.ProducerRecord; -import org.apache.kafka.common.serialization.StringSerializer; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import com.alibaba.otter.canal.kafka.producer.KafkaProperties.Topic; -import com.alibaba.otter.canal.protocol.CanalEntry; -import com.alibaba.otter.canal.protocol.Message; - -/** - * kafka producer 主操作类 - * - * @author machengyuan 2018-6-11 下午05:30:49 - * @version 1.0.0 - */ -public class CanalKafkaProducer { - - private static final Logger logger = LoggerFactory.getLogger(CanalKafkaProducer.class); - - private Producer producer; - - public void init(KafkaProperties kafkaProperties) { - Properties properties = new Properties(); - properties.put("bootstrap.servers", kafkaProperties.getServers()); - properties.put("acks", "all"); - properties.put("retries", kafkaProperties.getRetries()); - properties.put("batch.size", kafkaProperties.getBatchSize()); - properties.put("linger.ms", kafkaProperties.getLingerMs()); - properties.put("buffer.memory", kafkaProperties.getBufferMemory()); - properties.put("key.serializer", StringSerializer.class.getName()); - properties.put("value.serializer", MessageSerializer.class.getName()); - producer = new KafkaProducer(properties); - } - - public void stop() { - try { - logger.info("## stop the kafka producer"); - producer.close(); - } catch (Throwable e) { - logger.warn("##something goes wrong when stopping kafka producer:", e); - } finally { - logger.info("## kafka producer is down."); - } - } - - public void send(Topic topic, Message message) { - boolean valid = false; - if (message != null && !message.getEntries().isEmpty()) { - for (CanalEntry.Entry entry : message.getEntries()) { - if (entry.getEntryType() != CanalEntry.EntryType.TRANSACTIONBEGIN - && entry.getEntryType() != CanalEntry.EntryType.TRANSACTIONEND) { - valid = true; - break; - } - } - } - if (!valid) { - return; - } - - ProducerRecord record; - if (topic.getPartition() != null) { - record = new ProducerRecord(topic.getTopic(), topic.getPartition(), null, message); - } else { - record = new ProducerRecord(topic.getTopic(), message); - } - producer.send(record); - logger.debug("send message to kafka topic: {} \n {}", topic.getTopic(), message.toString()); - } -} diff --git a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/CanalKafkaStarter.java b/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/CanalKafkaStarter.java deleted file mode 100644 index 0ff018c2..00000000 --- a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/CanalKafkaStarter.java +++ /dev/null @@ -1,147 +0,0 @@ -package com.alibaba.otter.canal.kafka.producer; - -import java.io.FileInputStream; -import java.util.List; -import java.util.concurrent.ExecutorService; -import java.util.concurrent.Executors; - -import org.apache.commons.lang.StringUtils; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.yaml.snakeyaml.Yaml; - -import com.alibaba.otter.canal.kafka.CanalServerStarter; -import com.alibaba.otter.canal.kafka.producer.KafkaProperties.CanalDestination; -import com.alibaba.otter.canal.kafka.producer.KafkaProperties.Topic; -import com.alibaba.otter.canal.protocol.ClientIdentity; -import com.alibaba.otter.canal.protocol.Message; -import com.alibaba.otter.canal.server.embedded.CanalServerWithEmbedded; - -/** - * kafka 启动类 - * - * @author machengyuan 2018-6-11 下午05:30:49 - * @version 1.0.0 - */ -public class CanalKafkaStarter { - - private static final String CLASSPATH_URL_PREFIX = "classpath:"; - private static final Logger logger = LoggerFactory.getLogger(CanalKafkaStarter.class); - - private volatile static boolean running = false; - - private static ExecutorService executorService; - - private static CanalKafkaProducer canalKafkaProducer; - - private static KafkaProperties kafkaProperties; - - public static void init() { - try { - logger.info("## load kafka configurations"); - String conf = System.getProperty("kafka.conf", "classpath:kafka.yml"); - - if (conf.startsWith(CLASSPATH_URL_PREFIX)) { - conf = StringUtils.substringAfter(conf, CLASSPATH_URL_PREFIX); - kafkaProperties = new Yaml().loadAs(CanalKafkaStarter.class.getClassLoader().getResourceAsStream(conf), - KafkaProperties.class); - } else { - kafkaProperties = new Yaml().loadAs(new FileInputStream(conf), KafkaProperties.class); - } - - // 初始化 kafka producer - canalKafkaProducer = new CanalKafkaProducer(); - canalKafkaProducer.init(kafkaProperties); - - // 对应每个instance启动一个worker线程 - List destinations = kafkaProperties.getCanalDestinations(); - - executorService = Executors.newFixedThreadPool(destinations.size()); - - logger.info("## start the kafka workers."); - for (final CanalDestination destination : destinations) { - executorService.execute(new Runnable() { - - @Override - public void run() { - worker(destination); - } - }); - } - running = true; - logger.info("## the kafka workers is running now ......"); - Runtime.getRuntime().addShutdownHook(new Thread() { - - public void run() { - try { - logger.info("## stop the kafka workers"); - running = false; - executorService.shutdown(); - canalKafkaProducer.stop(); - } catch (Throwable e) { - logger.warn("##something goes wrong when stopping kafka workers:", e); - } finally { - logger.info("## canal kafka is down."); - } - } - - }); - - } catch (Throwable e) { - logger.error("## Something goes wrong when starting up the canal kafka workers:", e); - System.exit(0); - } - } - - private static void worker(CanalDestination destination) { - while (!running) - ; - while (!CanalServerStarter.isRunning()) - ; // 等待server启动完成 - logger.info("## start the canal consumer: {}.", destination.getCanalDestination()); - CanalServerWithEmbedded server = CanalServerWithEmbedded.instance(); - ClientIdentity clientIdentity = new ClientIdentity(destination.getCanalDestination(), (short) 1001, ""); - while (running) { - try { - if (!server.getCanalInstances().containsKey(clientIdentity.getDestination())) { - try { - Thread.sleep(3000); - } catch (InterruptedException e) { - // ignore - } - continue; - } - server.subscribe(clientIdentity); - logger.info("## the canal consumer {} is running now ......", destination.getCanalDestination()); - - while (running) { - Message message = server.getWithoutAck(clientIdentity, kafkaProperties.getCanalBatchSize()); // 获取指定数量的数据 - long batchId = message.getId(); - try { - int size = message.getEntries().size(); - if (batchId != -1 && size != 0) { - if (!StringUtils.isEmpty(destination.getTopic())) { - Topic topic = new Topic(); - topic.setTopic(destination.getTopic()); - topic.setPartition(destination.getPartition()); - destination.getTopics().add(topic); - } - for (Topic topic : destination.getTopics()) { - canalKafkaProducer.send(topic, message); // 发送message到所有topic - } - } - - if (batchId != -1) { - server.ack(clientIdentity, batchId); // 提交确认 - } - } catch (Exception e) { - server.rollback(clientIdentity); - logger.error(e.getMessage(), e); - } - } - } catch (Exception e) { - logger.error("process error!", e); - } - } - } -} diff --git a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/KafkaProperties.java b/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/KafkaProperties.java deleted file mode 100644 index 0b346137..00000000 --- a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/KafkaProperties.java +++ /dev/null @@ -1,161 +0,0 @@ -package com.alibaba.otter.canal.kafka.producer; - -import java.util.ArrayList; -import java.util.HashSet; -import java.util.List; -import java.util.Set; - -/** - * kafka 配置项 - * - * @author machengyuan 2018-6-11 下午05:30:49 - * @version 1.0.0 - */ -public class KafkaProperties { - - private String servers = "localhost:6667"; - private int retries = 0; - private int batchSize = 16384; - private int lingerMs = 1; - private long bufferMemory = 33554432L; - - private int canalBatchSize = 5; - - private List canalDestinations = new ArrayList(); - - public static class CanalDestination { - - private String canalDestination; - private String topic; - private Integer partition; - private Set topics = new HashSet(); - - public String getCanalDestination() { - return canalDestination; - } - - public void setCanalDestination(String canalDestination) { - this.canalDestination = canalDestination; - } - - public String getTopic() { - return topic; - } - - public void setTopic(String topic) { - this.topic = topic; - } - - public Integer getPartition() { - return partition; - } - - public void setPartition(Integer partition) { - this.partition = partition; - } - - public Set getTopics() { - return topics; - } - - public void setTopics(Set topics) { - this.topics = topics; - } - } - - public static class Topic { - - private String topic; - private Integer partition; - - public String getTopic() { - return topic; - } - - public void setTopic(String topic) { - this.topic = topic; - } - - public Integer getPartition() { - return partition; - } - - public void setPartition(Integer partition) { - this.partition = partition; - } - - @Override - public boolean equals(Object o) { - if (this == o) return true; - if (o == null || getClass() != o.getClass()) return false; - - Topic topic1 = (Topic) o; - - if (topic != null ? !topic.equals(topic1.topic) : topic1.topic != null) return false; - return partition != null ? partition.equals(topic1.partition) : topic1.partition == null; - } - - @Override - public int hashCode() { - int result = topic != null ? topic.hashCode() : 0; - result = 31 * result + (partition != null ? partition.hashCode() : 0); - return result; - } - } - - public String getServers() { - return servers; - } - - public void setServers(String servers) { - this.servers = servers; - } - - public int getRetries() { - return retries; - } - - public void setRetries(int retries) { - this.retries = retries; - } - - public int getBatchSize() { - return batchSize; - } - - public void setBatchSize(int batchSize) { - this.batchSize = batchSize; - } - - public int getLingerMs() { - return lingerMs; - } - - public void setLingerMs(int lingerMs) { - this.lingerMs = lingerMs; - } - - public long getBufferMemory() { - return bufferMemory; - } - - public void setBufferMemory(long bufferMemory) { - this.bufferMemory = bufferMemory; - } - - public int getCanalBatchSize() { - return canalBatchSize; - } - - public void setCanalBatchSize(int canalBatchSize) { - this.canalBatchSize = canalBatchSize; - } - - public List getCanalDestinations() { - return canalDestinations; - } - - public void setCanalDestinations(List canalDestinations) { - this.canalDestinations = canalDestinations; - } -} diff --git a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/MessageSerializer.java b/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/MessageSerializer.java deleted file mode 100644 index 339e4f8c..00000000 --- a/kafka/src/main/java/com/alibaba/otter/canal/kafka/producer/MessageSerializer.java +++ /dev/null @@ -1,50 +0,0 @@ -package com.alibaba.otter.canal.kafka.producer; - -import java.util.Map; - -import org.apache.kafka.common.errors.SerializationException; -import org.apache.kafka.common.serialization.Serializer; -import org.springframework.util.CollectionUtils; - -import com.alibaba.otter.canal.protocol.CanalEntry; -import com.alibaba.otter.canal.protocol.CanalPacket; -import com.alibaba.otter.canal.protocol.Message; - -/** - * Kafka Message类的序列化 - * - * @author machengyuan 2018-6-11 下午05:30:49 - * @version 1.0.0 - */ -public class MessageSerializer implements Serializer { - - @Override - public void configure(Map configs, boolean isKey) { - } - - @Override - public byte[] serialize(String topic, Message data) { - try { - if (data == null) return null; - else { - CanalPacket.Messages.Builder messageBuilder = CanalPacket.Messages.newBuilder(); - if (data.getId() != -1 && !CollectionUtils.isEmpty(data.getEntries())) { - for (CanalEntry.Entry entry : data.getEntries()) { - messageBuilder.addMessages(entry.toByteString()); - } - } - CanalPacket.Packet.Builder packetBuilder = CanalPacket.Packet.newBuilder(); - packetBuilder.setType(CanalPacket.PacketType.MESSAGES); - packetBuilder.setBody(messageBuilder.build().toByteString()); - return packetBuilder.build().toByteArray(); - } - } catch (Exception e) { - throw new SerializationException("Error when serializing message to byte[] "); - } - } - - @Override - public void close() { - // nothing to do - } -} diff --git a/kafka/src/main/resources/kafka.yml b/kafka/src/main/resources/kafka.yml deleted file mode 100644 index ab214319..00000000 --- a/kafka/src/main/resources/kafka.yml +++ /dev/null @@ -1,18 +0,0 @@ -servers: slave1:6667,slave2:6667,slave3:6667 -retries: 0 -batchSize: 16384 -lingerMs: 1 -bufferMemory: 33554432 -# canal的批次大小,单位 k -canalBatchSize: 50 - -canalDestinations: - - canalDestination: example - topic: example - partition: - # 一个destination可以对应多个topic -# topics: -# - topics: example -# partition: - - diff --git a/kafka/src/main/resources/logback.xml b/kafka/src/main/resources/logback.xml deleted file mode 100644 index 34e7b1e5..00000000 --- a/kafka/src/main/resources/logback.xml +++ /dev/null @@ -1,85 +0,0 @@ - - - - - %d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{56} - %msg%n - - - - - - - destination - canal - - - - ../logs/${destination}/${destination}.log - - - ../logs/${destination}/%d{yyyy-MM-dd}/${destination}-%d{yyyy-MM-dd}-%i.log.gz - - - 512MB - - 60 - - - - %d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{56} - %msg%n - - - - - - - - - destination - canal - - - - ../logs/${destination}/meta.log - - - ../logs/${destination}/%d{yyyy-MM-dd}/meta-%d{yyyy-MM-dd}-%i.log.gz - - - 32MB - - 60 - - - - %d{yyyy-MM-dd HH:mm:ss.SSS} - %msg%n - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/meta/pom.xml b/meta/pom.xml index 6192d92d..002f6231 100644 --- a/meta/pom.xml +++ b/meta/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter diff --git a/parse/pom.xml b/parse/pom.xml index 994d06f0..985d5de9 100644 --- a/parse/pom.xml +++ b/parse/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml canal.parse diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/exception/PositionNotFoundException.java b/parse/src/main/java/com/alibaba/otter/canal/parse/exception/PositionNotFoundException.java new file mode 100644 index 00000000..67a1d72d --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/exception/PositionNotFoundException.java @@ -0,0 +1,30 @@ +package com.alibaba.otter.canal.parse.exception; + +/** + * @author chengjin.lyf on 2018/7/20 下午2:54 + * @since 1.0.25 + */ +public class PositionNotFoundException extends CanalParseException { + + private static final long serialVersionUID = -7382448928116244017L; + + public PositionNotFoundException(String errorCode){ + super(errorCode); + } + + public PositionNotFoundException(String errorCode, Throwable cause){ + super(errorCode, cause); + } + + public PositionNotFoundException(String errorCode, String errorDesc){ + super(errorCode, errorDesc); + } + + public PositionNotFoundException(String errorCode, String errorDesc, Throwable cause){ + super(errorCode, errorDesc, cause); + } + + public PositionNotFoundException(Throwable cause){ + super(cause); + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/exception/ServerIdNotMatchException.java b/parse/src/main/java/com/alibaba/otter/canal/parse/exception/ServerIdNotMatchException.java new file mode 100644 index 00000000..4186c6ec --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/exception/ServerIdNotMatchException.java @@ -0,0 +1,32 @@ +package com.alibaba.otter.canal.parse.exception; + +import com.alibaba.otter.canal.common.CanalException; + +/** + * @author chengjin.lyf on 2018/8/8 下午1:07 + * @since 1.0.25 + */ +public class ServerIdNotMatchException extends CanalException { + + private static final long serialVersionUID = -6124989280379293953L; + + public ServerIdNotMatchException(String errorCode){ + super(errorCode); + } + + public ServerIdNotMatchException(String errorCode, Throwable cause){ + super(errorCode, cause); + } + + public ServerIdNotMatchException(String errorCode, String errorDesc){ + super(errorCode, errorDesc); + } + + public ServerIdNotMatchException(String errorCode, String errorDesc, Throwable cause){ + super(errorCode, errorDesc, cause); + } + + public ServerIdNotMatchException(Throwable cause){ + super(cause); + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/AbstractEventParser.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/AbstractEventParser.java index 54bb14e7..cd6e25be 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/AbstractEventParser.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/AbstractEventParser.java @@ -19,10 +19,13 @@ import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; import com.alibaba.otter.canal.common.alarm.CanalAlarmHandler; import com.alibaba.otter.canal.filter.CanalEventFilter; import com.alibaba.otter.canal.parse.CanalEventParser; +import com.alibaba.otter.canal.parse.driver.mysql.packets.GTIDSet; import com.alibaba.otter.canal.parse.driver.mysql.packets.MysqlGTIDSet; import com.alibaba.otter.canal.parse.exception.CanalParseException; +import com.alibaba.otter.canal.parse.exception.PositionNotFoundException; import com.alibaba.otter.canal.parse.exception.TableIdNotFoundException; import com.alibaba.otter.canal.parse.inbound.EventTransactionBuffer.TransactionFlushCallback; +import com.alibaba.otter.canal.parse.inbound.mysql.MysqlMultiStageCoprocessor; import com.alibaba.otter.canal.parse.index.CanalLogPositionManager; import com.alibaba.otter.canal.parse.support.AuthenticationInfo; import com.alibaba.otter.canal.protocol.CanalEntry; @@ -94,6 +97,8 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle .availableProcessors() * 60 / 100; // 60%的能力跑解析,剩余部分处理网络 protected int parallelBufferSize = 256; // 必须为2的幂 protected MultiStageCoprocessor multiStageCoprocessor; + protected ParserExceptionHandler parserExceptionHandler; + protected long serverId; protected abstract BinlogParser buildParser(); @@ -170,18 +175,28 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle preDump(erosaConnection); erosaConnection.connect();// 链接 + + long queryServerId = erosaConnection.queryServerId(); + if (queryServerId != 0) { + serverId = queryServerId; + } // 4. 获取最后的位置信息 + long start = System.currentTimeMillis(); + logger.warn("---> begin to find start position, it will be long time for reset or first position"); EntryPosition position = findStartPosition(erosaConnection); final EntryPosition startPosition = position; if (startPosition == null) { - throw new CanalParseException("can't find start position for " + destination); + throw new PositionNotFoundException("can't find start position for " + destination); } if (!processTableMeta(startPosition)) { throw new CanalParseException("can't find init table meta for " + destination + " with position : " + startPosition); } - logger.warn("find start position : {}", startPosition.toString()); + long end = System.currentTimeMillis(); + logger.warn("---> find start position successfully, {}", startPosition.toString() + " cost : " + + (end - start) + + "ms , the next step is binlog dump"); // 重新链接,因为在找position过程中可能有状态,需要断开后重建 erosaConnection.reconnect(); @@ -227,12 +242,14 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle if (parallel) { // build stage processor multiStageCoprocessor = buildMultiStageCoprocessor(); - multiStageCoprocessor.start(); - if (isGTIDMode()) { // 判断所属instance是否启用GTID模式,是的话调用ErosaConnection中GTID对应方法dump数据 - erosaConnection.dump(MysqlGTIDSet.parse(startPosition.getGtid()), multiStageCoprocessor); + GTIDSet gtidSet = MysqlGTIDSet.parse(startPosition.getGtid()); + ((MysqlMultiStageCoprocessor) multiStageCoprocessor).setGtidSet(gtidSet); + multiStageCoprocessor.start(); + erosaConnection.dump(gtidSet, multiStageCoprocessor); } else { + multiStageCoprocessor.start(); if (StringUtils.isEmpty(startPosition.getJournalName()) && startPosition.getTimestamp() != null) { erosaConnection.dump(startPosition.getTimestamp(), multiStageCoprocessor); @@ -277,6 +294,9 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle runningInfo.getAddress().toString()), e); sendAlarm(destination, ExceptionUtils.getFullStackTrace(e)); } + if (parserExceptionHandler != null) { + parserExceptionHandler.handle(e); + } } finally { // 重新置为中断状态 Thread.interrupted(); @@ -302,8 +322,13 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle eventSink.interrupt(); transactionBuffer.reset();// 重置一下缓冲队列,重新记录数据 binlogParser.reset();// 重新置位 - if (multiStageCoprocessor != null) { - multiStageCoprocessor.reset(); + if (multiStageCoprocessor != null && multiStageCoprocessor.isStart()) { + // 处理 RejectedExecutionException + try { + multiStageCoprocessor.stop(); + } catch (Throwable t) { + logger.debug("multi processor rejected:", t); + } } if (running) { @@ -331,6 +356,15 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle stopHeartBeat(); // 先停止心跳 parseThread.interrupt(); // 尝试中断 eventSink.interrupt(); + + if (multiStageCoprocessor != null && multiStageCoprocessor.isStart()) { + try { + multiStageCoprocessor.stop(); + } catch (Throwable t) { + logger.debug("multi processor rejected:", t); + } + } + try { parseThread.join();// 等待其结束 } catch (InterruptedException e) { @@ -343,10 +377,6 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle if (transactionBuffer.isStart()) { transactionBuffer.stop(); } - - if (multiStageCoprocessor != null && multiStageCoprocessor.isStart()) { - multiStageCoprocessor.stop(); - } } protected boolean consumeTheEventAndProfilingIfNecessary(List entrys) throws CanalSinkException, @@ -420,7 +450,7 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle return logPosition; } - protected void processSinkError(Throwable e, LogPosition lastPosition, String startBinlogFile, long startPosition) { + protected void processSinkError(Throwable e, LogPosition lastPosition, String startBinlogFile, Long startPosition) { if (lastPosition != null) { logger.warn(String.format("ERROR ## parse this event has an error , last position : [%s]", lastPosition.getPostion()), @@ -609,4 +639,20 @@ public abstract class AbstractEventParser extends AbstractCanalLifeCycle this.parallelBufferSize = parallelBufferSize; } + public ParserExceptionHandler getParserExceptionHandler() { + return parserExceptionHandler; + } + + public void setParserExceptionHandler(ParserExceptionHandler parserExceptionHandler) { + this.parserExceptionHandler = parserExceptionHandler; + } + + public long getServerId() { + return serverId; + } + + public void setServerId(long serverId) { + this.serverId = serverId; + } + } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/ErosaConnection.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/ErosaConnection.java index 6beb4a9e..5355e2e1 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/ErosaConnection.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/ErosaConnection.java @@ -40,4 +40,6 @@ public interface ErosaConnection { public void dump(GTIDSet gtidSet, MultiStageCoprocessor coprocessor) throws IOException; ErosaConnection fork(); + + public long queryServerId() throws IOException; } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/EventTransactionBuffer.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/EventTransactionBuffer.java index c3c7150f..8034d078 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/EventTransactionBuffer.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/EventTransactionBuffer.java @@ -80,6 +80,11 @@ public class EventTransactionBuffer extends AbstractCanalLifeCycle { flush(); } break; + case HEARTBEAT: + // master过来的heartbeat,说明binlog已经读完了,是idle状态 + put(entry); + flush(); + break; default: break; } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/MultiStageCoprocessor.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/MultiStageCoprocessor.java index 1c5c495d..364230d5 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/MultiStageCoprocessor.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/MultiStageCoprocessor.java @@ -2,6 +2,7 @@ package com.alibaba.otter.canal.parse.inbound; import com.alibaba.otter.canal.common.CanalLifeCycle; import com.taobao.tddl.dbsync.binlog.LogBuffer; +import com.taobao.tddl.dbsync.binlog.LogEvent; /** * 针对解析器提供一个多阶段协同的处理 @@ -21,9 +22,7 @@ public interface MultiStageCoprocessor extends CanalLifeCycle { /** * 网络数据投递 */ - public void publish(LogBuffer buffer); + public boolean publish(LogBuffer buffer); - public void publish(LogBuffer buffer, String binlogFileName); - - public void reset(); + public boolean publish(LogEvent event); } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/ParserExceptionHandler.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/ParserExceptionHandler.java new file mode 100644 index 00000000..3a77291d --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/ParserExceptionHandler.java @@ -0,0 +1,10 @@ +package com.alibaba.otter.canal.parse.inbound; + +/** + * @author chengjin.lyf on 2018/7/20 下午3:55 + * @since 1.0.25 + */ +public interface ParserExceptionHandler { + + void handle(Throwable e); +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/AbstractMysqlEventParser.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/AbstractMysqlEventParser.java index 8188cf83..af792ec8 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/AbstractMysqlEventParser.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/AbstractMysqlEventParser.java @@ -1,39 +1,44 @@ package com.alibaba.otter.canal.parse.inbound.mysql; import java.nio.charset.Charset; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; +import java.util.concurrent.atomic.AtomicLong; import com.alibaba.otter.canal.filter.CanalEventFilter; import com.alibaba.otter.canal.filter.aviater.AviaterRegexFilter; -import com.alibaba.otter.canal.parse.driver.mysql.packets.MysqlGTIDSet; +import com.alibaba.otter.canal.parse.CanalEventParser; import com.alibaba.otter.canal.parse.exception.CanalParseException; import com.alibaba.otter.canal.parse.inbound.AbstractEventParser; import com.alibaba.otter.canal.parse.inbound.BinlogParser; import com.alibaba.otter.canal.parse.inbound.MultiStageCoprocessor; import com.alibaba.otter.canal.parse.inbound.mysql.dbsync.LogEventConvert; +import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.DefaultTableMetaTSDBFactory; import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.TableMetaTSDB; -import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.TableMetaTSDBBuilder; +import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.TableMetaTSDBFactory; import com.alibaba.otter.canal.protocol.position.EntryPosition; public abstract class AbstractMysqlEventParser extends AbstractEventParser { - protected final Logger logger = LoggerFactory.getLogger(this.getClass()); - protected static final long BINLOG_START_OFFEST = 4L; + protected static final long BINLOG_START_OFFEST = 4L; + + protected TableMetaTSDBFactory tableMetaTSDBFactory = new DefaultTableMetaTSDBFactory(); + protected boolean enableTsdb = false; + protected int tsdbSnapshotInterval = 24; + protected int tsdbSnapshotExpire = 360; + protected String tsdbSpringXml; + protected TableMetaTSDB tableMetaTSDB; - protected boolean enableTsdb = false; - protected String tsdbSpringXml; - protected TableMetaTSDB tableMetaTSDB; // 编码信息 - protected byte connectionCharsetNumber = (byte) 33; - protected Charset connectionCharset = Charset.forName("UTF-8"); - protected boolean filterQueryDcl = false; - protected boolean filterQueryDml = false; - protected boolean filterQueryDdl = false; - protected boolean filterRows = false; - protected boolean filterTableError = false; - protected boolean useDruidDdlFilter = true; + protected byte connectionCharsetNumber = (byte) 33; + protected Charset connectionCharset = Charset.forName("UTF-8"); + protected boolean filterQueryDcl = false; + protected boolean filterQueryDml = false; + protected boolean filterQueryDdl = false; + protected boolean filterRows = false; + protected boolean filterTableError = false; + protected boolean useDruidDdlFilter = true; + // instance received binlog bytes + protected final AtomicLong receivedBinlogBytes = new AtomicLong(0L); + private final AtomicLong eventsPublishBlockingTime = new AtomicLong(0L); protected BinlogParser buildParser() { LogEventConvert convert = new LogEventConvert(); @@ -51,6 +56,7 @@ public abstract class AbstractMysqlEventParser extends AbstractEventParser { convert.setFilterQueryDdl(filterQueryDdl); convert.setFilterRows(filterRows); convert.setFilterTableError(filterTableError); + convert.setUseDruidDdlFilter(useDruidDdlFilter); return convert; } @@ -70,13 +76,6 @@ public abstract class AbstractMysqlEventParser extends AbstractEventParser { * @return */ protected boolean processTableMeta(EntryPosition position) { - if (isGTIDMode()) { - if (binlogParser instanceof LogEventConvert) { - // 记录gtid - ((LogEventConvert) binlogParser).setGtidSet(MysqlGTIDSet.parse(position.getGtid())); - } - } - if (tableMetaTSDB != null) { if (position.getTimestamp() == null || position.getTimestamp() <= 0) { throw new CanalParseException("use gtid and TableMeta TSDB should be config timestamp > 0"); @@ -91,8 +90,16 @@ public abstract class AbstractMysqlEventParser extends AbstractEventParser { public void start() throws CanalParseException { if (enableTsdb) { if (tableMetaTSDB == null) { - // 初始化 - tableMetaTSDB = TableMetaTSDBBuilder.build(destination, tsdbSpringXml); + synchronized (CanalEventParser.class) { + try { + // 设置当前正在加载的通道,加载spring查找文件时会用到该变量 + System.setProperty("canal.instance.destination", destination); + // 初始化 + tableMetaTSDB = tableMetaTSDBFactory.build(destination, tsdbSpringXml); + } finally { + System.setProperty("canal.instance.destination", ""); + } + } } } @@ -101,7 +108,7 @@ public abstract class AbstractMysqlEventParser extends AbstractEventParser { public void stop() throws CanalParseException { if (enableTsdb) { - TableMetaTSDBBuilder.destory(destination); + tableMetaTSDBFactory.destory(destination); tableMetaTSDB = null; } @@ -119,11 +126,13 @@ public abstract class AbstractMysqlEventParser extends AbstractEventParser { } protected MultiStageCoprocessor buildMultiStageCoprocessor() { - return new MysqlMultiStageCoprocessor(parallelBufferSize, + MysqlMultiStageCoprocessor mysqlMultiStageCoprocessor = new MysqlMultiStageCoprocessor(parallelBufferSize, parallelThreadSize, (LogEventConvert) binlogParser, transactionBuffer, destination); + mysqlMultiStageCoprocessor.setEventsPublishBlockingTime(eventsPublishBlockingTime); + return mysqlMultiStageCoprocessor; } // ============================ setter / getter ========================= @@ -173,7 +182,7 @@ public abstract class AbstractMysqlEventParser extends AbstractEventParser { if (this.enableTsdb) { if (tableMetaTSDB == null) { // 初始化 - tableMetaTSDB = TableMetaTSDBBuilder.build(destination, tsdbSpringXml); + tableMetaTSDB = tableMetaTSDBFactory.build(destination, tsdbSpringXml); } } } @@ -183,9 +192,37 @@ public abstract class AbstractMysqlEventParser extends AbstractEventParser { if (this.enableTsdb) { if (tableMetaTSDB == null) { // 初始化 - tableMetaTSDB = TableMetaTSDBBuilder.build(destination, tsdbSpringXml); + tableMetaTSDB = tableMetaTSDBFactory.build(destination, tsdbSpringXml); } } } + public void setTableMetaTSDBFactory(TableMetaTSDBFactory tableMetaTSDBFactory) { + this.tableMetaTSDBFactory = tableMetaTSDBFactory; + } + + public AtomicLong getEventsPublishBlockingTime() { + return this.eventsPublishBlockingTime; + } + + public AtomicLong getReceivedBinlogBytes() { + return this.receivedBinlogBytes; + } + + public int getTsdbSnapshotInterval() { + return tsdbSnapshotInterval; + } + + public void setTsdbSnapshotInterval(int tsdbSnapshotInterval) { + this.tsdbSnapshotInterval = tsdbSnapshotInterval; + } + + public int getTsdbSnapshotExpire() { + return tsdbSnapshotExpire; + } + + public void setTsdbSnapshotExpire(int tsdbSnapshotExpire) { + this.tsdbSnapshotExpire = tsdbSnapshotExpire; + } + } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinLogConnection.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinLogConnection.java index f97c4ccd..5cf5bb9d 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinLogConnection.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinLogConnection.java @@ -10,18 +10,18 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.alibaba.otter.canal.parse.driver.mysql.packets.GTIDSet; +import com.alibaba.otter.canal.parse.exception.CanalParseException; +import com.alibaba.otter.canal.parse.exception.ServerIdNotMatchException; import com.alibaba.otter.canal.parse.inbound.ErosaConnection; import com.alibaba.otter.canal.parse.inbound.MultiStageCoprocessor; import com.alibaba.otter.canal.parse.inbound.SinkFunction; import com.alibaba.otter.canal.parse.inbound.mysql.local.BinLogFileQueue; import com.taobao.tddl.dbsync.binlog.FileLogFetcher; -import com.taobao.tddl.dbsync.binlog.LogBuffer; import com.taobao.tddl.dbsync.binlog.LogContext; import com.taobao.tddl.dbsync.binlog.LogDecoder; import com.taobao.tddl.dbsync.binlog.LogEvent; import com.taobao.tddl.dbsync.binlog.LogPosition; import com.taobao.tddl.dbsync.binlog.event.QueryLogEvent; -import com.taobao.tddl.dbsync.binlog.event.RotateLogEvent; /** * local bin log connection (not real connection) @@ -36,6 +36,8 @@ public class LocalBinLogConnection implements ErosaConnection { private String directory; private int bufferSize = 16 * 1024; private boolean running = false; + private long serverId; + private FileParserListener parserListener; public LocalBinLogConnection(){ } @@ -88,14 +90,14 @@ public class LocalBinLogConnection implements ErosaConnection { while (running) { boolean needContinue = true; LogEvent event = null; - // 处理一下binlog文件名 - event = new RotateLogEvent(context.getLogPosition().getFileName(), 4); - func.sink(event); while (fetcher.fetch()) { event = decoder.decode(fetcher, context); if (event == null) { continue; } + if (serverId != 0 && event.getServerId() != serverId) { + throw new ServerIdNotMatchException("unexpected serverId " + serverId + " in binlog file !"); + } if (!func.sink(event)) { needContinue = false; @@ -103,8 +105,9 @@ public class LocalBinLogConnection implements ErosaConnection { } } + fetcher.close(); // 关闭上一个文件 + parserFinish(current.getName()); if (needContinue) {// 读取下一个 - fetcher.close(); // 关闭上一个文件 File nextFile; if (needWait) { @@ -160,6 +163,10 @@ public class LocalBinLogConnection implements ErosaConnection { while (fetcher.fetch()) { LogEvent event = decoder.decode(fetcher, context); if (event != null) { + if (serverId != 0 && event.getServerId() != serverId) { + throw new ServerIdNotMatchException("unexpected serverId " + serverId + " in binlog file !"); + } + if (event.getWhen() > timestampSeconds) { break; } @@ -176,6 +183,9 @@ public class LocalBinLogConnection implements ErosaConnection { } else if (LogEvent.XID_EVENT == event.getHeader().getType()) { lastXidLogFilename = current.getName(); lastXidLogFileOffset = event.getLogPos(); + } else if (LogEvent.FORMAT_DESCRIPTION_EVENT == event.getHeader().getType()) { + lastXidLogFilename = current.getName(); + lastXidLogFileOffset = event.getLogPos(); } } } @@ -212,21 +222,37 @@ public class LocalBinLogConnection implements ErosaConnection { @Override public void dump(String binlogfilename, Long binlogPosition, MultiStageCoprocessor coprocessor) throws IOException { File current = new File(directory, binlogfilename); + if (!current.exists()) { + throw new CanalParseException("binlog:" + binlogfilename + " is not found"); + } FileLogFetcher fetcher = new FileLogFetcher(bufferSize); + LogDecoder decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); + LogContext context = new LogContext(); try { fetcher.open(current, binlogPosition); + context.setLogPosition(new LogPosition(binlogfilename, binlogPosition)); while (running) { boolean needContinue = true; + LogEvent event = null; while (fetcher.fetch()) { - LogBuffer buffer = fetcher.duplicate(); - fetcher.consume(fetcher.limit()); - coprocessor.publish(buffer, binlogfilename); // set filename + event = decoder.decode(fetcher, context); + if (event == null) { + continue; + } + if (serverId != 0 && event.getServerId() != serverId) { + throw new ServerIdNotMatchException("unexpected serverId " + serverId + " in binlog file !"); + } + + if (!coprocessor.publish(event)) { + needContinue = false; + break; + } } + fetcher.close(); // 关闭上一个文件 + parserFinish(binlogfilename); if (needContinue) {// 读取下一个 - fetcher.close(); // 关闭上一个文件 - File nextFile; if (needWait) { nextFile = binlogs.waitForNextFile(current); @@ -254,6 +280,12 @@ public class LocalBinLogConnection implements ErosaConnection { } } + private void parserFinish(String fileName) { + if (parserListener != null) { + parserListener.onFinish(fileName); + } + } + @Override public void dump(long timestampMills, MultiStageCoprocessor coprocessor) throws IOException { List currentBinlogs = binlogs.currentBinlogs(); @@ -282,6 +314,10 @@ public class LocalBinLogConnection implements ErosaConnection { while (fetcher.fetch()) { LogEvent event = decoder.decode(fetcher, context); if (event != null) { + if (serverId != 0 && event.getServerId() != serverId) { + throw new ServerIdNotMatchException("unexpected serverId " + serverId + " in binlog file !"); + } + if (event.getWhen() > timestampSeconds) { break; } @@ -298,6 +334,9 @@ public class LocalBinLogConnection implements ErosaConnection { } else if (LogEvent.XID_EVENT == event.getHeader().getType()) { lastXidLogFilename = current.getName(); lastXidLogFileOffset = event.getLogPos(); + } else if (LogEvent.FORMAT_DESCRIPTION_EVENT == event.getHeader().getType()) { + lastXidLogFilename = current.getName(); + lastXidLogFileOffset = event.getLogPos(); } } } @@ -340,6 +379,11 @@ public class LocalBinLogConnection implements ErosaConnection { return connection; } + @Override + public long queryServerId() { + return 0; + } + public boolean isNeedWait() { return needWait; } @@ -364,4 +408,21 @@ public class LocalBinLogConnection implements ErosaConnection { this.bufferSize = bufferSize; } + public long getServerId() { + return serverId; + } + + public void setServerId(long serverId) { + this.serverId = serverId; + } + + public void setParserListener(FileParserListener parserListener) { + this.parserListener = parserListener; + } + + public interface FileParserListener { + + void onFinish(String fileName); + } + } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinlogEventParser.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinlogEventParser.java index ea6b0365..db235d9b 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinlogEventParser.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/LocalBinlogEventParser.java @@ -55,6 +55,9 @@ public class LocalBinlogEventParser extends AbstractMysqlEventParser implements ((DatabaseTableMeta) tableMetaTSDB).setConnection(metaConnection); ((DatabaseTableMeta) tableMetaTSDB).setFilter(eventFilter); ((DatabaseTableMeta) tableMetaTSDB).setBlackFilter(eventBlackFilter); + ((DatabaseTableMeta) tableMetaTSDB).setSnapshotInterval(tsdbSnapshotInterval); + ((DatabaseTableMeta) tableMetaTSDB).setSnapshotExpire(tsdbSnapshotExpire); + ((DatabaseTableMeta) tableMetaTSDB).init(destination); } tableMetaCache = new TableMetaCache(metaConnection, tableMetaTSDB); diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlConnection.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlConnection.java index 46f7e300..0ec5e7aa 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlConnection.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlConnection.java @@ -4,11 +4,14 @@ import static com.alibaba.otter.canal.parse.inbound.mysql.dbsync.DirectLogFetche import java.io.IOException; import java.net.InetSocketAddress; +import java.net.SocketAddress; import java.nio.charset.Charset; import java.util.List; import java.util.concurrent.TimeUnit; +import java.util.concurrent.atomic.AtomicLong; import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang.math.NumberUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -34,21 +37,25 @@ import com.taobao.tddl.dbsync.binlog.LogBuffer; import com.taobao.tddl.dbsync.binlog.LogContext; import com.taobao.tddl.dbsync.binlog.LogDecoder; import com.taobao.tddl.dbsync.binlog.LogEvent; +import com.taobao.tddl.dbsync.binlog.event.FormatDescriptionLogEvent; public class MysqlConnection implements ErosaConnection { - private static final Logger logger = LoggerFactory.getLogger(MysqlConnection.class); + private static final Logger logger = LoggerFactory.getLogger(MysqlConnection.class); private MysqlConnector connector; private long slaveId; - private Charset charset = Charset.forName("UTF-8"); + private Charset charset = Charset.forName("UTF-8"); private BinlogFormat binlogFormat; private BinlogImage binlogImage; // tsdb releated private AuthenticationInfo authInfo; - protected int connTimeout = 5 * 1000; // 5秒 - protected int soTimeout = 60 * 60 * 1000; // 1小时 + protected int connTimeout = 5 * 1000; // 5秒 + protected int soTimeout = 60 * 60 * 1000; // 1小时 + private int binlogChecksum = LogEvent.BINLOG_CHECKSUM_ALG_OFF; + // dump binlog bytes, 暂不包括meta与TSDB + private AtomicLong receivedBinlogBytes; public MysqlConnection(){ } @@ -113,7 +120,7 @@ public class MysqlConnection implements ErosaConnection { */ public void seek(String binlogfilename, Long binlogPosition, SinkFunction func) throws IOException { updateSettings(); - + loadBinlogChecksum(); sendBinlogDump(binlogfilename, binlogPosition); DirectLogFetcher fetcher = new DirectLogFetcher(connector.getReceiveBufferSize()); fetcher.start(connector.getChannel()); @@ -123,7 +130,9 @@ public class MysqlConnection implements ErosaConnection { decoder.handle(LogEvent.QUERY_EVENT); decoder.handle(LogEvent.XID_EVENT); LogContext context = new LogContext(); + context.setFormatDescription(new FormatDescriptionLogEvent(4, binlogChecksum)); while (fetcher.fetch()) { + accumulateReceivedBytes(fetcher.limit()); LogEvent event = null; event = decoder.decode(fetcher, context); @@ -139,13 +148,16 @@ public class MysqlConnection implements ErosaConnection { public void dump(String binlogfilename, Long binlogPosition, SinkFunction func) throws IOException { updateSettings(); + loadBinlogChecksum(); sendRegisterSlave(); sendBinlogDump(binlogfilename, binlogPosition); DirectLogFetcher fetcher = new DirectLogFetcher(connector.getReceiveBufferSize()); fetcher.start(connector.getChannel()); LogDecoder decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); LogContext context = new LogContext(); + context.setFormatDescription(new FormatDescriptionLogEvent(4, binlogChecksum)); while (fetcher.fetch()) { + accumulateReceivedBytes(fetcher.limit()); LogEvent event = null; event = decoder.decode(fetcher, context); @@ -166,6 +178,7 @@ public class MysqlConnection implements ErosaConnection { @Override public void dump(GTIDSet gtidSet, SinkFunction func) throws IOException { updateSettings(); + loadBinlogChecksum(); sendBinlogDumpGTID(gtidSet); DirectLogFetcher fetcher = new DirectLogFetcher(connector.getReceiveBufferSize()); @@ -173,7 +186,11 @@ public class MysqlConnection implements ErosaConnection { fetcher.start(connector.getChannel()); LogDecoder decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); LogContext context = new LogContext(); + context.setFormatDescription(new FormatDescriptionLogEvent(4, binlogChecksum)); + // fix bug: #890 将gtid传输至context中,供decode使用 + context.setGtidSet(gtidSet); while (fetcher.fetch()) { + accumulateReceivedBytes(fetcher.limit()); LogEvent event = null; event = decoder.decode(fetcher, context); @@ -197,16 +214,21 @@ public class MysqlConnection implements ErosaConnection { @Override public void dump(String binlogfilename, Long binlogPosition, MultiStageCoprocessor coprocessor) throws IOException { updateSettings(); + loadBinlogChecksum(); sendRegisterSlave(); sendBinlogDump(binlogfilename, binlogPosition); ((MysqlMultiStageCoprocessor) coprocessor).setConnection(this); + ((MysqlMultiStageCoprocessor) coprocessor).setBinlogChecksum(binlogChecksum); DirectLogFetcher fetcher = new DirectLogFetcher(connector.getReceiveBufferSize()); try { fetcher.start(connector.getChannel()); while (fetcher.fetch()) { + accumulateReceivedBytes(fetcher.limit()); LogBuffer buffer = fetcher.duplicate(); fetcher.consume(fetcher.limit()); - coprocessor.publish(buffer); + if (!coprocessor.publish(buffer)) { + break; + } } } finally { fetcher.close(); @@ -221,16 +243,20 @@ public class MysqlConnection implements ErosaConnection { @Override public void dump(GTIDSet gtidSet, MultiStageCoprocessor coprocessor) throws IOException { updateSettings(); + loadBinlogChecksum(); sendBinlogDumpGTID(gtidSet); - ((MysqlMultiStageCoprocessor) coprocessor).setConnection(this); + ((MysqlMultiStageCoprocessor) coprocessor).setBinlogChecksum(binlogChecksum); DirectLogFetcher fetcher = new DirectLogFetcher(connector.getReceiveBufferSize()); try { fetcher.start(connector.getChannel()); while (fetcher.fetch()) { + accumulateReceivedBytes(fetcher.limit()); LogBuffer buffer = fetcher.duplicate(); fetcher.consume(fetcher.limit()); - coprocessor.publish(buffer); + if (!coprocessor.publish(buffer)) { + break; + } } } finally { fetcher.close(); @@ -239,10 +265,18 @@ public class MysqlConnection implements ErosaConnection { private void sendRegisterSlave() throws IOException { RegisterSlaveCommandPacket cmd = new RegisterSlaveCommandPacket(); - cmd.reportHost = authInfo.getAddress().getAddress().getHostAddress(); + SocketAddress socketAddress = connector.getChannel().getLocalSocketAddress(); + if (socketAddress == null || !(socketAddress instanceof InetSocketAddress)) { + return; + } + + InetSocketAddress address = (InetSocketAddress) socketAddress; + String host = address.getHostString(); + int port = address.getPort(); + cmd.reportHost = host; + cmd.reportPort = port; cmd.reportPasswd = authInfo.getPassword(); cmd.reportUser = authInfo.getUsername(); - cmd.reportPort = authInfo.getAddress().getPort(); // 暂时先用master节点的port cmd.serverId = this.slaveId; byte[] cmdBody = cmd.toBytes(); @@ -320,6 +354,16 @@ public class MysqlConnection implements ErosaConnection { return connection; } + @Override + public long queryServerId() throws IOException { + ResultSetPacket resultSetPacket = query("show variables like 'server_id'"); + List fieldValues = resultSetPacket.getFieldValues(); + if (fieldValues == null || fieldValues.size() != 2) { + return 0; + } + return NumberUtils.toLong(fieldValues.get(1)); + } + // ====================== help method ==================== /** @@ -330,7 +374,6 @@ public class MysqlConnection implements ErosaConnection { *
    • net_read_timeout
    • * * - * @param channel * @throws IOException */ private void updateSettings() throws IOException { @@ -363,7 +406,8 @@ public class MysqlConnection implements ErosaConnection { // 如果不设置会出现错误: Slave can not handle replication events with the // checksum that master is configured to log // 但也不能乱设置,需要和mysql server的checksum配置一致,不然RotateLogEvent会出现乱码 - update("set @master_binlog_checksum= '@@global.binlog_checksum'"); + // '@@global.binlog_checksum'需要去掉单引号,在mysql 5.6.29下导致master退出 + update("set @master_binlog_checksum= @@global.binlog_checksum"); } catch (Exception e) { logger.warn("update master_binlog_checksum failed", e); } @@ -449,6 +493,37 @@ public class MysqlConnection implements ErosaConnection { } } + /** + * 获取主库checksum信息 + * + *
      +     * mariadb区别于mysql会在binlog的第一个事件Rotate_Event里也会采用checksum逻辑,而mysql是在第二个binlog事件之后才感知是否需要处理checksum
      +     * 导致maraidb只要是开启checksum就会出现binlog文件名解析乱码
      +     * fixed issue : https://github.com/alibaba/canal/issues/1081
      +     * 
      + */ + private void loadBinlogChecksum() { + ResultSetPacket rs = null; + try { + rs = query("select @@global.binlog_checksum"); + } catch (IOException e) { + throw new CanalParseException(e); + } + + List columnValues = rs.getFieldValues(); + if (columnValues != null && columnValues.size() >= 1 && columnValues.get(0).toUpperCase().equals("CRC32")) { + binlogChecksum = LogEvent.BINLOG_CHECKSUM_ALG_CRC32; + } else { + binlogChecksum = LogEvent.BINLOG_CHECKSUM_ALG_OFF; + } + } + + private void accumulateReceivedBytes(long x) { + if (receivedBinlogBytes != null) { + receivedBinlogBytes.addAndGet(x); + } + } + public static enum BinlogFormat { STATEMENT("STATEMENT"), ROW("ROW"), MIXED("MIXED"); @@ -588,4 +663,8 @@ public class MysqlConnection implements ErosaConnection { this.authInfo = authInfo; } + public void setReceivedBinlogBytes(AtomicLong receivedBinlogBytes) { + this.receivedBinlogBytes = receivedBinlogBytes; + } + } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlEventParser.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlEventParser.java index 6c2b9d4d..35e98f73 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlEventParser.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlEventParser.java @@ -8,7 +8,6 @@ import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.TimerTask; -import java.util.concurrent.atomic.AtomicLong; import org.apache.commons.lang.StringUtils; import org.springframework.util.CollectionUtils; @@ -36,41 +35,41 @@ import com.taobao.tddl.dbsync.binlog.LogEvent; /** * 基于向mysql server复制binlog实现 - * + * *
        * 1. 自身不控制mysql主备切换,由ha机制来控制. 比如接入tddl/cobar/自身心跳包成功率
        * 2. 切换机制
        * 
      - * + * * @author jianghang 2012-6-21 下午04:06:32 * @version 1.0.0 */ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalEventParser, CanalHASwitchable { - private CanalHAController haController = null; + private CanalHAController haController = null; - private int defaultConnectionTimeoutInSeconds = 30; // sotimeout - private int receiveBufferSize = 64 * 1024; - private int sendBufferSize = 64 * 1024; + private int defaultConnectionTimeoutInSeconds = 30; // sotimeout + private int receiveBufferSize = 64 * 1024; + private int sendBufferSize = 64 * 1024; // 数据库信息 - private AuthenticationInfo masterInfo; // 主库 - private AuthenticationInfo standbyInfo; // 备库 + protected AuthenticationInfo masterInfo; // 主库 + protected AuthenticationInfo standbyInfo; // 备库 // binlog信息 - private EntryPosition masterPosition; - private EntryPosition standbyPosition; - private long slaveId; // 链接到mysql的slave + protected EntryPosition masterPosition; + protected EntryPosition standbyPosition; + private long slaveId; // 链接到mysql的slave // 心跳检查信息 - private String detectingSQL; // 心跳sql - private MysqlConnection metaConnection; // 查询meta信息的链接 - private TableMetaCache tableMetaCache; // 对应meta - // cache - private int fallbackIntervalInSeconds = 60; // 切换回退时间 - private BinlogFormat[] supportBinlogFormats; // 支持的binlogFormat,如果设置会执行强校验 - private BinlogImage[] supportBinlogImages; // 支持的binlogImage,如果设置会执行强校验 + private String detectingSQL; // 心跳sql + private MysqlConnection metaConnection; // 查询meta信息的链接 + private TableMetaCache tableMetaCache; // 对应meta + private int fallbackIntervalInSeconds = 60; // 切换回退时间 + private BinlogFormat[] supportBinlogFormats; // 支持的binlogFormat,如果设置会执行强校验 + private BinlogImage[] supportBinlogImages; // 支持的binlogImage,如果设置会执行强校验 // update by yishun.chen,特殊异常处理参数 - private int dumpErrorCount = 0; // binlogDump失败异常计数 - private int dumpErrorCountThreshold = 2; // binlogDump失败异常计数阀值 + private int dumpErrorCount = 0; // binlogDump失败异常计数 + private int dumpErrorCountThreshold = 2; // binlogDump失败异常计数阀值 + private boolean rdsOssMode = false; protected ErosaConnection buildErosaConnection() { return buildMysqlConnection(this.runningInfo); @@ -123,6 +122,9 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE ((DatabaseTableMeta) tableMetaTSDB).setConnection(metaConnection); ((DatabaseTableMeta) tableMetaTSDB).setFilter(eventFilter); ((DatabaseTableMeta) tableMetaTSDB).setBlackFilter(eventBlackFilter); + ((DatabaseTableMeta) tableMetaTSDB).setSnapshotInterval(tsdbSnapshotInterval); + ((DatabaseTableMeta) tableMetaTSDB).setSnapshotExpire(tsdbSnapshotExpire); + ((DatabaseTableMeta) tableMetaTSDB).init(destination); } tableMetaCache = new TableMetaCache(metaConnection, tableMetaTSDB); @@ -133,6 +135,10 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE protected void afterDump(ErosaConnection connection) { super.afterDump(connection); + if (connection == null) { + throw new CanalParseException("illegal connection is null"); + } + if (!(connection instanceof MysqlConnection)) { throw new CanalParseException("Unsupported connection type : " + connection.getClass().getSimpleName()); } @@ -202,7 +208,7 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE /** * 心跳信息 - * + * * @author jianghang 2012-7-6 下午02:50:15 * @version 1.0.0 */ @@ -314,6 +320,7 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE connection.getConnector().setSendBufferSize(sendBufferSize); connection.getConnector().setSoTimeout(defaultConnectionTimeoutInSeconds * 1000); connection.setCharset(connectionCharset); + connection.setReceivedBinlogBytes(receivedBinlogBytes); // 随机生成slaveId if (this.slaveId <= 0) { this.slaveId = generateUniqueServerId(); @@ -351,7 +358,7 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE return logPosition.getPostion(); } - if (StringUtils.isNotEmpty(masterPosition.getGtid())) { + if (masterPosition != null && StringUtils.isNotEmpty(masterPosition.getGtid())) { return masterPosition; } } @@ -492,6 +499,12 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE dumpErrorCount = 0; return findPosition; } + + Long timestamp = logPosition.getPostion().getTimestamp(); + if (isRdsOssMode() && (timestamp != null && timestamp > 0)) { + // 如果binlog位点不存在,并且属于timestamp不为空,可以返回null走到oss binlog处理 + return null; + } } // 其余情况 logger.warn("prepare to find start position just last position\n {}", @@ -512,7 +525,7 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE private Long findTransactionBeginPosition(ErosaConnection mysqlConnection, final EntryPosition entryPosition) throws IOException { // 针对开始的第一条为非Begin记录,需要从该binlog扫描 - final AtomicLong preTransactionStartPosition = new AtomicLong(0L); + final java.util.concurrent.atomic.AtomicLong preTransactionStartPosition = new java.util.concurrent.atomic.AtomicLong(0L); mysqlConnection.reconnect(); mysqlConnection.seek(entryPosition.getJournalName(), 4L, new SinkFunction() { @@ -643,6 +656,9 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE throw new CanalParseException("command : 'show master status' has an error! pls check. you need (at least one of) the SUPER,REPLICATION CLIENT privilege(s) for this operation"); } EntryPosition endPosition = new EntryPosition(fields.get(0), Long.valueOf(fields.get(1))); + if (isGTIDMode() && fields.size() > 4) { + endPosition.setGtid(fields.get(4)); + } return endPosition; } catch (IOException e) { throw new CanalParseException("command : 'show master status' has an error!", e); @@ -735,31 +751,23 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE if (justForPositionTimestamp && logPosition.getPostion() == null && event.getWhen() > 0) { // 初始位点 entryPosition = new EntryPosition(searchBinlogFile, - event.getLogPos(), + event.getLogPos() - event.getEventLen(), event.getWhen() * 1000, event.getServerId()); logPosition.setPostion(entryPosition); } - if (entry == null) { - return true; - } + // 直接用event的位点来处理,解决一个binlog文件里没有任何事件导致死循环无法退出的问题 + String logfilename = event.getHeader().getLogFileName(); + // 记录的是binlog end offest, + // 因为与其对比的offest是show master status里的end offest + Long logfileoffset = event.getHeader().getLogPos(); + Long logposTimestamp = event.getHeader().getWhen() * 1000; + Long serverId = event.getHeader().getServerId(); - String logfilename = entry.getHeader().getLogfileName(); - Long logfileoffset = entry.getHeader().getLogfileOffset(); - Long logposTimestamp = entry.getHeader().getExecuteTime(); - Long serverId = entry.getHeader().getServerId(); - - if (CanalEntry.EntryType.TRANSACTIONBEGIN.equals(entry.getEntryType()) - || CanalEntry.EntryType.TRANSACTIONEND.equals(entry.getEntryType())) { - if (logger.isDebugEnabled()) { - logger.debug("compare exit condition:{},{},{}, startTimestamp={}...", new Object[] { - logfilename, logfileoffset, logposTimestamp, startTimestamp }); - } - // 事务头和尾寻找第一条记录时间戳,如果最小的一条记录都不满足条件,可直接退出 - if (logposTimestamp >= startTimestamp) { - return false; - } + // 如果最小的一条记录都不满足条件,可直接退出 + if (logposTimestamp >= startTimestamp) { + return false; } if (StringUtils.equals(endPosition.getJournalName(), logfilename) @@ -767,6 +775,10 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE return false; } + if (entry == null) { + return true; + } + // 记录一下上一个事务结束的位置,即下一个事务的position // position = current + // data.length,代表该事务的下一条offest,避免多余的事务重复 @@ -908,4 +920,12 @@ public class MysqlEventParser extends AbstractMysqlEventParser implements CanalE this.dumpErrorCountThreshold = dumpErrorCountThreshold; } + public boolean isRdsOssMode() { + return rdsOssMode; + } + + public void setRdsOssMode(boolean rdsOssMode) { + this.rdsOssMode = rdsOssMode; + } + } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlMultiStageCoprocessor.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlMultiStageCoprocessor.java index 6e02e22d..703de818 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlMultiStageCoprocessor.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlMultiStageCoprocessor.java @@ -2,11 +2,13 @@ package com.alibaba.otter.canal.parse.inbound.mysql; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; - -import org.apache.commons.lang.StringUtils; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.atomic.AtomicLong; +import java.util.concurrent.locks.LockSupport; import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; import com.alibaba.otter.canal.common.utils.NamedThreadFactory; +import com.alibaba.otter.canal.parse.driver.mysql.packets.GTIDSet; import com.alibaba.otter.canal.parse.exception.CanalParseException; import com.alibaba.otter.canal.parse.inbound.ErosaConnection; import com.alibaba.otter.canal.parse.inbound.EventTransactionBuffer; @@ -18,7 +20,8 @@ import com.lmax.disruptor.BatchEventProcessor; import com.lmax.disruptor.BlockingWaitStrategy; import com.lmax.disruptor.EventFactory; import com.lmax.disruptor.EventHandler; -import com.lmax.disruptor.FatalExceptionHandler; +import com.lmax.disruptor.ExceptionHandler; +import com.lmax.disruptor.InsufficientCapacityException; import com.lmax.disruptor.LifecycleAware; import com.lmax.disruptor.RingBuffer; import com.lmax.disruptor.Sequence; @@ -29,8 +32,8 @@ import com.taobao.tddl.dbsync.binlog.LogBuffer; import com.taobao.tddl.dbsync.binlog.LogContext; import com.taobao.tddl.dbsync.binlog.LogDecoder; import com.taobao.tddl.dbsync.binlog.LogEvent; -import com.taobao.tddl.dbsync.binlog.LogPosition; import com.taobao.tddl.dbsync.binlog.event.DeleteRowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.FormatDescriptionLogEvent; import com.taobao.tddl.dbsync.binlog.event.RowsLogEvent; import com.taobao.tddl.dbsync.binlog.event.UpdateRowsLogEvent; import com.taobao.tddl.dbsync.binlog.event.WriteRowsLogEvent; @@ -50,17 +53,24 @@ import com.taobao.tddl.dbsync.binlog.event.WriteRowsLogEvent; */ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implements MultiStageCoprocessor { - private LogEventConvert logEventConvert; - private EventTransactionBuffer transactionBuffer; - private ErosaConnection connection; + private static final int maxFullTimes = 10; + private LogEventConvert logEventConvert; + private EventTransactionBuffer transactionBuffer; + private ErosaConnection connection; - private int parserThreadCount; - private int ringBufferSize; - private RingBuffer disruptorMsgBuffer; - private ExecutorService parserExecutor; - private ExecutorService stageExecutor; - private String destination; - private CanalParseException exception; + private int parserThreadCount; + private int ringBufferSize; + private RingBuffer disruptorMsgBuffer; + private ExecutorService parserExecutor; + private ExecutorService stageExecutor; + private String destination; + private volatile CanalParseException exception; + private AtomicLong eventsPublishBlockingTime; + private GTIDSet gtidSet; + private WorkerPool workerPool; + private BatchEventProcessor simpleParserStage; + private BatchEventProcessor sinkStoreStage; + private LogContext logContext; public MysqlMultiStageCoprocessor(int ringBufferSize, int parserThreadCount, LogEventConvert logEventConvert, EventTransactionBuffer transactionBuffer, String destination){ @@ -78,18 +88,20 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement this.disruptorMsgBuffer = RingBuffer.createSingleProducer(new MessageEventFactory(), ringBufferSize, new BlockingWaitStrategy()); - - this.parserExecutor = Executors.newFixedThreadPool(parserThreadCount, - new NamedThreadFactory("MultiStageCoprocessor-Parser-" + destination)); + int tc = parserThreadCount > 0 ? parserThreadCount : 1; + this.parserExecutor = Executors.newFixedThreadPool(tc, new NamedThreadFactory("MultiStageCoprocessor-Parser-" + + destination)); this.stageExecutor = Executors.newFixedThreadPool(2, new NamedThreadFactory("MultiStageCoprocessor-other-" + destination)); SequenceBarrier sequenceBarrier = disruptorMsgBuffer.newBarrier(); - + ExceptionHandler exceptionHandler = new SimpleFatalExceptionHandler(); // stage 2 - BatchEventProcessor simpleParserStage = new BatchEventProcessor(disruptorMsgBuffer, + this.logContext = new LogContext(); + simpleParserStage = new BatchEventProcessor(disruptorMsgBuffer, sequenceBarrier, - new SimpleParserStage()); + new SimpleParserStage(logContext)); + simpleParserStage.setExceptionHandler(exceptionHandler); disruptorMsgBuffer.addGatingSequences(simpleParserStage.getSequence()); // stage 3 @@ -98,18 +110,19 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement for (int i = 0; i < parserThreadCount; i++) { workHandlers[i] = new DmlParserStage(); } - WorkerPool workerPool = new WorkerPool(disruptorMsgBuffer, + workerPool = new WorkerPool(disruptorMsgBuffer, dmlParserSequenceBarrier, - new FatalExceptionHandler(), + exceptionHandler, workHandlers); Sequence[] sequence = workerPool.getWorkerSequences(); disruptorMsgBuffer.addGatingSequences(sequence); // stage 4 SequenceBarrier sinkSequenceBarrier = disruptorMsgBuffer.newBarrier(sequence); - BatchEventProcessor sinkStoreStage = new BatchEventProcessor(disruptorMsgBuffer, + sinkStoreStage = new BatchEventProcessor(disruptorMsgBuffer, sinkSequenceBarrier, new SinkStoreStage()); + sinkStoreStage.setExceptionHandler(exceptionHandler); disruptorMsgBuffer.addGatingSequences(sinkStoreStage.getSequence()); // start work @@ -118,51 +131,116 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement workerPool.start(parserExecutor); } + public void setBinlogChecksum(int binlogChecksum) { + if (binlogChecksum != LogEvent.BINLOG_CHECKSUM_ALG_OFF) { + logContext.setFormatDescription(new FormatDescriptionLogEvent(4, binlogChecksum)); + } + } + @Override public void stop() { + // fix bug #968,对于pool与 + workerPool.halt(); + simpleParserStage.halt(); + sinkStoreStage.halt(); try { parserExecutor.shutdownNow(); + while (!parserExecutor.awaitTermination(1, TimeUnit.SECONDS)) { + if (parserExecutor.isShutdown() || parserExecutor.isTerminated()) { + break; + } + + parserExecutor.shutdownNow(); + } } catch (Throwable e) { // ignore } try { stageExecutor.shutdownNow(); + while (!stageExecutor.awaitTermination(1, TimeUnit.SECONDS)) { + if (stageExecutor.isShutdown() || stageExecutor.isTerminated()) { + break; + } + + stageExecutor.shutdownNow(); + } } catch (Throwable e) { // ignore } - disruptorMsgBuffer = null; super.stop(); } + public boolean publish(LogBuffer buffer) { + return this.publish(buffer, null); + } + /** * 网络数据投递 */ - public void publish(LogBuffer buffer) { - if (!isStart() && exception != null) { - throw exception; - } - long next = disruptorMsgBuffer.next(); - MessageEvent event = disruptorMsgBuffer.get(next); - event.setBuffer(buffer); - disruptorMsgBuffer.publish(next); + public boolean publish(LogEvent event) { + return this.publish(null, event); } - public void publish(LogBuffer buffer, String binlogFileName) { - if (!isStart() && exception != null) { + private boolean publish(LogBuffer buffer, LogEvent event) { + if (!isStart()) { + if (exception != null) { + throw exception; + } + return false; + } + + /** + * 由于改为processor仅终止自身stage而不是stop,那么需要由incident标识coprocessor是否正常工作。 + * 让dump线程能够及时感知 + */ + if (exception != null) { throw exception; } - long next = disruptorMsgBuffer.next(); - MessageEvent event = disruptorMsgBuffer.get(next); - event.setBuffer(buffer); - event.setBinlogFileName(binlogFileName); - disruptorMsgBuffer.publish(next); + boolean interupted = false; + long blockingStart = 0L; + int fullTimes = 0; + do { + try { + long next = disruptorMsgBuffer.tryNext(); + MessageEvent data = disruptorMsgBuffer.get(next); + if (buffer != null) { + data.setBuffer(buffer); + } else { + data.setEvent(event); + } + disruptorMsgBuffer.publish(next); + if (fullTimes > 0) { + eventsPublishBlockingTime.addAndGet(System.nanoTime() - blockingStart); + } + break; + } catch (InsufficientCapacityException e) { + if (fullTimes == 0) { + blockingStart = System.nanoTime(); + } + // park + // LockSupport.parkNanos(1L); + applyWait(++fullTimes); + interupted = Thread.interrupted(); + if (fullTimes % 1000 == 0) { + long nextStart = System.nanoTime(); + eventsPublishBlockingTime.addAndGet(nextStart - blockingStart); + blockingStart = nextStart; + } + } + } while (!interupted && isStart()); + return isStart(); } - @Override - public void reset() { - stop(); - start(); + // 处理无数据的情况,避免空循环挂死 + private void applyWait(int fullTimes) { + int newFullTimes = fullTimes > maxFullTimes ? maxFullTimes : fullTimes; + if (fullTimes <= 3) { // 3次以内 + Thread.yield(); + } else { // 超过3次,最多只sleep 1ms + LockSupport.parkNanos(100 * 1000L * newFullTimes); + } + } private class SimpleParserStage implements EventHandler, LifecycleAware { @@ -170,24 +248,23 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement private LogDecoder decoder; private LogContext context; - public SimpleParserStage(){ + public SimpleParserStage(LogContext context){ decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); - context = new LogContext(); + this.context = context; + if (gtidSet != null) { + context.setGtidSet(gtidSet); + } } public void onEvent(MessageEvent event, long sequence, boolean endOfBatch) throws Exception { try { - LogBuffer buffer = event.getBuffer(); - if (StringUtils.isNotEmpty(event.getBinlogFileName()) - && !context.getLogPosition().getFileName().equals(event.getBinlogFileName())) { - // set roate binlog file name - context.setLogPosition(new LogPosition(event.getBinlogFileName(), context.getLogPosition() - .getPosition())); + LogEvent logEvent = event.getEvent(); + if (logEvent == null) { + LogBuffer buffer = event.getBuffer(); + logEvent = decoder.decode(buffer, context); + event.setEvent(logEvent); } - LogEvent logEvent = decoder.decode(buffer, context); - event.setEvent(logEvent); - int eventType = logEvent.getHeader().getType(); TableMeta tableMeta = null; boolean needDmlParse = false; @@ -198,6 +275,7 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement needDmlParse = true; break; case LogEvent.UPDATE_ROWS_EVENT_V1: + case LogEvent.PARTIAL_UPDATE_ROWS_EVENT: case LogEvent.UPDATE_ROWS_EVENT: tableMeta = logEventConvert.parseRowsEventForTableMeta((UpdateRowsLogEvent) logEvent); needDmlParse = true; @@ -231,7 +309,7 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement @Override public void onShutdown() { - stop(); + } } @@ -267,7 +345,7 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement @Override public void onShutdown() { - stop(); + } } @@ -288,7 +366,6 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement // clear for gc event.setBuffer(null); - event.setBinlogFileName(null); event.setEvent(null); event.setTable(null); event.setEntry(null); @@ -306,27 +383,18 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement @Override public void onShutdown() { - stop(); + } } class MessageEvent { - private String binlogFileName; // for local binlog parse private LogBuffer buffer; private CanalEntry.Entry entry; private boolean needDmlParse = false; private TableMeta table; private LogEvent event; - public String getBinlogFileName() { - return binlogFileName; - } - - public void setBinlogFileName(String binlogFileName) { - this.binlogFileName = binlogFileName; - } - public LogBuffer getBuffer() { return buffer; } @@ -369,6 +437,21 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement } + class SimpleFatalExceptionHandler implements ExceptionHandler { + + @Override + public void handleEventException(final Throwable ex, final long sequence, final Object event) { + } + + @Override + public void handleOnStartException(final Throwable ex) { + } + + @Override + public void handleOnShutdownException(final Throwable ex) { + } + } + class MessageEventFactory implements EventFactory { public MessageEvent newInstance() { @@ -388,4 +471,12 @@ public class MysqlMultiStageCoprocessor extends AbstractCanalLifeCycle implement this.connection = connection; } + public void setEventsPublishBlockingTime(AtomicLong eventsPublishBlockingTime) { + this.eventsPublishBlockingTime = eventsPublishBlockingTime; + } + + public void setGtidSet(GTIDSet gtidSet) { + this.gtidSet = gtidSet; + } + } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/DirectLogFetcher.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/DirectLogFetcher.java index a85962cc..222d762a 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/DirectLogFetcher.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/DirectLogFetcher.java @@ -64,9 +64,6 @@ public class DirectLogFetcher extends LogFetcher { if ("1".equals(dbsemi)) { issemi = true; } - // 和mysql driver一样,提供buffer机制,提升读取binlog速度 - // this.input = new - // BufferedInputStream(channel.socket().getInputStream(), 16384); } /** diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/LogEventConvert.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/LogEventConvert.java index f99d551c..2832ff34 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/LogEventConvert.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/LogEventConvert.java @@ -17,7 +17,6 @@ import org.slf4j.LoggerFactory; import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; import com.alibaba.otter.canal.filter.aviater.AviaterRegexFilter; -import com.alibaba.otter.canal.parse.driver.mysql.packets.GTIDSet; import com.alibaba.otter.canal.parse.exception.CanalParseException; import com.alibaba.otter.canal.parse.exception.TableIdNotFoundException; import com.alibaba.otter.canal.parse.inbound.BinlogParser; @@ -42,6 +41,7 @@ import com.google.protobuf.ByteString; import com.taobao.tddl.dbsync.binlog.LogEvent; import com.taobao.tddl.dbsync.binlog.event.DeleteRowsLogEvent; import com.taobao.tddl.dbsync.binlog.event.GtidLogEvent; +import com.taobao.tddl.dbsync.binlog.event.HeartbeatLogEvent; import com.taobao.tddl.dbsync.binlog.event.IntvarLogEvent; import com.taobao.tddl.dbsync.binlog.event.LogHeader; import com.taobao.tddl.dbsync.binlog.event.QueryLogEvent; @@ -98,13 +98,6 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar private boolean filterRows = false; private boolean useDruidDdlFilter = true; - // latest gtid - private GTIDSet gtidSet; - - public LogEventConvert(GTIDSet gtidSet){ - this.gtidSet = gtidSet; - } - public LogEventConvert(){ } @@ -127,6 +120,7 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar case LogEvent.WRITE_ROWS_EVENT: return parseRowsEvent((WriteRowsLogEvent) logEvent); case LogEvent.UPDATE_ROWS_EVENT_V1: + case LogEvent.PARTIAL_UPDATE_ROWS_EVENT: case LogEvent.UPDATE_ROWS_EVENT: return parseRowsEvent((UpdateRowsLogEvent) logEvent); case LogEvent.DELETE_ROWS_EVENT_V1: @@ -144,6 +138,8 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar return parseRandLogEvent((RandLogEvent) logEvent); case LogEvent.GTID_LOG_EVENT: return parseGTIDLogEvent((GtidLogEvent) logEvent); + case LogEvent.HEARTBEAT_LOG_EVENT: + return parseHeartbeatLogEvent((HeartbeatLogEvent) logEvent); default: break; } @@ -158,14 +154,26 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar } } + private Entry parseHeartbeatLogEvent(HeartbeatLogEvent logEvent) { + Header.Builder headerBuilder = Header.newBuilder(); + headerBuilder.setEventType(EventType.MHEARTBEAT); + Entry.Builder entryBuilder = Entry.newBuilder(); + entryBuilder.setHeader(headerBuilder.build()); + entryBuilder.setEntryType(EntryType.HEARTBEAT); + return entryBuilder.build(); + } + private Entry parseGTIDLogEvent(GtidLogEvent logEvent) { LogHeader logHeader = logEvent.getHeader(); - String value = logEvent.getSid().toString() + ":" + logEvent.getGno(); Pair.Builder builder = Pair.newBuilder(); builder.setKey("gtid"); - builder.setValue(value); - if (gtidSet != null) { - gtidSet.update(value); + builder.setValue(logEvent.getGtidStr()); + + if (logEvent.getLastCommitted() != null) { + builder.setKey("lastCommitted"); + builder.setValue(String.valueOf(logEvent.getLastCommitted())); + builder.setKey("sequenceNumber"); + builder.setValue(String.valueOf(logEvent.getSequenceNumber())); } Header header = createHeader(logHeader, "", "", EventType.GTID); @@ -253,7 +261,9 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar return null; } - if (!isSeek) { + boolean isDml = (type == EventType.INSERT || type == EventType.UPDATE || type == EventType.DELETE); + + if (!isSeek && !isDml) { // 使用新的表结构元数据管理方式 EntryPosition position = createPosition(event.getHeader()); tableMetaCache.apply(position, event.getDbName(), queryString, null); @@ -261,8 +271,7 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar Header header = createHeader(event.getHeader(), schemaName, tableName, type); RowChange.Builder rowChangeBuider = RowChange.newBuilder(); - if (type != EventType.QUERY && type != EventType.INSERT && type != EventType.UPDATE - && type != EventType.DELETE) { + if (type != EventType.QUERY && !isDml) { rowChangeBuider.setIsDdl(true); } rowChangeBuider.setSql(queryString); @@ -496,7 +505,8 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar int type = event.getHeader().getType(); if (LogEvent.WRITE_ROWS_EVENT_V1 == type || LogEvent.WRITE_ROWS_EVENT == type) { eventType = EventType.INSERT; - } else if (LogEvent.UPDATE_ROWS_EVENT_V1 == type || LogEvent.UPDATE_ROWS_EVENT == type) { + } else if (LogEvent.UPDATE_ROWS_EVENT_V1 == type || LogEvent.UPDATE_ROWS_EVENT == type + || LogEvent.PARTIAL_UPDATE_ROWS_EVENT == type) { eventType = EventType.UPDATE; } else if (LogEvent.DELETE_ROWS_EVENT_V1 == type || LogEvent.DELETE_ROWS_EVENT == type) { eventType = EventType.DELETE; @@ -504,9 +514,6 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar throw new CanalParseException("unsupport event type :" + event.getHeader().getType()); } - TableMapLogEvent table = event.getTable(); - Header header = createHeader(event.getHeader(), table.getDbName(), table.getTableName(), eventType); - RowChange.Builder rowChangeBuider = RowChange.newBuilder(); rowChangeBuider.setTableId(event.getTableId()); rowChangeBuider.setIsDdl(false); @@ -517,7 +524,8 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar BitSet changeColumns = event.getChangeColumns(); boolean tableError = false; - while (buffer.nextOneRow(columns)) { + int rowsCount = 0; + while (buffer.nextOneRow(columns, false)) { // 处理row记录 RowData.Builder rowDataBuilder = RowData.newBuilder(); if (EventType.INSERT == eventType) { @@ -529,7 +537,7 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar } else { // update需要处理before/after tableError |= parseOneRow(rowDataBuilder, event, buffer, columns, false, tableMeta); - if (!buffer.nextOneRow(changeColumns)) { + if (!buffer.nextOneRow(changeColumns, true)) { rowChangeBuider.addRowDatas(rowDataBuilder.build()); break; } @@ -537,8 +545,15 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar tableError |= parseOneRow(rowDataBuilder, event, buffer, changeColumns, true, tableMeta); } + rowsCount++; rowChangeBuider.addRowDatas(rowDataBuilder.build()); } + TableMapLogEvent table = event.getTable(); + Header header = createHeader(event.getHeader(), + table.getDbName(), + table.getTableName(), + eventType, + rowsCount); RowChange rowChange = rowChangeBuider.build(); if (tableError) { @@ -555,8 +570,7 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar } private EntryPosition createPosition(LogHeader logHeader) { - return new EntryPosition(logHeader.getLogFileName(), - logHeader.getLogPos(), + return new EntryPosition(logHeader.getLogFileName(), logHeader.getLogPos() - logHeader.getEventLen(), // startPos logHeader.getWhen() * 1000L, logHeader.getServerId()); // 记录到秒 } @@ -565,7 +579,8 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar boolean isAfter, TableMeta tableMeta) throws UnsupportedEncodingException { int columnCnt = event.getTable().getColumnCnt(); ColumnInfo[] columnInfo = event.getTable().getColumnInfo(); - + // mysql8.0针对set @@global.binlog_row_metadata='FULL' 可以记录部分的metadata信息 + boolean existOptionalMetaData = event.getTable().isExistOptionalMetaData(); boolean tableError = false; // check table fileds count,只能处理加字段 boolean existRDSNoPrimaryKey = false; @@ -619,22 +634,44 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar continue; } - if (existRDSNoPrimaryKey && i == columnCnt - 1 && info.type == LogEvent.MYSQL_TYPE_LONGLONG) { - // 不解析最后一列 - buffer.nextValue(info.type, info.meta, false); - continue; - } - - Column.Builder columnBuilder = Column.newBuilder(); - FieldMeta fieldMeta = null; if (tableMeta != null && !tableError) { // 处理file meta fieldMeta = tableMeta.getFields().get(i); + } + + if (existRDSNoPrimaryKey && i == columnCnt - 1 && info.type == LogEvent.MYSQL_TYPE_LONGLONG) { + // 不解析最后一列 + buffer.nextValue(fieldMeta.getColumnName(), i, info.type, info.meta, false); + continue; + } + + if (fieldMeta != null && existOptionalMetaData && tableMetaCache.isOnTSDB()) { + // check column info + boolean check = StringUtils.equalsIgnoreCase(fieldMeta.getColumnName(), info.name); + check &= (fieldMeta.isUnsigned() == info.unsigned); + check &= (fieldMeta.isNullable() == info.nullable); + + if (!check) { + throw new CanalParseException("MySQL8.0 unmatch column metadata & pls submit issue , table : " + + tableMeta.getFullName() + ", db fieldMeta : " + + fieldMeta.toString() + " , binlog fieldMeta : " + info.toString() + + " , on : " + event.getHeader().getLogFileName() + ":" + + (event.getHeader().getLogPos() - event.getHeader().getEventLen())); + } + } + + Column.Builder columnBuilder = Column.newBuilder(); + if (fieldMeta != null) { columnBuilder.setName(fieldMeta.getColumnName()); columnBuilder.setIsKey(fieldMeta.isKey()); // 增加mysql type类型,issue 73 columnBuilder.setMysqlType(fieldMeta.getColumnType()); + } else if (existOptionalMetaData) { + columnBuilder.setName(info.name); + columnBuilder.setIsKey(info.pk); + // mysql8.0里没有mysql type类型 + // columnBuilder.setMysqlType(fieldMeta.getColumnType()); } columnBuilder.setIndex(i); columnBuilder.setIsNull(false); @@ -652,16 +689,9 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar isSingleBit = true; } } - buffer.nextValue(info.type, info.meta, isBinary); - if (existRDSNoPrimaryKey && i == columnCnt - 1 && info.type == LogEvent.MYSQL_TYPE_LONGLONG) { - // 不解析最后一列 - continue; - } + buffer.nextValue(fieldMeta.getColumnName(), i, info.type, info.meta, isBinary); int javaType = buffer.getJavaType(); - if (isSingleBit && javaType == Types.TINYINT) { - javaType = Types.BIT; - } if (buffer.isNull()) { columnBuilder.setIsNull(true); } else { @@ -674,7 +704,8 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar case Types.BIGINT: // 处理unsigned类型 Number number = (Number) value; - if (fieldMeta != null && fieldMeta.isUnsigned() && number.longValue() < 0) { + boolean isUnsigned = (fieldMeta != null ? fieldMeta.isUnsigned() : (existOptionalMetaData ? info.unsigned : false)); + if (isUnsigned && number.longValue() < 0) { switch (buffer.getLength()) { case 1: /* MYSQL_TYPE_TINY */ columnBuilder.setValue(String.valueOf(Integer.valueOf(TINYINT_MAX_VALUE @@ -710,6 +741,10 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar // 对象为number类型,直接valueof即可 columnBuilder.setValue(String.valueOf(value)); } + + if (isSingleBit && javaType == Types.TINYINT) { + javaType = Types.BIT; + } break; case Types.REAL: // float case Types.DOUBLE: // double @@ -747,6 +782,8 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar } else { // byte数组,直接使用iso-8859-1保留对应编码,浪费内存 columnBuilder.setValue(new String((byte[]) value, ISO_8859_1)); + // columnBuilder.setValueBytes(ByteString.copyFrom((byte[]) + // value)); javaType = Types.BLOB; } break; @@ -757,7 +794,6 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar default: columnBuilder.setValue(value.toString()); } - } columnBuilder.setSqlType(javaType); @@ -794,10 +830,16 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar } private Header createHeader(LogHeader logHeader, String schemaName, String tableName, EventType eventType) { + return createHeader(logHeader, schemaName, tableName, eventType, -1); + } + + private Header createHeader(LogHeader logHeader, String schemaName, String tableName, EventType eventType, + Integer rowsCount) { // header会做信息冗余,方便以后做检索或者过滤 Header.Builder headerBuilder = Header.newBuilder(); headerBuilder.setVersion(version); headerBuilder.setLogfileName(logHeader.getLogFileName()); + // 记录的是该binlog的start offest headerBuilder.setLogfileOffset(logHeader.getLogPos() - logHeader.getEventLen()); headerBuilder.setServerId(logHeader.getServerId()); headerBuilder.setServerenCode(UTF_8);// 经过java输出后所有的编码为unicode @@ -814,9 +856,30 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar } headerBuilder.setEventLength(logHeader.getEventLen()); // enable gtid position - if (gtidSet != null) { - String gtid = gtidSet.toString(); - headerBuilder.setGtid(gtid); + if (StringUtils.isNotEmpty(logHeader.getGtidSetStr())) { + headerBuilder.setGtid(logHeader.getGtidSetStr()); + } + // add current gtid + if (StringUtils.isNotEmpty(logHeader.getCurrentGtid())) { + Pair pair = createSpecialPair("curtGtid", logHeader.getCurrentGtid()); + headerBuilder.addProps(pair); + } + // add current gtid sequence no + if (StringUtils.isNotEmpty(logHeader.getCurrentGtidSn())) { + Pair pair = createSpecialPair("curtGtidSn", logHeader.getCurrentGtidSn()); + headerBuilder.addProps(pair); + } + + // add current gtid last committed + if (StringUtils.isNotEmpty(logHeader.getCurrentGtidLastCommit())) { + Pair pair = createSpecialPair("curtGtidLct", logHeader.getCurrentGtidLastCommit()); + headerBuilder.addProps(pair); + } + + // add rowsCount suppport + if (rowsCount > 0) { + Pair pair = createSpecialPair("rowsCount", String.valueOf(rowsCount)); + headerBuilder.addProps(pair); } return headerBuilder.build(); } @@ -850,11 +913,14 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar private TableMeta getTableMeta(String dbName, String tbName, boolean useCache, EntryPosition position) { try { return tableMetaCache.getTableMeta(dbName, tbName, useCache, position); - } catch (Exception e) { + } catch (Throwable e) { String message = ExceptionUtils.getRootCauseMessage(e); if (filterTableError) { if (StringUtils.contains(message, "errorNumber=1146") && StringUtils.contains(message, "doesn't exist")) { return null; + } else if (StringUtils.contains(message, "errorNumber=1142") + && StringUtils.contains(message, "command denied")) { + return null; } } @@ -938,8 +1004,7 @@ public class LogEventConvert extends AbstractCanalLifeCycle implements BinlogPar this.filterRows = filterRows; } - public void setGtidSet(GTIDSet gtidSet) { - this.gtidSet = gtidSet; + public void setUseDruidDdlFilter(boolean useDruidDdlFilter) { + this.useDruidDdlFilter = useDruidDdlFilter; } - } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/TableMetaCache.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/TableMetaCache.java index 4c1cef3c..69b8a3e9 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/TableMetaCache.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/dbsync/TableMetaCache.java @@ -39,6 +39,7 @@ public class TableMetaCache { public static final String EXTRA = "EXTRA"; private MysqlConnection connection; private boolean isOnRDS = false; + private boolean isOnTSDB = false; private TableMetaTSDB tableMetaTSDB; // 第一层tableId,第二层schema.table,解决tableId重复,对应多张表 @@ -67,6 +68,8 @@ public class TableMetaCache { } }); + } else { + isOnTSDB = true; } try { @@ -244,6 +247,15 @@ public class TableMetaCache { .toString(); } + + public boolean isOnTSDB() { + return isOnTSDB; + } + + public void setOnTSDB(boolean isOnTSDB) { + this.isOnTSDB = isOnTSDB; + } + public boolean isOnRDS() { return isOnRDS; } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/DruidDdlParser.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/DruidDdlParser.java index eda66921..68f1ff5a 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/DruidDdlParser.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/DruidDdlParser.java @@ -4,6 +4,8 @@ import java.util.ArrayList; import java.util.Arrays; import java.util.List; +import org.apache.commons.lang.StringUtils; + import com.alibaba.fastsql.sql.SQLUtils; import com.alibaba.fastsql.sql.ast.SQLExpr; import com.alibaba.fastsql.sql.ast.SQLStatement; @@ -18,9 +20,11 @@ import com.alibaba.fastsql.sql.ast.statement.SQLAlterTableItem; import com.alibaba.fastsql.sql.ast.statement.SQLAlterTableRename; import com.alibaba.fastsql.sql.ast.statement.SQLAlterTableStatement; import com.alibaba.fastsql.sql.ast.statement.SQLConstraint; +import com.alibaba.fastsql.sql.ast.statement.SQLCreateDatabaseStatement; import com.alibaba.fastsql.sql.ast.statement.SQLCreateIndexStatement; import com.alibaba.fastsql.sql.ast.statement.SQLCreateTableStatement; import com.alibaba.fastsql.sql.ast.statement.SQLDeleteStatement; +import com.alibaba.fastsql.sql.ast.statement.SQLDropDatabaseStatement; import com.alibaba.fastsql.sql.ast.statement.SQLDropIndexStatement; import com.alibaba.fastsql.sql.ast.statement.SQLDropTableStatement; import com.alibaba.fastsql.sql.ast.statement.SQLExprTableSource; @@ -67,6 +71,7 @@ public class DruidDdlParser { DdlResult ddlResult = new DdlResult(); processName(ddlResult, schmeaName, alterTable.getName(), true); processName(ddlResult, schmeaName, ((SQLAlterTableRename) item).getToName(), false); + ddlResult.setType(EventType.RENAME); ddlResults.add(ddlResult); } else if (item instanceof SQLAlterTableAddIndex) { DdlResult ddlResult = new DdlResult(); @@ -157,6 +162,17 @@ public class DruidDdlParser { processName(ddlResult, schmeaName, delete.getTableName(), false); ddlResult.setType(EventType.DELETE); ddlResults.add(ddlResult); + } else if (statement instanceof SQLCreateDatabaseStatement) { + DdlResult ddlResult = new DdlResult(); + ddlResult.setType(EventType.QUERY); + // 只设置schema + processName(ddlResult, schmeaName, null, false); + ddlResults.add(ddlResult); + } else if (statement instanceof SQLDropDatabaseStatement) { + DdlResult ddlResult = new DdlResult(); + ddlResult.setType(EventType.QUERY); + // 只设置schema + processName(ddlResult, schmeaName, null, false); } } @@ -165,6 +181,9 @@ public class DruidDdlParser { private static void processName(DdlResult ddlResult, String schema, SQLExpr sqlName, boolean isOri) { if (sqlName == null) { + if (StringUtils.isNotBlank(schema)) { + ddlResult.setSchemaName(schema); + } return; } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/SimpleDdlParser.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/SimpleDdlParser.java index 53f7de82..57d95dcc 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/SimpleDdlParser.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/ddl/SimpleDdlParser.java @@ -44,8 +44,8 @@ public class SimpleDdlParser { * http://dev.mysql.com/doc/refman/5.6/en/create-index.html * */ - public static final String CREATE_INDEX_PATTERN = "^\\s*CREATE\\s*(UNIQUE)?(FULLTEXT)?(SPATIAL)?\\s*INDEX\\s*(.*?)\\s*ON\\s*(.*?)$"; - public static final String DROP_INDEX_PATTERN = "^\\s*DROP\\s*INDEX\\s*(.*?)\\s*ON\\s*(.*?)$"; + public static final String CREATE_INDEX_PATTERN = "^\\s*CREATE\\s*(UNIQUE)?(FULLTEXT)?(SPATIAL)?\\s*INDEX\\s*(.*?)\\s+ON\\s+(.*?)$"; + public static final String DROP_INDEX_PATTERN = "^\\s*DROP\\s*INDEX\\s*(.*?)\\s+ON\\s+(.*?)$"; public static DdlResult parse(String queryString, String schmeaName) { queryString = removeComment(queryString); // 去除/* */的sql注释内容 diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/local/BinLogFileQueue.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/local/BinLogFileQueue.java index 224852cc..eb227303 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/local/BinLogFileQueue.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/local/BinLogFileQueue.java @@ -25,13 +25,14 @@ import com.alibaba.otter.canal.parse.exception.CanalParseException; */ public class BinLogFileQueue { - private String baseName = "mysql-bin."; - private List binlogs = new ArrayList(); - private File directory; - private ReentrantLock lock = new ReentrantLock(); - private Condition nextCondition = lock.newCondition(); - private Timer timer = new Timer(true); - private long reloadInterval = 10 * 1000L; // 10秒 + private String baseName = "mysql-bin."; + private List binlogs = new ArrayList(); + private File directory; + private ReentrantLock lock = new ReentrantLock(); + private Condition nextCondition = lock.newCondition(); + private Timer timer = new Timer(true); + private long reloadInterval = 10 * 1000L; // 10秒 + private CanalParseException exception = null; public BinLogFileQueue(String directory){ this(new File(directory)); @@ -52,9 +53,24 @@ public class BinLogFileQueue { timer.scheduleAtFixedRate(new TimerTask() { public void run() { - List files = listBinlogFiles(); - for (File file : files) { - offer(file); + try { + // File errorFile = new File(BinLogFileQueue.this.directory, + // errorFileName); + // if (errorFile.isFile() && errorFile.exists()) { + // String text = StringUtils.join(IOUtils.readLines(new + // FileInputStream(errorFile)), "\n"); + // exception = new CanalParseException(text); + // } + List files = listBinlogFiles(); + for (File file : files) { + offer(file); + } + } catch (Throwable e) { + exception = new CanalParseException(e); + } + + if (exception != null) { + offer(null); } } }, reloadInterval, reloadInterval); @@ -69,6 +85,10 @@ public class BinLogFileQueue { public File getNextFile(File pre) { try { lock.lockInterruptibly(); + if (exception != null) { + throw exception; + } + if (binlogs.size() == 0) { return null; } else { @@ -94,6 +114,10 @@ public class BinLogFileQueue { public File getBefore(File file) { try { lock.lockInterruptibly(); + if (exception != null) { + throw exception; + } + if (binlogs.size() == 0) { return null; } else { @@ -130,6 +154,9 @@ public class BinLogFileQueue { nextCondition.await();// 等待新文件 } + if (exception != null) { + throw exception; + } if (pre == null) {// 第一次 return binlogs.get(0); } else { @@ -170,13 +197,16 @@ public class BinLogFileQueue { private boolean offer(File file) { try { lock.lockInterruptibly(); - if (!binlogs.contains(file)) { - binlogs.add(file); - nextCondition.signalAll();// 唤醒 - return true; - } else { - return false; + if (file != null) { + if (!binlogs.contains(file)) { + binlogs.add(file); + nextCondition.signalAll();// 唤醒 + return true; + } } + + nextCondition.signalAll();// 唤醒 + return false; } catch (InterruptedException e) { Thread.currentThread().interrupt(); return false; diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/BinlogDownloadQueue.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/BinlogDownloadQueue.java new file mode 100644 index 00000000..b90b89d5 --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/BinlogDownloadQueue.java @@ -0,0 +1,351 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds; + +import io.netty.handler.codec.http.HttpResponseStatus; + +import java.io.BufferedOutputStream; +import java.io.File; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.security.cert.CertificateException; +import java.security.cert.X509Certificate; +import java.util.Collections; +import java.util.Comparator; +import java.util.Iterator; +import java.util.LinkedList; +import java.util.List; +import java.util.concurrent.LinkedBlockingQueue; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.locks.LockSupport; + +import javax.net.ssl.SSLContext; + +import org.apache.commons.compress.archivers.tar.TarArchiveEntry; +import org.apache.commons.compress.archivers.tar.TarArchiveInputStream; +import org.apache.commons.io.FileUtils; +import org.apache.commons.io.IOUtils; +import org.apache.commons.lang.StringUtils; +import org.apache.http.HttpResponse; +import org.apache.http.client.config.RequestConfig; +import org.apache.http.client.methods.HttpGet; +import org.apache.http.config.RegistryBuilder; +import org.apache.http.conn.socket.ConnectionSocketFactory; +import org.apache.http.conn.socket.PlainConnectionSocketFactory; +import org.apache.http.conn.ssl.NoopHostnameVerifier; +import org.apache.http.conn.ssl.SSLConnectionSocketFactory; +import org.apache.http.impl.client.CloseableHttpClient; +import org.apache.http.impl.client.HttpClientBuilder; +import org.apache.http.impl.conn.PoolingHttpClientConnectionManager; +import org.apache.http.ssl.SSLContextBuilder; +import org.apache.http.ssl.TrustStrategy; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.parse.exception.CanalParseException; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.BinlogFile; + +/** + * @author chengjin.lyf on 2018/8/7 下午3:10 + * @since 1.0.25 + */ +public class BinlogDownloadQueue { + + private static final Logger logger = LoggerFactory.getLogger(BinlogDownloadQueue.class); + private static final int TIMEOUT = 10000; + + private LinkedBlockingQueue downloadQueue = new LinkedBlockingQueue(); + private LinkedBlockingQueue taskQueue = new LinkedBlockingQueue(); + private LinkedList binlogList; + private final int batchFileSize; + private Thread downloadThread; + public boolean running = true; + private final String destDir; + private String hostId; + private int currentSize; + private String lastDownload; + + public BinlogDownloadQueue(List downloadQueue, int batchFileSize, String destDir) throws IOException{ + this.binlogList = new LinkedList(downloadQueue); + this.batchFileSize = batchFileSize; + this.destDir = destDir; + this.currentSize = 0; + prepareBinlogList(); + cleanDir(); + } + + private void prepareBinlogList() { + for (BinlogFile binlog : this.binlogList) { + String fileName = StringUtils.substringBetween(binlog.getDownloadLink(), "mysql-bin.", "?"); + binlog.setFileName(fileName); + } + Collections.sort(this.binlogList, new Comparator() { + + @Override + public int compare(BinlogFile o1, BinlogFile o2) { + return o1.getFileName().compareTo(o2.getFileName()); + } + }); + } + + public void cleanDir() throws IOException { + File destDirFile = new File(destDir); + FileUtils.forceMkdir(destDirFile); + FileUtils.cleanDirectory(destDirFile); + } + + public void silenceDownload() { + if (downloadThread != null) { + return; + } + downloadThread = new Thread(new DownloadThread(), "download-" + destDir); + downloadThread.setDaemon(true); + downloadThread.start(); + } + + public BinlogFile tryOne() throws Throwable { + BinlogFile binlogFile = binlogList.poll(); + if (binlogFile == null) { + throw new CanalParseException("download binlog is null"); + } + download(binlogFile); + hostId = binlogFile.getHostInstanceID(); + this.currentSize++; + return binlogFile; + } + + public void notifyNotMatch() { + this.currentSize--; + filter(hostId); + } + + private void filter(String hostInstanceId) { + Iterator it = binlogList.iterator(); + while (it.hasNext()) { + BinlogFile bf = it.next(); + if (bf.getHostInstanceID().equalsIgnoreCase(hostInstanceId)) { + it.remove(); + } else { + hostId = bf.getHostInstanceID(); + } + } + } + + public boolean isLastFile(String fileName) { + String needCompareName = lastDownload; + if (StringUtils.isNotEmpty(needCompareName) && StringUtils.endsWith(needCompareName, "tar")) { + needCompareName = needCompareName.substring(0, needCompareName.indexOf(".")); + } + return (needCompareName == null || fileName.equalsIgnoreCase(needCompareName)) && binlogList.isEmpty(); + } + + public void prepare() throws InterruptedException { + for (int i = this.currentSize; i < batchFileSize && !binlogList.isEmpty(); i++) { + BinlogFile binlogFile = null; + while (!binlogList.isEmpty()) { + binlogFile = binlogList.poll(); + if (!binlogFile.getHostInstanceID().equalsIgnoreCase(hostId)) { + continue; + } + break; + } + if (binlogFile == null) { + break; + } + this.downloadQueue.put(binlogFile); + this.lastDownload = "mysql-bin." + binlogFile.getFileName(); + this.currentSize++; + } + } + + public void downOne() { + this.currentSize--; + } + + public void release() { + running = false; + this.currentSize = 0; + binlogList.clear(); + downloadQueue.clear(); + try { + downloadThread.interrupt(); + downloadThread.join();// 等待其结束 + } catch (InterruptedException e) { + // ignore + } finally { + downloadThread = null; + } + } + + private void download(BinlogFile binlogFile) throws Throwable { + String downloadLink = binlogFile.getDownloadLink(); + String fileName = binlogFile.getFileName(); + + downloadLink = downloadLink.trim(); + CloseableHttpClient httpClient = null; + if (downloadLink.startsWith("https")) { + HttpClientBuilder builder = HttpClientBuilder.create(); + builder.setMaxConnPerRoute(50); + builder.setMaxConnTotal(100); + // 创建支持忽略证书的https + final SSLContext sslContext = new SSLContextBuilder().loadTrustMaterial(null, new TrustStrategy() { + + @Override + public boolean isTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException { + return true; + } + }).build(); + + httpClient = HttpClientBuilder.create() + .setSSLContext(sslContext) + .setConnectionManager(new PoolingHttpClientConnectionManager(RegistryBuilder. create() + .register("http", PlainConnectionSocketFactory.INSTANCE) + .register("https", new SSLConnectionSocketFactory(sslContext, NoopHostnameVerifier.INSTANCE)) + .build())) + .build(); + } else { + httpClient = HttpClientBuilder.create().setMaxConnPerRoute(50).setMaxConnTotal(100).build(); + } + + HttpGet httpGet = new HttpGet(downloadLink); + RequestConfig requestConfig = RequestConfig.custom() + .setConnectTimeout(TIMEOUT) + .setConnectionRequestTimeout(TIMEOUT) + .setSocketTimeout(TIMEOUT) + .build(); + httpGet.setConfig(requestConfig); + HttpResponse response = httpClient.execute(httpGet); + int statusCode = response.getStatusLine().getStatusCode(); + if (statusCode != HttpResponseStatus.OK.code()) { + throw new RuntimeException("download failed , url:" + downloadLink + " , statusCode:" + statusCode); + } + saveFile(new File(destDir), "mysql-bin." + fileName, response); + } + + private static void saveFile(File parentFile, String fileName, HttpResponse response) throws IOException { + InputStream is = response.getEntity().getContent(); + long totalSize = Long.parseLong(response.getFirstHeader("Content-Length").getValue()); + if (response.getFirstHeader("Content-Disposition") != null) { + fileName = response.getFirstHeader("Content-Disposition").getValue(); + fileName = StringUtils.substringAfter(fileName, "filename="); + } + boolean isTar = StringUtils.endsWith(fileName, ".tar"); + FileUtils.forceMkdir(parentFile); + FileOutputStream fos = null; + try { + if (isTar) { + TarArchiveInputStream tais = new TarArchiveInputStream(is); + TarArchiveEntry tarArchiveEntry = null; + while ((tarArchiveEntry = tais.getNextTarEntry()) != null) { + String name = tarArchiveEntry.getName(); + File tarFile = new File(parentFile, name + ".tmp"); + logger.info("start to download file " + tarFile.getName()); + if (tarFile.exists()) { + tarFile.delete(); + } + BufferedOutputStream bos = null; + try { + bos = new BufferedOutputStream(new FileOutputStream(tarFile)); + int read = -1; + byte[] buffer = new byte[1024]; + while ((read = tais.read(buffer)) != -1) { + bos.write(buffer, 0, read); + } + logger.info("download file " + tarFile.getName() + " end!"); + tarFile.renameTo(new File(parentFile, name)); + } finally { + IOUtils.closeQuietly(bos); + } + } + tais.close(); + } else { + File file = new File(parentFile, fileName + ".tmp"); + if (file.exists()) { + file.delete(); + } + + if (!file.isFile()) { + file.createNewFile(); + } + try { + fos = new FileOutputStream(file); + byte[] buffer = new byte[1024]; + int len; + long copySize = 0; + long nextPrintProgress = 0; + logger.info("start to download file " + file.getName()); + while ((len = is.read(buffer)) != -1) { + fos.write(buffer, 0, len); + copySize += len; + long progress = copySize * 100 / totalSize; + if (progress >= nextPrintProgress) { + logger.info("download " + file.getName() + " progress : " + progress + + "% , download size : " + copySize + ", total size : " + totalSize); + nextPrintProgress += 10; + } + } + logger.info("download file " + file.getName() + " end!"); + fos.flush(); + } finally { + IOUtils.closeQuietly(fos); + } + file.renameTo(new File(parentFile, fileName)); + } + } finally { + IOUtils.closeQuietly(fos); + } + } + + public void execute(Runnable runnable) throws InterruptedException { + taskQueue.put(runnable); + } + + private class DownloadThread implements Runnable { + + @Override + public void run() { + while (running) { + BinlogFile binlogFile = null; + try { + binlogFile = downloadQueue.poll(5000, TimeUnit.MILLISECONDS); + if (binlogFile != null) { + int retry = 1; + while (true) { + try { + download(binlogFile); + break; + } catch (Throwable e) { + if (retry % 10 == 0) { + retry = retry + 1; + try { + logger.warn("download failed + " + binlogFile.toString() + "], retry : " + + retry, e); + // File errorFile = new File(destDir, + // "error.txt"); + // FileWriter writer = new + // FileWriter(errorFile); + // writer.write(ExceptionUtils.getFullStackTrace(e)); + // writer.flush(); + // IOUtils.closeQuietly(writer); + LockSupport.parkNanos(TimeUnit.MILLISECONDS.toNanos(100 * retry)); + } catch (Throwable e1) { + logger.error("write error failed", e1); + } + } else { + retry = retry + 1; + } + } + } + } + + Runnable runnable = taskQueue.poll(5000, TimeUnit.MILLISECONDS); + if (runnable != null) { + runnable.run(); + } + } catch (Throwable e) { + logger.error("task process failed", e); + } + } + + } + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/HttpHelper.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/HttpHelper.java index 7b641ade..9ed865fe 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/HttpHelper.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/HttpHelper.java @@ -155,6 +155,7 @@ public class HttpHelper { .register("https", new SSLConnectionSocketFactory(sslContext, NoopHostnameVerifier.INSTANCE)) .build())) .build(); + // ---------------- 创建支持https 的client成功--------- URI uri = new URIBuilder(url).build(); diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsBinlogEventParserProxy.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsBinlogEventParserProxy.java new file mode 100644 index 00000000..f3a220b0 --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsBinlogEventParserProxy.java @@ -0,0 +1,177 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds; + +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.ThreadFactory; + +import org.apache.commons.lang.StringUtils; + +import com.alibaba.otter.canal.parse.exception.PositionNotFoundException; +import com.alibaba.otter.canal.parse.inbound.ParserExceptionHandler; +import com.alibaba.otter.canal.parse.inbound.mysql.MysqlEventParser; + +/** + * aliyun rds的binlog parser支持 + * + *
      + * 注意点:aliyun的binlog会有定期清理并备份到oss上, 这里实现了一份自动下载oss+rds binlog的机制
      + * 
      + * + * @author chengjin.lyf on 2018/7/20 上午10:52 + * @since 1.0.25 + */ +public class RdsBinlogEventParserProxy extends MysqlEventParser { + + private String rdsOpenApiUrl = "https://rds.aliyuncs.com/"; // openapi地址 + private String accesskey; // 云账号的ak + private String secretkey; // 云账号sk + private String instanceId; // rds实例id + private String directory; // binlog目录 + private int batchFileSize = 4; // 最多下载的binlog文件数量 + + private RdsLocalBinlogEventParser rdsLocalBinlogEventParser = null; + private ExecutorService executorService = Executors.newSingleThreadExecutor(new ThreadFactory() { + + @Override + public Thread newThread(Runnable r) { + Thread t = new Thread(r, + "rds-binlog-daemon-thread"); + t.setDaemon(true); + return t; + } + }); + + @Override + public void start() { + if (rdsLocalBinlogEventParser == null && StringUtils.isNotEmpty(accesskey) && StringUtils.isNotEmpty(secretkey) + && StringUtils.isNotEmpty(instanceId)) { + rdsLocalBinlogEventParser = new RdsLocalBinlogEventParser(); + // rds oss mode + setRdsOssMode(true); + final ParserExceptionHandler targetHandler = this.getParserExceptionHandler(); + if (directory == null) { + directory = System.getProperty("java.io.tmpdir", "/tmp") + "/" + destination; + } + rdsLocalBinlogEventParser.setLogPositionManager(this.getLogPositionManager()); + rdsLocalBinlogEventParser.setDestination(destination); + rdsLocalBinlogEventParser.setAlarmHandler(this.getAlarmHandler()); + rdsLocalBinlogEventParser.setConnectionCharset(this.connectionCharset); + rdsLocalBinlogEventParser.setConnectionCharsetNumber(this.connectionCharsetNumber); + rdsLocalBinlogEventParser.setEnableTsdb(this.enableTsdb); + rdsLocalBinlogEventParser.setEventBlackFilter(this.eventBlackFilter); + rdsLocalBinlogEventParser.setFilterQueryDcl(this.filterQueryDcl); + rdsLocalBinlogEventParser.setFilterQueryDdl(this.filterQueryDdl); + rdsLocalBinlogEventParser.setFilterQueryDml(this.filterQueryDml); + rdsLocalBinlogEventParser.setFilterRows(this.filterRows); + rdsLocalBinlogEventParser.setFilterTableError(this.filterTableError); + // rdsLocalBinlogEventParser.setIsGTIDMode(this.isGTIDMode); + rdsLocalBinlogEventParser.setMasterInfo(this.masterInfo); + rdsLocalBinlogEventParser.setEventFilter(this.eventFilter); + rdsLocalBinlogEventParser.setMasterPosition(this.masterPosition); + rdsLocalBinlogEventParser.setTransactionSize(this.transactionSize); + rdsLocalBinlogEventParser.setUrl(this.rdsOpenApiUrl); + rdsLocalBinlogEventParser.setAccesskey(this.accesskey); + rdsLocalBinlogEventParser.setSecretkey(this.secretkey); + rdsLocalBinlogEventParser.setInstanceId(this.instanceId); + rdsLocalBinlogEventParser.setEventSink(eventSink); + rdsLocalBinlogEventParser.setDirectory(directory); + rdsLocalBinlogEventParser.setBatchFileSize(batchFileSize); + rdsLocalBinlogEventParser.setParallel(this.parallel); + rdsLocalBinlogEventParser.setParallelBufferSize(this.parallelBufferSize); + rdsLocalBinlogEventParser.setParallelThreadSize(this.parallelThreadSize); + rdsLocalBinlogEventParser.setFinishListener(new RdsLocalBinlogEventParser.ParseFinishListener() { + + @Override + public void onFinish() { + executorService.execute(new Runnable() { + + @Override + public void run() { + rdsLocalBinlogEventParser.stop(); + RdsBinlogEventParserProxy.this.start(); + } + }); + + } + }); + this.setParserExceptionHandler(new ParserExceptionHandler() { + + @Override + public void handle(Throwable e) { + handleMysqlParserException(e); + if (targetHandler != null) { + targetHandler.handle(e); + } + } + }); + } + + super.start(); + } + + private void handleMysqlParserException(Throwable throwable) { + if (throwable instanceof PositionNotFoundException) { + logger.info("remove rds not found position, try download rds binlog!"); + executorService.execute(new Runnable() { + + @Override + public void run() { + try { + logger.info("stop mysql parser!"); + RdsBinlogEventParserProxy rdsBinlogEventParserProxy = RdsBinlogEventParserProxy.this; + long serverId = rdsBinlogEventParserProxy.getServerId(); + rdsLocalBinlogEventParser.setServerId(serverId); + rdsBinlogEventParserProxy.stop(); + } catch (Throwable e) { + logger.info("handle exception failed", e); + } + + try { + logger.info("start rds mysql binlog parser!"); + rdsLocalBinlogEventParser.start(); + } catch (Throwable e) { + logger.info("handle exception failed", e); + rdsLocalBinlogEventParser.stop(); + RdsBinlogEventParserProxy rdsBinlogEventParserProxy = RdsBinlogEventParserProxy.this; + rdsBinlogEventParserProxy.start();// 继续重试 + } + } + }); + } + } + + @Override + public void stop() { + super.stop(); + } + + @Override + public boolean isStart() { + return super.isStart(); + } + + public void setRdsOpenApiUrl(String rdsOpenApiUrl) { + this.rdsOpenApiUrl = rdsOpenApiUrl; + } + + public void setAccesskey(String accesskey) { + this.accesskey = accesskey; + } + + public void setSecretkey(String secretkey) { + this.secretkey = secretkey; + } + + public void setInstanceId(String instanceId) { + this.instanceId = instanceId; + } + + public void setDirectory(String directory) { + this.directory = directory; + } + + public void setBatchFileSize(int batchFileSize) { + this.batchFileSize = batchFileSize; + } + +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsBinlogOpenApi.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsBinlogOpenApi.java index eb638739..2e79c536 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsBinlogOpenApi.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsBinlogOpenApi.java @@ -1,46 +1,21 @@ package com.alibaba.otter.canal.parse.inbound.mysql.rds; -import io.netty.handler.codec.http.HttpResponseStatus; - -import java.io.BufferedOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.UnsupportedEncodingException; -import java.net.URLEncoder; -import java.text.SimpleDateFormat; +import java.net.URI; +import java.net.URISyntaxException; import java.util.Collections; import java.util.Date; -import java.util.HashMap; import java.util.List; -import java.util.Map; -import java.util.TimeZone; -import java.util.TreeMap; -import java.util.UUID; -import javax.crypto.Mac; -import javax.crypto.SecretKey; -import javax.crypto.spec.SecretKeySpec; - -import org.apache.commons.codec.binary.Base64; -import org.apache.commons.compress.archivers.tar.TarArchiveEntry; -import org.apache.commons.compress.archivers.tar.TarArchiveInputStream; -import org.apache.commons.io.FileUtils; -import org.apache.commons.io.IOUtils; import org.apache.commons.lang.StringUtils; -import org.apache.http.HttpResponse; -import org.apache.http.client.config.RequestConfig; -import org.apache.http.client.methods.HttpGet; -import org.apache.http.impl.client.CloseableHttpClient; -import org.apache.http.impl.client.HttpClientBuilder; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import com.alibaba.fastjson.JSON; -import com.alibaba.fastjson.JSONArray; -import com.alibaba.fastjson.JSONObject; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.BinlogFile; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.DescribeBinlogFileResult; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.RdsBackupPolicy; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.RdsItem; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.request.DescribeBackupPolicyRequest; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.request.DescribeBinlogFilesRequest; /** * @author agapple 2017年10月14日 下午1:53:52 @@ -48,287 +23,78 @@ import com.alibaba.fastjson.JSONObject; */ public class RdsBinlogOpenApi { - protected static final Logger logger = LoggerFactory.getLogger(RdsBinlogOpenApi.class); - private static final String ISO8601_DATE_FORMAT = "yyyy-MM-dd'T'HH:mm:ss'Z'"; - private static final int TIMEOUT = 10000; - private static final String ENCODING = "UTF-8"; - private static final String MAC_NAME = "HmacSHA1"; - private static final String API_VERSION = "2014-08-15"; - private static final String SIGNATURE_VERSION = "1.0"; + protected static final Logger logger = LoggerFactory.getLogger(RdsBinlogOpenApi.class); - public static void downloadBinlogFiles(String url, String ak, String sk, String dbInstanceId, Date startTime, - Date endTime, File destDir) throws Throwable { - int pageSize = 100; - int pageNumber = 0; - int pageRecordCount = 1; - String hostInstanceID = null; - while (pageRecordCount > 0 && pageRecordCount <= pageSize) { - pageNumber += 1; - String result = describeBinlogFiles(url, ak, sk, dbInstanceId, startTime, endTime, pageSize, pageNumber); - JSONObject jsobObj = JSON.parseObject(result); - pageRecordCount = jsobObj.getInteger("PageRecordCount"); - - if (pageRecordCount > 0) { - FileUtils.forceMkdir(destDir); - File hostIdFile = new File(destDir, "hostId"); - if (hostIdFile.exists()) { - List lines = IOUtils.readLines(new FileInputStream(hostIdFile)); - hostInstanceID = StringUtils.join(lines, "\n"); - } - - String itemStr = jsobObj.getString("Items"); - JSONObject binLogFileObj = JSONObject.parseObject(itemStr); - JSONArray items = binLogFileObj.getJSONArray("BinLogFile"); - if (items == null || items.isEmpty()) { - continue; - } - for (int i = 0; i < items.size(); i++) { - JSONObject item = (JSONObject) items.get(i); - String oneHostInstanceID = item.getString("HostInstanceID"); - if (hostInstanceID == null) { - hostInstanceID = oneHostInstanceID; - FileOutputStream hostIdFileOut = null; - try { - hostIdFileOut = new FileOutputStream(hostIdFile); - hostIdFileOut.write(oneHostInstanceID.getBytes()); - hostIdFileOut.flush(); - } finally { - IOUtils.closeQuietly(hostIdFileOut); - } - } - - if (hostInstanceID.equals(oneHostInstanceID)) { // 只选择一个host下载 - String downloadLink = item.getString("DownloadLink"); - String fileName = StringUtils.substringBetween(downloadLink, "mysql-bin.", ".tar"); - if (StringUtils.isNotEmpty(fileName)) { - File currentFile = new File(destDir, "mysql-bin." + fileName); - if (currentFile.isFile() && currentFile.exists()) { - // 检查一下文件是否存在,存在就就没必要下载了 - continue; - } - } - - HttpGet httpGet = new HttpGet(downloadLink); - CloseableHttpClient httpClient = HttpClientBuilder.create() - .setMaxConnPerRoute(50) - .setMaxConnTotal(100) - .build(); - RequestConfig requestConfig = RequestConfig.custom() - .setConnectTimeout(TIMEOUT) - .setConnectionRequestTimeout(TIMEOUT) - .setSocketTimeout(TIMEOUT) - .build(); - httpGet.setConfig(requestConfig); - HttpResponse response = httpClient.execute(httpGet); - int statusCode = response.getStatusLine().getStatusCode(); - if (statusCode != HttpResponseStatus.OK.code()) { - throw new RuntimeException("download failed , url:" + downloadLink + " , statusCode:" - + statusCode); - } - saveFile(destDir, response); - } - } + public static List listBinlogFiles(String url, String ak, String sk, String dbInstanceId, + Date startTime, Date endTime) { + DescribeBinlogFilesRequest request = new DescribeBinlogFilesRequest(); + if (StringUtils.isNotEmpty(url)) { + try { + URI uri = new URI(url); + request.setEndPoint(uri.getHost()); + } catch (URISyntaxException e) { + logger.error("resolve url host failed, will use default rds endpoint!"); } } - } - - private static void saveFile(File parentFile, HttpResponse response) throws IOException { - InputStream is = response.getEntity().getContent(); - long totalSize = Long.parseLong(response.getFirstHeader("Content-Length").getValue()); - String fileName = response.getFirstHeader("Content-Disposition").getValue(); - fileName = StringUtils.substringAfter(fileName, "filename="); - boolean isTar = StringUtils.endsWith(fileName, ".tar"); - FileUtils.forceMkdir(parentFile); - FileOutputStream fos = null; - try { - if (isTar) { - TarArchiveInputStream tais = new TarArchiveInputStream(is); - TarArchiveEntry tarArchiveEntry = null; - while ((tarArchiveEntry = tais.getNextTarEntry()) != null) { - String name = tarArchiveEntry.getName(); - File tarFile = new File(parentFile, name); - logger.info("start to download file " + tarFile.getName()); - BufferedOutputStream bos = null; - try { - bos = new BufferedOutputStream(new FileOutputStream(tarFile)); - int read = -1; - byte[] buffer = new byte[1024]; - while ((read = tais.read(buffer)) != -1) { - bos.write(buffer, 0, read); - } - logger.info("download file " + tarFile.getName() + " end!"); - } finally { - IOUtils.closeQuietly(bos); - } - } - tais.close(); - } else { - File file = new File(parentFile, fileName); - if (!file.isFile()) { - file.createNewFile(); + request.setStartDate(startTime); + request.setEndDate(endTime); + request.setPageNumber(1); + request.setPageSize(100); + request.setRdsInstanceId(dbInstanceId); + request.setAccessKeyId(ak); + request.setAccessKeySecret(sk); + DescribeBinlogFileResult result = null; + int retryTime = 3; + while (true) { + try { + result = request.doAction(); + break; + } catch (Exception e) { + if (retryTime-- <= 0) { + throw new RuntimeException(e); } try { - fos = new FileOutputStream(file); - byte[] buffer = new byte[1024]; - int len; - long copySize = 0; - long nextPrintProgress = 0; - logger.info("start to download file " + file.getName()); - while ((len = is.read(buffer)) != -1) { - fos.write(buffer, 0, len); - copySize += len; - long progress = copySize * 100 / totalSize; - if (progress >= nextPrintProgress) { - logger.info("download " + file.getName() + " progress : " + progress - + "% , download size : " + copySize + ", total size : " + totalSize); - nextPrintProgress += 10; - } - } - logger.info("download file " + file.getName() + " end!"); - fos.flush(); - } finally { - IOUtils.closeQuietly(fos); + Thread.sleep(100L); + } catch (InterruptedException e1) { } } - } finally { - IOUtils.closeQuietly(fos); } - } - - public static String describeBinlogFiles(String url, String ak, String sk, String dbInstanceId, Date startTime, - Date endTime, int pageSize, int pageNumber) throws Exception { - Map paramMap = new HashMap(); - paramMap.put("Action", "DescribeBinlogFiles"); - paramMap.put("DBInstanceId", dbInstanceId); // rds实例id - paramMap.put("StartTime", formatIso8601Date(startTime)); - paramMap.put("EndTime", formatIso8601Date(endTime)); - paramMap.put("PageSize", String.valueOf(pageSize)); - paramMap.put("PageNumber", String.valueOf(pageNumber)); - return doRequest(url, paramMap, ak, sk); - } - - private static String doRequest(String domin, Map param, String ak, String sk) throws Exception { - param.put("AccessKeyId", ak); - param.put("SignatureMethod", "HMAC-SHA1"); - param.put("SignatureVersion", SIGNATURE_VERSION); - param.put("Version", API_VERSION); - param.put("SignatureNonce", UUID.randomUUID().toString()); - param.put("Format", "JSON"); - param.put("Timestamp", formatIso8601Date(new Date())); - String signStr = generate("POST", param, sk); - param.put("Signature", signStr); - String request = concatQueryString(param); - String url = domin + "?" + request; - String result = HttpHelper.post(url, null, Collections.EMPTY_MAP, TIMEOUT); - return result; - } - - public static String concatQueryString(Map parameters) throws UnsupportedEncodingException { - if (null == parameters) { - return null; + if (result == null) { + return Collections.EMPTY_LIST; } - StringBuilder urlBuilder = new StringBuilder(""); - for (Map.Entry entry : parameters.entrySet()) { - String key = entry.getKey(); - String val = entry.getValue(); - urlBuilder.append(encode(key)); - if (val != null) { - urlBuilder.append("=").append(encode(val)); + RdsItem rdsItem = result.getItems(); + if (rdsItem != null) { + return rdsItem.getBinLogFile(); + } + return Collections.EMPTY_LIST; + } + + public static RdsBackupPolicy queryBinlogBackupPolicy(String url, String ak, String sk, String dbInstanceId) { + DescribeBackupPolicyRequest request = new DescribeBackupPolicyRequest(); + if (StringUtils.isNotEmpty(url)) { + try { + URI uri = new URI(url); + request.setEndPoint(uri.getHost()); + } catch (URISyntaxException e) { + logger.error("resolve url host failed, will use default rds endpoint!"); } - urlBuilder.append("&"); } - int strIndex = urlBuilder.length(); - if (parameters.size() > 0) { - urlBuilder.deleteCharAt(strIndex - 1); - } - return urlBuilder.toString(); - } - - public static String encode(String value) throws UnsupportedEncodingException { - return URLEncoder.encode(value, "UTF-8"); - } - - private static String formatIso8601Date(Date date) { - SimpleDateFormat df = new SimpleDateFormat(ISO8601_DATE_FORMAT); - df.setTimeZone(TimeZone.getTimeZone("GMT")); - return df.format(date); - } - - /** - * 使用 HMAC-SHA1 签名方法对对encryptText进行签名 - * - * @param encryptText 被签名的字符串 - * @param encryptKey 密钥 - * @return - * @throws Exception - */ - public static byte[] HmacSHA1Encrypt(String encryptText, String encryptKey) throws Exception { - byte[] data = encryptKey.getBytes(ENCODING); - // 根据给定的字节数组构造一个密钥,第二参数指定一个密钥算法的名称 - SecretKey secretKey = new SecretKeySpec(data, MAC_NAME); - // 生成一个指定 Mac 算法 的 Mac 对象 - Mac mac = Mac.getInstance(MAC_NAME); - // 用给定密钥初始化 Mac 对象 - mac.init(secretKey); - - byte[] text = encryptText.getBytes(ENCODING); - // 完成 Mac 操作 - return mac.doFinal(text); - } - - private static String base64(byte input[]) throws UnsupportedEncodingException { - return new String(Base64.encodeBase64(input), ENCODING); - } - - /** 对参数名称和参数值进行URL编码 **/ - public static String generate(String method, Map parameter, String accessKeySecret) - throws Exception { - String signString = generateSignString(method, parameter); - byte[] signBytes = HmacSHA1Encrypt(signString, accessKeySecret + "&"); - String signature = base64(signBytes); - if ("POST".equals(method)) { - return signature; - } - return URLEncoder.encode(signature, "UTF-8"); - } - - private static String generateQueryString(TreeMap treeMap) { - StringBuilder canonicalizedQueryString = new StringBuilder(); - boolean first = true; - for (String key : treeMap.navigableKeySet()) { - String value = treeMap.get(key); - if (!first) { - canonicalizedQueryString.append("&"); + request.setRdsInstanceId(dbInstanceId); + request.setAccessKeyId(ak); + request.setAccessKeySecret(sk); + int retryTime = 3; + while (true) { + try { + return request.doAction(); + } catch (Exception e) { + if (retryTime-- <= 0) { + throw new RuntimeException(e); + } + try { + Thread.sleep(100L); + } catch (InterruptedException e1) { + } } - first = false; - canonicalizedQueryString.append(percentEncode(key)).append("=").append(percentEncode(value)); } - return canonicalizedQueryString.toString(); - } - - public static String generateSignString(String httpMethod, Map parameter) throws IOException { - TreeMap sortParameter = new TreeMap(); - sortParameter.putAll(parameter); - String canonicalizedQueryString = generateQueryString(sortParameter); - if (null == httpMethod) { - throw new RuntimeException("httpMethod can not be empty"); - } - /** 构造待签名的字符串* */ - StringBuilder stringToSign = new StringBuilder(); - stringToSign.append(httpMethod).append("&"); - stringToSign.append(percentEncode("/")).append("&"); - stringToSign.append(percentEncode(canonicalizedQueryString)); - return stringToSign.toString(); - } - - public static String percentEncode(String value) { - try { - return value == null ? null : URLEncoder.encode(value, ENCODING) - .replaceAll("\\+", "%20") - .replaceAll("\\*", "%2A") - .replaceAll("%7E", "~"); - } catch (Exception e) { - } - return ""; } } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsLocalBinlogEventParser.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsLocalBinlogEventParser.java index 68be38e5..2e0960fe 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsLocalBinlogEventParser.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/RdsLocalBinlogEventParser.java @@ -2,14 +2,23 @@ package com.alibaba.otter.canal.parse.inbound.mysql.rds; import java.io.File; import java.util.Date; +import java.util.List; import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang.math.NumberUtils; import org.springframework.util.Assert; import com.alibaba.otter.canal.parse.CanalEventParser; import com.alibaba.otter.canal.parse.exception.CanalParseException; +import com.alibaba.otter.canal.parse.exception.PositionNotFoundException; +import com.alibaba.otter.canal.parse.exception.ServerIdNotMatchException; +import com.alibaba.otter.canal.parse.inbound.ErosaConnection; +import com.alibaba.otter.canal.parse.inbound.ParserExceptionHandler; +import com.alibaba.otter.canal.parse.inbound.mysql.LocalBinLogConnection; import com.alibaba.otter.canal.parse.inbound.mysql.LocalBinlogEventParser; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.BinlogFile; import com.alibaba.otter.canal.protocol.position.EntryPosition; +import com.alibaba.otter.canal.protocol.position.LogPosition; /** * 基于rds binlog备份文件的复制 @@ -17,47 +26,112 @@ import com.alibaba.otter.canal.protocol.position.EntryPosition; * @author agapple 2017年10月15日 下午1:27:36 * @since 1.0.25 */ -public class RdsLocalBinlogEventParser extends LocalBinlogEventParser implements CanalEventParser { +public class RdsLocalBinlogEventParser extends LocalBinlogEventParser implements CanalEventParser, LocalBinLogConnection.FileParserListener { - private String url = "https://rds.aliyuncs.com/"; // openapi地址 - private String accesskey; // 云账号的ak - private String secretkey; // 云账号sk - private String instanceId; // rds实例id - private Long startTime; - private Long endTime; + private String url; // openapi地址 + private String accesskey; // 云账号的ak + private String secretkey; // 云账号sk + private String instanceId; // rds实例id + private Long startTime; + private Long endTime; + private BinlogDownloadQueue binlogDownloadQueue; + private ParseFinishListener finishListener; + private int batchFileSize; public RdsLocalBinlogEventParser(){ } public void start() throws CanalParseException { try { - Assert.notNull(startTime); Assert.notNull(accesskey); Assert.notNull(secretkey); Assert.notNull(instanceId); Assert.notNull(url); + Assert.notNull(directory); + if (endTime == null) { endTime = System.currentTimeMillis(); } - RdsBinlogOpenApi.downloadBinlogFiles(url, + EntryPosition entryPosition = findStartPosition(null); + if (entryPosition == null) { + throw new PositionNotFoundException("position not found!"); + } + Long startTimeInMill = entryPosition.getTimestamp(); + if (startTimeInMill == null || startTimeInMill <= 0) { + throw new PositionNotFoundException("position timestamp is empty!"); + } + + startTime = startTimeInMill; + List binlogFiles = RdsBinlogOpenApi.listBinlogFiles(url, accesskey, secretkey, instanceId, new Date(startTime), - new Date(endTime), - new File(directory)); + new Date(endTime)); + if (binlogFiles.isEmpty()) { + throw new CanalParseException("start timestamp : " + startTimeInMill + " binlog files is empty"); + } - // 更新一下时间戳 - masterPosition = new EntryPosition(startTime); + binlogDownloadQueue = new BinlogDownloadQueue(binlogFiles, batchFileSize, directory); + binlogDownloadQueue.silenceDownload(); + needWait = true; + // try to download one file,use to test server id + binlogDownloadQueue.tryOne(); } catch (Throwable e) { logger.error("download binlog failed", e); throw new CanalParseException(e); } + setParserExceptionHandler(new ParserExceptionHandler() { + @Override + public void handle(Throwable e) { + handleMysqlParserException(e); + } + }); super.start(); } + private void handleMysqlParserException(Throwable throwable) { + if (throwable instanceof ServerIdNotMatchException) { + logger.error("server id not match, try download another rds binlog!"); + binlogDownloadQueue.notifyNotMatch(); + try { + binlogDownloadQueue.cleanDir(); + binlogDownloadQueue.tryOne(); + binlogDownloadQueue.prepare(); + } catch (Throwable e) { + throw new RuntimeException(e); + } + + try { + binlogDownloadQueue.execute(new Runnable() { + + @Override + public void run() { + RdsLocalBinlogEventParser.super.stop(); + RdsLocalBinlogEventParser.super.start(); + } + }); + } catch (InterruptedException e) { + throw new RuntimeException(e); + } + + } + } + + @Override + protected ErosaConnection buildErosaConnection() { + ErosaConnection connection = super.buildErosaConnection(); + if (connection instanceof LocalBinLogConnection) { + LocalBinLogConnection localBinLogConnection = (LocalBinLogConnection) connection; + localBinLogConnection.setNeedWait(true); + localBinLogConnection.setServerId(serverId); + localBinLogConnection.setParserListener(this); + } + return connection; + } + public String getUrl() { return url; } @@ -68,44 +142,87 @@ public class RdsLocalBinlogEventParser extends LocalBinlogEventParser implements } } - public String getAccesskey() { - return accesskey; - } - public void setAccesskey(String accesskey) { this.accesskey = accesskey; } - public String getSecretkey() { - return secretkey; - } - public void setSecretkey(String secretkey) { this.secretkey = secretkey; } - public String getInstanceId() { - return instanceId; - } - public void setInstanceId(String instanceId) { this.instanceId = instanceId; } - public Long getStartTime() { - return startTime; - } - public void setStartTime(Long startTime) { this.startTime = startTime; } - public Long getEndTime() { - return endTime; - } - public void setEndTime(Long endTime) { this.endTime = endTime; } + @Override + public void onFinish(String fileName) { + try { + binlogDownloadQueue.downOne(); + File needDeleteFile = new File(directory + File.separator + fileName); + if (needDeleteFile.exists()) { + needDeleteFile.delete(); + } + // 处理下logManager位点问题 + LogPosition logPosition = logPositionManager.getLatestIndexBy(destination); + Long timestamp = 0L; + if (logPosition != null && logPosition.getPostion() != null) { + timestamp = logPosition.getPostion().getTimestamp(); + EntryPosition position = logPosition.getPostion(); + LogPosition newLogPosition = new LogPosition(); + String journalName = position.getJournalName(); + int sepIdx = journalName.indexOf("."); + String fileIndex = journalName.substring(sepIdx + 1); + int index = NumberUtils.toInt(fileIndex) + 1; + String newJournalName = journalName.substring(0, sepIdx) + "." + + StringUtils.leftPad(String.valueOf(index), fileIndex.length(), "0"); + newLogPosition.setPostion(new EntryPosition(newJournalName, + 4L, + position.getTimestamp(), + position.getServerId())); + newLogPosition.setIdentity(logPosition.getIdentity()); + logPositionManager.persistLogPosition(destination, newLogPosition); + } + + if (binlogDownloadQueue.isLastFile(fileName)) { + logger.warn("last file : " + fileName + " , timestamp : " + timestamp + + " , all file parse complete, switch to mysql parser!"); + finishListener.onFinish(); + return; + } else { + logger.warn("parse local binlog file : " + fileName + " , timestamp : " + timestamp + + " , try the next binlog !"); + } + binlogDownloadQueue.prepare(); + } catch (Exception e) { + logger.error("prepare download binlog file failed!", e); + throw new RuntimeException(e); + } + } + + @Override + public void stop() { + this.binlogDownloadQueue.release(); + super.stop(); + } + + public void setFinishListener(ParseFinishListener finishListener) { + this.finishListener = finishListener; + } + + public interface ParseFinishListener { + + void onFinish(); + } + + public void setBatchFileSize(int batchFileSize) { + this.batchFileSize = batchFileSize; + } } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/BinlogFile.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/BinlogFile.java new file mode 100644 index 00000000..bee87521 --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/BinlogFile.java @@ -0,0 +1,80 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds.data; + +/** + * @author chengjin.lyf on 2018/8/7 下午2:26 + * @since 1.0.25 + */ +public class BinlogFile { + + private Long FileSize; + private String LogBeginTime; + private String LogEndTime; + private String DownloadLink; + private String HostInstanceID; + private String LinkExpiredTime; + private String fileName; + + public Long getFileSize() { + return FileSize; + } + + public void setFileSize(Long fileSize) { + FileSize = fileSize; + } + + public String getLogBeginTime() { + return LogBeginTime; + } + + public void setLogBeginTime(String logBeginTime) { + LogBeginTime = logBeginTime; + } + + public String getLogEndTime() { + return LogEndTime; + } + + public void setLogEndTime(String logEndTime) { + LogEndTime = logEndTime; + } + + public String getDownloadLink() { + return DownloadLink; + } + + public void setDownloadLink(String downloadLink) { + DownloadLink = downloadLink; + } + + public String getHostInstanceID() { + return HostInstanceID; + } + + public void setHostInstanceID(String hostInstanceID) { + HostInstanceID = hostInstanceID; + } + + public String getLinkExpiredTime() { + return LinkExpiredTime; + } + + public void setLinkExpiredTime(String linkExpiredTime) { + LinkExpiredTime = linkExpiredTime; + } + + public String getFileName() { + return fileName; + } + + public void setFileName(String fileName) { + this.fileName = fileName; + } + + @Override + public String toString() { + return "BinlogFile [FileSize=" + FileSize + ", LogBeginTime=" + LogBeginTime + ", LogEndTime=" + LogEndTime + + ", DownloadLink=" + DownloadLink + ", HostInstanceID=" + HostInstanceID + ", LinkExpiredTime=" + + LinkExpiredTime + ", fileName=" + fileName + "]"; + } + +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/DescribeBinlogFileResult.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/DescribeBinlogFileResult.java new file mode 100644 index 00000000..d5b6820d --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/DescribeBinlogFileResult.java @@ -0,0 +1,63 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds.data; + +/** + * @author chengjin.lyf on 2018/8/7 下午2:26 + * @since 1.0.25 + */ +public class DescribeBinlogFileResult { + + private RdsItem Items; + private long PageNumber; + private long TotalRecordCount; + private long TotalFileSize; + private String RequestId; + private long PageRecordCount; + + public RdsItem getItems() { + return Items; + } + + public void setItems(RdsItem items) { + Items = items; + } + + public long getPageNumber() { + return PageNumber; + } + + public void setPageNumber(long pageNumber) { + PageNumber = pageNumber; + } + + public long getTotalRecordCount() { + return TotalRecordCount; + } + + public void setTotalRecordCount(long totalRecordCount) { + TotalRecordCount = totalRecordCount; + } + + public long getTotalFileSize() { + return TotalFileSize; + } + + public void setTotalFileSize(long totalFileSize) { + TotalFileSize = totalFileSize; + } + + public String getRequestId() { + return RequestId; + } + + public void setRequestId(String requestId) { + RequestId = requestId; + } + + public long getPageRecordCount() { + return PageRecordCount; + } + + public void setPageRecordCount(long pageRecordCount) { + PageRecordCount = pageRecordCount; + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/RdsBackupPolicy.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/RdsBackupPolicy.java new file mode 100644 index 00000000..e007671a --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/RdsBackupPolicy.java @@ -0,0 +1,78 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds.data; + +/** + * @author chengjin.lyf on 2018/8/7 下午2:26 + * @since 1.0.25 + */ +public class RdsBackupPolicy { + + /** + * 数据备份保留天数(7到730天)。 + */ + private String BackupRetentionPeriod; + /** + * 数据备份时间,格式:HH:mmZ- HH:mm Z。 + */ + private String PreferredBackupTime; + /** + * 数据备份周期。Monday:周一;Tuesday:周二;Wednesday:周三;Thursday:周四;Friday:周五;Saturday: + * 周六;Sunday:周日。 + */ + private String PreferredBackupPeriod; + /** + * 日志备份状态。Enable:开启;Disabled:关闭。 + */ + private boolean BackupLog; + /** + * 日志备份保留天数(7到730天)。 + */ + private int LogBackupRetentionPeriod; + + public String getBackupRetentionPeriod() { + return BackupRetentionPeriod; + } + + public void setBackupRetentionPeriod(String backupRetentionPeriod) { + BackupRetentionPeriod = backupRetentionPeriod; + } + + public String getPreferredBackupTime() { + return PreferredBackupTime; + } + + public void setPreferredBackupTime(String preferredBackupTime) { + PreferredBackupTime = preferredBackupTime; + } + + public String getPreferredBackupPeriod() { + return PreferredBackupPeriod; + } + + public void setPreferredBackupPeriod(String preferredBackupPeriod) { + PreferredBackupPeriod = preferredBackupPeriod; + } + + public boolean isBackupLog() { + return BackupLog; + } + + public void setBackupLog(boolean backupLog) { + BackupLog = backupLog; + } + + public int getLogBackupRetentionPeriod() { + return LogBackupRetentionPeriod; + } + + public void setLogBackupRetentionPeriod(int logBackupRetentionPeriod) { + LogBackupRetentionPeriod = logBackupRetentionPeriod; + } + + @Override + public String toString() { + return "RdsBackupPolicy [BackupRetentionPeriod=" + BackupRetentionPeriod + ", PreferredBackupTime=" + + PreferredBackupTime + ", PreferredBackupPeriod=" + PreferredBackupPeriod + ", BackupLog=" + BackupLog + + ", LogBackupRetentionPeriod=" + LogBackupRetentionPeriod + "]"; + } + +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/RdsItem.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/RdsItem.java new file mode 100644 index 00000000..81c484e3 --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/data/RdsItem.java @@ -0,0 +1,26 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds.data; + +import java.util.List; + +/** + * @author chengjin.lyf on 2018/8/7 下午2:26 + * @since 1.0.25 + */ +public class RdsItem { + + private List BinLogFile; + + public List getBinLogFile() { + return BinLogFile; + } + + public void setBinLogFile(List binLogFile) { + BinLogFile = binLogFile; + } + + @Override + public String toString() { + return "RdsItem [BinLogFile=" + BinLogFile + "]"; + } + +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/AbstractRequest.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/AbstractRequest.java new file mode 100644 index 00000000..f43523b5 --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/AbstractRequest.java @@ -0,0 +1,251 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds.request; + +import io.netty.handler.codec.http.HttpResponseStatus; + +import java.io.IOException; +import java.io.UnsupportedEncodingException; +import java.net.URLEncoder; +import java.security.cert.CertificateException; +import java.security.cert.X509Certificate; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.Map; +import java.util.TimeZone; +import java.util.TreeMap; +import java.util.UUID; +import java.util.concurrent.TimeUnit; + +import javax.crypto.Mac; +import javax.crypto.SecretKey; +import javax.crypto.spec.SecretKeySpec; +import javax.net.ssl.SSLContext; + +import org.apache.commons.codec.binary.Base64; +import org.apache.commons.lang.StringUtils; +import org.apache.http.HttpResponse; +import org.apache.http.HttpStatus; +import org.apache.http.client.config.RequestConfig; +import org.apache.http.client.methods.HttpGet; +import org.apache.http.config.Registry; +import org.apache.http.config.RegistryBuilder; +import org.apache.http.conn.HttpClientConnectionManager; +import org.apache.http.conn.socket.PlainConnectionSocketFactory; +import org.apache.http.conn.ssl.SSLConnectionSocketFactory; +import org.apache.http.conn.ssl.TrustStrategy; +import org.apache.http.impl.client.CloseableHttpClient; +import org.apache.http.impl.client.HttpClientBuilder; +import org.apache.http.impl.conn.PoolingHttpClientConnectionManager; +import org.apache.http.ssl.SSLContexts; +import org.apache.http.util.EntityUtils; + +/** + * @author chengjin.lyf on 2018/8/7 下午2:26 + * @since 1.0.25 + */ +public abstract class AbstractRequest { + + /** + * 要求的编码格式 + */ + private static final String ENCODING = "UTF-8"; + /** + * 要求的sign签名算法 + */ + private static final String MAC_NAME = "HmacSHA1"; + + private String accessKeyId; + + private String accessKeySecret; + + /** + * api 版本 + */ + private String version; + + private String endPoint = "rds.aliyuncs.com"; + + private String protocol = "http"; + + public void setProtocol(String protocol) { + this.protocol = protocol; + } + + private int timeout = (int) TimeUnit.MINUTES.toMillis(1); + + private Map treeMap = new TreeMap(); + + public void putQueryString(String name, String value) { + if (StringUtils.isBlank(name) || StringUtils.isBlank(value)) { + return; + } + treeMap.put(name, value); + } + + public void setVersion(String version) { + this.version = version; + } + + public void setEndPoint(String endPoint) { + this.endPoint = endPoint; + } + + public void setAccessKeyId(String accessKeyId) { + this.accessKeyId = accessKeyId; + } + + public void setAccessKeySecret(String accessKeySecret) { + this.accessKeySecret = accessKeySecret; + } + + /** + * 使用 HMAC-SHA1 签名方法对对encryptText进行签名 + * + * @param encryptText 被签名的字符串 + * @param encryptKey 密钥 + * @return + * @throws Exception + */ + private byte[] HmacSHA1Encrypt(String encryptText, String encryptKey) throws Exception { + byte[] data = encryptKey.getBytes(ENCODING); + // 根据给定的字节数组构造一个密钥,第二参数指定一个密钥算法的名称 + SecretKey secretKey = new SecretKeySpec(data, MAC_NAME); + // 生成一个指定 Mac 算法 的 Mac 对象 + Mac mac = Mac.getInstance(MAC_NAME); + // 用给定密钥初始化 Mac 对象 + mac.init(secretKey); + + byte[] text = encryptText.getBytes(ENCODING); + // 完成 Mac 操作 + return mac.doFinal(text); + } + + private String base64(byte input[]) throws UnsupportedEncodingException { + return new String(Base64.encodeBase64(input), ENCODING); + } + + private String concatQueryString(Map parameters) throws UnsupportedEncodingException { + if (null == parameters) { + return null; + } + StringBuilder urlBuilder = new StringBuilder(""); + for (Map.Entry entry : parameters.entrySet()) { + String key = entry.getKey(); + String val = entry.getValue(); + urlBuilder.append(encode(key)); + if (val != null) { + urlBuilder.append("=").append(encode(val)); + } + urlBuilder.append("&"); + } + int strIndex = urlBuilder.length(); + if (parameters.size() > 0) { + urlBuilder.deleteCharAt(strIndex - 1); + } + return urlBuilder.toString(); + } + + private String encode(String value) throws UnsupportedEncodingException { + return URLEncoder.encode(value, "UTF-8"); + } + + private String makeSignature(TreeMap paramMap) throws Exception { + String cqs = concatQueryString(paramMap); + cqs = encode(cqs); + cqs = cqs.replaceAll("\\+", "%20"); + cqs = cqs.replaceAll("\\*", "%2A"); + cqs = cqs.replaceAll("%7E", "~"); + StringBuilder stringBuilder = new StringBuilder(); + stringBuilder.append("GET").append("&").append(encode("/")).append("&").append(cqs); + return base64(HmacSHA1Encrypt(stringBuilder.toString(), accessKeySecret + "&")); + } + + public final String formatUTCTZ(Date date) { + SimpleDateFormat sdf = new SimpleDateFormat("YYYY-MM-dd'T'HH:mm:ss'Z'"); + sdf.setTimeZone(TimeZone.getTimeZone("UTC")); + return sdf.format(date); + } + + private void fillCommonParam(Map p) { + p.put("Format", "JSON"); + p.put("Version", version); + p.put("AccessKeyId", accessKeyId); + p.put("SignatureMethod", "HMAC-SHA1"); // 此处不能用变量 MAC_NAME + p.put("Timestamp", formatUTCTZ(new Date())); + p.put("SignatureVersion", "1.0"); + p.put("SignatureNonce", UUID.randomUUID().toString()); + } + + private String makeRequestString(Map param) throws Exception { + fillCommonParam(param); + String sign = makeSignature(new TreeMap(param)); + StringBuilder builder = new StringBuilder(); + for (Map.Entry entry : param.entrySet()) { + builder.append(encode(entry.getKey())).append("=").append(encode(entry.getValue())).append("&"); + } + builder.append("Signature").append("=").append(sign); + return builder.toString(); + } + + /** + * 执行http请求 + * + * @param getMethod + * @return + * @throws IOException + */ + @SuppressWarnings("deprecation") + private final HttpResponse executeHttpRequest(HttpGet getMethod, String host) throws Exception { + SSLContext sslContext = SSLContexts.custom().loadTrustMaterial(null, new TrustStrategy() { + + @Override + public boolean isTrusted(X509Certificate[] arg0, String arg1) throws CertificateException { + return true; + } + }).build(); + SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslContext, + new String[] { "TLSv1" }, + null, + SSLConnectionSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER); + Registry registry = RegistryBuilder.create() + .register("http", PlainConnectionSocketFactory.INSTANCE) + .register("https", sslsf) + .build(); + HttpClientConnectionManager httpClientConnectionManager = new PoolingHttpClientConnectionManager(registry); + CloseableHttpClient httpClient = HttpClientBuilder.create() + .setMaxConnPerRoute(50) + .setMaxConnTotal(100) + .setConnectionManager(httpClientConnectionManager) + .build(); + RequestConfig requestConfig = RequestConfig.custom() + .setConnectTimeout(timeout) + .setConnectionRequestTimeout(timeout) + .setSocketTimeout(timeout) + .build(); + getMethod.setConfig(requestConfig); + HttpResponse response = httpClient.execute(getMethod); + int statusCode = response.getStatusLine().getStatusCode(); + if (statusCode != HttpResponseStatus.OK.code() && statusCode != HttpResponseStatus.PARTIAL_CONTENT.code()) { + String result = EntityUtils.toString(response.getEntity()); + throw new RuntimeException("return error !" + response.getStatusLine().getReasonPhrase() + ", " + result); + } + return response; + } + + protected abstract T processResult(HttpResponse response) throws Exception; + + protected void processBefore() { + + } + + public final T doAction() throws Exception { + processBefore(); + String requestStr = makeRequestString(treeMap); + HttpGet httpGet = new HttpGet(protocol + "://" + endPoint + "?" + requestStr); + HttpResponse response = executeHttpRequest(httpGet, endPoint); + if (response.getStatusLine().getStatusCode() != HttpStatus.SC_OK) { + String result = EntityUtils.toString(response.getEntity()); + throw new RuntimeException("http request failed! " + result); + } + return processResult(response); + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/DescribeBackupPolicyRequest.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/DescribeBackupPolicyRequest.java new file mode 100644 index 00000000..cf51961a --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/DescribeBackupPolicyRequest.java @@ -0,0 +1,40 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds.request; + +import org.apache.http.HttpResponse; +import org.apache.http.util.EntityUtils; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.JSONObject; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.RdsBackupPolicy; + +/** + * rds 备份策略查询 + * + * @author chengjin.lyf on 2018/8/7 下午3:41 + * @since 1.0.25 + */ +public class DescribeBackupPolicyRequest extends AbstractRequest { + + public DescribeBackupPolicyRequest(){ + setVersion("2014-08-15"); + putQueryString("Action", "DescribeBackupPolicy"); + + } + + public void setRdsInstanceId(String rdsInstanceId) { + putQueryString("DBInstanceId", rdsInstanceId); + } + + @Override + protected RdsBackupPolicy processResult(HttpResponse response) throws Exception { + String result = EntityUtils.toString(response.getEntity()); + JSONObject jsonObj = JSON.parseObject(result); + RdsBackupPolicy policy = new RdsBackupPolicy(); + policy.setBackupRetentionPeriod(jsonObj.getString("BackupRetentionPeriod")); + policy.setBackupLog(jsonObj.getString("BackupLog").equalsIgnoreCase("Enable")); + policy.setLogBackupRetentionPeriod(jsonObj.getIntValue("LogBackupRetentionPeriod")); + policy.setPreferredBackupPeriod(jsonObj.getString("PreferredBackupPeriod")); + policy.setPreferredBackupTime(jsonObj.getString("PreferredBackupTime")); + return policy; + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/DescribeBinlogFilesRequest.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/DescribeBinlogFilesRequest.java new file mode 100644 index 00000000..8aa90569 --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/rds/request/DescribeBinlogFilesRequest.java @@ -0,0 +1,55 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.rds.request; + +import java.util.Date; + +import org.apache.http.HttpResponse; +import org.apache.http.util.EntityUtils; + +import com.alibaba.fastjson.JSONObject; +import com.alibaba.fastjson.TypeReference; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.DescribeBinlogFileResult; + +/** + * @author chengjin.lyf on 2018/8/7 下午3:41 + * @since 1.0.25 + */ +public class DescribeBinlogFilesRequest extends AbstractRequest { + + public DescribeBinlogFilesRequest(){ + setVersion("2014-08-15"); + putQueryString("Action", "DescribeBinlogFiles"); + } + + public void setRdsInstanceId(String rdsInstanceId) { + putQueryString("DBInstanceId", rdsInstanceId); + } + + public void setPageSize(int pageSize) { + putQueryString("PageSize", String.valueOf(pageSize)); + } + + public void setPageNumber(int pageNumber) { + putQueryString("PageNumber", String.valueOf(pageNumber)); + } + + public void setStartDate(Date startDate) { + putQueryString("StartTime", formatUTCTZ(startDate)); + } + + public void setEndDate(Date endDate) { + putQueryString("EndTime", formatUTCTZ(endDate)); + } + + public void setResourceOwnerId(Long resourceOwnerId) { + putQueryString("ResourceOwnerId", String.valueOf(resourceOwnerId)); + } + + @Override + protected DescribeBinlogFileResult processResult(HttpResponse response) throws Exception { + String result = EntityUtils.toString(response.getEntity()); + DescribeBinlogFileResult describeBinlogFileResult = JSONObject.parseObject(result, + new TypeReference() { + }); + return describeBinlogFileResult; + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/DatabaseTableMeta.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/DatabaseTableMeta.java index 585f1de9..033dcae5 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/DatabaseTableMeta.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/DatabaseTableMeta.java @@ -7,8 +7,12 @@ import java.util.List; import java.util.Map; import java.util.concurrent.Executors; import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.ScheduledFuture; import java.util.concurrent.ThreadFactory; import java.util.concurrent.TimeUnit; +import java.util.concurrent.atomic.AtomicBoolean; +import java.util.concurrent.locks.ReadWriteLock; +import java.util.concurrent.locks.ReentrantReadWriteLock; import java.util.regex.Pattern; import org.apache.commons.beanutils.BeanUtils; @@ -44,19 +48,34 @@ import com.alibaba.otter.canal.protocol.position.EntryPosition; */ public class DatabaseTableMeta implements TableMetaTSDB { - public static final EntryPosition INIT_POSITION = new EntryPosition("0", 0L, -2L, -1L); - private static Logger logger = LoggerFactory.getLogger(DatabaseTableMeta.class); - private static Pattern pattern = Pattern.compile("Duplicate entry '.*' for key '*'"); - private static Pattern h2Pattern = Pattern.compile("Unique index or primary key violation"); - private String destination; - private MemoryTableMeta memoryTableMeta; - private MysqlConnection connection; // 查询meta信息的链接 - private CanalEventFilter filter; - private CanalEventFilter blackFilter; - private EntryPosition lastPosition; - private ScheduledExecutorService scheduler; - private MetaHistoryDAO metaHistoryDAO; - private MetaSnapshotDAO metaSnapshotDAO; + public static final EntryPosition INIT_POSITION = new EntryPosition("0", 0L, -2L, -1L); + private static Logger logger = LoggerFactory.getLogger(DatabaseTableMeta.class); + private static Pattern pattern = Pattern.compile("Duplicate entry '.*' for key '*'"); + private static Pattern h2Pattern = Pattern.compile("Unique index or primary key violation"); + private static ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor(new ThreadFactory() { + + @Override + public Thread newThread(Runnable r) { + Thread thread = new Thread(r, + "[scheduler-table-meta-snapshot]"); + thread.setDaemon(true); + return thread; + } + }); + private ReadWriteLock lock = new ReentrantReadWriteLock(); + private AtomicBoolean initialized = new AtomicBoolean(false); + private String destination; + private MemoryTableMeta memoryTableMeta; + private volatile MysqlConnection connection; // 查询meta信息的链接 + private CanalEventFilter filter; + private CanalEventFilter blackFilter; + private EntryPosition lastPosition; + private boolean hasNewDdl; + private MetaHistoryDAO metaHistoryDAO; + private MetaSnapshotDAO metaSnapshotDAO; + private int snapshotInterval = 24; + private int snapshotExpire = 360; + private ScheduledFuture scheduleSnapshotFuture; public DatabaseTableMeta(){ @@ -64,50 +83,84 @@ public class DatabaseTableMeta implements TableMetaTSDB { @Override public boolean init(final String destination) { - this.destination = destination; - this.memoryTableMeta = new MemoryTableMeta(); - this.scheduler = Executors.newSingleThreadScheduledExecutor(new ThreadFactory() { + if (initialized.compareAndSet(false, true)) { + this.destination = destination; + this.memoryTableMeta = new MemoryTableMeta(); - @Override - public Thread newThread(Runnable r) { - return new Thread(r, "[scheduler-table-meta-snapshot]"); + // 24小时生成一份snapshot + if (snapshotInterval > 0) { + scheduleSnapshotFuture = scheduler.scheduleWithFixedDelay(new Runnable() { + + @Override + public void run() { + boolean applyResult = false; + try { + MDC.put("destination", destination); + applyResult = applySnapshotToDB(lastPosition, false); + } catch (Throwable e) { + logger.error("scheudle applySnapshotToDB faield", e); + } + + try { + MDC.put("destination", destination); + if (applyResult) { + snapshotExpire((int) TimeUnit.HOURS.toSeconds(snapshotExpire)); + } + } catch (Throwable e) { + logger.error("scheudle snapshotExpire faield", e); + } + } + }, snapshotInterval, snapshotInterval, TimeUnit.HOURS); } - }); - - // 24小时生成一份snapshot - scheduler.scheduleWithFixedDelay(new Runnable() { - - @Override - public void run() { - try { - MDC.put("destination", destination); - applySnapshotToDB(lastPosition, false); - } catch (Throwable e) { - logger.error("scheudle applySnapshotToDB faield", e); - } - } - }, 24, 24, TimeUnit.HOURS); + } return true; } + @Override + public void destory() { + if (memoryTableMeta != null) { + memoryTableMeta.destory(); + } + + if (connection != null) { + try { + connection.disconnect(); + } catch (IOException e) { + logger.error("ERROR # disconnect meta connection for address:{}", connection.getConnector() + .getAddress(), e); + } + } + + if (scheduleSnapshotFuture != null) { + scheduleSnapshotFuture.cancel(false); + } + } + @Override public TableMeta find(String schema, String table) { - synchronized (memoryTableMeta) { + lock.readLock().lock(); + try { return memoryTableMeta.find(schema, table); + } finally { + lock.readLock().unlock(); } } @Override public boolean apply(EntryPosition position, String schema, String ddl, String extra) { // 首先记录到内存结构 - synchronized (memoryTableMeta) { + lock.writeLock().lock(); + try { if (memoryTableMeta.apply(position, schema, ddl, extra)) { this.lastPosition = position; + this.hasNewDdl = true; // 同步每次变更给远程做历史记录 return applyHistoryToDB(position, schema, ddl, extra); } else { throw new RuntimeException("apply to memory is failed"); } + } finally { + lock.writeLock().unlock(); } } @@ -150,9 +203,13 @@ public class DatabaseTableMeta implements TableMetaTSDB { } for (String schema : schemas) { - packet = connection.query("show tables from `" + schema + "`"); + // filter views + packet = connection.query("show full tables from `" + schema + "` where Table_type = 'BASE TABLE'"); List tables = new ArrayList(); for (String table : packet.getFieldValues()) { + if ("BASE TABLE".equalsIgnoreCase(table)) { + continue; + } String fullName = schema + "." + table; if (blackFilter == null || !blackFilter.filter(fullName)) { if (filter == null || filter.filter(fullName)) { @@ -231,28 +288,41 @@ public class DatabaseTableMeta implements TableMetaTSDB { */ private boolean applySnapshotToDB(EntryPosition position, boolean init) { // 获取一份快照 - MemoryTableMeta tmpMemoryTableMeta = new MemoryTableMeta(); Map schemaDdls = null; - synchronized (memoryTableMeta) { - if (!init && position == null) { + lock.readLock().lock(); + try { + if (!init && !hasNewDdl) { // 如果是持续构建,则识别一下是否有DDL变更过,如果没有就忽略了 return false; } + this.hasNewDdl = false; schemaDdls = memoryTableMeta.snapshot(); - for (Map.Entry entry : schemaDdls.entrySet()) { - tmpMemoryTableMeta.apply(position, entry.getKey(), entry.getValue(), null); - } + } finally { + lock.readLock().unlock(); + } + + MemoryTableMeta tmpMemoryTableMeta = new MemoryTableMeta(); + for (Map.Entry entry : schemaDdls.entrySet()) { + tmpMemoryTableMeta.apply(position, entry.getKey(), entry.getValue(), null); } // 基于临时内存对象进行对比 boolean compareAll = true; for (Schema schema : tmpMemoryTableMeta.getRepository().getSchemas()) { for (String table : schema.showTables()) { - if (!compareTableMetaDbAndMemory(connection, tmpMemoryTableMeta, schema.getName(), table)) { - compareAll = false; + String fullName = schema + "." + table; + if (blackFilter == null || !blackFilter.filter(fullName)) { + if (filter == null || filter.filter(fullName)) { + // issue : https://github.com/alibaba/canal/issues/1168 + // 在生成snapshot时重新过滤一遍 + if (!compareTableMetaDbAndMemory(connection, tmpMemoryTableMeta, schema.getName(), table)) { + compareAll = false; + } + } } } } + if (compareAll) { Map content = new HashMap(); content.put("destination", destination); @@ -298,13 +368,24 @@ public class DatabaseTableMeta implements TableMetaTSDB { createDDL = packet.getFieldValues().get(1); tableMetaFromDB.setFields(TableMetaCache.parseTableMeta(schema, table, packet)); } - } catch (IOException e) { - if (e.getMessage().contains("errorNumber=1146")) { - logger.error("table not exist in db , pls check :" + getFullName(schema, table) + " , mem : " - + tableMetaFromMem); - return false; + } catch (Throwable e) { + try { + // retry for broke pipe, see: + // https://github.com/alibaba/canal/issues/724 + connection.reconnect(); + ResultSetPacket packet = connection.query("show create table " + getFullName(schema, table)); + if (packet.getFieldValues().size() > 1) { + createDDL = packet.getFieldValues().get(1); + tableMetaFromDB.setFields(TableMetaCache.parseTableMeta(schema, table, packet)); + } + } catch (IOException e1) { + if (e.getMessage().contains("errorNumber=1146")) { + logger.error("table not exist in db , pls check :" + getFullName(schema, table) + " , mem : " + + tableMetaFromMem); + return false; + } + throw new CanalParseException(e); } - throw new CanalParseException(e); } boolean result = compareTableMeta(tableMetaFromMem, tableMetaFromDB); @@ -425,7 +506,26 @@ public class DatabaseTableMeta implements TableMetaTSDB { return false; } - if (!StringUtils.equalsIgnoreCase(sourceField.getColumnType(), targetField.getColumnType())) { + // if (!StringUtils.equalsIgnoreCase(sourceField.getColumnType(), + // targetField.getColumnType())) { + // return false; + // } + + // https://github.com/alibaba/canal/issues/1100 + // 支持一下 int vs int(10) + if ((sourceField.isUnsigned() && !targetField.isUnsigned()) + || (!sourceField.isUnsigned() && targetField.isUnsigned())) { + return false; + } + + String sign = sourceField.isUnsigned() ? "unsigned" : "signed"; + String sourceColumnType = StringUtils.removeEndIgnoreCase(sourceField.getColumnType(), sign).trim(); + String targetColumnType = StringUtils.removeEndIgnoreCase(targetField.getColumnType(), sign).trim(); + + boolean columnTypeCompare = false; + columnTypeCompare |= StringUtils.containsIgnoreCase(sourceColumnType, targetColumnType); + columnTypeCompare |= StringUtils.containsIgnoreCase(targetColumnType, sourceColumnType); + if (!columnTypeCompare) { return false; } @@ -448,6 +548,10 @@ public class DatabaseTableMeta implements TableMetaTSDB { return true; } + private int snapshotExpire(int expireTimestamp) { + return metaSnapshotDAO.deleteByTimestamp(destination, expireTimestamp); + } + public void setConnection(MysqlConnection connection) { this.connection = connection; } @@ -476,6 +580,22 @@ public class DatabaseTableMeta implements TableMetaTSDB { this.blackFilter = blackFilter; } + public int getSnapshotInterval() { + return snapshotInterval; + } + + public void setSnapshotInterval(int snapshotInterval) { + this.snapshotInterval = snapshotInterval; + } + + public int getSnapshotExpire() { + return snapshotExpire; + } + + public void setSnapshotExpire(int snapshotExpire) { + this.snapshotExpire = snapshotExpire; + } + public MysqlConnection getConnection() { return connection; } diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/DefaultTableMetaTSDBFactory.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/DefaultTableMetaTSDBFactory.java new file mode 100644 index 00000000..00e2744b --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/DefaultTableMetaTSDBFactory.java @@ -0,0 +1,19 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.tsdb; + +/** + * @author agapple 2017年10月11日 下午8:45:40 + * @since 1.0.25 + */ +public class DefaultTableMetaTSDBFactory implements TableMetaTSDBFactory { + + /** + * 代理一下tableMetaTSDB的获取,使用隔离的spring定义 + */ + public TableMetaTSDB build(String destination, String springXml) { + return TableMetaTSDBBuilder.build(destination, springXml); + } + + public void destory(String destination) { + TableMetaTSDBBuilder.destory(destination); + } +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta.java index 127df1c4..dcd490f8 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta.java @@ -58,6 +58,11 @@ public class MemoryTableMeta implements TableMetaTSDB { public boolean init(String destination) { return true; } + + @Override + public void destory() { + tableMetas.clear(); + } public boolean apply(EntryPosition position, String schema, String ddl, String extra) { tableMetas.clear(); @@ -68,7 +73,8 @@ public class MemoryTableMeta implements TableMetaTSDB { try { // druid暂时flush privileges语法解析有问题 - if (!StringUtils.startsWithIgnoreCase(StringUtils.trim(ddl), "flush")) { + if (!StringUtils.startsWithIgnoreCase(StringUtils.trim(ddl), "flush") + && !StringUtils.startsWithIgnoreCase(StringUtils.trim(ddl), "grant")) { repository.console(ddl); } } catch (Throwable e) { @@ -94,7 +100,7 @@ public class MemoryTableMeta implements TableMetaTSDB { tableMeta = tableMetas.get(keys); if (tableMeta == null) { Schema schemaRep = repository.findSchema(schema); - if (schema == null) { + if (schemaRep == null) { return null; } SchemaObject data = schemaRep.findTable(table); @@ -207,6 +213,7 @@ public class MemoryTableMeta implements TableMetaTSDB { fieldMeta.setNullable(true); } else if (constraint instanceof SQLColumnPrimaryKey) { fieldMeta.setKey(true); + fieldMeta.setNullable(false); } else if (constraint instanceof SQLColumnUniqueKey) { fieldMeta.setUnique(true); } @@ -219,6 +226,7 @@ public class MemoryTableMeta implements TableMetaTSDB { String name = getSqlName(pk.getExpr()); FieldMeta field = tableMeta.getFieldMetaByName(name); field.setKey(true); + field.setNullable(false); } } else if (element instanceof MySqlUnique) { MySqlUnique column = (MySqlUnique) element; diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDB.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDB.java index d712adbe..f968ae12 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDB.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDB.java @@ -18,6 +18,11 @@ public interface TableMetaTSDB { */ public boolean init(String destination); + /** + * 销毁资源 + */ + public void destory(); + /** * 获取当前的表结构 */ diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDBBuilder.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDBBuilder.java index 8e37ef71..75b97f14 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDBBuilder.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDBBuilder.java @@ -10,12 +10,15 @@ import org.springframework.context.support.ClassPathXmlApplicationContext; import com.google.common.collect.Maps; /** - * @author agapple 2017年10月11日 下午8:45:40 + * tableMeta构造器 + * + * @author agapple 2018年8月8日 上午11:01:08 * @since 1.0.25 */ + public class TableMetaTSDBBuilder { - protected final static Logger logger = LoggerFactory.getLogger(TableMetaTSDBBuilder.class); + protected final static Logger logger = LoggerFactory.getLogger(DefaultTableMetaTSDBFactory.class); private static ConcurrentMap contexts = Maps.newConcurrentMap(); /** @@ -33,7 +36,6 @@ public class TableMetaTSDBBuilder { } } TableMetaTSDB tableMetaTSDB = (TableMetaTSDB) applicationContext.getBean("tableMetaTSDB"); - tableMetaTSDB.init(destination); logger.info("{} init TableMetaTSDB with {}", destination, springXml); return tableMetaTSDB; } else { diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDBFactory.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDBFactory.java new file mode 100644 index 00000000..950645a8 --- /dev/null +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/TableMetaTSDBFactory.java @@ -0,0 +1,18 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.tsdb; + +/** + * tableMeta构造器,允许重载实现 + * + * @author agapple 2018年8月8日 上午11:01:08 + * @since 1.0.26 + */ + +public interface TableMetaTSDBFactory { + + /** + * 代理一下tableMetaTSDB的获取,使用隔离的spring定义 + */ + public TableMetaTSDB build(String destination, String springXml); + + public void destory(String destination); +} diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaHistoryDAO.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaHistoryDAO.java index 6ec51614..c214d88f 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaHistoryDAO.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaHistoryDAO.java @@ -1,7 +1,5 @@ package com.alibaba.otter.canal.parse.inbound.mysql.tsdb.dao; -import java.text.SimpleDateFormat; -import java.util.Date; import java.util.HashMap; import java.util.List; @@ -37,13 +35,12 @@ public class MetaHistoryDAO extends MetaBaseDAO { /** * 删除interval秒之前的数据 */ - public Integer deleteByGmtModified(int interval) { + public Integer deleteByTimestamp(String destination, int interval) { HashMap params = Maps.newHashMapWithExpectedSize(2); long timestamp = System.currentTimeMillis() - interval * 1000; - Date date = new Date(timestamp); - SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); - params.put("timestamp", format.format(date)); - return getSqlMapClientTemplate().delete("meta_history.deleteByGmtModified", params); + params.put("timestamp", timestamp); + params.put("destination", destination); + return getSqlMapClientTemplate().delete("meta_history.deleteByTimestamp", params); } protected void initDao() throws Exception { diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaSnapshotDAO.java b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaSnapshotDAO.java index f525031a..ff79b107 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaSnapshotDAO.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/dao/MetaSnapshotDAO.java @@ -1,7 +1,5 @@ package com.alibaba.otter.canal.parse.inbound.mysql.tsdb.dao; -import java.text.SimpleDateFormat; -import java.util.Date; import java.util.HashMap; import com.google.common.collect.Maps; @@ -40,13 +38,12 @@ public class MetaSnapshotDAO extends MetaBaseDAO { /** * 删除interval秒之前的数据 */ - public Integer deleteByGmtModified(int interval) { + public Integer deleteByTimestamp(String destination, int interval) { HashMap params = Maps.newHashMapWithExpectedSize(2); long timestamp = System.currentTimeMillis() - interval * 1000; - Date date = new Date(timestamp); - SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); - params.put("timestamp", format.format(date)); - return getSqlMapClientTemplate().delete("meta_snapshot.deleteByGmtModified", params); + params.put("timestamp", timestamp); + params.put("destination", destination); + return getSqlMapClientTemplate().delete("meta_snapshot.deleteByTimestamp", params); } protected void initDao() throws Exception { diff --git a/parse/src/main/java/com/alibaba/otter/canal/parse/support/AuthenticationInfo.java b/parse/src/main/java/com/alibaba/otter/canal/parse/support/AuthenticationInfo.java index 5446d068..6b12ef0d 100644 --- a/parse/src/main/java/com/alibaba/otter/canal/parse/support/AuthenticationInfo.java +++ b/parse/src/main/java/com/alibaba/otter/canal/parse/support/AuthenticationInfo.java @@ -2,21 +2,32 @@ package com.alibaba.otter.canal.parse.support; import java.net.InetSocketAddress; +import com.alibaba.druid.filter.config.ConfigTools; import org.apache.commons.lang.builder.ToStringBuilder; import org.apache.commons.lang.builder.ToStringStyle; /** * 数据库认证信息 - * + * * @author jianghang 2012-7-11 上午11:22:19 * @version 1.0.0 */ public class AuthenticationInfo { + + private InetSocketAddress address; // 主库信息 private String username; // 帐号 private String password; // 密码 - private String defaultDatabaseName; // 默认链接的数据库 + private String defaultDatabaseName;// 默认链接的数据库 + private String pwdPublicKey; //公钥 + private boolean enableDruid; //是否使用druid加密解密数据库密码 + + public void initPwd() throws Exception{ + if (enableDruid) { + this.password = ConfigTools.decrypt(pwdPublicKey, password); + } + } public AuthenticationInfo(){ super(); @@ -65,6 +76,22 @@ public class AuthenticationInfo { this.defaultDatabaseName = defaultDatabaseName; } + public String getPwdPublicKey() { + return pwdPublicKey; + } + + public void setPwdPublicKey(String pwdPublicKey) { + this.pwdPublicKey = pwdPublicKey; + } + + public boolean isEnableDruid() { + return enableDruid; + } + + public void setEnableDruid(boolean enableDruid) { + this.enableDruid = enableDruid; + } + @Override public String toString() { return ToStringBuilder.reflectionToString(this, ToStringStyle.DEFAULT_STYLE); diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/DirectLogFetcherTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/DirectLogFetcherTest.java index aa48f9a3..089163d3 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/DirectLogFetcherTest.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/DirectLogFetcherTest.java @@ -1,7 +1,15 @@ package com.alibaba.otter.canal.parse; +import static com.alibaba.otter.canal.parse.inbound.mysql.dbsync.DirectLogFetcher.MASTER_HEARTBEAT_PERIOD_SECONDS; + import java.io.IOException; +import java.io.Serializable; +import java.io.UnsupportedEncodingException; import java.net.InetSocketAddress; +import java.nio.charset.Charset; +import java.util.BitSet; +import java.util.List; +import java.util.concurrent.TimeUnit; import org.apache.commons.lang.StringUtils; import org.junit.Assert; @@ -10,29 +18,48 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.alibaba.otter.canal.parse.driver.mysql.MysqlConnector; +import com.alibaba.otter.canal.parse.driver.mysql.MysqlQueryExecutor; import com.alibaba.otter.canal.parse.driver.mysql.MysqlUpdateExecutor; import com.alibaba.otter.canal.parse.driver.mysql.packets.HeaderPacket; import com.alibaba.otter.canal.parse.driver.mysql.packets.client.BinlogDumpCommandPacket; import com.alibaba.otter.canal.parse.driver.mysql.packets.client.RegisterSlaveCommandPacket; import com.alibaba.otter.canal.parse.driver.mysql.packets.server.ErrorPacket; +import com.alibaba.otter.canal.parse.driver.mysql.packets.server.ResultSetPacket; import com.alibaba.otter.canal.parse.driver.mysql.utils.PacketManager; +import com.alibaba.otter.canal.parse.exception.CanalParseException; import com.alibaba.otter.canal.parse.inbound.mysql.dbsync.DirectLogFetcher; import com.taobao.tddl.dbsync.binlog.LogContext; import com.taobao.tddl.dbsync.binlog.LogDecoder; import com.taobao.tddl.dbsync.binlog.LogEvent; +import com.taobao.tddl.dbsync.binlog.event.DeleteRowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.FormatDescriptionLogEvent; +import com.taobao.tddl.dbsync.binlog.event.QueryLogEvent; import com.taobao.tddl.dbsync.binlog.event.RotateLogEvent; +import com.taobao.tddl.dbsync.binlog.event.RowsLogBuffer; +import com.taobao.tddl.dbsync.binlog.event.RowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.RowsQueryLogEvent; +import com.taobao.tddl.dbsync.binlog.event.TableMapLogEvent; +import com.taobao.tddl.dbsync.binlog.event.TableMapLogEvent.ColumnInfo; +import com.taobao.tddl.dbsync.binlog.event.UpdateRowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.WriteRowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.XidLogEvent; +import com.taobao.tddl.dbsync.binlog.event.mariadb.AnnotateRowsEvent; public class DirectLogFetcherTest { - protected final Logger logger = LoggerFactory.getLogger(this.getClass()); + protected final Logger logger = LoggerFactory.getLogger(this.getClass()); + protected String binlogFileName = "mysql-bin.000001"; + protected Charset charset = Charset.forName("utf-8"); + private int binlogChecksum; @Test public void testSimple() { DirectLogFetcher fetcher = new DirectLogFetcher(); try { - MysqlConnector connector = new MysqlConnector(new InetSocketAddress("127.0.0.1", 3306), "xxxx", "xxxx"); + MysqlConnector connector = new MysqlConnector(new InetSocketAddress("127.0.0.1", 3306), "root", "hello"); connector.connect(); updateSettings(connector); + loadBinlogChecksum(connector); sendRegisterSlave(connector, 3); sendBinlogDump(connector, "mysql-bin.000001", 4L, 3); @@ -40,6 +67,8 @@ public class DirectLogFetcherTest { LogDecoder decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); LogContext context = new LogContext(); + context.setFormatDescription(new FormatDescriptionLogEvent(4, binlogChecksum)); + while (fetcher.fetch()) { LogEvent event = null; event = decoder.decode(fetcher, context); @@ -57,21 +86,22 @@ public class DirectLogFetcherTest { break; case LogEvent.WRITE_ROWS_EVENT_V1: case LogEvent.WRITE_ROWS_EVENT: - // parseRowsEvent((WriteRowsLogEvent) event); + parseRowsEvent((WriteRowsLogEvent) event); break; case LogEvent.UPDATE_ROWS_EVENT_V1: + case LogEvent.PARTIAL_UPDATE_ROWS_EVENT: case LogEvent.UPDATE_ROWS_EVENT: - // parseRowsEvent((UpdateRowsLogEvent) event); + parseRowsEvent((UpdateRowsLogEvent) event); break; case LogEvent.DELETE_ROWS_EVENT_V1: case LogEvent.DELETE_ROWS_EVENT: - // parseRowsEvent((DeleteRowsLogEvent) event); + parseRowsEvent((DeleteRowsLogEvent) event); break; case LogEvent.QUERY_EVENT: - // parseQueryEvent((QueryLogEvent) event); + parseQueryEvent((QueryLogEvent) event); break; case LogEvent.ROWS_QUERY_LOG_EVENT: - // parseRowsQueryEvent((RowsQueryLogEvent) event); + parseRowsQueryEvent((RowsQueryLogEvent) event); break; case LogEvent.ANNOTATE_ROWS_EVENT: break; @@ -165,7 +195,7 @@ public class DirectLogFetcherTest { // 如果不设置会出现错误: Slave can not handle replication events with the // checksum that master is configured to log // 但也不能乱设置,需要和mysql server的checksum配置一致,不然RotateLogEvent会出现乱码 - update("set @master_binlog_checksum= '@@global.binlog_checksum'", connector); + update("set @master_binlog_checksum= @@global.binlog_checksum", connector); } catch (Exception e) { logger.warn("update master_binlog_checksum failed", e); } @@ -186,6 +216,34 @@ public class DirectLogFetcherTest { } catch (Exception e) { logger.warn("update mariadb_slave_capability failed", e); } + + try { + long period = TimeUnit.SECONDS.toNanos(MASTER_HEARTBEAT_PERIOD_SECONDS); + update("SET @master_heartbeat_period=" + period, connector); + } catch (Exception e) { + logger.warn("update master_heartbeat_period failed", e); + } + } + + private void loadBinlogChecksum(MysqlConnector connector) { + ResultSetPacket rs = null; + try { + rs = query("select @@global.binlog_checksum", connector); + } catch (IOException e) { + throw new CanalParseException(e); + } + + List columnValues = rs.getFieldValues(); + if (columnValues != null && columnValues.size() >= 1 && columnValues.get(0).toUpperCase().equals("CRC32")) { + binlogChecksum = LogEvent.BINLOG_CHECKSUM_ALG_CRC32; + } else { + binlogChecksum = LogEvent.BINLOG_CHECKSUM_ALG_OFF; + } + } + + public ResultSetPacket query(String cmd, MysqlConnector connector) throws IOException { + MysqlQueryExecutor exector = new MysqlQueryExecutor(connector); + return exector.query(cmd); } public void update(String cmd, MysqlConnector connector) throws IOException { @@ -193,4 +251,98 @@ public class DirectLogFetcherTest { exector.update(cmd); } + protected void parseQueryEvent(QueryLogEvent event) { + System.out.println(String.format("================> binlog[%s:%s] , name[%s]", + binlogFileName, + event.getHeader().getLogPos() - event.getHeader().getEventLen(), + event.getCatalog())); + System.out.println("sql : " + event.getQuery()); + } + + protected void parseRowsQueryEvent(RowsQueryLogEvent event) throws Exception { + System.out.println(String.format("================> binlog[%s:%s]", binlogFileName, event.getHeader() + .getLogPos() - event.getHeader().getEventLen())); + System.out.println("sql : " + new String(event.getRowsQuery().getBytes("ISO-8859-1"), charset.name())); + } + + protected void parseAnnotateRowsEvent(AnnotateRowsEvent event) throws Exception { + System.out.println(String.format("================> binlog[%s:%s]", binlogFileName, event.getHeader() + .getLogPos() - event.getHeader().getEventLen())); + System.out.println("sql : " + new String(event.getRowsQuery().getBytes("ISO-8859-1"), charset.name())); + } + + protected void parseXidEvent(XidLogEvent event) throws Exception { + System.out.println(String.format("================> binlog[%s:%s]", binlogFileName, event.getHeader() + .getLogPos() - event.getHeader().getEventLen())); + System.out.println("xid : " + event.getXid()); + } + + protected void parseRowsEvent(RowsLogEvent event) { + try { + System.out.println(String.format("================> binlog[%s:%s] , name[%s,%s]", + binlogFileName, + event.getHeader().getLogPos() - event.getHeader().getEventLen(), + event.getTable().getDbName(), + event.getTable().getTableName())); + RowsLogBuffer buffer = event.getRowsBuf(charset.name()); + BitSet columns = event.getColumns(); + BitSet changeColumns = event.getChangeColumns(); + while (buffer.nextOneRow(columns)) { + // 处理row记录 + int type = event.getHeader().getType(); + if (LogEvent.WRITE_ROWS_EVENT_V1 == type || LogEvent.WRITE_ROWS_EVENT == type) { + // insert的记录放在before字段中 + parseOneRow(event, buffer, columns, true); + } else if (LogEvent.DELETE_ROWS_EVENT_V1 == type || LogEvent.DELETE_ROWS_EVENT == type) { + // delete的记录放在before字段中 + parseOneRow(event, buffer, columns, false); + } else { + // update需要处理before/after + System.out.println("-------> before"); + parseOneRow(event, buffer, columns, false); + if (!buffer.nextOneRow(changeColumns, true)) { + break; + } + System.out.println("-------> after"); + parseOneRow(event, buffer, changeColumns, true); + } + + } + } catch (Exception e) { + throw new RuntimeException("parse row data failed.", e); + } + } + + protected void parseOneRow(RowsLogEvent event, RowsLogBuffer buffer, BitSet cols, boolean isAfter) + throws UnsupportedEncodingException { + TableMapLogEvent map = event.getTable(); + if (map == null) { + throw new RuntimeException("not found TableMap with tid=" + event.getTableId()); + } + + final int columnCnt = map.getColumnCnt(); + final ColumnInfo[] columnInfo = map.getColumnInfo(); + + for (int i = 0; i < columnCnt; i++) { + if (!cols.get(i)) { + continue; + } + + ColumnInfo info = columnInfo[i]; + buffer.nextValue(null, i, info.type, info.meta); + + if (buffer.isNull()) { + // + } else { + final Serializable value = buffer.getValue(); + if (value instanceof byte[]) { + System.out.println(new String((byte[]) value)); + } else { + System.out.println(value); + } + } + } + + } + } diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogDumpPerformanceTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogDumpPerformanceTest.java new file mode 100644 index 00000000..25c88764 --- /dev/null +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogDumpPerformanceTest.java @@ -0,0 +1,89 @@ +package com.alibaba.otter.canal.parse; + +import java.net.InetSocketAddress; +import java.nio.charset.Charset; +import java.util.List; +import java.util.concurrent.atomic.AtomicLong; + +import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; +import com.alibaba.otter.canal.parse.exception.CanalParseException; +import com.alibaba.otter.canal.parse.inbound.mysql.MysqlEventParser; +import com.alibaba.otter.canal.parse.index.AbstractLogPositionManager; +import com.alibaba.otter.canal.parse.support.AuthenticationInfo; +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.position.EntryPosition; +import com.alibaba.otter.canal.protocol.position.LogPosition; +import com.alibaba.otter.canal.sink.CanalEventSink; +import com.alibaba.otter.canal.sink.exception.CanalSinkException; + +public class MysqlBinlogDumpPerformanceTest { + + public static void main(String args[]) { + final MysqlEventParser controller = new MysqlEventParser(); + final EntryPosition startPosition = new EntryPosition("mysql-bin.000007", 89796293L, 100L); + controller.setConnectionCharset(Charset.forName("UTF-8")); + controller.setSlaveId(3344L); + controller.setDetectingEnable(false); + controller.setFilterQueryDml(true); + controller.setMasterInfo(new AuthenticationInfo(new InetSocketAddress("100.81.154.142", 3306), "canal", "canal")); + controller.setMasterPosition(startPosition); + controller.setEnableTsdb(false); + controller.setDestination("example"); + controller.setTsdbSpringXml("classpath:spring/tsdb/h2-tsdb.xml"); + // controller.setEventFilter(new AviaterRegexFilter("test\\..*")); + // controller.setEventBlackFilter(new + // AviaterRegexFilter("canal_tsdb\\..*")); + controller.setParallel(true); + controller.setParallelBufferSize(256); + controller.setParallelThreadSize(16); + controller.setIsGTIDMode(false); + final AtomicLong sum = new AtomicLong(0); + final AtomicLong last = new AtomicLong(0); + final AtomicLong start = new AtomicLong(System.currentTimeMillis()); + final AtomicLong end = new AtomicLong(0); + controller.setEventSink(new AbstractCanalEventSinkTest>() { + + public boolean sink(List entrys, InetSocketAddress remoteAddress, String destination) + throws CanalSinkException, + InterruptedException { + + sum.addAndGet(entrys.size()); + long current = sum.get(); + if (current - last.get() >= 100000) { + end.set(System.currentTimeMillis()); + long tps = ((current - last.get()) * 1000) / (end.get() - start.get()); + System.out.println(" total : " + sum + " , cost : " + (end.get() - start.get()) + " , tps : " + tps); + last.set(current); + start.set(end.get()); + } + return true; + } + + }); + controller.setLogPositionManager(new AbstractLogPositionManager() { + + @Override + public LogPosition getLatestIndexBy(String destination) { + return null; + } + + @Override + public void persistLogPosition(String destination, LogPosition logPosition) throws CanalParseException { + } + }); + + controller.start(); + + try { + Thread.sleep(100 * 1000 * 1000L); + } catch (InterruptedException e) { + } + controller.stop(); + } + + public static abstract class AbstractCanalEventSinkTest extends AbstractCanalLifeCycle implements CanalEventSink { + + public void interrupt() { + } + } +} diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogEventPerformanceTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogEventPerformanceTest.java new file mode 100644 index 00000000..e92fecb5 --- /dev/null +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogEventPerformanceTest.java @@ -0,0 +1,82 @@ +package com.alibaba.otter.canal.parse; + +import java.io.IOException; +import java.net.InetSocketAddress; +import java.nio.charset.Charset; +import java.util.concurrent.atomic.AtomicLong; + +import com.alibaba.otter.canal.parse.driver.mysql.MysqlConnector; +import com.alibaba.otter.canal.parse.driver.mysql.MysqlUpdateExecutor; +import com.alibaba.otter.canal.parse.driver.mysql.packets.HeaderPacket; +import com.alibaba.otter.canal.parse.driver.mysql.packets.client.BinlogDumpCommandPacket; +import com.alibaba.otter.canal.parse.driver.mysql.utils.PacketManager; +import com.alibaba.otter.canal.parse.inbound.mysql.dbsync.DirectLogFetcher; +import com.taobao.tddl.dbsync.binlog.LogContext; +import com.taobao.tddl.dbsync.binlog.LogDecoder; +import com.taobao.tddl.dbsync.binlog.LogEvent; + +public class MysqlBinlogEventPerformanceTest { + + protected static Charset charset = Charset.forName("utf-8"); + + public static void main(String args[]) { + DirectLogFetcher fetcher = new DirectLogFetcher(); + try { + MysqlConnector connector = new MysqlConnector(new InetSocketAddress("127.0.0.1", 3306), "root", "hello"); + connector.connect(); + updateSettings(connector); + sendBinlogDump(connector, "mysql-bin.000006", 120L, 3); + fetcher.start(connector.getChannel()); + LogDecoder decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); + LogContext context = new LogContext(); + AtomicLong sum = new AtomicLong(0); + long start = System.currentTimeMillis(); + long last = 0; + long end = 0; + while (fetcher.fetch()) { + decoder.decode(fetcher, context); + sum.incrementAndGet(); + long current = sum.get(); + if (current - last >= 100000) { + end = System.currentTimeMillis(); + long tps = ((current - last) * 1000) / (end - start); + System.out.println(" total : " + sum + " , cost : " + (end - start) + " , tps : " + tps); + last = current; + start = end; + } + } + } catch (Exception e) { + e.printStackTrace(); + } finally { + try { + fetcher.close(); + } catch (IOException e) { + } + } + } + + private static void sendBinlogDump(MysqlConnector connector, String binlogfilename, Long binlogPosition, int slaveId) + throws IOException { + BinlogDumpCommandPacket binlogDumpCmd = new BinlogDumpCommandPacket(); + binlogDumpCmd.binlogFileName = binlogfilename; + binlogDumpCmd.binlogPosition = binlogPosition; + binlogDumpCmd.slaveServerId = slaveId; + byte[] cmdBody = binlogDumpCmd.toBytes(); + + HeaderPacket binlogDumpHeader = new HeaderPacket(); + binlogDumpHeader.setPacketBodyLength(cmdBody.length); + binlogDumpHeader.setPacketSequenceNumber((byte) 0x00); + PacketManager.writePkg(connector.getChannel(), binlogDumpHeader.toBytes(), cmdBody); + } + + private static void updateSettings(MysqlConnector connector) throws IOException { + update("set @master_binlog_checksum= '@@global.binlog_checksum'", connector); + update("SET @mariadb_slave_capability='" + LogEvent.MARIA_SLAVE_CAPABILITY_MINE + "'", connector); + } + + public static void update(String cmd, MysqlConnector connector) throws IOException { + MysqlUpdateExecutor exector = new MysqlUpdateExecutor(connector); + exector.update(cmd); + } + +} diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogParsePerformanceTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogParsePerformanceTest.java new file mode 100644 index 00000000..70b2dbd7 --- /dev/null +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/MysqlBinlogParsePerformanceTest.java @@ -0,0 +1,193 @@ +package com.alibaba.otter.canal.parse; + +import java.io.IOException; +import java.io.UnsupportedEncodingException; +import java.net.InetSocketAddress; +import java.nio.charset.Charset; +import java.util.BitSet; +import java.util.concurrent.ArrayBlockingQueue; +import java.util.concurrent.BlockingQueue; +import java.util.concurrent.atomic.AtomicLong; + +import com.alibaba.otter.canal.parse.driver.mysql.MysqlConnector; +import com.alibaba.otter.canal.parse.driver.mysql.MysqlUpdateExecutor; +import com.alibaba.otter.canal.parse.driver.mysql.packets.HeaderPacket; +import com.alibaba.otter.canal.parse.driver.mysql.packets.client.BinlogDumpCommandPacket; +import com.alibaba.otter.canal.parse.driver.mysql.utils.PacketManager; +import com.alibaba.otter.canal.parse.inbound.mysql.dbsync.DirectLogFetcher; +import com.taobao.tddl.dbsync.binlog.LogBuffer; +import com.taobao.tddl.dbsync.binlog.LogContext; +import com.taobao.tddl.dbsync.binlog.LogDecoder; +import com.taobao.tddl.dbsync.binlog.LogEvent; +import com.taobao.tddl.dbsync.binlog.event.DeleteRowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.RowsLogBuffer; +import com.taobao.tddl.dbsync.binlog.event.RowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.TableMapLogEvent; +import com.taobao.tddl.dbsync.binlog.event.TableMapLogEvent.ColumnInfo; +import com.taobao.tddl.dbsync.binlog.event.UpdateRowsLogEvent; +import com.taobao.tddl.dbsync.binlog.event.WriteRowsLogEvent; + +public class MysqlBinlogParsePerformanceTest { + + protected static Charset charset = Charset.forName("utf-8"); + + public static void main(String args[]) { + DirectLogFetcher fetcher = new DirectLogFetcher(); + try { + MysqlConnector connector = new MysqlConnector(new InetSocketAddress("127.0.0.1", 3306), "root", "hello"); + connector.connect(); + updateSettings(connector); + sendBinlogDump(connector, "mysql-bin.000006", 120L, 3); + fetcher.start(connector.getChannel()); + final BlockingQueue buffer = new ArrayBlockingQueue(1024); + Thread thread = new Thread(new Runnable() { + + @Override + public void run() { + try { + consumer(buffer); + } catch (IOException e) { + e.printStackTrace(); + } catch (InterruptedException e) { + e.printStackTrace(); + } + } + }); + thread.start(); + + while (fetcher.fetch()) { + buffer.put(fetcher.duplicate()); + fetcher.consume(fetcher.limit()); + } + } catch (Exception e) { + e.printStackTrace(); + } finally { + try { + fetcher.close(); + } catch (IOException e) { + } + } + } + + public static void consumer(BlockingQueue buffer) throws IOException, InterruptedException { + LogDecoder decoder = new LogDecoder(LogEvent.UNKNOWN_EVENT, LogEvent.ENUM_END_EVENT); + LogContext context = new LogContext(); + + AtomicLong sum = new AtomicLong(0); + long start = System.currentTimeMillis(); + long last = 0; + long end = 0; + while (true) { + LogEvent event = null; + event = decoder.decode(buffer.take(), context); + int eventType = event.getHeader().getType(); + switch (eventType) { + case LogEvent.ROTATE_EVENT: + break; + case LogEvent.WRITE_ROWS_EVENT_V1: + case LogEvent.WRITE_ROWS_EVENT: + parseRowsEvent((WriteRowsLogEvent) event, sum); + break; + case LogEvent.UPDATE_ROWS_EVENT_V1: + case LogEvent.PARTIAL_UPDATE_ROWS_EVENT: + case LogEvent.UPDATE_ROWS_EVENT: + parseRowsEvent((UpdateRowsLogEvent) event, sum); + break; + case LogEvent.DELETE_ROWS_EVENT_V1: + case LogEvent.DELETE_ROWS_EVENT: + parseRowsEvent((DeleteRowsLogEvent) event, sum); + break; + case LogEvent.XID_EVENT: + sum.incrementAndGet(); + break; + case LogEvent.QUERY_EVENT: + sum.incrementAndGet(); + break; + default: + break; + } + + long current = sum.get(); + if (current - last >= 100000) { + end = System.currentTimeMillis(); + long tps = ((current - last) * 1000) / (end - start); + System.out.println(" total : " + sum + " , cost : " + (end - start) + " , tps : " + tps); + last = current; + start = end; + } + } + } + + private static void sendBinlogDump(MysqlConnector connector, String binlogfilename, Long binlogPosition, int slaveId) + throws IOException { + BinlogDumpCommandPacket binlogDumpCmd = new BinlogDumpCommandPacket(); + binlogDumpCmd.binlogFileName = binlogfilename; + binlogDumpCmd.binlogPosition = binlogPosition; + binlogDumpCmd.slaveServerId = slaveId; + byte[] cmdBody = binlogDumpCmd.toBytes(); + + HeaderPacket binlogDumpHeader = new HeaderPacket(); + binlogDumpHeader.setPacketBodyLength(cmdBody.length); + binlogDumpHeader.setPacketSequenceNumber((byte) 0x00); + PacketManager.writePkg(connector.getChannel(), binlogDumpHeader.toBytes(), cmdBody); + } + + private static void updateSettings(MysqlConnector connector) throws IOException { + update("set @master_binlog_checksum= '@@global.binlog_checksum'", connector); + update("SET @mariadb_slave_capability='" + LogEvent.MARIA_SLAVE_CAPABILITY_MINE + "'", connector); + } + + public static void update(String cmd, MysqlConnector connector) throws IOException { + MysqlUpdateExecutor exector = new MysqlUpdateExecutor(connector); + exector.update(cmd); + } + + public static void parseRowsEvent(RowsLogEvent event, AtomicLong sum) { + try { + RowsLogBuffer buffer = event.getRowsBuf(charset.name()); + BitSet columns = event.getColumns(); + BitSet changeColumns = event.getChangeColumns(); + while (buffer.nextOneRow(columns)) { + int type = event.getHeader().getType(); + if (LogEvent.WRITE_ROWS_EVENT_V1 == type || LogEvent.WRITE_ROWS_EVENT == type) { + parseOneRow(event, buffer, columns, true); + } else if (LogEvent.DELETE_ROWS_EVENT_V1 == type || LogEvent.DELETE_ROWS_EVENT == type) { + parseOneRow(event, buffer, columns, false); + } else { + parseOneRow(event, buffer, columns, false); + if (!buffer.nextOneRow(changeColumns, true)) { + break; + } + parseOneRow(event, buffer, changeColumns, true); + } + + sum.incrementAndGet(); + } + } catch (Exception e) { + throw new RuntimeException("parse row data failed.", e); + } + } + + public static void parseOneRow(RowsLogEvent event, RowsLogBuffer buffer, BitSet cols, boolean isAfter) + throws UnsupportedEncodingException { + TableMapLogEvent map = event.getTable(); + if (map == null) { + throw new RuntimeException("not found TableMap with tid=" + event.getTableId()); + } + + final int columnCnt = map.getColumnCnt(); + final ColumnInfo[] columnInfo = map.getColumnInfo(); + for (int i = 0; i < columnCnt; i++) { + if (!cols.get(i)) { + continue; + } + + ColumnInfo info = columnInfo[i]; + buffer.nextValue(null, i, info.type, info.meta); + if (buffer.isNull()) { + } else { + buffer.getValue(); + } + } + } +} diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/group/DummyEventStore.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/group/DummyEventStore.java index 24f7f551..c542e5c0 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/group/DummyEventStore.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/group/DummyEventStore.java @@ -7,7 +7,6 @@ import java.util.Date; import java.util.List; import java.util.concurrent.TimeUnit; -import com.alibaba.otter.canal.protocol.CanalEntry; import com.alibaba.otter.canal.protocol.CanalEntry.EntryType; import com.alibaba.otter.canal.protocol.position.Position; import com.alibaba.otter.canal.store.CanalEventStore; @@ -18,7 +17,7 @@ import com.alibaba.otter.canal.store.model.Events; public class DummyEventStore implements CanalEventStore { private static final String DATE_FORMAT = "yyyy-MM-dd HH:mm:ss"; - private static final String messgae = "{0} [{1}:{2}:{3}] {4} {5}.{6}"; + private static final String messgae = "{0} [{1}:{2}:{3}]"; public void ack(Position position) throws CanalStoreException { @@ -82,46 +81,40 @@ public class DummyEventStore implements CanalEventStore { public void put(List datas) throws InterruptedException, CanalStoreException { for (Event data : datas) { - CanalEntry.Header header = data.getEntry().getHeader(); - Date date = new Date(header.getExecuteTime()); + Date date = new Date(data.getExecuteTime()); SimpleDateFormat format = new SimpleDateFormat(DATE_FORMAT); - if (data.getEntry().getEntryType() == EntryType.TRANSACTIONBEGIN - || data.getEntry().getEntryType() == EntryType.TRANSACTIONEND) { + if (data.getEntryType() == EntryType.TRANSACTIONBEGIN || data.getEntryType() == EntryType.TRANSACTIONEND) { // System.out.println(MessageFormat.format(messgae, new Object[] // { Thread.currentThread().getName(), // header.getLogfilename(), header.getLogfileoffset(), // format.format(date), // data.getEntry().getEntryType(), "" })); - System.out.println(data.getEntry().getEntryType()); + System.out.println(data.getEntryType()); } else { System.out.println(MessageFormat.format(messgae, - new Object[] { Thread.currentThread().getName(), header.getLogfileName(), - String.valueOf(header.getLogfileOffset()), format.format(date), header.getEventType(), - header.getSchemaName(), header.getTableName() })); + new Object[] { Thread.currentThread().getName(), data.getJournalName(), + String.valueOf(data.getPosition()), format.format(date) })); } } } public boolean put(List datas, long timeout, TimeUnit unit) throws InterruptedException, CanalStoreException { for (Event data : datas) { - CanalEntry.Header header = data.getEntry().getHeader(); - Date date = new Date(header.getExecuteTime()); + Date date = new Date(data.getExecuteTime()); SimpleDateFormat format = new SimpleDateFormat(DATE_FORMAT); - if (data.getEntry().getEntryType() == EntryType.TRANSACTIONBEGIN - || data.getEntry().getEntryType() == EntryType.TRANSACTIONEND) { + if (data.getEntryType() == EntryType.TRANSACTIONBEGIN || data.getEntryType() == EntryType.TRANSACTIONEND) { // System.out.println(MessageFormat.format(messgae, new Object[] // { Thread.currentThread().getName(), // header.getLogfilename(), header.getLogfileoffset(), // format.format(date), // data.getEntry().getEntryType(), "" })); - System.out.println(data.getEntry().getEntryType()); + System.out.println(data.getEntryType()); } else { System.out.println(MessageFormat.format(messgae, - new Object[] { Thread.currentThread().getName(), header.getLogfileName(), - String.valueOf(header.getLogfileOffset()), format.format(date), header.getEventType(), - header.getSchemaName(), header.getTableName() })); + new Object[] { Thread.currentThread().getName(), data.getJournalName(), + String.valueOf(data.getPosition()), format.format(date) })); } } return true; @@ -131,23 +124,20 @@ public class DummyEventStore implements CanalEventStore { System.out.println("\n>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>"); for (Event data : datas) { - CanalEntry.Header header = data.getEntry().getHeader(); - Date date = new Date(header.getExecuteTime()); + Date date = new Date(data.getExecuteTime()); SimpleDateFormat format = new SimpleDateFormat(DATE_FORMAT); - if (data.getEntry().getEntryType() == EntryType.TRANSACTIONBEGIN - || data.getEntry().getEntryType() == EntryType.TRANSACTIONEND) { + if (data.getEntryType() == EntryType.TRANSACTIONBEGIN || data.getEntryType() == EntryType.TRANSACTIONEND) { // System.out.println(MessageFormat.format(messgae, new Object[] // { Thread.currentThread().getName(), // header.getLogfilename(), header.getLogfileoffset(), // format.format(date), // data.getEntry().getEntryType(), "" })); - System.out.println(data.getEntry().getEntryType()); + System.out.println(data.getEntryType()); } else { System.out.println(MessageFormat.format(messgae, - new Object[] { Thread.currentThread().getName(), header.getLogfileName(), - String.valueOf(header.getLogfileOffset()), format.format(date), header.getEventType(), - header.getSchemaName(), header.getTableName() })); + new Object[] { Thread.currentThread().getName(), data.getJournalName(), + String.valueOf(data.getPosition()), format.format(date) })); } } diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlDumpTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlDumpTest.java index 6849c5b3..8c749891 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlDumpTest.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/MysqlDumpTest.java @@ -29,18 +29,21 @@ public class MysqlDumpTest { @Test public void testSimple() { final MysqlEventParser controller = new MysqlEventParser(); - final EntryPosition startPosition = new EntryPosition("mysql-bin.000012", 34051L, 100L); + final EntryPosition startPosition = new EntryPosition("mysql-bin.000001", 4L); // startPosition.setGtid("f1ceb61a-a5d5-11e7-bdee-107c3dbcf8a7:1-17"); controller.setConnectionCharset(Charset.forName("UTF-8")); controller.setSlaveId(3344L); controller.setDetectingEnable(false); - controller.setMasterInfo(new AuthenticationInfo(new InetSocketAddress("127.0.0.1", 3306), "canal", "canal")); + controller.setMasterInfo(new AuthenticationInfo(new InetSocketAddress("127.0.0.1", 3306), "root", "hello")); controller.setMasterPosition(startPosition); controller.setEnableTsdb(true); controller.setDestination("example"); controller.setTsdbSpringXml("classpath:tsdb/h2-tsdb.xml"); controller.setEventFilter(new AviaterRegexFilter("test\\..*")); controller.setEventBlackFilter(new AviaterRegexFilter("canal_tsdb\\..*")); + controller.setParallel(true); + controller.setParallelBufferSize(256); + controller.setParallelThreadSize(2); controller.setIsGTIDMode(false); controller.setEventSink(new AbstractCanalEventSinkTest>() { diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/RdsBinlogEventParserProxyTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/RdsBinlogEventParserProxyTest.java new file mode 100644 index 00000000..546ee58c --- /dev/null +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/RdsBinlogEventParserProxyTest.java @@ -0,0 +1,119 @@ +package com.alibaba.otter.canal.parse.inbound.mysql; + +import java.net.InetSocketAddress; +import java.util.Calendar; +import java.util.List; +import java.util.concurrent.atomic.AtomicLong; + +import org.junit.Assert; +import org.junit.Test; + +import com.alibaba.otter.canal.filter.aviater.AviaterRegexFilter; +import com.alibaba.otter.canal.parse.helper.TimeoutChecker; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.RdsBinlogEventParserProxy; +import com.alibaba.otter.canal.parse.index.AbstractLogPositionManager; +import com.alibaba.otter.canal.parse.stub.AbstractCanalEventSinkTest; +import com.alibaba.otter.canal.parse.support.AuthenticationInfo; +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.position.EntryPosition; +import com.alibaba.otter.canal.protocol.position.LogPosition; +import com.alibaba.otter.canal.sink.exception.CanalSinkException; + +/** + * @author chengjin.lyf on 2018/7/21 下午5:24 + * @since 1.0.25 + */ +public class RdsBinlogEventParserProxyTest { + + private static final String DETECTING_SQL = "insert into retl.xdual values(1,now()) on duplicate key update x=now()"; + private static final String MYSQL_ADDRESS = ""; + private static final String USERNAME = ""; + private static final String PASSWORD = ""; + public static final String DBNAME = ""; + public static final String TBNAME = ""; + public static final String DDL = ""; + + @Test + public void test_timestamp() throws InterruptedException { + final TimeoutChecker timeoutChecker = new TimeoutChecker(3000 * 1000); + final AtomicLong entryCount = new AtomicLong(0); + final EntryPosition entryPosition = new EntryPosition(); + + final RdsBinlogEventParserProxy controller = new RdsBinlogEventParserProxy(); + Calendar calendar = Calendar.getInstance(); + calendar.add(Calendar.HOUR_OF_DAY, -24 * 4); + final EntryPosition defaultPosition = buildPosition(null, null, calendar.getTimeInMillis()); + controller.setSlaveId(3344L); + controller.setDetectingEnable(false); + controller.setDetectingSQL(DETECTING_SQL); + controller.setMasterInfo(buildAuthentication()); + controller.setMasterPosition(defaultPosition); + controller.setInstanceId(""); + controller.setAccesskey(""); + controller.setSecretkey(""); + controller.setDirectory("/tmp/binlog"); + controller.setEventBlackFilter(new AviaterRegexFilter("mysql\\.*")); + controller.setFilterTableError(true); + controller.setBatchFileSize(4); + controller.setEventSink(new AbstractCanalEventSinkTest>() { + + @Override + public boolean sink(List entrys, InetSocketAddress remoteAddress, String destination) + throws CanalSinkException { + for (CanalEntry.Entry entry : entrys) { + if (entry.getEntryType() != CanalEntry.EntryType.HEARTBEAT) { + entryCount.incrementAndGet(); + + String logfilename = entry.getHeader().getLogfileName(); + long logfileoffset = entry.getHeader().getLogfileOffset(); + long executeTime = entry.getHeader().getExecuteTime(); + + entryPosition.setJournalName(logfilename); + entryPosition.setPosition(logfileoffset); + entryPosition.setTimestamp(executeTime); + break; + } + } + return true; + } + }); + + controller.setLogPositionManager(new AbstractLogPositionManager() { + + private LogPosition logPosition; + + public void persistLogPosition(String destination, LogPosition logPosition) { + this.logPosition = logPosition; + } + + public LogPosition getLatestIndexBy(String destination) { + return logPosition; + } + }); + + controller.start(); + timeoutChecker.waitForIdle(); + + if (controller.isStart()) { + controller.stop(); + } + + // check + Assert.assertTrue(entryCount.get() > 0); + + // 对比第一条数据和起始的position相同 + Assert.assertEquals(entryPosition.getJournalName(), "mysql-bin.000001"); + Assert.assertTrue(entryPosition.getPosition() <= 6163L); + Assert.assertTrue(entryPosition.getTimestamp() <= defaultPosition.getTimestamp()); + } + + // ======================== helper method ======================= + + private EntryPosition buildPosition(String binlogFile, Long offest, Long timestamp) { + return new EntryPosition(binlogFile, offest, timestamp); + } + + private AuthenticationInfo buildAuthentication() { + return new AuthenticationInfo(new InetSocketAddress(MYSQL_ADDRESS, 3306), USERNAME, PASSWORD); + } +} diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/RdsBinlogOpenApiTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/RdsBinlogOpenApiTest.java index 596847ae..25a14284 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/RdsBinlogOpenApiTest.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/RdsBinlogOpenApiTest.java @@ -1,11 +1,14 @@ package com.alibaba.otter.canal.parse.inbound.mysql; -import java.io.File; import java.util.Date; +import java.util.List; import org.apache.commons.lang.time.DateUtils; +import org.junit.Test; import com.alibaba.otter.canal.parse.inbound.mysql.rds.RdsBinlogOpenApi; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.BinlogFile; +import com.alibaba.otter.canal.parse.inbound.mysql.rds.data.RdsBackupPolicy; /** * @author agapple 2017年10月15日 下午2:14:34 @@ -13,15 +16,19 @@ import com.alibaba.otter.canal.parse.inbound.mysql.rds.RdsBinlogOpenApi; */ public class RdsBinlogOpenApiTest { + @Test public void testSimple() throws Throwable { - Date startTime = DateUtils.parseDate("2017-10-13 20:56:58", new String[] { "yyyy-MM-dd HH:mm:ss" }); - Date endTime = DateUtils.parseDate("2017-10-14 02:57:59", new String[] { "yyyy-MM-dd HH:mm:ss" }); - RdsBinlogOpenApi.downloadBinlogFiles("https://rds.aliyuncs.com/", - "", - "", - "rm-bp180v4mfjnm157es", - startTime, - endTime, - new File("/tmp/binlog/")); + Date startTime = DateUtils.parseDate("2018-08-10 12:00:00", new String[] { "yyyy-MM-dd HH:mm:ss" }); + Date endTime = DateUtils.parseDate("2018-08-11 12:00:00", new String[] { "yyyy-MM-dd HH:mm:ss" }); + String url = "https://rds.aliyuncs.com/"; + String ak = ""; + String sk = ""; + String dbInstanceId = ""; + + RdsBackupPolicy backupPolicy = RdsBinlogOpenApi.queryBinlogBackupPolicy(url, ak, sk, dbInstanceId); + System.out.println(backupPolicy); + + List binlogFiles = RdsBinlogOpenApi.listBinlogFiles(url, ak, sk, dbInstanceId, startTime, endTime); + System.out.println(binlogFiles); } } diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/SimpleDdlParserTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/SimpleDdlParserTest.java index f2bb1ce4..ed528d86 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/SimpleDdlParserTest.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/SimpleDdlParserTest.java @@ -225,5 +225,19 @@ public class SimpleDdlParserTest { Assert.assertNotNull(result); Assert.assertEquals("retl", result.getSchemaName()); Assert.assertEquals("retl_mark", result.getTableName()); + + // test index name contains 'on' -- version + queryString = "create index schema_new_index_version_s_idx on q_contract_account (contract_id,main_contract_id)"; + result = SimpleDdlParser.parse(queryString, "retl"); + Assert.assertNotNull(result); + Assert.assertEquals("retl", result.getSchemaName()); + Assert.assertEquals("q_contract_account", result.getTableName()); + + queryString = "drop index schema_new_index_version_s_idx on q_contract_account"; + result = SimpleDdlParser.parse(queryString, "retl"); + Assert.assertNotNull(result); + Assert.assertEquals("retl", result.getSchemaName()); + Assert.assertEquals("q_contract_account", result.getTableName()); + } } diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/FastsqlSchemaTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/FastsqlSchemaTest.java index c7e25607..bf0deafe 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/FastsqlSchemaTest.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/FastsqlSchemaTest.java @@ -18,13 +18,19 @@ public class FastsqlSchemaTest { @Test public void testSimple() throws FileNotFoundException, IOException { SchemaRepository repository = new SchemaRepository(JdbcConstants.MYSQL); - String sql = "create table yushitai_test.card_record ( id bigint auto_increment) auto_increment=256 " - + "; alter table yushitai_test.card_record add column customization_id bigint unsigned NOT NULL COMMENT 'TEST' ;" - + "; rename table yushitai_test.card_record to yushitai_test._card_record_del;"; + String sql = "create table yushitai_test.card_record ( id bigint auto_increment, name varchar(32) DEFAULT NULL) auto_increment=256 " + + "ALTER TABLE yushitai_test.card_record ADD COLUMN remark2 varchar(255) DEFAULT NULL , ALGORITHM=inplace,LOCK=NONE;" + + "ALTER TABLE yushitai_test.card_record modify COLUMN name varchar(64) DEFAULT NULL , ALGORITHM=copy,LOCK=SHARED; " + + "alter table yushitai_test.card_record add index index_name(name) ;" + + "alter table yushitai_test.card_record add index index_name(name) ;" + + "alter table yushitai_test.card_record add Constraint pk_id PRIMARY KEY (id);" + + "alter table yushitai_test.card_record add Constraint pk_id PRIMARY KEY (id);" + + "alter table yushitai_test.card_record add Constraint UNIQUE index uk_name(name);" + + "alter table yushitai_test.card_record add Constraint UNIQUE index uk_name(name);"; repository.console(sql); repository.setDefaultSchema("yushitai_test"); - SchemaObject table = repository.findTable("_card_record_del"); + SchemaObject table = repository.findTable("card_record"); System.out.println(table.getStatement().toString()); } } diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta_DDL_Test.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta_DDL_Test.java index e3005b62..fa0999fe 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta_DDL_Test.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MemoryTableMeta_DDL_Test.java @@ -37,4 +37,19 @@ public class MemoryTableMeta_DDL_Test { meta = memoryTableMeta.find("yushitai_test", "_card_record_gho"); Assert.assertNull(meta); } + + @Test + public void test2() throws Throwable { + MemoryTableMeta memoryTableMeta = new MemoryTableMeta(); + URL url = Thread.currentThread().getContextClassLoader().getResource("dummy.txt"); + File dummyFile = new File(url.getFile()); + File create = new File(dummyFile.getParent() + "/ddl", "ddl_test2.sql"); + String sql = StringUtils.join(IOUtils.readLines(new FileInputStream(create)), "\n"); + memoryTableMeta.apply(null, "test", sql, null); + + TableMeta meta = memoryTableMeta.find("yushitai_test", "card_record"); + System.out.println(meta); + Assert.assertEquals(meta.getFieldMetaByName("id").isKey(), true); + Assert.assertEquals(meta.getFieldMetaByName("name").isUnique(), true); + } } diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MetaHistoryDAOTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MetaHistoryDAOTest.java index b199a326..cea6c087 100644 --- a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MetaHistoryDAOTest.java +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MetaHistoryDAOTest.java @@ -16,7 +16,7 @@ import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.dao.MetaHistoryDO; * Created by wanshao Date: 2017/9/20 Time: 下午5:00 **/ @RunWith(SpringJUnit4ClassRunner.class) -@ContextConfiguration(locations = { "/tsdb/mysql-tsdb.xml" }) +@ContextConfiguration(locations = { "/tsdb/h2-tsdb.xml" }) public class MetaHistoryDAOTest { @Resource @@ -24,7 +24,22 @@ public class MetaHistoryDAOTest { @Test public void testSimple() { - List metaHistoryDOList = metaHistoryDAO.findByTimestamp("test", 0L, 0L); + MetaHistoryDO historyDO = new MetaHistoryDO(); + historyDO.setDestination("test"); + historyDO.setBinlogFile("000001"); + historyDO.setBinlogOffest(4L); + historyDO.setBinlogMasterId("1"); + historyDO.setBinlogTimestamp(System.currentTimeMillis() - 7300 * 1000); + historyDO.setSqlSchema("test"); + historyDO.setUseSchema("test"); + historyDO.setSqlTable("testTable"); + historyDO.setSqlTable("drop table testTable"); + metaHistoryDAO.insert(historyDO); + + int count = metaHistoryDAO.deleteByTimestamp("test", 7200); + System.out.println(count); + + List metaHistoryDOList = metaHistoryDAO.findByTimestamp("test", 0L, System.currentTimeMillis()); for (MetaHistoryDO metaHistoryDO : metaHistoryDOList) { System.out.println(metaHistoryDO.getId()); } diff --git a/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MetaSnapshotDAOTest.java b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MetaSnapshotDAOTest.java new file mode 100644 index 00000000..f503e4b2 --- /dev/null +++ b/parse/src/test/java/com/alibaba/otter/canal/parse/inbound/mysql/tsdb/MetaSnapshotDAOTest.java @@ -0,0 +1,41 @@ +package com.alibaba.otter.canal.parse.inbound.mysql.tsdb; + +import javax.annotation.Resource; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.test.context.ContextConfiguration; +import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; + +import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.dao.MetaSnapshotDAO; +import com.alibaba.otter.canal.parse.inbound.mysql.tsdb.dao.MetaSnapshotDO; + +/** + * Created by wanshao Date: 2017/9/20 Time: 下午5:00 + **/ +@RunWith(SpringJUnit4ClassRunner.class) +@ContextConfiguration(locations = { "/tsdb/h2-tsdb.xml" }) +public class MetaSnapshotDAOTest { + + @Resource + MetaSnapshotDAO metaSnapshotDAO; + + @Test + public void testSimple() { + MetaSnapshotDO metaSnapshotDO = new MetaSnapshotDO(); + metaSnapshotDO.setDestination("test"); + metaSnapshotDO.setBinlogFile("000001"); + metaSnapshotDO.setBinlogOffest(4L); + metaSnapshotDO.setBinlogMasterId("1"); + metaSnapshotDO.setBinlogTimestamp(System.currentTimeMillis() - 7300 * 1000); + metaSnapshotDO.setData("test"); + metaSnapshotDAO.insert(metaSnapshotDO); + + MetaSnapshotDO snapshotDO = metaSnapshotDAO.findByTimestamp("test", System.currentTimeMillis()); + System.out.println(snapshotDO); + + int count = metaSnapshotDAO.deleteByTimestamp("test", 7200); + System.out.println(count); + } + +} diff --git a/parse/src/test/resources/ddl/ddl_test2.sql b/parse/src/test/resources/ddl/ddl_test2.sql new file mode 100644 index 00000000..aaf7d286 --- /dev/null +++ b/parse/src/test/resources/ddl/ddl_test2.sql @@ -0,0 +1,8 @@ +CREATE TABLE yushitai_test.card_record ( + id bigint AUTO_INCREMENT, + name varchar(32) DEFAULT NULL, + alias varchar(32) DEFAULT NULL, + INDEX index_name(name), + CONSTRAINT pk_id PRIMARY KEY (id), + UNIQUE uk_name (name,alias) +) AUTO_INCREMENT = 256 diff --git a/parse/src/test/resources/tsdb/h2-tsdb.xml b/parse/src/test/resources/tsdb/h2-tsdb.xml index c0a3d385..dcb6bc47 100644 --- a/parse/src/test/resources/tsdb/h2-tsdb.xml +++ b/parse/src/test/resources/tsdb/h2-tsdb.xml @@ -7,7 +7,7 @@ default-autowire="byName"> - + diff --git a/parse/src/test/resources/tsdb/mysql-tsdb.xml b/parse/src/test/resources/tsdb/mysql-tsdb.xml index 099c034d..44f97203 100644 --- a/parse/src/test/resources/tsdb/mysql-tsdb.xml +++ b/parse/src/test/resources/tsdb/mysql-tsdb.xml @@ -7,7 +7,7 @@ default-autowire="byName"> - + diff --git a/parse/src/test/resources/tsdb/sql-map/sqlmap_history.xml b/parse/src/test/resources/tsdb/sql-map/sqlmap_history.xml index 7445bf69..58957c28 100644 --- a/parse/src/test/resources/tsdb/sql-map/sqlmap_history.xml +++ b/parse/src/test/resources/tsdb/sql-map/sqlmap_history.xml @@ -36,10 +36,10 @@ - + \ No newline at end of file diff --git a/parse/src/test/resources/tsdb/sql-map/sqlmap_snapshot.xml b/parse/src/test/resources/tsdb/sql-map/sqlmap_snapshot.xml index 7ba0a435..60827c6c 100644 --- a/parse/src/test/resources/tsdb/sql-map/sqlmap_snapshot.xml +++ b/parse/src/test/resources/tsdb/sql-map/sqlmap_snapshot.xml @@ -54,10 +54,10 @@ where destination=#destination# - + 0 ]]> \ No newline at end of file diff --git a/pom.xml b/pom.xml index 8ab961ea..e5ba86c9 100644 --- a/pom.xml +++ b/pom.xml @@ -4,7 +4,7 @@ canal pom canal module for otter ${project.version} - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT https://github.com/alibaba/canal org.sonatype.oss @@ -66,16 +66,6 @@ false - - alibaba - http://code.alibabatech.com/mvn/releases/ - - true - - - false - - sonatype sonatype @@ -106,10 +96,10 @@ true true - 1.6 - 1.6 + 1.7 + 1.7 UTF-8 - 3.2.9.RELEASE + 3.2.18.RELEASE @@ -127,8 +117,8 @@ client deployer example - kafka - kafka-client + prometheus + client-adapter @@ -246,7 +236,7 @@ com.google.protobuf protobuf-java - 2.6.1 + 3.6.1 org.apache.ibatis @@ -256,7 +246,7 @@ com.alibaba.fastsql fastsql - 2.0.0_preview_371 + 2.0.0_preview_644 com.alibaba @@ -307,7 +297,21 @@ 5.1.40 - + + com.google.code.findbugs + jsr305 + 3.0.2 + + + com.aliyun.openservices + aliware-apache-rocketmq-cloud + 1.0 + + + org.apache.rocketmq + rocketmq-client + 4.3.0 + @@ -341,7 +345,7 @@ org.apache.maven.plugins maven-compiler-plugin - 3.2 + 3.7.0 ${java_source_version} ${java_target_version} @@ -377,61 +381,24 @@ - + org.apache.maven.plugins + maven-javadoc-plugin + 2.9.1 + + + attach-javadocs + + jar + + + + + ${file_encoding} + ${file_encoding} + -Xdoclint:none + + src/main/java src/test/java diff --git a/prometheus/pom.xml b/prometheus/pom.xml new file mode 100644 index 00000000..f6357c20 --- /dev/null +++ b/prometheus/pom.xml @@ -0,0 +1,54 @@ + + + + canal + com.alibaba.otter + 1.1.3-SNAPSHOT + + 4.0.0 + + com.alibaba.otter + canal.prometheus + 1.1.3-SNAPSHOT + canal prometheus module for otter ${project.version} + + + org.jctools + jctools-core + 2.1.2 + + + io.prometheus + simpleclient + 0.4.0 + + + io.prometheus + simpleclient_hotspot + 0.4.0 + + + io.prometheus + simpleclient_httpserver + 0.4.0 + + + io.prometheus + simpleclient_pushgateway + 0.4.0 + + + com.alibaba.otter + canal.instance.core + ${project.version} + provided + + + com.alibaba.otter + canal.server + ${project.version} + provided + + + + diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/CanalInstanceExports.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/CanalInstanceExports.java new file mode 100644 index 00000000..6f50214c --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/CanalInstanceExports.java @@ -0,0 +1,85 @@ +package com.alibaba.otter.canal.prometheus; + +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.prometheus.impl.*; +import io.prometheus.client.Collector; +import io.prometheus.client.CollectorRegistry; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.Collections; +import java.util.List; + +/** + * @author Chuanyi Li + */ +public class CanalInstanceExports { + + private static final Logger logger = LoggerFactory.getLogger(CanalInstanceExports.class); + public static final String DEST = "destination"; + public static final String[] DEST_LABELS = {DEST}; + public static final List DEST_LABELS_LIST = Collections.singletonList(DEST); + private final Collector storeCollector; + private final Collector entryCollector; + private final Collector metaCollector; + private final Collector sinkCollector; + private final Collector parserCollector; + + private CanalInstanceExports() { + this.storeCollector = StoreCollector.instance(); + this.entryCollector = EntryCollector.instance(); + this.metaCollector = MetaCollector.instance(); + this.sinkCollector = SinkCollector.instance(); + this.parserCollector = ParserCollector.instance(); + } + + private static class SingletonHolder { + private static final CanalInstanceExports SINGLETON = new CanalInstanceExports(); + } + + public static CanalInstanceExports instance() { + return SingletonHolder.SINGLETON; + } + + public void initialize() { + storeCollector.register(); + entryCollector.register(); + metaCollector.register(); + sinkCollector.register(); + parserCollector.register(); + } + + public void terminate() { + CollectorRegistry.defaultRegistry.unregister(storeCollector); + CollectorRegistry.defaultRegistry.unregister(entryCollector); + CollectorRegistry.defaultRegistry.unregister(metaCollector); + CollectorRegistry.defaultRegistry.unregister(sinkCollector); + CollectorRegistry.defaultRegistry.unregister(parserCollector); + } + + void register(CanalInstance instance) { + requiredInstanceRegistry(storeCollector).register(instance); + requiredInstanceRegistry(entryCollector).register(instance); + requiredInstanceRegistry(metaCollector).register(instance); + requiredInstanceRegistry(sinkCollector).register(instance); + requiredInstanceRegistry(parserCollector).register(instance); + logger.info("Successfully register metrics for instance {}.", instance.getDestination()); + } + + void unregister(CanalInstance instance) { + requiredInstanceRegistry(storeCollector).unregister(instance); + requiredInstanceRegistry(entryCollector).unregister(instance); + requiredInstanceRegistry(metaCollector).unregister(instance); + requiredInstanceRegistry(sinkCollector).unregister(instance); + requiredInstanceRegistry(parserCollector).unregister(instance); + logger.info("Successfully unregister metrics for instance {}.", instance.getDestination()); + } + + private InstanceRegistry requiredInstanceRegistry(Collector collector) { + if (!(collector instanceof InstanceRegistry)) { + throw new IllegalArgumentException("Canal prometheus collector need to implement InstanceRegistry."); + } + return (InstanceRegistry) collector; + } + +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/InstanceRegistry.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/InstanceRegistry.java new file mode 100644 index 00000000..e320efc4 --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/InstanceRegistry.java @@ -0,0 +1,14 @@ +package com.alibaba.otter.canal.prometheus; + +import com.alibaba.otter.canal.instance.core.CanalInstance; + +/** + * @author Chuanyi Li + */ +public interface InstanceRegistry { + + void register(CanalInstance instance); + + void unregister(CanalInstance instance); + +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/PrometheusProvider.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/PrometheusProvider.java new file mode 100644 index 00000000..12b8675f --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/PrometheusProvider.java @@ -0,0 +1,15 @@ +package com.alibaba.otter.canal.prometheus; + +import com.alibaba.otter.canal.spi.CanalMetricsProvider; +import com.alibaba.otter.canal.spi.CanalMetricsService; + +/** + * @author Chuanyi Li + */ +public class PrometheusProvider implements CanalMetricsProvider { + + @Override + public CanalMetricsService getService() { + return PrometheusService.getInstance(); + } +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/PrometheusService.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/PrometheusService.java new file mode 100644 index 00000000..18bf63f7 --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/PrometheusService.java @@ -0,0 +1,121 @@ +package com.alibaba.otter.canal.prometheus; + +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.prometheus.impl.PrometheusClientInstanceProfiler; +import com.alibaba.otter.canal.server.netty.ClientInstanceProfiler; +import com.alibaba.otter.canal.spi.CanalMetricsService; +import io.prometheus.client.exporter.HTTPServer; +import io.prometheus.client.hotspot.DefaultExports; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.io.IOException; + +import static com.alibaba.otter.canal.server.netty.CanalServerWithNettyProfiler.NOP; +import static com.alibaba.otter.canal.server.netty.CanalServerWithNettyProfiler.profiler; + +/** + * @author Chuanyi Li + */ +public class PrometheusService implements CanalMetricsService { + + private static final Logger logger = LoggerFactory.getLogger(PrometheusService.class); + private final CanalInstanceExports instanceExports; + private volatile boolean running = false; + private int port; + private HTTPServer server; + private final ClientInstanceProfiler clientProfiler; + + private PrometheusService() { + this.instanceExports = CanalInstanceExports.instance(); + this.clientProfiler = PrometheusClientInstanceProfiler.instance(); + } + + private static class SingletonHolder { + private static final PrometheusService SINGLETON = new PrometheusService(); + } + + public static PrometheusService getInstance() { + return SingletonHolder.SINGLETON; + } + + @Override + public void initialize() { + try { + logger.info("Start prometheus HTTPServer on port {}.", port); + //TODO 2.Https? + server = new HTTPServer(port); + } catch (IOException e) { + logger.warn("Unable to start prometheus HTTPServer.", e); + return; + } + try { + // JVM exports + DefaultExports.initialize(); + instanceExports.initialize(); + if (!clientProfiler.isStart()) { + clientProfiler.start(); + } + profiler().setInstanceProfiler(clientProfiler); + } catch (Throwable t) { + logger.warn("Unable to initialize server exports.", t); + } + + running = true; + } + + @Override + public void terminate() { + running = false; + try { + instanceExports.terminate(); + if (clientProfiler.isStart()) { + clientProfiler.stop(); + } + profiler().setInstanceProfiler(NOP); + if (server != null) { + server.stop(); + } + } catch (Throwable t) { + logger.warn("Something happened while terminating.", t); + } + } + + @Override + public boolean isRunning() { + return running; + } + + @Override + public void register(CanalInstance instance) { + if (instance.isStart()) { + logger.warn("Cannot register metrics for destination {} that is running.", instance.getDestination()); + return; + } + try { + instanceExports.register(instance); + } catch (Throwable t) { + logger.warn("Unable to register instance exports for {}.", instance.getDestination(), t); + } + logger.info("Register metrics for destination {}.", instance.getDestination()); + } + + @Override + public void unregister(CanalInstance instance) { + if (instance.isStart()) { + logger.warn("Try unregister metrics after destination {} is stopped.", instance.getDestination()); + } + try { + instanceExports.unregister(instance); + } catch (Throwable t) { + logger.warn("Unable to unregister instance exports for {}.", instance.getDestination(), t); + } + logger.info("Unregister metrics for destination {}.", instance.getDestination()); + } + + @Override + public void setServerPort(int port) { + this.port = port; + } + +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/EntryCollector.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/EntryCollector.java new file mode 100644 index 00000000..bbd51720 --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/EntryCollector.java @@ -0,0 +1,134 @@ +package com.alibaba.otter.canal.prometheus.impl; + +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.prometheus.InstanceRegistry; +import com.alibaba.otter.canal.sink.CanalEventDownStreamHandler; +import com.alibaba.otter.canal.sink.CanalEventSink; +import com.alibaba.otter.canal.sink.entry.EntryEventSink; +import com.google.common.base.Preconditions; +import io.prometheus.client.Collector; +import io.prometheus.client.CounterMetricFamily; +import io.prometheus.client.GaugeMetricFamily; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.atomic.AtomicLong; + +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST_LABELS_LIST; + +/** + * @author Chuanyi Li + */ +public class EntryCollector extends Collector implements InstanceRegistry { + + private static final Logger logger = LoggerFactory.getLogger(SinkCollector.class); + private static final String DELAY = "canal_instance_traffic_delay"; + private static final String TRANSACTION = "canal_instance_transactions"; + private static final String DELAY_HELP = "Traffic delay of canal instance in milliseconds"; + private static final String TRANSACTION_HELP = "Transactions counter of canal instance"; + private final ConcurrentMap instances = new ConcurrentHashMap(); + + private EntryCollector() {} + + private static class SingletonHolder { + private static final EntryCollector SINGLETON = new EntryCollector(); + } + + public static EntryCollector instance() { + return SingletonHolder.SINGLETON; + } + + @Override + public List collect() { + List mfs = new ArrayList(); + GaugeMetricFamily delay = new GaugeMetricFamily(DELAY, + DELAY_HELP, DEST_LABELS_LIST); + CounterMetricFamily transactions = new CounterMetricFamily(TRANSACTION, + TRANSACTION_HELP, DEST_LABELS_LIST); + for (EntryMetricsHolder emh : instances.values()) { + long now = System.currentTimeMillis(); + long latest = emh.latestExecTime.get(); + // execTime > now,delay显示为0 + long d = (now >= latest) ? (now - latest) : 0; + delay.addMetric(emh.destLabelValues, d); + transactions.addMetric(emh.destLabelValues, emh.transactionCounter.doubleValue()); + } + mfs.add(delay); + mfs.add(transactions); + return mfs; + } + + @Override + public void register(CanalInstance instance) { + final String destination = instance.getDestination(); + EntryMetricsHolder holder = new EntryMetricsHolder(); + holder.destLabelValues = Collections.singletonList(destination); + CanalEventSink sink = instance.getEventSink(); + if (!(sink instanceof EntryEventSink)) { + throw new IllegalArgumentException("CanalEventSink must be EntryEventSink"); + } + EntryEventSink entrySink = (EntryEventSink) sink; + PrometheusCanalEventDownStreamHandler handler = assembleHandler(entrySink); + holder.latestExecTime = handler.getLatestExecuteTime(); + holder.transactionCounter = handler.getTransactionCounter(); + Preconditions.checkNotNull(holder.latestExecTime); + Preconditions.checkNotNull(holder.transactionCounter); + EntryMetricsHolder old = instances.put(destination, holder); + if (old != null) { + logger.warn("Remove stale EntryCollector for instance {}.", destination); + } + } + + @Override + public void unregister(CanalInstance instance) { + final String destination = instance.getDestination(); + CanalEventSink sink = instance.getEventSink(); + if (!(sink instanceof EntryEventSink)) { + throw new IllegalArgumentException("CanalEventSink must be EntryEventSink"); + } + unloadHandler((EntryEventSink) sink); + instances.remove(destination); + } + + private PrometheusCanalEventDownStreamHandler assembleHandler(EntryEventSink entrySink) { + PrometheusCanalEventDownStreamHandler ph = new PrometheusCanalEventDownStreamHandler(); + List handlers = entrySink.getHandlers(); + for (CanalEventDownStreamHandler handler : handlers) { + if (handler instanceof PrometheusCanalEventDownStreamHandler) { + throw new IllegalStateException("PrometheusCanalEventDownStreamHandler already exists in handlers."); + } + } + entrySink.addHandler(ph, 0); + return ph; + } + + private void unloadHandler(EntryEventSink entrySink) { + List handlers = entrySink.getHandlers(); + int i = 0; + for (; i < handlers.size(); i++) { + if (handlers.get(i) instanceof PrometheusCanalEventDownStreamHandler) { + break; + } + } + entrySink.removeHandler(i); + // Ensure no PrometheusCanalEventDownStreamHandler + handlers = entrySink.getHandlers(); + for (CanalEventDownStreamHandler handler : handlers) { + if (handler instanceof PrometheusCanalEventDownStreamHandler) { + throw new IllegalStateException("Multiple prometheusCanalEventDownStreamHandler exists in handlers."); + } + } + } + + private class EntryMetricsHolder { + private AtomicLong latestExecTime; + private AtomicLong transactionCounter; + private List destLabelValues; + } + +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/MetaCollector.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/MetaCollector.java new file mode 100644 index 00000000..e51e8e29 --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/MetaCollector.java @@ -0,0 +1,91 @@ +package com.alibaba.otter.canal.prometheus.impl; + +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.instance.spring.CanalInstanceWithSpring; +import com.alibaba.otter.canal.meta.CanalMetaManager; +import com.alibaba.otter.canal.prometheus.InstanceRegistry; +import com.alibaba.otter.canal.protocol.ClientIdentity; +import com.google.common.base.Preconditions; +import io.prometheus.client.Collector; +import io.prometheus.client.GaugeMetricFamily; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.*; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; + +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST_LABELS_LIST; + +/** + * @author Chuanyi Li + */ +public class MetaCollector extends Collector implements InstanceRegistry { + + private static final List INFO_LABELS_LIST = Arrays.asList("destination", "mode"); + private static final Logger logger = LoggerFactory.getLogger(MetaCollector.class); + private static final String INSTANCE = "canal_instance"; + private static final String INSTANCE_HELP = "Canal instance"; + private static final String SUBSCRIPTION = "canal_instance_subscriptions"; + private static final String SUBSCRIPTION_HELP = "Canal instance subscriptions"; + private final ConcurrentMap instances = new ConcurrentHashMap(); + + private MetaCollector() {} + + private static class SingletonHolder { + private static final MetaCollector SINGLETON = new MetaCollector(); + } + + public static MetaCollector instance() { + return SingletonHolder.SINGLETON; + } + + @Override + public List collect() { + List mfs = new ArrayList(); + GaugeMetricFamily instanceInfo = new GaugeMetricFamily(INSTANCE, + INSTANCE_HELP, INFO_LABELS_LIST); + GaugeMetricFamily subsInfo = new GaugeMetricFamily(SUBSCRIPTION, + SUBSCRIPTION_HELP, DEST_LABELS_LIST); + for (Map.Entry nme : instances.entrySet()) { + final String destination = nme.getKey(); + final MetaMetricsHolder nmh = nme.getValue(); + instanceInfo.addMetric(nmh.infoLabelValues, 1); + List subs = nmh.metaManager.listAllSubscribeInfo(destination); + int count = subs == null ? 0 : subs.size(); + subsInfo.addMetric(nmh.destLabelValues, count); + } + mfs.add(instanceInfo); + mfs.add(subsInfo); + return mfs; + } + + @Override + public void register(CanalInstance instance) { + final String destination = instance.getDestination(); + MetaMetricsHolder holder = new MetaMetricsHolder(); + String mode = (instance instanceof CanalInstanceWithSpring) ? "spring" : "manager"; + holder.infoLabelValues = Arrays.asList(destination, mode); + holder.destLabelValues = Collections.singletonList(destination); + holder.metaManager = instance.getMetaManager(); + Preconditions.checkNotNull(holder.metaManager); + MetaMetricsHolder old = instances.put(destination, holder); + if (old != null) { + logger.warn("Remove stale MetaCollector for instance {}.", destination); + } + } + + @Override + public void unregister(CanalInstance instance) { + final String destination = instance.getDestination(); + instances.remove(destination); + } + + private class MetaMetricsHolder { + private List infoLabelValues; + private List destLabelValues; + private CanalMetaManager metaManager; + } + + +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/ParserCollector.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/ParserCollector.java new file mode 100644 index 00000000..660bf1ca --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/ParserCollector.java @@ -0,0 +1,158 @@ +package com.alibaba.otter.canal.prometheus.impl; + +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST; + +import com.alibaba.otter.canal.parse.inbound.group.GroupEventParser; +import com.alibaba.otter.canal.parse.inbound.mysql.AbstractMysqlEventParser; +import io.prometheus.client.Collector; +import io.prometheus.client.CounterMetricFamily; +import io.prometheus.client.GaugeMetricFamily; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.atomic.AtomicLong; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.parse.CanalEventParser; +import com.alibaba.otter.canal.prometheus.InstanceRegistry; +import com.google.common.base.Preconditions; + +/** + * @author Chuanyi Li + */ +public class ParserCollector extends Collector implements InstanceRegistry { + + private static final Logger logger = LoggerFactory.getLogger(ParserCollector.class); + private static final long NANO_PER_MILLI = 1000 * 1000L; + private static final String PUBLISH_BLOCKING = "canal_instance_publish_blocking_time"; + private static final String RECEIVED_BINLOG = "canal_instance_received_binlog_bytes"; + private static final String PARSER_MODE = "canal_instance_parser_mode"; + private static final String MODE_LABEL = "parallel"; + private static final String PARSER_LABEL = "parser"; + private static final String PUBLISH_BLOCKING_HELP = "Publish blocking time of dump thread in milliseconds"; + private static final String RECEIVED_BINLOG_HELP = "Received binlog bytes"; + private static final String MODE_HELP = "Parser mode(parallel/serial) of instance"; + private final List modeLabels = Arrays.asList(DEST, MODE_LABEL); + private final List parserLabels = Arrays.asList(DEST, PARSER_LABEL); + private final ConcurrentMap instances = new ConcurrentHashMap<>(); + + private ParserCollector() {} + + private static class SingletonHolder { + private static final ParserCollector SINGLETON = new ParserCollector(); + } + + public static ParserCollector instance() { + return SingletonHolder.SINGLETON; + } + + @Override + public List collect() { + List mfs = new ArrayList<>(); + CounterMetricFamily bytesCounter = new CounterMetricFamily(RECEIVED_BINLOG, + RECEIVED_BINLOG_HELP, parserLabels); + GaugeMetricFamily modeGauge = new GaugeMetricFamily(PARSER_MODE, + MODE_HELP, modeLabels); + CounterMetricFamily blockingCounter = new CounterMetricFamily(PUBLISH_BLOCKING, + PUBLISH_BLOCKING_HELP, parserLabels); + for (ParserMetricsHolder emh : instances.values()) { + if (emh instanceof GroupParserMetricsHolder) { + GroupParserMetricsHolder group = (GroupParserMetricsHolder) emh; + for (ParserMetricsHolder semh : group.holders) { + singleCollect(bytesCounter, blockingCounter, modeGauge, semh); + } + } + else { + singleCollect(bytesCounter, blockingCounter, modeGauge, emh); + } + } + mfs.add(bytesCounter); + mfs.add(modeGauge); + if (!blockingCounter.samples.isEmpty()) { + mfs.add(blockingCounter); + } + return mfs; + } + + private void singleCollect(CounterMetricFamily bytesCounter, CounterMetricFamily blockingCounter, GaugeMetricFamily modeGauge, ParserMetricsHolder holder) { + if (holder.isParallel) { + blockingCounter.addMetric(holder.parserLabelValues, (holder.eventsPublishBlockingTime.doubleValue() / NANO_PER_MILLI)); + } + modeGauge.addMetric(holder.modeLabelValues, 1); + bytesCounter.addMetric(holder.parserLabelValues, holder.receivedBinlogBytes.doubleValue()); + } + + @Override + public void register(CanalInstance instance) { + final String destination = instance.getDestination(); + ParserMetricsHolder holder; + CanalEventParser parser = instance.getEventParser(); + if (parser instanceof AbstractMysqlEventParser) { + holder = singleHolder(destination, (AbstractMysqlEventParser)parser, "0"); + } else if (parser instanceof GroupEventParser) { + holder = groupHolder(destination, (GroupEventParser)parser); + } else { + throw new IllegalArgumentException("CanalEventParser must be either AbstractMysqlEventParser or GroupEventParser."); + } + Preconditions.checkNotNull(holder); + ParserMetricsHolder old = instances.put(destination, holder); + if (old != null) { + logger.warn("Remove stale ParserCollector for instance {}.", destination); + } + } + + private ParserMetricsHolder singleHolder(String destination, AbstractMysqlEventParser parser, String id) { + ParserMetricsHolder holder = new ParserMetricsHolder(); + holder.parserLabelValues = Arrays.asList(destination, id); + holder.modeLabelValues = Arrays.asList(destination, Boolean.toString(parser.isParallel())); + holder.eventsPublishBlockingTime = parser.getEventsPublishBlockingTime(); + holder.receivedBinlogBytes = parser.getReceivedBinlogBytes(); + holder.isParallel = parser.isParallel(); + Preconditions.checkNotNull(holder.eventsPublishBlockingTime); + Preconditions.checkNotNull(holder.receivedBinlogBytes); + return holder; + } + + private GroupParserMetricsHolder groupHolder(String destination, GroupEventParser group) { + List parsers = group.getEventParsers(); + GroupParserMetricsHolder groupHolder = new GroupParserMetricsHolder(); + int num = parsers.size(); + for (int i = 0; i < num; i ++) { + CanalEventParser parser = parsers.get(i); + if (parser instanceof AbstractMysqlEventParser) { + ParserMetricsHolder single = singleHolder(destination, (AbstractMysqlEventParser)parser, Integer.toString(i + 1)); + groupHolder.holders.add(single); + } else { + logger.warn("Null or non AbstractMysqlEventParser, ignore."); + } + } + return groupHolder; + } + + @Override + public void unregister(CanalInstance instance) { + final String destination = instance.getDestination(); + instances.remove(destination); + } + + private class ParserMetricsHolder { + private List parserLabelValues; + private List modeLabelValues; + // metrics for single parser + private AtomicLong receivedBinlogBytes; + private AtomicLong eventsPublishBlockingTime; + // parser mode + private boolean isParallel; + } + + private class GroupParserMetricsHolder extends ParserMetricsHolder { + private final List holders = new ArrayList<>(); + } + +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/PrometheusCanalEventDownStreamHandler.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/PrometheusCanalEventDownStreamHandler.java new file mode 100644 index 00000000..0bfacffe --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/PrometheusCanalEventDownStreamHandler.java @@ -0,0 +1,79 @@ +package com.alibaba.otter.canal.prometheus.impl; + +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.CanalEntry.EntryType; +import com.alibaba.otter.canal.sink.AbstractCanalEventDownStreamHandler; +import com.alibaba.otter.canal.store.model.Event; + +import java.util.List; +import java.util.concurrent.atomic.AtomicLong; + +/** + * @author Chuanyi Li + */ +public class PrometheusCanalEventDownStreamHandler extends AbstractCanalEventDownStreamHandler> { + + private final AtomicLong latestExecuteTime = new AtomicLong(System.currentTimeMillis()); + private final AtomicLong transactionCounter = new AtomicLong(0L); + + @Override + public List before(List events) { + long localExecTime = 0L; + if (events != null && !events.isEmpty()) { + for (Event e : events) { + EntryType type = e.getEntryType(); + if (type == null) continue; + switch (type) { + case TRANSACTIONBEGIN: { + long exec = e.getExecuteTime(); + if (exec > 0) localExecTime = exec; + break; + } + case ROWDATA: { + long exec = e.getExecuteTime(); + if (exec > 0) localExecTime = exec; + break; + } + case TRANSACTIONEND: { + long exec = e.getExecuteTime(); + if (exec > 0) localExecTime = exec; + transactionCounter.incrementAndGet(); + break; + } + case HEARTBEAT: + CanalEntry.EventType eventType = e.getEventType(); + if (eventType == CanalEntry.EventType.MHEARTBEAT) { + localExecTime = System.currentTimeMillis(); + } + break; + default: + break; + } + } + if (localExecTime > 0) { + latestExecuteTime.lazySet(localExecTime); + } + } + return events; + } + + @Override + public void start() { + + super.start(); + } + + @Override + public void stop() { + super.stop(); + } + + public AtomicLong getLatestExecuteTime() { + return latestExecuteTime; + } + + public AtomicLong getTransactionCounter() { + return transactionCounter; + } + +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/PrometheusClientInstanceProfiler.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/PrometheusClientInstanceProfiler.java new file mode 100644 index 00000000..afc96405 --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/PrometheusClientInstanceProfiler.java @@ -0,0 +1,141 @@ +package com.alibaba.otter.canal.prometheus.impl; + +import com.alibaba.otter.canal.protocol.CanalPacket.PacketType; +import com.alibaba.otter.canal.server.netty.ClientInstanceProfiler; +import com.alibaba.otter.canal.server.netty.listener.ChannelFutureAggregator.ClientRequestResult; +import io.prometheus.client.CollectorRegistry; +import io.prometheus.client.Counter; +import io.prometheus.client.Histogram; + +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST; +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST_LABELS; + +/** + * @author Chuanyi Li + */ +public class PrometheusClientInstanceProfiler implements ClientInstanceProfiler { + + private static final long NANO_PER_MILLI = 1000 * 1000L; + private static final String PACKET_TYPE = "canal_instance_client_packets"; + private static final String OUTBOUND_BYTES = "canal_instance_client_bytes"; + private static final String EMPTY_BATCHES = "canal_instance_client_empty_batches"; + private static final String ERRORS = "canal_instance_client_request_error"; + private static final String LATENCY = "canal_instance_client_request_latency"; + private final Counter outboundCounter; + private final Counter packetsCounter; + private final Counter emptyBatchesCounter; + private final Counter errorsCounter; + private final Histogram responseLatency; + private volatile boolean running = false; + + private static class SingletonHolder { + private static final PrometheusClientInstanceProfiler SINGLETON = new PrometheusClientInstanceProfiler(); + } + + public static PrometheusClientInstanceProfiler instance() { + return SingletonHolder.SINGLETON; + } + + private PrometheusClientInstanceProfiler() { + this.outboundCounter = Counter.build() + .labelNames(DEST_LABELS) + .name(OUTBOUND_BYTES) + .help("Total bytes sent to client.") + .create(); + this.packetsCounter = Counter.build() + .labelNames(new String[]{DEST, "packetType"}) + .name(PACKET_TYPE) + .help("Total packets sent to client.") + .create(); + this.emptyBatchesCounter = Counter.build() + .labelNames(DEST_LABELS) + .name(EMPTY_BATCHES) + .help("Total empty batches sent to client.") + .create(); + this.errorsCounter = Counter.build() + .labelNames(new String[]{DEST, "errorCode"}) + .name(ERRORS) + .help("Total client request errors.") + .create(); + this.responseLatency = Histogram.build() + .labelNames(DEST_LABELS) + .name(LATENCY) + .help("Client request latency.") + // buckets in milliseconds + .buckets(2.5, 10.0, 25.0, 100.0) + .create(); + } + + @Override + public void profiling(ClientRequestResult result) { + String destination = result.getDestination(); + PacketType type = result.getType(); + outboundCounter.labels(destination).inc(result.getAmount()); + short errorCode = result.getErrorCode(); + if (errorCode > 0) { + errorsCounter.labels(destination, Short.toString(errorCode)).inc(); + } + long latency = result.getLatency(); + responseLatency.labels(destination).observe(((double) latency) / NANO_PER_MILLI); + switch (type) { + case GET: + boolean empty = result.getEmpty(); + // 区分一下空包 + if (empty) { + emptyBatchesCounter.labels(destination).inc(); + } else { + packetsCounter.labels(destination, type.name()).inc(); + } + break; + // reserve for others + default: + packetsCounter.labels(destination, type.name()).inc(); + break; + } + } + + @Override + public void start() { + if (outboundCounter != null) { + outboundCounter.register(); + } + if (packetsCounter != null) { + packetsCounter.register(); + } + if (emptyBatchesCounter != null) { + emptyBatchesCounter.register(); + } + if (errorsCounter != null) { + errorsCounter.register(); + } + if (responseLatency != null) { + responseLatency.register(); + } + running = true; + } + + @Override + public void stop() { + running = false; + if (outboundCounter != null) { + CollectorRegistry.defaultRegistry.unregister(outboundCounter); + } + if (packetsCounter != null) { + CollectorRegistry.defaultRegistry.unregister(packetsCounter); + } + if (emptyBatchesCounter != null) { + CollectorRegistry.defaultRegistry.unregister(emptyBatchesCounter); + } + if (errorsCounter != null) { + CollectorRegistry.defaultRegistry.unregister(errorsCounter); + } + if (responseLatency != null) { + CollectorRegistry.defaultRegistry.unregister(responseLatency); + } + } + + @Override + public boolean isStart() { + return running; + } +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/SinkCollector.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/SinkCollector.java new file mode 100644 index 00000000..61dc4d64 --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/SinkCollector.java @@ -0,0 +1,84 @@ +package com.alibaba.otter.canal.prometheus.impl; + +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.prometheus.InstanceRegistry; +import com.alibaba.otter.canal.sink.CanalEventSink; +import com.alibaba.otter.canal.sink.entry.EntryEventSink; +import com.google.common.base.Preconditions; +import io.prometheus.client.Collector; +import io.prometheus.client.CounterMetricFamily; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.atomic.AtomicLong; + +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST_LABELS_LIST; +import static java.util.concurrent.TimeUnit.NANOSECONDS; + +/** + * @author Chuanyi Li + */ +public class SinkCollector extends Collector implements InstanceRegistry { + + private static final Logger logger = LoggerFactory.getLogger(SinkCollector.class); + private static final long NANO_PER_MILLI = 1000 * 1000L; + private static final String SINK_BLOCKING_TIME = "canal_instance_sink_blocking_time"; + private static final String SINK_BLOCK_TIME_HELP = "Total sink blocking time in milliseconds"; + private final ConcurrentMap instances = new ConcurrentHashMap(); + + private SinkCollector() {} + + private static class SingletonHolder { + private static final SinkCollector SINGLETON = new SinkCollector(); + } + + public static SinkCollector instance() { + return SingletonHolder.SINGLETON; + } + + @Override + public List collect() { + List mfs = new ArrayList(); + CounterMetricFamily blockingCounter = new CounterMetricFamily(SINK_BLOCKING_TIME, + SINK_BLOCK_TIME_HELP, DEST_LABELS_LIST); + for (SinkMetricsHolder smh : instances.values()) { + blockingCounter.addMetric(smh.destLabelValues, (smh.eventsSinkBlockingTime.doubleValue() / NANO_PER_MILLI)); + } + mfs.add(blockingCounter); + return mfs; + } + + @Override + public void register(CanalInstance instance) { + final String destination = instance.getDestination(); + SinkMetricsHolder holder = new SinkMetricsHolder(); + holder.destLabelValues = Collections.singletonList(destination); + CanalEventSink sink = instance.getEventSink(); + if (!(sink instanceof EntryEventSink)) { + throw new IllegalArgumentException("CanalEventSink must be EntryEventSink"); + } + EntryEventSink entrySink = (EntryEventSink) sink; + holder.eventsSinkBlockingTime = entrySink.getEventsSinkBlockingTime(); + Preconditions.checkNotNull(holder.eventsSinkBlockingTime); + SinkMetricsHolder old = instances.put(destination, holder); + if (old != null) { + logger.warn("Remote stale SinkCollector for instance {}.", destination); + } + } + + @Override + public void unregister(CanalInstance instance) { + final String destination = instance.getDestination(); + instances.remove(destination); + } + + private class SinkMetricsHolder { + private AtomicLong eventsSinkBlockingTime; + private List destLabelValues; + } +} diff --git a/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/StoreCollector.java b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/StoreCollector.java new file mode 100644 index 00000000..cb26f228 --- /dev/null +++ b/prometheus/src/main/java/com/alibaba/otter/canal/prometheus/impl/StoreCollector.java @@ -0,0 +1,193 @@ +package com.alibaba.otter.canal.prometheus.impl; + +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.prometheus.InstanceRegistry; +import com.alibaba.otter.canal.store.CanalEventStore; +import com.alibaba.otter.canal.store.memory.MemoryEventStoreWithBuffer; +import com.alibaba.otter.canal.store.model.BatchMode; +import com.google.common.base.Preconditions; +import io.prometheus.client.Collector; +import io.prometheus.client.CounterMetricFamily; +import io.prometheus.client.GaugeMetricFamily; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.atomic.AtomicLong; + +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST; +import static com.alibaba.otter.canal.prometheus.CanalInstanceExports.DEST_LABELS_LIST; + +/** + * @author Chuanyi Li + */ +public class StoreCollector extends Collector implements InstanceRegistry { + + private static final Logger logger = LoggerFactory.getLogger(SinkCollector.class); + private static final String PRODUCE = "canal_instance_store_produce_seq"; + private static final String CONSUME = "canal_instance_store_consume_seq"; + private static final String STORE = "canal_instance_store"; + private static final String PRODUCE_MEM = "canal_instance_store_produce_mem"; + private static final String CONSUME_MEM = "canal_instance_store_consume_mem"; + private static final String PUT_DELAY = "canal_instance_put_delay"; + private static final String GET_DELAY = "canal_instance_get_delay"; + private static final String ACK_DELAY = "canal_instance_ack_delay"; + private static final String PUT_ROWS = "canal_instance_put_rows"; + private static final String GET_ROWS = "canal_instance_get_rows"; + private static final String ACK_ROWS = "canal_instance_ack_rows"; + private static final String PRODUCE_HELP = "Produced events counter of canal instance"; + private static final String CONSUME_HELP = "Consumed events counter of canal instance"; + private static final String STORE_HELP = "Canal instance info"; + private static final String PRODUCE_MEM_HELP = "Produced mem bytes of canal instance"; + private static final String CONSUME_MEM_HELP = "Consumed mem bytes of canal instance"; + private static final String PUT_DELAY_HELP = "Traffic delay of canal instance put"; + private static final String GET_DELAY_HELP = "Traffic delay of canal instance get"; + private static final String ACK_DELAY_HELP = "Traffic delay of canal instance ack"; + private static final String PUT_ROWS_HELP = "Put table rows of canal instance"; + private static final String GET_ROWS_HELP = "Got table rows of canal instance"; + private static final String ACK_ROWS_HELP = "Acked table rows of canal instance"; + private final ConcurrentMap instances = new ConcurrentHashMap(); + private final List storeLabelsList = Arrays.asList(DEST, "batchMode", "size"); + + private StoreCollector() {} + + private static class SingletonHolder { + private static final StoreCollector SINGLETON = new StoreCollector(); + } + + public static StoreCollector instance() { + return SingletonHolder.SINGLETON; + } + + @Override + public List collect() { + List mfs = new ArrayList(); + CounterMetricFamily put = new CounterMetricFamily(PRODUCE, + PRODUCE_HELP, DEST_LABELS_LIST); + CounterMetricFamily ack = new CounterMetricFamily(CONSUME, + CONSUME_HELP, DEST_LABELS_LIST); + GaugeMetricFamily store = new GaugeMetricFamily(STORE, + STORE_HELP, storeLabelsList); + CounterMetricFamily putMem = new CounterMetricFamily(PRODUCE_MEM, + PRODUCE_MEM_HELP, DEST_LABELS_LIST); + CounterMetricFamily ackMem = new CounterMetricFamily(CONSUME_MEM, + CONSUME_MEM_HELP, DEST_LABELS_LIST); + GaugeMetricFamily putDelay = new GaugeMetricFamily(PUT_DELAY, + PUT_DELAY_HELP, DEST_LABELS_LIST); + GaugeMetricFamily getDelay = new GaugeMetricFamily(GET_DELAY, + GET_DELAY_HELP, DEST_LABELS_LIST); + GaugeMetricFamily ackDelay = new GaugeMetricFamily(ACK_DELAY, + ACK_DELAY_HELP, DEST_LABELS_LIST); + CounterMetricFamily putRows = new CounterMetricFamily(PUT_ROWS, + PUT_ROWS_HELP, DEST_LABELS_LIST); + CounterMetricFamily getRows = new CounterMetricFamily(GET_ROWS, + GET_ROWS_HELP, DEST_LABELS_LIST); + CounterMetricFamily ackRows = new CounterMetricFamily(ACK_ROWS, + ACK_ROWS_HELP, DEST_LABELS_LIST); + boolean hasMem = false; + for (StoreMetricsHolder smh : instances.values()) { + final boolean isMem = smh.batchMode.isMemSize(); + put.addMetric(smh.destLabelValues, smh.putSeq.doubleValue()); + ack.addMetric(smh.destLabelValues, smh.ackSeq.doubleValue()); + long pet = smh.putExecTime.get(); + // 防止出现启动时,未消费造成的get, ack延时小于前阶段的情况 + long get = Math.min(smh.getExecTime.get(), pet); + long aet = Math.min(smh.ackExecTime.get(), get); + long now = System.currentTimeMillis(); + // execTime > now,delay显示为0 + long pd = (now >= pet) ? (now - pet) : 0; + putDelay.addMetric(smh.destLabelValues, pd); + long gd = (now >= get) ? (now - get) : 0; + getDelay.addMetric(smh.destLabelValues, gd); + long ad = (now >= aet) ? (now - aet) : 0; + ackDelay.addMetric(smh.destLabelValues, ad); + putRows.addMetric(smh.destLabelValues, smh.putTableRows.doubleValue()); + getRows.addMetric(smh.destLabelValues, smh.getTableRows.doubleValue()); + ackRows.addMetric(smh.destLabelValues, smh.ackTableRows.doubleValue()); + store.addMetric(smh.storeLabelValues, 1); + if (isMem) { + hasMem = true; + putMem.addMetric(smh.destLabelValues, smh.putMemSize.doubleValue()); + ackMem.addMetric(smh.destLabelValues, smh.ackMemSize.doubleValue()); + } + } + mfs.add(put); + mfs.add(ack); + mfs.add(store); + mfs.add(putDelay); + mfs.add(getDelay); + mfs.add(ackDelay); + mfs.add(putRows); + mfs.add(getRows); + mfs.add(ackRows); + if (hasMem) { + mfs.add(putMem); + mfs.add(ackMem); + } + return mfs; + } + + @Override + public void register(CanalInstance instance) { + final String destination = instance.getDestination(); + StoreMetricsHolder holder = new StoreMetricsHolder(); + CanalEventStore store = instance.getEventStore(); + if (!(store instanceof MemoryEventStoreWithBuffer)) { + throw new IllegalArgumentException("EventStore must be MemoryEventStoreWithBuffer"); + } + MemoryEventStoreWithBuffer memStore = (MemoryEventStoreWithBuffer) store; + holder.batchMode = memStore.getBatchMode(); + holder.putSeq = memStore.getPutSequence(); + holder.ackSeq = memStore.getAckSequence(); + holder.destLabelValues = Collections.singletonList(destination); + holder.size = memStore.getBufferSize(); + holder.storeLabelValues = Arrays.asList(destination, holder.batchMode.name(), Integer.toString(holder.size)); + holder.putExecTime = memStore.getPutExecTime(); + holder.getExecTime = memStore.getGetExecTime(); + holder.ackExecTime = memStore.getAckExecTime(); + holder.putTableRows = memStore.getPutTableRows(); + holder.getTableRows = memStore.getGetTableRows(); + holder.ackTableRows = memStore.getAckTableRows(); + Preconditions.checkNotNull(holder.batchMode); + Preconditions.checkNotNull(holder.putSeq); + Preconditions.checkNotNull(holder.ackSeq); + if (holder.batchMode.isMemSize()) { + holder.putMemSize = memStore.getPutMemSize(); + holder.ackMemSize = memStore.getAckMemSize(); + Preconditions.checkNotNull(holder.putMemSize); + Preconditions.checkNotNull(holder.ackMemSize); + } + StoreMetricsHolder old = instances.putIfAbsent(destination, holder); + if (old != null) { + logger.warn("Remote stale StoreCollector for instance {}.", destination); + } + } + + @Override + public void unregister(CanalInstance instance) { + final String destination = instance.getDestination(); + instances.remove(destination); + } + + private class StoreMetricsHolder { + private AtomicLong putSeq; + private AtomicLong ackSeq; + private BatchMode batchMode; + private AtomicLong putMemSize; + private AtomicLong ackMemSize; + private AtomicLong putExecTime; + private AtomicLong getExecTime; + private AtomicLong ackExecTime; + private AtomicLong putTableRows; + private AtomicLong getTableRows; + private AtomicLong ackTableRows; + private int size; + private List destLabelValues; + private List storeLabelValues; + } +} diff --git a/prometheus/src/main/resources/META-INF/services/com.alibaba.otter.canal.spi.CanalMetricsProvider b/prometheus/src/main/resources/META-INF/services/com.alibaba.otter.canal.spi.CanalMetricsProvider new file mode 100644 index 00000000..9adbf8d1 --- /dev/null +++ b/prometheus/src/main/resources/META-INF/services/com.alibaba.otter.canal.spi.CanalMetricsProvider @@ -0,0 +1 @@ +com.alibaba.otter.canal.prometheus.PrometheusProvider diff --git a/protocol/pom.xml b/protocol/pom.xml index ec7c7867..1b776b7e 100644 --- a/protocol/pom.xml +++ b/protocol/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter diff --git a/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalEntry.java b/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalEntry.java index 1a0979db..0ff7d1ab 100644 --- a/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalEntry.java +++ b/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalEntry.java @@ -4,13051 +4,12836 @@ package com.alibaba.otter.canal.protocol; public final class CanalEntry { - - private CanalEntry(){ - } - - public static void registerAllExtensions(com.google.protobuf.ExtensionRegistry registry) { - } - + private CanalEntry() {} + public static void registerAllExtensions( + com.google.protobuf.ExtensionRegistry registry) { + } + /** + * Protobuf enum {@code com.alibaba.otter.canal.protocol.EntryType} + * + *
      +   **打散后的事件类型,主要用于标识事务的开始,变更数据,结束*
      +   * 
      + */ + public enum EntryType + implements com.google.protobuf.ProtocolMessageEnum { /** - * Protobuf enum {@code com.alibaba.otter.canal.protocol.EntryType} + * TRANSACTIONBEGIN = 1; + */ + TRANSACTIONBEGIN(0, 1), + /** + * ROWDATA = 2; + */ + ROWDATA(1, 2), + /** + * TRANSACTIONEND = 3; + */ + TRANSACTIONEND(2, 3), + /** + * HEARTBEAT = 4; * *
      -     * *打散后的事件类型,主要用于标识事务的开始,变更数据,结束*
      +     ** 心跳类型,内部使用,外部暂不可见,可忽略 *
            * 
      */ - public enum EntryType implements com.google.protobuf.ProtocolMessageEnum { - /** - * TRANSACTIONBEGIN = 1; - */ - TRANSACTIONBEGIN(0, 1), - /** - * ROWDATA = 2; - */ - ROWDATA(1, 2), - /** - * TRANSACTIONEND = 3; - */ - TRANSACTIONEND(2, 3), - /** - * HEARTBEAT = 4; - * - *
      -         * * 心跳类型,内部使用,外部暂不可见,可忽略 *
      -         * 
      - */ - HEARTBEAT(3, 4), - /** - * GTIDLOG = 5; - */ - GTIDLOG(4, 5), ; - - /** - * TRANSACTIONBEGIN = 1; - */ - public static final int TRANSACTIONBEGIN_VALUE = 1; - /** - * ROWDATA = 2; - */ - public static final int ROWDATA_VALUE = 2; - /** - * TRANSACTIONEND = 3; - */ - public static final int TRANSACTIONEND_VALUE = 3; - /** - * HEARTBEAT = 4; - * - *
      -         * * 心跳类型,内部使用,外部暂不可见,可忽略 *
      -         * 
      - */ - public static final int HEARTBEAT_VALUE = 4; - /** - * GTIDLOG = 5; - */ - public static final int GTIDLOG_VALUE = 5; - - public final int getNumber() { - return value; - } - - public static EntryType valueOf(int value) { - switch (value) { - case 1: - return TRANSACTIONBEGIN; - case 2: - return ROWDATA; - case 3: - return TRANSACTIONEND; - case 4: - return HEARTBEAT; - case 5: - return GTIDLOG; - default: - return null; - } - } - - public static com.google.protobuf.Internal.EnumLiteMap internalGetValueMap() { - return internalValueMap; - } - - private static com.google.protobuf.Internal.EnumLiteMap internalValueMap = new com.google.protobuf.Internal.EnumLiteMap() { - - public EntryType findValueByNumber(int number) { - return EntryType.valueOf(number); - } - }; - - public final com.google.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() { - return getDescriptor().getValues().get(index); - } - - public final com.google.protobuf.Descriptors.EnumDescriptor getDescriptorForType() { - return getDescriptor(); - } - - public static final com.google.protobuf.Descriptors.EnumDescriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.getDescriptor().getEnumTypes().get(0); - } - - private static final EntryType[] VALUES = values(); - - public static EntryType valueOf(com.google.protobuf.Descriptors.EnumValueDescriptor desc) { - if (desc.getType() != getDescriptor()) { - throw new java.lang.IllegalArgumentException("EnumValueDescriptor is not for this type."); - } - return VALUES[desc.getIndex()]; - } - - private final int index; - private final int value; - - private EntryType(int index, int value){ - this.index = index; - this.value = value; - } - - // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.EntryType) - } + HEARTBEAT(3, 4), + /** + * GTIDLOG = 5; + */ + GTIDLOG(4, 5), + ; /** - * Protobuf enum {@code com.alibaba.otter.canal.protocol.EventType} + * TRANSACTIONBEGIN = 1; + */ + public static final int TRANSACTIONBEGIN_VALUE = 1; + /** + * ROWDATA = 2; + */ + public static final int ROWDATA_VALUE = 2; + /** + * TRANSACTIONEND = 3; + */ + public static final int TRANSACTIONEND_VALUE = 3; + /** + * HEARTBEAT = 4; * *
      -     * * 事件类型 *
      +     ** 心跳类型,内部使用,外部暂不可见,可忽略 *
            * 
      */ - public enum EventType implements com.google.protobuf.ProtocolMessageEnum { - /** - * INSERT = 1; - */ - INSERT(0, 1), - /** - * UPDATE = 2; - */ - UPDATE(1, 2), - /** - * DELETE = 3; - */ - DELETE(2, 3), - /** - * CREATE = 4; - */ - CREATE(3, 4), - /** - * ALTER = 5; - */ - ALTER(4, 5), - /** - * ERASE = 6; - */ - ERASE(5, 6), - /** - * QUERY = 7; - */ - QUERY(6, 7), - /** - * TRUNCATE = 8; - */ - TRUNCATE(7, 8), - /** - * RENAME = 9; - */ - RENAME(8, 9), - /** - * CINDEX = 10; - * - *
      -         * *CREATE INDEX*
      -         * 
      - */ - CINDEX(9, 10), - /** - * DINDEX = 11; - */ - DINDEX(10, 11), - /** - * GTID = 12; - */ - GTID(11, 12), - /** - * XASTART = 13; - * - *
      -         * * XA *
      -         * 
      - */ - XASTART(12, 13), - /** - * XAEND = 14; - */ - XAEND(13, 14), - /** - * XACOMMIT = 15; - */ - XACOMMIT(14, 15), - /** - * XAROLLBACK = 16; - */ - XAROLLBACK(15, 16), ; + public static final int HEARTBEAT_VALUE = 4; + /** + * GTIDLOG = 5; + */ + public static final int GTIDLOG_VALUE = 5; - /** - * INSERT = 1; - */ - public static final int INSERT_VALUE = 1; - /** - * UPDATE = 2; - */ - public static final int UPDATE_VALUE = 2; - /** - * DELETE = 3; - */ - public static final int DELETE_VALUE = 3; - /** - * CREATE = 4; - */ - public static final int CREATE_VALUE = 4; - /** - * ALTER = 5; - */ - public static final int ALTER_VALUE = 5; - /** - * ERASE = 6; - */ - public static final int ERASE_VALUE = 6; - /** - * QUERY = 7; - */ - public static final int QUERY_VALUE = 7; - /** - * TRUNCATE = 8; - */ - public static final int TRUNCATE_VALUE = 8; - /** - * RENAME = 9; - */ - public static final int RENAME_VALUE = 9; - /** - * CINDEX = 10; - * - *
      -         * *CREATE INDEX*
      -         * 
      - */ - public static final int CINDEX_VALUE = 10; - /** - * DINDEX = 11; - */ - public static final int DINDEX_VALUE = 11; - /** - * GTID = 12; - */ - public static final int GTID_VALUE = 12; - /** - * XASTART = 13; - * - *
      -         * * XA *
      -         * 
      - */ - public static final int XASTART_VALUE = 13; - /** - * XAEND = 14; - */ - public static final int XAEND_VALUE = 14; - /** - * XACOMMIT = 15; - */ - public static final int XACOMMIT_VALUE = 15; - /** - * XAROLLBACK = 16; - */ - public static final int XAROLLBACK_VALUE = 16; - public final int getNumber() { - return value; - } + public final int getNumber() { return value; } - public static EventType valueOf(int value) { - switch (value) { - case 1: - return INSERT; - case 2: - return UPDATE; - case 3: - return DELETE; - case 4: - return CREATE; - case 5: - return ALTER; - case 6: - return ERASE; - case 7: - return QUERY; - case 8: - return TRUNCATE; - case 9: - return RENAME; - case 10: - return CINDEX; - case 11: - return DINDEX; - case 12: - return GTID; - case 13: - return XASTART; - case 14: - return XAEND; - case 15: - return XACOMMIT; - case 16: - return XAROLLBACK; - default: - return null; - } - } - - public static com.google.protobuf.Internal.EnumLiteMap internalGetValueMap() { - return internalValueMap; - } - - private static com.google.protobuf.Internal.EnumLiteMap internalValueMap = new com.google.protobuf.Internal.EnumLiteMap() { - - public EventType findValueByNumber(int number) { - return EventType.valueOf(number); - } - }; - - public final com.google.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() { - return getDescriptor().getValues().get(index); - } - - public final com.google.protobuf.Descriptors.EnumDescriptor getDescriptorForType() { - return getDescriptor(); - } - - public static final com.google.protobuf.Descriptors.EnumDescriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.getDescriptor().getEnumTypes().get(1); - } - - private static final EventType[] VALUES = values(); - - public static EventType valueOf(com.google.protobuf.Descriptors.EnumValueDescriptor desc) { - if (desc.getType() != getDescriptor()) { - throw new java.lang.IllegalArgumentException("EnumValueDescriptor is not for this type."); - } - return VALUES[desc.getIndex()]; - } - - private final int index; - private final int value; - - private EventType(int index, int value){ - this.index = index; - this.value = value; - } - - // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.EventType) + public static EntryType valueOf(int value) { + switch (value) { + case 1: return TRANSACTIONBEGIN; + case 2: return ROWDATA; + case 3: return TRANSACTIONEND; + case 4: return HEARTBEAT; + case 5: return GTIDLOG; + default: return null; + } } + public static com.google.protobuf.Internal.EnumLiteMap + internalGetValueMap() { + return internalValueMap; + } + private static com.google.protobuf.Internal.EnumLiteMap + internalValueMap = + new com.google.protobuf.Internal.EnumLiteMap() { + public EntryType findValueByNumber(int number) { + return EntryType.valueOf(number); + } + }; + + public final com.google.protobuf.Descriptors.EnumValueDescriptor + getValueDescriptor() { + return getDescriptor().getValues().get(index); + } + public final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptorForType() { + return getDescriptor(); + } + public static final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptor() { + return CanalEntry.getDescriptor().getEnumTypes().get(0); + } + + private static final EntryType[] VALUES = values(); + + public static EntryType valueOf( + com.google.protobuf.Descriptors.EnumValueDescriptor desc) { + if (desc.getType() != getDescriptor()) { + throw new IllegalArgumentException( + "EnumValueDescriptor is not for this type."); + } + return VALUES[desc.getIndex()]; + } + + private final int index; + private final int value; + + private EntryType(int index, int value) { + this.index = index; + this.value = value; + } + + // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.EntryType) + } + + /** + * Protobuf enum {@code com.alibaba.otter.canal.protocol.EventType} + * + *
      +   ** 事件类型 *
      +   * 
      + */ + public enum EventType + implements com.google.protobuf.ProtocolMessageEnum { + /** + * INSERT = 1; + */ + INSERT(0, 1), + /** + * UPDATE = 2; + */ + UPDATE(1, 2), + /** + * DELETE = 3; + */ + DELETE(2, 3), + /** + * CREATE = 4; + */ + CREATE(3, 4), + /** + * ALTER = 5; + */ + ALTER(4, 5), + /** + * ERASE = 6; + */ + ERASE(5, 6), + /** + * QUERY = 7; + */ + QUERY(6, 7), + /** + * TRUNCATE = 8; + */ + TRUNCATE(7, 8), + /** + * RENAME = 9; + */ + RENAME(8, 9), + /** + * CINDEX = 10; + * + *
      +     **CREATE INDEX*
      +     * 
      + */ + CINDEX(9, 10), + /** + * DINDEX = 11; + */ + DINDEX(10, 11), + /** + * GTID = 12; + */ + GTID(11, 12), + /** + * XACOMMIT = 13; + * + *
      +     ** XA *
      +     * 
      + */ + XACOMMIT(12, 13), + /** + * XAROLLBACK = 14; + */ + XAROLLBACK(13, 14), + /** + * MHEARTBEAT = 15; + * + *
      +     ** MASTER HEARTBEAT *
      +     * 
      + */ + MHEARTBEAT(14, 15), + ; + /** - * Protobuf enum {@code com.alibaba.otter.canal.protocol.Type} + * INSERT = 1; + */ + public static final int INSERT_VALUE = 1; + /** + * UPDATE = 2; + */ + public static final int UPDATE_VALUE = 2; + /** + * DELETE = 3; + */ + public static final int DELETE_VALUE = 3; + /** + * CREATE = 4; + */ + public static final int CREATE_VALUE = 4; + /** + * ALTER = 5; + */ + public static final int ALTER_VALUE = 5; + /** + * ERASE = 6; + */ + public static final int ERASE_VALUE = 6; + /** + * QUERY = 7; + */ + public static final int QUERY_VALUE = 7; + /** + * TRUNCATE = 8; + */ + public static final int TRUNCATE_VALUE = 8; + /** + * RENAME = 9; + */ + public static final int RENAME_VALUE = 9; + /** + * CINDEX = 10; * *
      -     * *数据库类型*
      +     **CREATE INDEX*
            * 
      */ - public enum Type implements com.google.protobuf.ProtocolMessageEnum { - /** - * ORACLE = 1; - */ - ORACLE(0, 1), - /** - * MYSQL = 2; - */ - MYSQL(1, 2), - /** - * PGSQL = 3; - */ - PGSQL(2, 3), ; + public static final int CINDEX_VALUE = 10; + /** + * DINDEX = 11; + */ + public static final int DINDEX_VALUE = 11; + /** + * GTID = 12; + */ + public static final int GTID_VALUE = 12; + /** + * XACOMMIT = 13; + * + *
      +     ** XA *
      +     * 
      + */ + public static final int XACOMMIT_VALUE = 13; + /** + * XAROLLBACK = 14; + */ + public static final int XAROLLBACK_VALUE = 14; + /** + * MHEARTBEAT = 15; + * + *
      +     ** MASTER HEARTBEAT *
      +     * 
      + */ + public static final int MHEARTBEAT_VALUE = 15; - /** - * ORACLE = 1; - */ - public static final int ORACLE_VALUE = 1; - /** - * MYSQL = 2; - */ - public static final int MYSQL_VALUE = 2; - /** - * PGSQL = 3; - */ - public static final int PGSQL_VALUE = 3; - public final int getNumber() { - return value; - } + public final int getNumber() { return value; } - public static Type valueOf(int value) { - switch (value) { - case 1: - return ORACLE; - case 2: - return MYSQL; - case 3: - return PGSQL; - default: - return null; - } - } - - public static com.google.protobuf.Internal.EnumLiteMap internalGetValueMap() { - return internalValueMap; - } - - private static com.google.protobuf.Internal.EnumLiteMap internalValueMap = new com.google.protobuf.Internal.EnumLiteMap() { - - public Type findValueByNumber(int number) { - return Type.valueOf(number); - } - }; - - public final com.google.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() { - return getDescriptor().getValues().get(index); - } - - public final com.google.protobuf.Descriptors.EnumDescriptor getDescriptorForType() { - return getDescriptor(); - } - - public static final com.google.protobuf.Descriptors.EnumDescriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.getDescriptor().getEnumTypes().get(2); - } - - private static final Type[] VALUES = values(); - - public static Type valueOf(com.google.protobuf.Descriptors.EnumValueDescriptor desc) { - if (desc.getType() != getDescriptor()) { - throw new java.lang.IllegalArgumentException("EnumValueDescriptor is not for this type."); - } - return VALUES[desc.getIndex()]; - } - - private final int index; - private final int value; - - private Type(int index, int value){ - this.index = index; - this.value = value; - } - - // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.Type) + public static EventType valueOf(int value) { + switch (value) { + case 1: return INSERT; + case 2: return UPDATE; + case 3: return DELETE; + case 4: return CREATE; + case 5: return ALTER; + case 6: return ERASE; + case 7: return QUERY; + case 8: return TRUNCATE; + case 9: return RENAME; + case 10: return CINDEX; + case 11: return DINDEX; + case 12: return GTID; + case 13: return XACOMMIT; + case 14: return XAROLLBACK; + case 15: return MHEARTBEAT; + default: return null; + } } - public interface EntryOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Entry) - com.google.protobuf.MessageOrBuilder { + public static com.google.protobuf.Internal.EnumLiteMap + internalGetValueMap() { + return internalValueMap; + } + private static com.google.protobuf.Internal.EnumLiteMap + internalValueMap = + new com.google.protobuf.Internal.EnumLiteMap() { + public EventType findValueByNumber(int number) { + return EventType.valueOf(number); + } + }; - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -         * *协议头部信息*
      -         * 
      - */ - boolean hasHeader(); - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -         * *协议头部信息*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Header getHeader(); - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -         * *协议头部信息*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.HeaderOrBuilder getHeaderOrBuilder(); - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -         * *打散后的事件类型*
      -         * 
      - */ - boolean hasEntryType(); - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -         * *打散后的事件类型*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.EntryType getEntryType(); - - /** - * optional bytes storeValue = 3; - * - *
      -         * *传输的二进制数组*
      -         * 
      - */ - boolean hasStoreValue(); - - /** - * optional bytes storeValue = 3; - * - *
      -         * *传输的二进制数组*
      -         * 
      - */ - com.google.protobuf.ByteString getStoreValue(); + public final com.google.protobuf.Descriptors.EnumValueDescriptor + getValueDescriptor() { + return getDescriptor().getValues().get(index); + } + public final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptorForType() { + return getDescriptor(); + } + public static final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptor() { + return CanalEntry.getDescriptor().getEnumTypes().get(1); } + private static final EventType[] VALUES = values(); + + public static EventType valueOf( + com.google.protobuf.Descriptors.EnumValueDescriptor desc) { + if (desc.getType() != getDescriptor()) { + throw new IllegalArgumentException( + "EnumValueDescriptor is not for this type."); + } + return VALUES[desc.getIndex()]; + } + + private final int index; + private final int value; + + private EventType(int index, int value) { + this.index = index; + this.value = value; + } + + // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.EventType) + } + + /** + * Protobuf enum {@code com.alibaba.otter.canal.protocol.Type} + * + *
      +   **数据库类型*
      +   * 
      + */ + public enum Type + implements com.google.protobuf.ProtocolMessageEnum { + /** + * ORACLE = 1; + */ + ORACLE(0, 1), + /** + * MYSQL = 2; + */ + MYSQL(1, 2), + /** + * PGSQL = 3; + */ + PGSQL(2, 3), + ; + + /** + * ORACLE = 1; + */ + public static final int ORACLE_VALUE = 1; + /** + * MYSQL = 2; + */ + public static final int MYSQL_VALUE = 2; + /** + * PGSQL = 3; + */ + public static final int PGSQL_VALUE = 3; + + + public final int getNumber() { return value; } + + public static Type valueOf(int value) { + switch (value) { + case 1: return ORACLE; + case 2: return MYSQL; + case 3: return PGSQL; + default: return null; + } + } + + public static com.google.protobuf.Internal.EnumLiteMap + internalGetValueMap() { + return internalValueMap; + } + private static com.google.protobuf.Internal.EnumLiteMap + internalValueMap = + new com.google.protobuf.Internal.EnumLiteMap() { + public Type findValueByNumber(int number) { + return Type.valueOf(number); + } + }; + + public final com.google.protobuf.Descriptors.EnumValueDescriptor + getValueDescriptor() { + return getDescriptor().getValues().get(index); + } + public final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptorForType() { + return getDescriptor(); + } + public static final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptor() { + return CanalEntry.getDescriptor().getEnumTypes().get(2); + } + + private static final Type[] VALUES = values(); + + public static Type valueOf( + com.google.protobuf.Descriptors.EnumValueDescriptor desc) { + if (desc.getType() != getDescriptor()) { + throw new IllegalArgumentException( + "EnumValueDescriptor is not for this type."); + } + return VALUES[desc.getIndex()]; + } + + private final int index; + private final int value; + + private Type(int index, int value) { + this.index = index; + this.value = value; + } + + // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.Type) + } + + public interface EntryOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Entry) + com.google.protobuf.MessageOrBuilder { + + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +     **协议头部信息*
      +     * 
      + */ + boolean hasHeader(); + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +     **协议头部信息*
      +     * 
      + */ + Header getHeader(); + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +     **协议头部信息*
      +     * 
      + */ + HeaderOrBuilder getHeaderOrBuilder(); + + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +     **打散后的事件类型*
      +     * 
      + */ + boolean hasEntryType(); + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +     **打散后的事件类型*
      +     * 
      + */ + EntryType getEntryType(); + + /** + * optional bytes storeValue = 3; + * + *
      +     **传输的二进制数组*
      +     * 
      + */ + boolean hasStoreValue(); + /** + * optional bytes storeValue = 3; + * + *
      +     **传输的二进制数组*
      +     * 
      + */ + com.google.protobuf.ByteString getStoreValue(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.Entry} + * + *
      +   ****************************************************************
      +   * message model
      +   *如果要在Enum中新增类型,确保以前的类型的下标值不变.
      +   ***************************************************************
      +   * 
      + */ + public static final class Entry extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Entry) + EntryOrBuilder { + // Use Entry.newBuilder() to construct. + private Entry(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private Entry(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final Entry defaultInstance; + public static Entry getDefaultInstance() { + return defaultInstance; + } + + public Entry getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Entry( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 10: { + Header.Builder subBuilder = null; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + subBuilder = header_.toBuilder(); + } + header_ = input.readMessage(Header.PARSER, extensionRegistry); + if (subBuilder != null) { + subBuilder.mergeFrom(header_); + header_ = subBuilder.buildPartial(); + } + bitField0_ |= 0x00000001; + break; + } + case 16: { + int rawValue = input.readEnum(); + EntryType value = EntryType.valueOf(rawValue); + if (value == null) { + unknownFields.mergeVarintField(2, rawValue); + } else { + bitField0_ |= 0x00000002; + entryType_ = value; + } + break; + } + case 26: { + bitField0_ |= 0x00000004; + storeValue_ = input.readBytes(); + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Entry.class, Builder.class); + } + + public static com.google.protobuf.Parser PARSER = + new com.google.protobuf.AbstractParser() { + public Entry parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Entry(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + private int bitField0_; + public static final int HEADER_FIELD_NUMBER = 1; + private Header header_; + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +     **协议头部信息*
      +     * 
      + */ + public boolean hasHeader() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +     **协议头部信息*
      +     * 
      + */ + public Header getHeader() { + return header_; + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +     **协议头部信息*
      +     * 
      + */ + public HeaderOrBuilder getHeaderOrBuilder() { + return header_; + } + + public static final int ENTRYTYPE_FIELD_NUMBER = 2; + private EntryType entryType_; + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +     **打散后的事件类型*
      +     * 
      + */ + public boolean hasEntryType() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +     **打散后的事件类型*
      +     * 
      + */ + public EntryType getEntryType() { + return entryType_; + } + + public static final int STOREVALUE_FIELD_NUMBER = 3; + private com.google.protobuf.ByteString storeValue_; + /** + * optional bytes storeValue = 3; + * + *
      +     **传输的二进制数组*
      +     * 
      + */ + public boolean hasStoreValue() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional bytes storeValue = 3; + * + *
      +     **传输的二进制数组*
      +     * 
      + */ + public com.google.protobuf.ByteString getStoreValue() { + return storeValue_; + } + + private void initFields() { + header_ = Header.getDefaultInstance(); + entryType_ = EntryType.ROWDATA; + storeValue_ = com.google.protobuf.ByteString.EMPTY; + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + if (((bitField0_ & 0x00000001) == 0x00000001)) { + output.writeMessage(1, header_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + output.writeEnum(2, entryType_.getNumber()); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + output.writeBytes(3, storeValue_); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(1, header_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + size += com.google.protobuf.CodedOutputStream + .computeEnumSize(2, entryType_.getNumber()); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(3, storeValue_); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static Entry parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Entry parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Entry parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Entry parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Entry parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Entry parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static Entry parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static Entry parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static Entry parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Entry parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(Entry prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.Entry} * *
            ****************************************************************
      -     *  message model
      -     * 如果要在Enum中新增类型,确保以前的类型的下标值不变.
      +     * message model
      +     *如果要在Enum中新增类型,确保以前的类型的下标值不变.
            ***************************************************************
            * 
      */ - public static final class Entry extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Entry) - EntryOrBuilder { - - // Use Entry.newBuilder() to construct. - private Entry(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Entry(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Entry defaultInstance; - - public static Entry getDefaultInstance() { - return defaultInstance; - } - - public Entry getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Entry(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.alibaba.otter.canal.protocol.CanalEntry.Header.Builder subBuilder = null; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - subBuilder = header_.toBuilder(); - } - header_ = input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Header.PARSER, - extensionRegistry); - if (subBuilder != null) { - subBuilder.mergeFrom(header_); - header_ = subBuilder.buildPartial(); - } - bitField0_ |= 0x00000001; - break; - } - case 16: { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalEntry.EntryType value = com.alibaba.otter.canal.protocol.CanalEntry.EntryType.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(2, rawValue); - } else { - bitField0_ |= 0x00000002; - entryType_ = value; - } - break; - } - case 26: { - bitField0_ |= 0x00000004; - storeValue_ = input.readBytes(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Entry.class, - com.alibaba.otter.canal.protocol.CanalEntry.Entry.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Entry parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Entry(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int HEADER_FIELD_NUMBER = 1; - private com.alibaba.otter.canal.protocol.CanalEntry.Header header_; - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -         * *协议头部信息*
      -         * 
      - */ - public boolean hasHeader() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -         * *协议头部信息*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Header getHeader() { - return header_; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -         * *协议头部信息*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.HeaderOrBuilder getHeaderOrBuilder() { - return header_; - } - - public static final int ENTRYTYPE_FIELD_NUMBER = 2; - private com.alibaba.otter.canal.protocol.CanalEntry.EntryType entryType_; - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -         * *打散后的事件类型*
      -         * 
      - */ - public boolean hasEntryType() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -         * *打散后的事件类型*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.EntryType getEntryType() { - return entryType_; - } - - public static final int STOREVALUE_FIELD_NUMBER = 3; - private com.google.protobuf.ByteString storeValue_; - - /** - * optional bytes storeValue = 3; - * - *
      -         * *传输的二进制数组*
      -         * 
      - */ - public boolean hasStoreValue() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional bytes storeValue = 3; - * - *
      -         * *传输的二进制数组*
      -         * 
      - */ - public com.google.protobuf.ByteString getStoreValue() { - return storeValue_; - } - - private void initFields() { - header_ = com.alibaba.otter.canal.protocol.CanalEntry.Header.getDefaultInstance(); - entryType_ = com.alibaba.otter.canal.protocol.CanalEntry.EntryType.ROWDATA; - storeValue_ = com.google.protobuf.ByteString.EMPTY; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeMessage(1, header_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeEnum(2, entryType_.getNumber()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeBytes(3, storeValue_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(1, header_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeEnumSize(2, entryType_.getNumber()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(3, storeValue_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Entry parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Entry prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Entry} - * - *
      -         ****************************************************************
      -         *  message model
      -         * 如果要在Enum中新增类型,确保以前的类型的下标值不变.
      -         ***************************************************************
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Entry) - com.alibaba.otter.canal.protocol.CanalEntry.EntryOrBuilder { + EntryOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; - } + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Entry.class, Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Entry.class, - com.alibaba.otter.canal.protocol.CanalEntry.Entry.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.Entry.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.Entry.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - getHeaderFieldBuilder(); - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - if (headerBuilder_ == null) { - header_ = com.alibaba.otter.canal.protocol.CanalEntry.Header.getDefaultInstance(); - } else { - headerBuilder_.clear(); - } - bitField0_ = (bitField0_ & ~0x00000001); - entryType_ = com.alibaba.otter.canal.protocol.CanalEntry.EntryType.ROWDATA; - bitField0_ = (bitField0_ & ~0x00000002); - storeValue_ = com.google.protobuf.ByteString.EMPTY; - bitField0_ = (bitField0_ & ~0x00000004); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Entry getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.Entry.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Entry build() { - com.alibaba.otter.canal.protocol.CanalEntry.Entry result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Entry buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.Entry result = new com.alibaba.otter.canal.protocol.CanalEntry.Entry(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - if (headerBuilder_ == null) { - result.header_ = header_; - } else { - result.header_ = headerBuilder_.build(); - } - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.entryType_ = entryType_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.storeValue_ = storeValue_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.Entry) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.Entry) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.Entry other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.Entry.getDefaultInstance()) return this; - if (other.hasHeader()) { - mergeHeader(other.getHeader()); - } - if (other.hasEntryType()) { - setEntryType(other.getEntryType()); - } - if (other.hasStoreValue()) { - setStoreValue(other.getStoreValue()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.Entry parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.Entry) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private com.alibaba.otter.canal.protocol.CanalEntry.Header header_ = com.alibaba.otter.canal.protocol.CanalEntry.Header.getDefaultInstance(); - private com.google.protobuf.SingleFieldBuilder headerBuilder_; - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public boolean hasHeader() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Header getHeader() { - if (headerBuilder_ == null) { - return header_; - } else { - return headerBuilder_.getMessage(); - } - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public Builder setHeader(com.alibaba.otter.canal.protocol.CanalEntry.Header value) { - if (headerBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - header_ = value; - onChanged(); - } else { - headerBuilder_.setMessage(value); - } - bitField0_ |= 0x00000001; - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public Builder setHeader(com.alibaba.otter.canal.protocol.CanalEntry.Header.Builder builderForValue) { - if (headerBuilder_ == null) { - header_ = builderForValue.build(); - onChanged(); - } else { - headerBuilder_.setMessage(builderForValue.build()); - } - bitField0_ |= 0x00000001; - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public Builder mergeHeader(com.alibaba.otter.canal.protocol.CanalEntry.Header value) { - if (headerBuilder_ == null) { - if (((bitField0_ & 0x00000001) == 0x00000001) - && header_ != com.alibaba.otter.canal.protocol.CanalEntry.Header.getDefaultInstance()) { - header_ = com.alibaba.otter.canal.protocol.CanalEntry.Header.newBuilder(header_) - .mergeFrom(value) - .buildPartial(); - } else { - header_ = value; - } - onChanged(); - } else { - headerBuilder_.mergeFrom(value); - } - bitField0_ |= 0x00000001; - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public Builder clearHeader() { - if (headerBuilder_ == null) { - header_ = com.alibaba.otter.canal.protocol.CanalEntry.Header.getDefaultInstance(); - onChanged(); - } else { - headerBuilder_.clear(); - } - bitField0_ = (bitField0_ & ~0x00000001); - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Header.Builder getHeaderBuilder() { - bitField0_ |= 0x00000001; - onChanged(); - return getHeaderFieldBuilder().getBuilder(); - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.HeaderOrBuilder getHeaderOrBuilder() { - if (headerBuilder_ != null) { - return headerBuilder_.getMessageOrBuilder(); - } else { - return header_; - } - } - - /** - * optional .com.alibaba.otter.canal.protocol.Header header = 1; - * - *
      -             * *协议头部信息*
      -             * 
      - */ - private com.google.protobuf.SingleFieldBuilder getHeaderFieldBuilder() { - if (headerBuilder_ == null) { - headerBuilder_ = new com.google.protobuf.SingleFieldBuilder(getHeader(), - getParentForChildren(), - isClean()); - header_ = null; - } - return headerBuilder_; - } - - private com.alibaba.otter.canal.protocol.CanalEntry.EntryType entryType_ = com.alibaba.otter.canal.protocol.CanalEntry.EntryType.ROWDATA; - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -             * *打散后的事件类型*
      -             * 
      - */ - public boolean hasEntryType() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -             * *打散后的事件类型*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.EntryType getEntryType() { - return entryType_; - } - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -             * *打散后的事件类型*
      -             * 
      - */ - public Builder setEntryType(com.alibaba.otter.canal.protocol.CanalEntry.EntryType value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - entryType_ = value; - onChanged(); - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; - * - *
      -             * *打散后的事件类型*
      -             * 
      - */ - public Builder clearEntryType() { - bitField0_ = (bitField0_ & ~0x00000002); - entryType_ = com.alibaba.otter.canal.protocol.CanalEntry.EntryType.ROWDATA; - onChanged(); - return this; - } - - private com.google.protobuf.ByteString storeValue_ = com.google.protobuf.ByteString.EMPTY; - - /** - * optional bytes storeValue = 3; - * - *
      -             * *传输的二进制数组*
      -             * 
      - */ - public boolean hasStoreValue() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional bytes storeValue = 3; - * - *
      -             * *传输的二进制数组*
      -             * 
      - */ - public com.google.protobuf.ByteString getStoreValue() { - return storeValue_; - } - - /** - * optional bytes storeValue = 3; - * - *
      -             * *传输的二进制数组*
      -             * 
      - */ - public Builder setStoreValue(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - storeValue_ = value; - onChanged(); - return this; - } - - /** - * optional bytes storeValue = 3; - * - *
      -             * *传输的二进制数组*
      -             * 
      - */ - public Builder clearStoreValue() { - bitField0_ = (bitField0_ & ~0x00000004); - storeValue_ = getDefaultInstance().getStoreValue(); - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Entry) + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { + getHeaderFieldBuilder(); } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new Entry(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + if (headerBuilder_ == null) { + header_ = Header.getDefaultInstance(); + } else { + headerBuilder_.clear(); } + bitField0_ = (bitField0_ & ~0x00000001); + entryType_ = EntryType.ROWDATA; + bitField0_ = (bitField0_ & ~0x00000002); + storeValue_ = com.google.protobuf.ByteString.EMPTY; + bitField0_ = (bitField0_ & ~0x00000004); + return this; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Entry) + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; + } + + public Entry getDefaultInstanceForType() { + return Entry.getDefaultInstance(); + } + + public Entry build() { + Entry result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); + } + return result; + } + + public Entry buildPartial() { + Entry result = new Entry(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + if (((from_bitField0_ & 0x00000001) == 0x00000001)) { + to_bitField0_ |= 0x00000001; + } + if (headerBuilder_ == null) { + result.header_ = header_; + } else { + result.header_ = headerBuilder_.build(); + } + if (((from_bitField0_ & 0x00000002) == 0x00000002)) { + to_bitField0_ |= 0x00000002; + } + result.entryType_ = entryType_; + if (((from_bitField0_ & 0x00000004) == 0x00000004)) { + to_bitField0_ |= 0x00000004; + } + result.storeValue_ = storeValue_; + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof Entry) { + return mergeFrom((Entry)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(Entry other) { + if (other == Entry.getDefaultInstance()) return this; + if (other.hasHeader()) { + mergeHeader(other.getHeader()); + } + if (other.hasEntryType()) { + setEntryType(other.getEntryType()); + } + if (other.hasStoreValue()) { + setStoreValue(other.getStoreValue()); + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + Entry parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (Entry) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private Header header_ = Header.getDefaultInstance(); + private com.google.protobuf.SingleFieldBuilder< + Header, Header.Builder, HeaderOrBuilder> headerBuilder_; + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public boolean hasHeader() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public Header getHeader() { + if (headerBuilder_ == null) { + return header_; + } else { + return headerBuilder_.getMessage(); + } + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public Builder setHeader(Header value) { + if (headerBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + header_ = value; + onChanged(); + } else { + headerBuilder_.setMessage(value); + } + bitField0_ |= 0x00000001; + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public Builder setHeader( + Header.Builder builderForValue) { + if (headerBuilder_ == null) { + header_ = builderForValue.build(); + onChanged(); + } else { + headerBuilder_.setMessage(builderForValue.build()); + } + bitField0_ |= 0x00000001; + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public Builder mergeHeader(Header value) { + if (headerBuilder_ == null) { + if (((bitField0_ & 0x00000001) == 0x00000001) && + header_ != Header.getDefaultInstance()) { + header_ = + Header.newBuilder(header_).mergeFrom(value).buildPartial(); + } else { + header_ = value; + } + onChanged(); + } else { + headerBuilder_.mergeFrom(value); + } + bitField0_ |= 0x00000001; + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public Builder clearHeader() { + if (headerBuilder_ == null) { + header_ = Header.getDefaultInstance(); + onChanged(); + } else { + headerBuilder_.clear(); + } + bitField0_ = (bitField0_ & ~0x00000001); + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public Header.Builder getHeaderBuilder() { + bitField0_ |= 0x00000001; + onChanged(); + return getHeaderFieldBuilder().getBuilder(); + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + public HeaderOrBuilder getHeaderOrBuilder() { + if (headerBuilder_ != null) { + return headerBuilder_.getMessageOrBuilder(); + } else { + return header_; + } + } + /** + * optional .com.alibaba.otter.canal.protocol.Header header = 1; + * + *
      +       **协议头部信息*
      +       * 
      + */ + private com.google.protobuf.SingleFieldBuilder< + Header, Header.Builder, HeaderOrBuilder> + getHeaderFieldBuilder() { + if (headerBuilder_ == null) { + headerBuilder_ = new com.google.protobuf.SingleFieldBuilder< + Header, Header.Builder, HeaderOrBuilder>( + getHeader(), + getParentForChildren(), + isClean()); + header_ = null; + } + return headerBuilder_; + } + + private EntryType entryType_ = EntryType.ROWDATA; + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +       **打散后的事件类型*
      +       * 
      + */ + public boolean hasEntryType() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +       **打散后的事件类型*
      +       * 
      + */ + public EntryType getEntryType() { + return entryType_; + } + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +       **打散后的事件类型*
      +       * 
      + */ + public Builder setEntryType(EntryType value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + entryType_ = value; + onChanged(); + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.EntryType entryType = 2 [default = ROWDATA]; + * + *
      +       **打散后的事件类型*
      +       * 
      + */ + public Builder clearEntryType() { + bitField0_ = (bitField0_ & ~0x00000002); + entryType_ = EntryType.ROWDATA; + onChanged(); + return this; + } + + private com.google.protobuf.ByteString storeValue_ = com.google.protobuf.ByteString.EMPTY; + /** + * optional bytes storeValue = 3; + * + *
      +       **传输的二进制数组*
      +       * 
      + */ + public boolean hasStoreValue() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional bytes storeValue = 3; + * + *
      +       **传输的二进制数组*
      +       * 
      + */ + public com.google.protobuf.ByteString getStoreValue() { + return storeValue_; + } + /** + * optional bytes storeValue = 3; + * + *
      +       **传输的二进制数组*
      +       * 
      + */ + public Builder setStoreValue(com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000004; + storeValue_ = value; + onChanged(); + return this; + } + /** + * optional bytes storeValue = 3; + * + *
      +       **传输的二进制数组*
      +       * 
      + */ + public Builder clearStoreValue() { + bitField0_ = (bitField0_ & ~0x00000004); + storeValue_ = getDefaultInstance().getStoreValue(); + onChanged(); + return this; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Entry) } - public interface HeaderOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Header) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -         * *协议的版本号*
      -         * 
      - */ - boolean hasVersion(); - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -         * *协议的版本号*
      -         * 
      - */ - int getVersion(); - - /** - * optional string logfileName = 2; - * - *
      -         * *binlog/redolog 文件名*
      -         * 
      - */ - boolean hasLogfileName(); - - /** - * optional string logfileName = 2; - * - *
      -         * *binlog/redolog 文件名*
      -         * 
      - */ - java.lang.String getLogfileName(); - - /** - * optional string logfileName = 2; - * - *
      -         * *binlog/redolog 文件名*
      -         * 
      - */ - com.google.protobuf.ByteString getLogfileNameBytes(); - - /** - * optional int64 logfileOffset = 3; - * - *
      -         * *binlog/redolog 文件的偏移位置*
      -         * 
      - */ - boolean hasLogfileOffset(); - - /** - * optional int64 logfileOffset = 3; - * - *
      -         * *binlog/redolog 文件的偏移位置*
      -         * 
      - */ - long getLogfileOffset(); - - /** - * optional int64 serverId = 4; - * - *
      -         * *服务端serverId*
      -         * 
      - */ - boolean hasServerId(); - - /** - * optional int64 serverId = 4; - * - *
      -         * *服务端serverId*
      -         * 
      - */ - long getServerId(); - - /** - * optional string serverenCode = 5; - * - *
      -         * * 变更数据的编码 *
      -         * 
      - */ - boolean hasServerenCode(); - - /** - * optional string serverenCode = 5; - * - *
      -         * * 变更数据的编码 *
      -         * 
      - */ - java.lang.String getServerenCode(); - - /** - * optional string serverenCode = 5; - * - *
      -         * * 变更数据的编码 *
      -         * 
      - */ - com.google.protobuf.ByteString getServerenCodeBytes(); - - /** - * optional int64 executeTime = 6; - * - *
      -         * *变更数据的执行时间 *
      -         * 
      - */ - boolean hasExecuteTime(); - - /** - * optional int64 executeTime = 6; - * - *
      -         * *变更数据的执行时间 *
      -         * 
      - */ - long getExecuteTime(); - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -         * * 变更数据的来源*
      -         * 
      - */ - boolean hasSourceType(); - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -         * * 变更数据的来源*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Type getSourceType(); - - /** - * optional string schemaName = 8; - * - *
      -         * * 变更数据的schemaname*
      -         * 
      - */ - boolean hasSchemaName(); - - /** - * optional string schemaName = 8; - * - *
      -         * * 变更数据的schemaname*
      -         * 
      - */ - java.lang.String getSchemaName(); - - /** - * optional string schemaName = 8; - * - *
      -         * * 变更数据的schemaname*
      -         * 
      - */ - com.google.protobuf.ByteString getSchemaNameBytes(); - - /** - * optional string tableName = 9; - * - *
      -         * *变更数据的tablename*
      -         * 
      - */ - boolean hasTableName(); - - /** - * optional string tableName = 9; - * - *
      -         * *变更数据的tablename*
      -         * 
      - */ - java.lang.String getTableName(); - - /** - * optional string tableName = 9; - * - *
      -         * *变更数据的tablename*
      -         * 
      - */ - com.google.protobuf.ByteString getTableNameBytes(); - - /** - * optional int64 eventLength = 10; - * - *
      -         * *每个event的长度*
      -         * 
      - */ - boolean hasEventLength(); - - /** - * optional int64 eventLength = 10; - * - *
      -         * *每个event的长度*
      -         * 
      - */ - long getEventLength(); - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - boolean hasEventType(); - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.EventType getEventType(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - int getPropsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index); - - /** - * optional string gtid = 13; - * - *
      -         * *当前事务的gitd*
      -         * 
      - */ - boolean hasGtid(); - - /** - * optional string gtid = 13; - * - *
      -         * *当前事务的gitd*
      -         * 
      - */ - java.lang.String getGtid(); - - /** - * optional string gtid = 13; - * - *
      -         * *当前事务的gitd*
      -         * 
      - */ - com.google.protobuf.ByteString getGtidBytes(); + static { + defaultInstance = new Entry(true); + defaultInstance.initFields(); } + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Entry) + } + + public interface HeaderOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Header) + com.google.protobuf.MessageOrBuilder { + + /** + * optional int32 version = 1 [default = 1]; + * + *
      +     **协议的版本号*
      +     * 
      + */ + boolean hasVersion(); + /** + * optional int32 version = 1 [default = 1]; + * + *
      +     **协议的版本号*
      +     * 
      + */ + int getVersion(); + + /** + * optional string logfileName = 2; + * + *
      +     **binlog/redolog 文件名*
      +     * 
      + */ + boolean hasLogfileName(); + /** + * optional string logfileName = 2; + * + *
      +     **binlog/redolog 文件名*
      +     * 
      + */ + String getLogfileName(); + /** + * optional string logfileName = 2; + * + *
      +     **binlog/redolog 文件名*
      +     * 
      + */ + com.google.protobuf.ByteString + getLogfileNameBytes(); + + /** + * optional int64 logfileOffset = 3; + * + *
      +     **binlog/redolog 文件的偏移位置*
      +     * 
      + */ + boolean hasLogfileOffset(); + /** + * optional int64 logfileOffset = 3; + * + *
      +     **binlog/redolog 文件的偏移位置*
      +     * 
      + */ + long getLogfileOffset(); + + /** + * optional int64 serverId = 4; + * + *
      +     **服务端serverId*
      +     * 
      + */ + boolean hasServerId(); + /** + * optional int64 serverId = 4; + * + *
      +     **服务端serverId*
      +     * 
      + */ + long getServerId(); + + /** + * optional string serverenCode = 5; + * + *
      +     ** 变更数据的编码 *
      +     * 
      + */ + boolean hasServerenCode(); + /** + * optional string serverenCode = 5; + * + *
      +     ** 变更数据的编码 *
      +     * 
      + */ + String getServerenCode(); + /** + * optional string serverenCode = 5; + * + *
      +     ** 变更数据的编码 *
      +     * 
      + */ + com.google.protobuf.ByteString + getServerenCodeBytes(); + + /** + * optional int64 executeTime = 6; + * + *
      +     **变更数据的执行时间 *
      +     * 
      + */ + boolean hasExecuteTime(); + /** + * optional int64 executeTime = 6; + * + *
      +     **变更数据的执行时间 *
      +     * 
      + */ + long getExecuteTime(); + + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +     ** 变更数据的来源*
      +     * 
      + */ + boolean hasSourceType(); + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +     ** 变更数据的来源*
      +     * 
      + */ + Type getSourceType(); + + /** + * optional string schemaName = 8; + * + *
      +     ** 变更数据的schemaname*
      +     * 
      + */ + boolean hasSchemaName(); + /** + * optional string schemaName = 8; + * + *
      +     ** 变更数据的schemaname*
      +     * 
      + */ + String getSchemaName(); + /** + * optional string schemaName = 8; + * + *
      +     ** 变更数据的schemaname*
      +     * 
      + */ + com.google.protobuf.ByteString + getSchemaNameBytes(); + + /** + * optional string tableName = 9; + * + *
      +     **变更数据的tablename*
      +     * 
      + */ + boolean hasTableName(); + /** + * optional string tableName = 9; + * + *
      +     **变更数据的tablename*
      +     * 
      + */ + String getTableName(); + /** + * optional string tableName = 9; + * + *
      +     **变更数据的tablename*
      +     * 
      + */ + com.google.protobuf.ByteString + getTableNameBytes(); + + /** + * optional int64 eventLength = 10; + * + *
      +     **每个event的长度*
      +     * 
      + */ + boolean hasEventLength(); + /** + * optional int64 eventLength = 10; + * + *
      +     **每个event的长度*
      +     * 
      + */ + long getEventLength(); + + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + boolean hasEventType(); + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + EventType getEventType(); + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + Pair getProps(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + int getPropsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + PairOrBuilder getPropsOrBuilder(int index); + + /** + * optional string gtid = 13; + * + *
      +     **当前事务的gitd*
      +     * 
      + */ + boolean hasGtid(); + /** + * optional string gtid = 13; + * + *
      +     **当前事务的gitd*
      +     * 
      + */ + String getGtid(); + /** + * optional string gtid = 13; + * + *
      +     **当前事务的gitd*
      +     * 
      + */ + com.google.protobuf.ByteString + getGtidBytes(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.Header} + * + *
      +   **message Header*
      +   * 
      + */ + public static final class Header extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Header) + HeaderOrBuilder { + // Use Header.newBuilder() to construct. + private Header(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private Header(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final Header defaultInstance; + public static Header getDefaultInstance() { + return defaultInstance; + } + + public Header getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Header( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 8: { + bitField0_ |= 0x00000001; + version_ = input.readInt32(); + break; + } + case 18: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000002; + logfileName_ = bs; + break; + } + case 24: { + bitField0_ |= 0x00000004; + logfileOffset_ = input.readInt64(); + break; + } + case 32: { + bitField0_ |= 0x00000008; + serverId_ = input.readInt64(); + break; + } + case 42: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000010; + serverenCode_ = bs; + break; + } + case 48: { + bitField0_ |= 0x00000020; + executeTime_ = input.readInt64(); + break; + } + case 56: { + int rawValue = input.readEnum(); + Type value = Type.valueOf(rawValue); + if (value == null) { + unknownFields.mergeVarintField(7, rawValue); + } else { + bitField0_ |= 0x00000040; + sourceType_ = value; + } + break; + } + case 66: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000080; + schemaName_ = bs; + break; + } + case 74: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000100; + tableName_ = bs; + break; + } + case 80: { + bitField0_ |= 0x00000200; + eventLength_ = input.readInt64(); + break; + } + case 88: { + int rawValue = input.readEnum(); + EventType value = EventType.valueOf(rawValue); + if (value == null) { + unknownFields.mergeVarintField(11, rawValue); + } else { + bitField0_ |= 0x00000400; + eventType_ = value; + } + break; + } + case 98: { + if (!((mutable_bitField0_ & 0x00000800) == 0x00000800)) { + props_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000800; + } + props_.add(input.readMessage(Pair.PARSER, extensionRegistry)); + break; + } + case 106: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000800; + gtid_ = bs; + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + if (((mutable_bitField0_ & 0x00000800) == 0x00000800)) { + props_ = java.util.Collections.unmodifiableList(props_); + } + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Header.class, Builder.class); + } + + public static com.google.protobuf.Parser
      PARSER = + new com.google.protobuf.AbstractParser
      () { + public Header parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Header(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser
      getParserForType() { + return PARSER; + } + + private int bitField0_; + public static final int VERSION_FIELD_NUMBER = 1; + private int version_; + /** + * optional int32 version = 1 [default = 1]; + * + *
      +     **协议的版本号*
      +     * 
      + */ + public boolean hasVersion() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int32 version = 1 [default = 1]; + * + *
      +     **协议的版本号*
      +     * 
      + */ + public int getVersion() { + return version_; + } + + public static final int LOGFILENAME_FIELD_NUMBER = 2; + private Object logfileName_; + /** + * optional string logfileName = 2; + * + *
      +     **binlog/redolog 文件名*
      +     * 
      + */ + public boolean hasLogfileName() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string logfileName = 2; + * + *
      +     **binlog/redolog 文件名*
      +     * 
      + */ + public String getLogfileName() { + Object ref = logfileName_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + logfileName_ = s; + } + return s; + } + } + /** + * optional string logfileName = 2; + * + *
      +     **binlog/redolog 文件名*
      +     * 
      + */ + public com.google.protobuf.ByteString + getLogfileNameBytes() { + Object ref = logfileName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + logfileName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int LOGFILEOFFSET_FIELD_NUMBER = 3; + private long logfileOffset_; + /** + * optional int64 logfileOffset = 3; + * + *
      +     **binlog/redolog 文件的偏移位置*
      +     * 
      + */ + public boolean hasLogfileOffset() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional int64 logfileOffset = 3; + * + *
      +     **binlog/redolog 文件的偏移位置*
      +     * 
      + */ + public long getLogfileOffset() { + return logfileOffset_; + } + + public static final int SERVERID_FIELD_NUMBER = 4; + private long serverId_; + /** + * optional int64 serverId = 4; + * + *
      +     **服务端serverId*
      +     * 
      + */ + public boolean hasServerId() { + return ((bitField0_ & 0x00000008) == 0x00000008); + } + /** + * optional int64 serverId = 4; + * + *
      +     **服务端serverId*
      +     * 
      + */ + public long getServerId() { + return serverId_; + } + + public static final int SERVERENCODE_FIELD_NUMBER = 5; + private Object serverenCode_; + /** + * optional string serverenCode = 5; + * + *
      +     ** 变更数据的编码 *
      +     * 
      + */ + public boolean hasServerenCode() { + return ((bitField0_ & 0x00000010) == 0x00000010); + } + /** + * optional string serverenCode = 5; + * + *
      +     ** 变更数据的编码 *
      +     * 
      + */ + public String getServerenCode() { + Object ref = serverenCode_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + serverenCode_ = s; + } + return s; + } + } + /** + * optional string serverenCode = 5; + * + *
      +     ** 变更数据的编码 *
      +     * 
      + */ + public com.google.protobuf.ByteString + getServerenCodeBytes() { + Object ref = serverenCode_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + serverenCode_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int EXECUTETIME_FIELD_NUMBER = 6; + private long executeTime_; + /** + * optional int64 executeTime = 6; + * + *
      +     **变更数据的执行时间 *
      +     * 
      + */ + public boolean hasExecuteTime() { + return ((bitField0_ & 0x00000020) == 0x00000020); + } + /** + * optional int64 executeTime = 6; + * + *
      +     **变更数据的执行时间 *
      +     * 
      + */ + public long getExecuteTime() { + return executeTime_; + } + + public static final int SOURCETYPE_FIELD_NUMBER = 7; + private Type sourceType_; + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +     ** 变更数据的来源*
      +     * 
      + */ + public boolean hasSourceType() { + return ((bitField0_ & 0x00000040) == 0x00000040); + } + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +     ** 变更数据的来源*
      +     * 
      + */ + public Type getSourceType() { + return sourceType_; + } + + public static final int SCHEMANAME_FIELD_NUMBER = 8; + private Object schemaName_; + /** + * optional string schemaName = 8; + * + *
      +     ** 变更数据的schemaname*
      +     * 
      + */ + public boolean hasSchemaName() { + return ((bitField0_ & 0x00000080) == 0x00000080); + } + /** + * optional string schemaName = 8; + * + *
      +     ** 变更数据的schemaname*
      +     * 
      + */ + public String getSchemaName() { + Object ref = schemaName_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + schemaName_ = s; + } + return s; + } + } + /** + * optional string schemaName = 8; + * + *
      +     ** 变更数据的schemaname*
      +     * 
      + */ + public com.google.protobuf.ByteString + getSchemaNameBytes() { + Object ref = schemaName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + schemaName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int TABLENAME_FIELD_NUMBER = 9; + private Object tableName_; + /** + * optional string tableName = 9; + * + *
      +     **变更数据的tablename*
      +     * 
      + */ + public boolean hasTableName() { + return ((bitField0_ & 0x00000100) == 0x00000100); + } + /** + * optional string tableName = 9; + * + *
      +     **变更数据的tablename*
      +     * 
      + */ + public String getTableName() { + Object ref = tableName_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + tableName_ = s; + } + return s; + } + } + /** + * optional string tableName = 9; + * + *
      +     **变更数据的tablename*
      +     * 
      + */ + public com.google.protobuf.ByteString + getTableNameBytes() { + Object ref = tableName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + tableName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int EVENTLENGTH_FIELD_NUMBER = 10; + private long eventLength_; + /** + * optional int64 eventLength = 10; + * + *
      +     **每个event的长度*
      +     * 
      + */ + public boolean hasEventLength() { + return ((bitField0_ & 0x00000200) == 0x00000200); + } + /** + * optional int64 eventLength = 10; + * + *
      +     **每个event的长度*
      +     * 
      + */ + public long getEventLength() { + return eventLength_; + } + + public static final int EVENTTYPE_FIELD_NUMBER = 11; + private EventType eventType_; + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + public boolean hasEventType() { + return ((bitField0_ & 0x00000400) == 0x00000400); + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + public EventType getEventType() { + return eventType_; + } + + public static final int PROPS_FIELD_NUMBER = 12; + private java.util.List props_; + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List getPropsList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List + getPropsOrBuilderList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + public int getPropsCount() { + return props_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + public Pair getProps(int index) { + return props_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +     **预留扩展*
      +     * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + return props_.get(index); + } + + public static final int GTID_FIELD_NUMBER = 13; + private Object gtid_; + /** + * optional string gtid = 13; + * + *
      +     **当前事务的gitd*
      +     * 
      + */ + public boolean hasGtid() { + return ((bitField0_ & 0x00000800) == 0x00000800); + } + /** + * optional string gtid = 13; + * + *
      +     **当前事务的gitd*
      +     * 
      + */ + public String getGtid() { + Object ref = gtid_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + gtid_ = s; + } + return s; + } + } + /** + * optional string gtid = 13; + * + *
      +     **当前事务的gitd*
      +     * 
      + */ + public com.google.protobuf.ByteString + getGtidBytes() { + Object ref = gtid_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + gtid_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + private void initFields() { + version_ = 1; + logfileName_ = ""; + logfileOffset_ = 0L; + serverId_ = 0L; + serverenCode_ = ""; + executeTime_ = 0L; + sourceType_ = Type.MYSQL; + schemaName_ = ""; + tableName_ = ""; + eventLength_ = 0L; + eventType_ = EventType.UPDATE; + props_ = java.util.Collections.emptyList(); + gtid_ = ""; + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + if (((bitField0_ & 0x00000001) == 0x00000001)) { + output.writeInt32(1, version_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + output.writeBytes(2, getLogfileNameBytes()); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + output.writeInt64(3, logfileOffset_); + } + if (((bitField0_ & 0x00000008) == 0x00000008)) { + output.writeInt64(4, serverId_); + } + if (((bitField0_ & 0x00000010) == 0x00000010)) { + output.writeBytes(5, getServerenCodeBytes()); + } + if (((bitField0_ & 0x00000020) == 0x00000020)) { + output.writeInt64(6, executeTime_); + } + if (((bitField0_ & 0x00000040) == 0x00000040)) { + output.writeEnum(7, sourceType_.getNumber()); + } + if (((bitField0_ & 0x00000080) == 0x00000080)) { + output.writeBytes(8, getSchemaNameBytes()); + } + if (((bitField0_ & 0x00000100) == 0x00000100)) { + output.writeBytes(9, getTableNameBytes()); + } + if (((bitField0_ & 0x00000200) == 0x00000200)) { + output.writeInt64(10, eventLength_); + } + if (((bitField0_ & 0x00000400) == 0x00000400)) { + output.writeEnum(11, eventType_.getNumber()); + } + for (int i = 0; i < props_.size(); i++) { + output.writeMessage(12, props_.get(i)); + } + if (((bitField0_ & 0x00000800) == 0x00000800)) { + output.writeBytes(13, getGtidBytes()); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size(1, version_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(2, getLogfileNameBytes()); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(3, logfileOffset_); + } + if (((bitField0_ & 0x00000008) == 0x00000008)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(4, serverId_); + } + if (((bitField0_ & 0x00000010) == 0x00000010)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(5, getServerenCodeBytes()); + } + if (((bitField0_ & 0x00000020) == 0x00000020)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(6, executeTime_); + } + if (((bitField0_ & 0x00000040) == 0x00000040)) { + size += com.google.protobuf.CodedOutputStream + .computeEnumSize(7, sourceType_.getNumber()); + } + if (((bitField0_ & 0x00000080) == 0x00000080)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(8, getSchemaNameBytes()); + } + if (((bitField0_ & 0x00000100) == 0x00000100)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(9, getTableNameBytes()); + } + if (((bitField0_ & 0x00000200) == 0x00000200)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(10, eventLength_); + } + if (((bitField0_ & 0x00000400) == 0x00000400)) { + size += com.google.protobuf.CodedOutputStream + .computeEnumSize(11, eventType_.getNumber()); + } + for (int i = 0; i < props_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(12, props_.get(i)); + } + if (((bitField0_ & 0x00000800) == 0x00000800)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(13, getGtidBytes()); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static Header parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Header parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Header parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Header parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Header parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Header parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static Header parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static Header parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static Header parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Header parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(Header prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.Header} * *
      -     * *message Header*
      +     **message Header*
            * 
      */ - public static final class Header extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Header) - HeaderOrBuilder { - - // Use Header.newBuilder() to construct. - private Header(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Header(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Header defaultInstance; - - public static Header getDefaultInstance() { - return defaultInstance; - } - - public Header getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Header(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - version_ = input.readInt32(); - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - logfileName_ = bs; - break; - } - case 24: { - bitField0_ |= 0x00000004; - logfileOffset_ = input.readInt64(); - break; - } - case 32: { - bitField0_ |= 0x00000008; - serverId_ = input.readInt64(); - break; - } - case 42: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000010; - serverenCode_ = bs; - break; - } - case 48: { - bitField0_ |= 0x00000020; - executeTime_ = input.readInt64(); - break; - } - case 56: { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalEntry.Type value = com.alibaba.otter.canal.protocol.CanalEntry.Type.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(7, rawValue); - } else { - bitField0_ |= 0x00000040; - sourceType_ = value; - } - break; - } - case 66: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000080; - schemaName_ = bs; - break; - } - case 74: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000100; - tableName_ = bs; - break; - } - case 80: { - bitField0_ |= 0x00000200; - eventLength_ = input.readInt64(); - break; - } - case 88: { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalEntry.EventType value = com.alibaba.otter.canal.protocol.CanalEntry.EventType.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(11, rawValue); - } else { - bitField0_ |= 0x00000400; - eventType_ = value; - } - break; - } - case 98: { - if (!((mutable_bitField0_ & 0x00000800) == 0x00000800)) { - props_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000800; - } - props_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Pair.PARSER, - extensionRegistry)); - break; - } - case 106: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000800; - gtid_ = bs; - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000800) == 0x00000800)) { - props_ = java.util.Collections.unmodifiableList(props_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Header.class, - com.alibaba.otter.canal.protocol.CanalEntry.Header.Builder.class); - } - - public static com.google.protobuf.Parser
      PARSER = new com.google.protobuf.AbstractParser
      () { - - public Header parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Header(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser
      getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int VERSION_FIELD_NUMBER = 1; - private int version_; - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -         * *协议的版本号*
      -         * 
      - */ - public boolean hasVersion() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -         * *协议的版本号*
      -         * 
      - */ - public int getVersion() { - return version_; - } - - public static final int LOGFILENAME_FIELD_NUMBER = 2; - private java.lang.Object logfileName_; - - /** - * optional string logfileName = 2; - * - *
      -         * *binlog/redolog 文件名*
      -         * 
      - */ - public boolean hasLogfileName() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string logfileName = 2; - * - *
      -         * *binlog/redolog 文件名*
      -         * 
      - */ - public java.lang.String getLogfileName() { - java.lang.Object ref = logfileName_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - logfileName_ = s; - } - return s; - } - } - - /** - * optional string logfileName = 2; - * - *
      -         * *binlog/redolog 文件名*
      -         * 
      - */ - public com.google.protobuf.ByteString getLogfileNameBytes() { - java.lang.Object ref = logfileName_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - logfileName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int LOGFILEOFFSET_FIELD_NUMBER = 3; - private long logfileOffset_; - - /** - * optional int64 logfileOffset = 3; - * - *
      -         * *binlog/redolog 文件的偏移位置*
      -         * 
      - */ - public boolean hasLogfileOffset() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 logfileOffset = 3; - * - *
      -         * *binlog/redolog 文件的偏移位置*
      -         * 
      - */ - public long getLogfileOffset() { - return logfileOffset_; - } - - public static final int SERVERID_FIELD_NUMBER = 4; - private long serverId_; - - /** - * optional int64 serverId = 4; - * - *
      -         * *服务端serverId*
      -         * 
      - */ - public boolean hasServerId() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional int64 serverId = 4; - * - *
      -         * *服务端serverId*
      -         * 
      - */ - public long getServerId() { - return serverId_; - } - - public static final int SERVERENCODE_FIELD_NUMBER = 5; - private java.lang.Object serverenCode_; - - /** - * optional string serverenCode = 5; - * - *
      -         * * 变更数据的编码 *
      -         * 
      - */ - public boolean hasServerenCode() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional string serverenCode = 5; - * - *
      -         * * 变更数据的编码 *
      -         * 
      - */ - public java.lang.String getServerenCode() { - java.lang.Object ref = serverenCode_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - serverenCode_ = s; - } - return s; - } - } - - /** - * optional string serverenCode = 5; - * - *
      -         * * 变更数据的编码 *
      -         * 
      - */ - public com.google.protobuf.ByteString getServerenCodeBytes() { - java.lang.Object ref = serverenCode_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - serverenCode_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int EXECUTETIME_FIELD_NUMBER = 6; - private long executeTime_; - - /** - * optional int64 executeTime = 6; - * - *
      -         * *变更数据的执行时间 *
      -         * 
      - */ - public boolean hasExecuteTime() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional int64 executeTime = 6; - * - *
      -         * *变更数据的执行时间 *
      -         * 
      - */ - public long getExecuteTime() { - return executeTime_; - } - - public static final int SOURCETYPE_FIELD_NUMBER = 7; - private com.alibaba.otter.canal.protocol.CanalEntry.Type sourceType_; - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -         * * 变更数据的来源*
      -         * 
      - */ - public boolean hasSourceType() { - return ((bitField0_ & 0x00000040) == 0x00000040); - } - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -         * * 变更数据的来源*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Type getSourceType() { - return sourceType_; - } - - public static final int SCHEMANAME_FIELD_NUMBER = 8; - private java.lang.Object schemaName_; - - /** - * optional string schemaName = 8; - * - *
      -         * * 变更数据的schemaname*
      -         * 
      - */ - public boolean hasSchemaName() { - return ((bitField0_ & 0x00000080) == 0x00000080); - } - - /** - * optional string schemaName = 8; - * - *
      -         * * 变更数据的schemaname*
      -         * 
      - */ - public java.lang.String getSchemaName() { - java.lang.Object ref = schemaName_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - schemaName_ = s; - } - return s; - } - } - - /** - * optional string schemaName = 8; - * - *
      -         * * 变更数据的schemaname*
      -         * 
      - */ - public com.google.protobuf.ByteString getSchemaNameBytes() { - java.lang.Object ref = schemaName_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - schemaName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int TABLENAME_FIELD_NUMBER = 9; - private java.lang.Object tableName_; - - /** - * optional string tableName = 9; - * - *
      -         * *变更数据的tablename*
      -         * 
      - */ - public boolean hasTableName() { - return ((bitField0_ & 0x00000100) == 0x00000100); - } - - /** - * optional string tableName = 9; - * - *
      -         * *变更数据的tablename*
      -         * 
      - */ - public java.lang.String getTableName() { - java.lang.Object ref = tableName_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - tableName_ = s; - } - return s; - } - } - - /** - * optional string tableName = 9; - * - *
      -         * *变更数据的tablename*
      -         * 
      - */ - public com.google.protobuf.ByteString getTableNameBytes() { - java.lang.Object ref = tableName_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - tableName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int EVENTLENGTH_FIELD_NUMBER = 10; - private long eventLength_; - - /** - * optional int64 eventLength = 10; - * - *
      -         * *每个event的长度*
      -         * 
      - */ - public boolean hasEventLength() { - return ((bitField0_ & 0x00000200) == 0x00000200); - } - - /** - * optional int64 eventLength = 10; - * - *
      -         * *每个event的长度*
      -         * 
      - */ - public long getEventLength() { - return eventLength_; - } - - public static final int EVENTTYPE_FIELD_NUMBER = 11; - private com.alibaba.otter.canal.protocol.CanalEntry.EventType eventType_; - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - public boolean hasEventType() { - return ((bitField0_ & 0x00000400) == 0x00000400); - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.EventType getEventType() { - return eventType_; - } - - public static final int PROPS_FIELD_NUMBER = 12; - private java.util.List props_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsOrBuilderList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public int getPropsCount() { - return props_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - return props_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - return props_.get(index); - } - - public static final int GTID_FIELD_NUMBER = 13; - private java.lang.Object gtid_; - - /** - * optional string gtid = 13; - * - *
      -         * *当前事务的gitd*
      -         * 
      - */ - public boolean hasGtid() { - return ((bitField0_ & 0x00000800) == 0x00000800); - } - - /** - * optional string gtid = 13; - * - *
      -         * *当前事务的gitd*
      -         * 
      - */ - public java.lang.String getGtid() { - java.lang.Object ref = gtid_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - gtid_ = s; - } - return s; - } - } - - /** - * optional string gtid = 13; - * - *
      -         * *当前事务的gitd*
      -         * 
      - */ - public com.google.protobuf.ByteString getGtidBytes() { - java.lang.Object ref = gtid_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - gtid_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - private void initFields() { - version_ = 1; - logfileName_ = ""; - logfileOffset_ = 0L; - serverId_ = 0L; - serverenCode_ = ""; - executeTime_ = 0L; - sourceType_ = com.alibaba.otter.canal.protocol.CanalEntry.Type.MYSQL; - schemaName_ = ""; - tableName_ = ""; - eventLength_ = 0L; - eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - props_ = java.util.Collections.emptyList(); - gtid_ = ""; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt32(1, version_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getLogfileNameBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeInt64(3, logfileOffset_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - output.writeInt64(4, serverId_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - output.writeBytes(5, getServerenCodeBytes()); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - output.writeInt64(6, executeTime_); - } - if (((bitField0_ & 0x00000040) == 0x00000040)) { - output.writeEnum(7, sourceType_.getNumber()); - } - if (((bitField0_ & 0x00000080) == 0x00000080)) { - output.writeBytes(8, getSchemaNameBytes()); - } - if (((bitField0_ & 0x00000100) == 0x00000100)) { - output.writeBytes(9, getTableNameBytes()); - } - if (((bitField0_ & 0x00000200) == 0x00000200)) { - output.writeInt64(10, eventLength_); - } - if (((bitField0_ & 0x00000400) == 0x00000400)) { - output.writeEnum(11, eventType_.getNumber()); - } - for (int i = 0; i < props_.size(); i++) { - output.writeMessage(12, props_.get(i)); - } - if (((bitField0_ & 0x00000800) == 0x00000800)) { - output.writeBytes(13, getGtidBytes()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(1, version_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getLogfileNameBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(3, logfileOffset_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(4, serverId_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(5, getServerenCodeBytes()); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(6, executeTime_); - } - if (((bitField0_ & 0x00000040) == 0x00000040)) { - size += com.google.protobuf.CodedOutputStream.computeEnumSize(7, sourceType_.getNumber()); - } - if (((bitField0_ & 0x00000080) == 0x00000080)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(8, getSchemaNameBytes()); - } - if (((bitField0_ & 0x00000100) == 0x00000100)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(9, getTableNameBytes()); - } - if (((bitField0_ & 0x00000200) == 0x00000200)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(10, eventLength_); - } - if (((bitField0_ & 0x00000400) == 0x00000400)) { - size += com.google.protobuf.CodedOutputStream.computeEnumSize(11, eventType_.getNumber()); - } - for (int i = 0; i < props_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(12, props_.get(i)); - } - if (((bitField0_ & 0x00000800) == 0x00000800)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(13, getGtidBytes()); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Header parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Header prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Header} - * - *
      -         * *message Header*
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Header) - com.alibaba.otter.canal.protocol.CanalEntry.HeaderOrBuilder { - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Header.class, - com.alibaba.otter.canal.protocol.CanalEntry.Header.Builder.class); - } - - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.Header.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - getPropsFieldBuilder(); - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - version_ = 1; - bitField0_ = (bitField0_ & ~0x00000001); - logfileName_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - logfileOffset_ = 0L; - bitField0_ = (bitField0_ & ~0x00000004); - serverId_ = 0L; - bitField0_ = (bitField0_ & ~0x00000008); - serverenCode_ = ""; - bitField0_ = (bitField0_ & ~0x00000010); - executeTime_ = 0L; - bitField0_ = (bitField0_ & ~0x00000020); - sourceType_ = com.alibaba.otter.canal.protocol.CanalEntry.Type.MYSQL; - bitField0_ = (bitField0_ & ~0x00000040); - schemaName_ = ""; - bitField0_ = (bitField0_ & ~0x00000080); - tableName_ = ""; - bitField0_ = (bitField0_ & ~0x00000100); - eventLength_ = 0L; - bitField0_ = (bitField0_ & ~0x00000200); - eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - bitField0_ = (bitField0_ & ~0x00000400); - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000800); - } else { - propsBuilder_.clear(); - } - gtid_ = ""; - bitField0_ = (bitField0_ & ~0x00001000); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Header getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.Header.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Header build() { - com.alibaba.otter.canal.protocol.CanalEntry.Header result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Header buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.Header result = new com.alibaba.otter.canal.protocol.CanalEntry.Header(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.version_ = version_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.logfileName_ = logfileName_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.logfileOffset_ = logfileOffset_; - if (((from_bitField0_ & 0x00000008) == 0x00000008)) { - to_bitField0_ |= 0x00000008; - } - result.serverId_ = serverId_; - if (((from_bitField0_ & 0x00000010) == 0x00000010)) { - to_bitField0_ |= 0x00000010; - } - result.serverenCode_ = serverenCode_; - if (((from_bitField0_ & 0x00000020) == 0x00000020)) { - to_bitField0_ |= 0x00000020; - } - result.executeTime_ = executeTime_; - if (((from_bitField0_ & 0x00000040) == 0x00000040)) { - to_bitField0_ |= 0x00000040; - } - result.sourceType_ = sourceType_; - if (((from_bitField0_ & 0x00000080) == 0x00000080)) { - to_bitField0_ |= 0x00000080; - } - result.schemaName_ = schemaName_; - if (((from_bitField0_ & 0x00000100) == 0x00000100)) { - to_bitField0_ |= 0x00000100; - } - result.tableName_ = tableName_; - if (((from_bitField0_ & 0x00000200) == 0x00000200)) { - to_bitField0_ |= 0x00000200; - } - result.eventLength_ = eventLength_; - if (((from_bitField0_ & 0x00000400) == 0x00000400)) { - to_bitField0_ |= 0x00000400; - } - result.eventType_ = eventType_; - if (propsBuilder_ == null) { - if (((bitField0_ & 0x00000800) == 0x00000800)) { - props_ = java.util.Collections.unmodifiableList(props_); - bitField0_ = (bitField0_ & ~0x00000800); - } - result.props_ = props_; - } else { - result.props_ = propsBuilder_.build(); - } - if (((from_bitField0_ & 0x00001000) == 0x00001000)) { - to_bitField0_ |= 0x00000800; - } - result.gtid_ = gtid_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.Header) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.Header) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.Header other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.Header.getDefaultInstance()) return this; - if (other.hasVersion()) { - setVersion(other.getVersion()); - } - if (other.hasLogfileName()) { - bitField0_ |= 0x00000002; - logfileName_ = other.logfileName_; - onChanged(); - } - if (other.hasLogfileOffset()) { - setLogfileOffset(other.getLogfileOffset()); - } - if (other.hasServerId()) { - setServerId(other.getServerId()); - } - if (other.hasServerenCode()) { - bitField0_ |= 0x00000010; - serverenCode_ = other.serverenCode_; - onChanged(); - } - if (other.hasExecuteTime()) { - setExecuteTime(other.getExecuteTime()); - } - if (other.hasSourceType()) { - setSourceType(other.getSourceType()); - } - if (other.hasSchemaName()) { - bitField0_ |= 0x00000080; - schemaName_ = other.schemaName_; - onChanged(); - } - if (other.hasTableName()) { - bitField0_ |= 0x00000100; - tableName_ = other.tableName_; - onChanged(); - } - if (other.hasEventLength()) { - setEventLength(other.getEventLength()); - } - if (other.hasEventType()) { - setEventType(other.getEventType()); - } - if (propsBuilder_ == null) { - if (!other.props_.isEmpty()) { - if (props_.isEmpty()) { - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000800); - } else { - ensurePropsIsMutable(); - props_.addAll(other.props_); - } - onChanged(); - } - } else { - if (!other.props_.isEmpty()) { - if (propsBuilder_.isEmpty()) { - propsBuilder_.dispose(); - propsBuilder_ = null; - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000800); - propsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getPropsFieldBuilder() : null; - } else { - propsBuilder_.addAllMessages(other.props_); - } - } - } - if (other.hasGtid()) { - bitField0_ |= 0x00001000; - gtid_ = other.gtid_; - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.Header parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.Header) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private int version_ = 1; - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -             * *协议的版本号*
      -             * 
      - */ - public boolean hasVersion() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -             * *协议的版本号*
      -             * 
      - */ - public int getVersion() { - return version_; - } - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -             * *协议的版本号*
      -             * 
      - */ - public Builder setVersion(int value) { - bitField0_ |= 0x00000001; - version_ = value; - onChanged(); - return this; - } - - /** - * optional int32 version = 1 [default = 1]; - * - *
      -             * *协议的版本号*
      -             * 
      - */ - public Builder clearVersion() { - bitField0_ = (bitField0_ & ~0x00000001); - version_ = 1; - onChanged(); - return this; - } - - private java.lang.Object logfileName_ = ""; - - /** - * optional string logfileName = 2; - * - *
      -             * *binlog/redolog 文件名*
      -             * 
      - */ - public boolean hasLogfileName() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string logfileName = 2; - * - *
      -             * *binlog/redolog 文件名*
      -             * 
      - */ - public java.lang.String getLogfileName() { - java.lang.Object ref = logfileName_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - logfileName_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string logfileName = 2; - * - *
      -             * *binlog/redolog 文件名*
      -             * 
      - */ - public com.google.protobuf.ByteString getLogfileNameBytes() { - java.lang.Object ref = logfileName_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - logfileName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string logfileName = 2; - * - *
      -             * *binlog/redolog 文件名*
      -             * 
      - */ - public Builder setLogfileName(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - logfileName_ = value; - onChanged(); - return this; - } - - /** - * optional string logfileName = 2; - * - *
      -             * *binlog/redolog 文件名*
      -             * 
      - */ - public Builder clearLogfileName() { - bitField0_ = (bitField0_ & ~0x00000002); - logfileName_ = getDefaultInstance().getLogfileName(); - onChanged(); - return this; - } - - /** - * optional string logfileName = 2; - * - *
      -             * *binlog/redolog 文件名*
      -             * 
      - */ - public Builder setLogfileNameBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - logfileName_ = value; - onChanged(); - return this; - } - - private long logfileOffset_; - - /** - * optional int64 logfileOffset = 3; - * - *
      -             * *binlog/redolog 文件的偏移位置*
      -             * 
      - */ - public boolean hasLogfileOffset() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 logfileOffset = 3; - * - *
      -             * *binlog/redolog 文件的偏移位置*
      -             * 
      - */ - public long getLogfileOffset() { - return logfileOffset_; - } - - /** - * optional int64 logfileOffset = 3; - * - *
      -             * *binlog/redolog 文件的偏移位置*
      -             * 
      - */ - public Builder setLogfileOffset(long value) { - bitField0_ |= 0x00000004; - logfileOffset_ = value; - onChanged(); - return this; - } - - /** - * optional int64 logfileOffset = 3; - * - *
      -             * *binlog/redolog 文件的偏移位置*
      -             * 
      - */ - public Builder clearLogfileOffset() { - bitField0_ = (bitField0_ & ~0x00000004); - logfileOffset_ = 0L; - onChanged(); - return this; - } - - private long serverId_; - - /** - * optional int64 serverId = 4; - * - *
      -             * *服务端serverId*
      -             * 
      - */ - public boolean hasServerId() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional int64 serverId = 4; - * - *
      -             * *服务端serverId*
      -             * 
      - */ - public long getServerId() { - return serverId_; - } - - /** - * optional int64 serverId = 4; - * - *
      -             * *服务端serverId*
      -             * 
      - */ - public Builder setServerId(long value) { - bitField0_ |= 0x00000008; - serverId_ = value; - onChanged(); - return this; - } - - /** - * optional int64 serverId = 4; - * - *
      -             * *服务端serverId*
      -             * 
      - */ - public Builder clearServerId() { - bitField0_ = (bitField0_ & ~0x00000008); - serverId_ = 0L; - onChanged(); - return this; - } - - private java.lang.Object serverenCode_ = ""; - - /** - * optional string serverenCode = 5; - * - *
      -             * * 变更数据的编码 *
      -             * 
      - */ - public boolean hasServerenCode() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional string serverenCode = 5; - * - *
      -             * * 变更数据的编码 *
      -             * 
      - */ - public java.lang.String getServerenCode() { - java.lang.Object ref = serverenCode_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - serverenCode_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string serverenCode = 5; - * - *
      -             * * 变更数据的编码 *
      -             * 
      - */ - public com.google.protobuf.ByteString getServerenCodeBytes() { - java.lang.Object ref = serverenCode_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - serverenCode_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string serverenCode = 5; - * - *
      -             * * 变更数据的编码 *
      -             * 
      - */ - public Builder setServerenCode(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000010; - serverenCode_ = value; - onChanged(); - return this; - } - - /** - * optional string serverenCode = 5; - * - *
      -             * * 变更数据的编码 *
      -             * 
      - */ - public Builder clearServerenCode() { - bitField0_ = (bitField0_ & ~0x00000010); - serverenCode_ = getDefaultInstance().getServerenCode(); - onChanged(); - return this; - } - - /** - * optional string serverenCode = 5; - * - *
      -             * * 变更数据的编码 *
      -             * 
      - */ - public Builder setServerenCodeBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000010; - serverenCode_ = value; - onChanged(); - return this; - } - - private long executeTime_; - - /** - * optional int64 executeTime = 6; - * - *
      -             * *变更数据的执行时间 *
      -             * 
      - */ - public boolean hasExecuteTime() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional int64 executeTime = 6; - * - *
      -             * *变更数据的执行时间 *
      -             * 
      - */ - public long getExecuteTime() { - return executeTime_; - } - - /** - * optional int64 executeTime = 6; - * - *
      -             * *变更数据的执行时间 *
      -             * 
      - */ - public Builder setExecuteTime(long value) { - bitField0_ |= 0x00000020; - executeTime_ = value; - onChanged(); - return this; - } - - /** - * optional int64 executeTime = 6; - * - *
      -             * *变更数据的执行时间 *
      -             * 
      - */ - public Builder clearExecuteTime() { - bitField0_ = (bitField0_ & ~0x00000020); - executeTime_ = 0L; - onChanged(); - return this; - } - - private com.alibaba.otter.canal.protocol.CanalEntry.Type sourceType_ = com.alibaba.otter.canal.protocol.CanalEntry.Type.MYSQL; - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -             * * 变更数据的来源*
      -             * 
      - */ - public boolean hasSourceType() { - return ((bitField0_ & 0x00000040) == 0x00000040); - } - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -             * * 变更数据的来源*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Type getSourceType() { - return sourceType_; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -             * * 变更数据的来源*
      -             * 
      - */ - public Builder setSourceType(com.alibaba.otter.canal.protocol.CanalEntry.Type value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000040; - sourceType_ = value; - onChanged(); - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; - * - *
      -             * * 变更数据的来源*
      -             * 
      - */ - public Builder clearSourceType() { - bitField0_ = (bitField0_ & ~0x00000040); - sourceType_ = com.alibaba.otter.canal.protocol.CanalEntry.Type.MYSQL; - onChanged(); - return this; - } - - private java.lang.Object schemaName_ = ""; - - /** - * optional string schemaName = 8; - * - *
      -             * * 变更数据的schemaname*
      -             * 
      - */ - public boolean hasSchemaName() { - return ((bitField0_ & 0x00000080) == 0x00000080); - } - - /** - * optional string schemaName = 8; - * - *
      -             * * 变更数据的schemaname*
      -             * 
      - */ - public java.lang.String getSchemaName() { - java.lang.Object ref = schemaName_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - schemaName_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string schemaName = 8; - * - *
      -             * * 变更数据的schemaname*
      -             * 
      - */ - public com.google.protobuf.ByteString getSchemaNameBytes() { - java.lang.Object ref = schemaName_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - schemaName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string schemaName = 8; - * - *
      -             * * 变更数据的schemaname*
      -             * 
      - */ - public Builder setSchemaName(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000080; - schemaName_ = value; - onChanged(); - return this; - } - - /** - * optional string schemaName = 8; - * - *
      -             * * 变更数据的schemaname*
      -             * 
      - */ - public Builder clearSchemaName() { - bitField0_ = (bitField0_ & ~0x00000080); - schemaName_ = getDefaultInstance().getSchemaName(); - onChanged(); - return this; - } - - /** - * optional string schemaName = 8; - * - *
      -             * * 变更数据的schemaname*
      -             * 
      - */ - public Builder setSchemaNameBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000080; - schemaName_ = value; - onChanged(); - return this; - } - - private java.lang.Object tableName_ = ""; - - /** - * optional string tableName = 9; - * - *
      -             * *变更数据的tablename*
      -             * 
      - */ - public boolean hasTableName() { - return ((bitField0_ & 0x00000100) == 0x00000100); - } - - /** - * optional string tableName = 9; - * - *
      -             * *变更数据的tablename*
      -             * 
      - */ - public java.lang.String getTableName() { - java.lang.Object ref = tableName_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - tableName_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string tableName = 9; - * - *
      -             * *变更数据的tablename*
      -             * 
      - */ - public com.google.protobuf.ByteString getTableNameBytes() { - java.lang.Object ref = tableName_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - tableName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string tableName = 9; - * - *
      -             * *变更数据的tablename*
      -             * 
      - */ - public Builder setTableName(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000100; - tableName_ = value; - onChanged(); - return this; - } - - /** - * optional string tableName = 9; - * - *
      -             * *变更数据的tablename*
      -             * 
      - */ - public Builder clearTableName() { - bitField0_ = (bitField0_ & ~0x00000100); - tableName_ = getDefaultInstance().getTableName(); - onChanged(); - return this; - } - - /** - * optional string tableName = 9; - * - *
      -             * *变更数据的tablename*
      -             * 
      - */ - public Builder setTableNameBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000100; - tableName_ = value; - onChanged(); - return this; - } - - private long eventLength_; - - /** - * optional int64 eventLength = 10; - * - *
      -             * *每个event的长度*
      -             * 
      - */ - public boolean hasEventLength() { - return ((bitField0_ & 0x00000200) == 0x00000200); - } - - /** - * optional int64 eventLength = 10; - * - *
      -             * *每个event的长度*
      -             * 
      - */ - public long getEventLength() { - return eventLength_; - } - - /** - * optional int64 eventLength = 10; - * - *
      -             * *每个event的长度*
      -             * 
      - */ - public Builder setEventLength(long value) { - bitField0_ |= 0x00000200; - eventLength_ = value; - onChanged(); - return this; - } - - /** - * optional int64 eventLength = 10; - * - *
      -             * *每个event的长度*
      -             * 
      - */ - public Builder clearEventLength() { - bitField0_ = (bitField0_ & ~0x00000200); - eventLength_ = 0L; - onChanged(); - return this; - } - - private com.alibaba.otter.canal.protocol.CanalEntry.EventType eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public boolean hasEventType() { - return ((bitField0_ & 0x00000400) == 0x00000400); - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.EventType getEventType() { - return eventType_; - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public Builder setEventType(com.alibaba.otter.canal.protocol.CanalEntry.EventType value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000400; - eventType_ = value; - onChanged(); - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public Builder clearEventType() { - bitField0_ = (bitField0_ & ~0x00000400); - eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - onChanged(); - return this; - } - - private java.util.List props_ = java.util.Collections.emptyList(); - - private void ensurePropsIsMutable() { - if (!((bitField0_ & 0x00000800) == 0x00000800)) { - props_ = new java.util.ArrayList(props_); - bitField0_ |= 0x00000800; - } - } - - private com.google.protobuf.RepeatedFieldBuilder propsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsList() { - if (propsBuilder_ == null) { - return java.util.Collections.unmodifiableList(props_); - } else { - return propsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public int getPropsCount() { - if (propsBuilder_ == null) { - return props_.size(); - } else { - return propsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.set(index, value); - onChanged(); - } else { - propsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.set(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(value); - onChanged(); - } else { - propsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(index, value); - onChanged(); - } else { - propsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addAllProps(java.lang.Iterable values) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, props_); - onChanged(); - } else { - propsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder clearProps() { - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000800); - onChanged(); - } else { - propsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder removeProps(int index) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.remove(index); - onChanged(); - } else { - propsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder getPropsBuilder(int index) { - return getPropsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsOrBuilderList() { - if (propsBuilder_ != null) { - return propsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(props_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder() { - return getPropsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder(int index) { - return getPropsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsBuilderList() { - return getPropsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getPropsFieldBuilder() { - if (propsBuilder_ == null) { - propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(props_, - ((bitField0_ & 0x00000800) == 0x00000800), - getParentForChildren(), - isClean()); - props_ = null; - } - return propsBuilder_; - } - - private java.lang.Object gtid_ = ""; - - /** - * optional string gtid = 13; - * - *
      -             * *当前事务的gitd*
      -             * 
      - */ - public boolean hasGtid() { - return ((bitField0_ & 0x00001000) == 0x00001000); - } - - /** - * optional string gtid = 13; - * - *
      -             * *当前事务的gitd*
      -             * 
      - */ - public java.lang.String getGtid() { - java.lang.Object ref = gtid_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - gtid_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string gtid = 13; - * - *
      -             * *当前事务的gitd*
      -             * 
      - */ - public com.google.protobuf.ByteString getGtidBytes() { - java.lang.Object ref = gtid_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - gtid_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string gtid = 13; - * - *
      -             * *当前事务的gitd*
      -             * 
      - */ - public Builder setGtid(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00001000; - gtid_ = value; - onChanged(); - return this; - } - - /** - * optional string gtid = 13; - * - *
      -             * *当前事务的gitd*
      -             * 
      - */ - public Builder clearGtid() { - bitField0_ = (bitField0_ & ~0x00001000); - gtid_ = getDefaultInstance().getGtid(); - onChanged(); - return this; - } - - /** - * optional string gtid = 13; - * - *
      -             * *当前事务的gitd*
      -             * 
      - */ - public Builder setGtidBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00001000; - gtid_ = value; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Header) + HeaderOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Header.class, Builder.class); + } + + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.Header.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } + + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { + getPropsFieldBuilder(); } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new Header(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + version_ = 1; + bitField0_ = (bitField0_ & ~0x00000001); + logfileName_ = ""; + bitField0_ = (bitField0_ & ~0x00000002); + logfileOffset_ = 0L; + bitField0_ = (bitField0_ & ~0x00000004); + serverId_ = 0L; + bitField0_ = (bitField0_ & ~0x00000008); + serverenCode_ = ""; + bitField0_ = (bitField0_ & ~0x00000010); + executeTime_ = 0L; + bitField0_ = (bitField0_ & ~0x00000020); + sourceType_ = Type.MYSQL; + bitField0_ = (bitField0_ & ~0x00000040); + schemaName_ = ""; + bitField0_ = (bitField0_ & ~0x00000080); + tableName_ = ""; + bitField0_ = (bitField0_ & ~0x00000100); + eventLength_ = 0L; + bitField0_ = (bitField0_ & ~0x00000200); + eventType_ = EventType.UPDATE; + bitField0_ = (bitField0_ & ~0x00000400); + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000800); + } else { + propsBuilder_.clear(); } + gtid_ = ""; + bitField0_ = (bitField0_ & ~0x00001000); + return this; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Header) + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; + } + + public Header getDefaultInstanceForType() { + return Header.getDefaultInstance(); + } + + public Header build() { + Header result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); + } + return result; + } + + public Header buildPartial() { + Header result = new Header(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + if (((from_bitField0_ & 0x00000001) == 0x00000001)) { + to_bitField0_ |= 0x00000001; + } + result.version_ = version_; + if (((from_bitField0_ & 0x00000002) == 0x00000002)) { + to_bitField0_ |= 0x00000002; + } + result.logfileName_ = logfileName_; + if (((from_bitField0_ & 0x00000004) == 0x00000004)) { + to_bitField0_ |= 0x00000004; + } + result.logfileOffset_ = logfileOffset_; + if (((from_bitField0_ & 0x00000008) == 0x00000008)) { + to_bitField0_ |= 0x00000008; + } + result.serverId_ = serverId_; + if (((from_bitField0_ & 0x00000010) == 0x00000010)) { + to_bitField0_ |= 0x00000010; + } + result.serverenCode_ = serverenCode_; + if (((from_bitField0_ & 0x00000020) == 0x00000020)) { + to_bitField0_ |= 0x00000020; + } + result.executeTime_ = executeTime_; + if (((from_bitField0_ & 0x00000040) == 0x00000040)) { + to_bitField0_ |= 0x00000040; + } + result.sourceType_ = sourceType_; + if (((from_bitField0_ & 0x00000080) == 0x00000080)) { + to_bitField0_ |= 0x00000080; + } + result.schemaName_ = schemaName_; + if (((from_bitField0_ & 0x00000100) == 0x00000100)) { + to_bitField0_ |= 0x00000100; + } + result.tableName_ = tableName_; + if (((from_bitField0_ & 0x00000200) == 0x00000200)) { + to_bitField0_ |= 0x00000200; + } + result.eventLength_ = eventLength_; + if (((from_bitField0_ & 0x00000400) == 0x00000400)) { + to_bitField0_ |= 0x00000400; + } + result.eventType_ = eventType_; + if (propsBuilder_ == null) { + if (((bitField0_ & 0x00000800) == 0x00000800)) { + props_ = java.util.Collections.unmodifiableList(props_); + bitField0_ = (bitField0_ & ~0x00000800); + } + result.props_ = props_; + } else { + result.props_ = propsBuilder_.build(); + } + if (((from_bitField0_ & 0x00001000) == 0x00001000)) { + to_bitField0_ |= 0x00000800; + } + result.gtid_ = gtid_; + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof Header) { + return mergeFrom((Header)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(Header other) { + if (other == Header.getDefaultInstance()) return this; + if (other.hasVersion()) { + setVersion(other.getVersion()); + } + if (other.hasLogfileName()) { + bitField0_ |= 0x00000002; + logfileName_ = other.logfileName_; + onChanged(); + } + if (other.hasLogfileOffset()) { + setLogfileOffset(other.getLogfileOffset()); + } + if (other.hasServerId()) { + setServerId(other.getServerId()); + } + if (other.hasServerenCode()) { + bitField0_ |= 0x00000010; + serverenCode_ = other.serverenCode_; + onChanged(); + } + if (other.hasExecuteTime()) { + setExecuteTime(other.getExecuteTime()); + } + if (other.hasSourceType()) { + setSourceType(other.getSourceType()); + } + if (other.hasSchemaName()) { + bitField0_ |= 0x00000080; + schemaName_ = other.schemaName_; + onChanged(); + } + if (other.hasTableName()) { + bitField0_ |= 0x00000100; + tableName_ = other.tableName_; + onChanged(); + } + if (other.hasEventLength()) { + setEventLength(other.getEventLength()); + } + if (other.hasEventType()) { + setEventType(other.getEventType()); + } + if (propsBuilder_ == null) { + if (!other.props_.isEmpty()) { + if (props_.isEmpty()) { + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000800); + } else { + ensurePropsIsMutable(); + props_.addAll(other.props_); + } + onChanged(); + } + } else { + if (!other.props_.isEmpty()) { + if (propsBuilder_.isEmpty()) { + propsBuilder_.dispose(); + propsBuilder_ = null; + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000800); + propsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getPropsFieldBuilder() : null; + } else { + propsBuilder_.addAllMessages(other.props_); + } + } + } + if (other.hasGtid()) { + bitField0_ |= 0x00001000; + gtid_ = other.gtid_; + onChanged(); + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + Header parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (Header) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private int version_ = 1; + /** + * optional int32 version = 1 [default = 1]; + * + *
      +       **协议的版本号*
      +       * 
      + */ + public boolean hasVersion() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int32 version = 1 [default = 1]; + * + *
      +       **协议的版本号*
      +       * 
      + */ + public int getVersion() { + return version_; + } + /** + * optional int32 version = 1 [default = 1]; + * + *
      +       **协议的版本号*
      +       * 
      + */ + public Builder setVersion(int value) { + bitField0_ |= 0x00000001; + version_ = value; + onChanged(); + return this; + } + /** + * optional int32 version = 1 [default = 1]; + * + *
      +       **协议的版本号*
      +       * 
      + */ + public Builder clearVersion() { + bitField0_ = (bitField0_ & ~0x00000001); + version_ = 1; + onChanged(); + return this; + } + + private Object logfileName_ = ""; + /** + * optional string logfileName = 2; + * + *
      +       **binlog/redolog 文件名*
      +       * 
      + */ + public boolean hasLogfileName() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string logfileName = 2; + * + *
      +       **binlog/redolog 文件名*
      +       * 
      + */ + public String getLogfileName() { + Object ref = logfileName_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + logfileName_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string logfileName = 2; + * + *
      +       **binlog/redolog 文件名*
      +       * 
      + */ + public com.google.protobuf.ByteString + getLogfileNameBytes() { + Object ref = logfileName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + logfileName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string logfileName = 2; + * + *
      +       **binlog/redolog 文件名*
      +       * 
      + */ + public Builder setLogfileName( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + logfileName_ = value; + onChanged(); + return this; + } + /** + * optional string logfileName = 2; + * + *
      +       **binlog/redolog 文件名*
      +       * 
      + */ + public Builder clearLogfileName() { + bitField0_ = (bitField0_ & ~0x00000002); + logfileName_ = getDefaultInstance().getLogfileName(); + onChanged(); + return this; + } + /** + * optional string logfileName = 2; + * + *
      +       **binlog/redolog 文件名*
      +       * 
      + */ + public Builder setLogfileNameBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + logfileName_ = value; + onChanged(); + return this; + } + + private long logfileOffset_ ; + /** + * optional int64 logfileOffset = 3; + * + *
      +       **binlog/redolog 文件的偏移位置*
      +       * 
      + */ + public boolean hasLogfileOffset() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional int64 logfileOffset = 3; + * + *
      +       **binlog/redolog 文件的偏移位置*
      +       * 
      + */ + public long getLogfileOffset() { + return logfileOffset_; + } + /** + * optional int64 logfileOffset = 3; + * + *
      +       **binlog/redolog 文件的偏移位置*
      +       * 
      + */ + public Builder setLogfileOffset(long value) { + bitField0_ |= 0x00000004; + logfileOffset_ = value; + onChanged(); + return this; + } + /** + * optional int64 logfileOffset = 3; + * + *
      +       **binlog/redolog 文件的偏移位置*
      +       * 
      + */ + public Builder clearLogfileOffset() { + bitField0_ = (bitField0_ & ~0x00000004); + logfileOffset_ = 0L; + onChanged(); + return this; + } + + private long serverId_ ; + /** + * optional int64 serverId = 4; + * + *
      +       **服务端serverId*
      +       * 
      + */ + public boolean hasServerId() { + return ((bitField0_ & 0x00000008) == 0x00000008); + } + /** + * optional int64 serverId = 4; + * + *
      +       **服务端serverId*
      +       * 
      + */ + public long getServerId() { + return serverId_; + } + /** + * optional int64 serverId = 4; + * + *
      +       **服务端serverId*
      +       * 
      + */ + public Builder setServerId(long value) { + bitField0_ |= 0x00000008; + serverId_ = value; + onChanged(); + return this; + } + /** + * optional int64 serverId = 4; + * + *
      +       **服务端serverId*
      +       * 
      + */ + public Builder clearServerId() { + bitField0_ = (bitField0_ & ~0x00000008); + serverId_ = 0L; + onChanged(); + return this; + } + + private Object serverenCode_ = ""; + /** + * optional string serverenCode = 5; + * + *
      +       ** 变更数据的编码 *
      +       * 
      + */ + public boolean hasServerenCode() { + return ((bitField0_ & 0x00000010) == 0x00000010); + } + /** + * optional string serverenCode = 5; + * + *
      +       ** 变更数据的编码 *
      +       * 
      + */ + public String getServerenCode() { + Object ref = serverenCode_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + serverenCode_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string serverenCode = 5; + * + *
      +       ** 变更数据的编码 *
      +       * 
      + */ + public com.google.protobuf.ByteString + getServerenCodeBytes() { + Object ref = serverenCode_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + serverenCode_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string serverenCode = 5; + * + *
      +       ** 变更数据的编码 *
      +       * 
      + */ + public Builder setServerenCode( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000010; + serverenCode_ = value; + onChanged(); + return this; + } + /** + * optional string serverenCode = 5; + * + *
      +       ** 变更数据的编码 *
      +       * 
      + */ + public Builder clearServerenCode() { + bitField0_ = (bitField0_ & ~0x00000010); + serverenCode_ = getDefaultInstance().getServerenCode(); + onChanged(); + return this; + } + /** + * optional string serverenCode = 5; + * + *
      +       ** 变更数据的编码 *
      +       * 
      + */ + public Builder setServerenCodeBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000010; + serverenCode_ = value; + onChanged(); + return this; + } + + private long executeTime_ ; + /** + * optional int64 executeTime = 6; + * + *
      +       **变更数据的执行时间 *
      +       * 
      + */ + public boolean hasExecuteTime() { + return ((bitField0_ & 0x00000020) == 0x00000020); + } + /** + * optional int64 executeTime = 6; + * + *
      +       **变更数据的执行时间 *
      +       * 
      + */ + public long getExecuteTime() { + return executeTime_; + } + /** + * optional int64 executeTime = 6; + * + *
      +       **变更数据的执行时间 *
      +       * 
      + */ + public Builder setExecuteTime(long value) { + bitField0_ |= 0x00000020; + executeTime_ = value; + onChanged(); + return this; + } + /** + * optional int64 executeTime = 6; + * + *
      +       **变更数据的执行时间 *
      +       * 
      + */ + public Builder clearExecuteTime() { + bitField0_ = (bitField0_ & ~0x00000020); + executeTime_ = 0L; + onChanged(); + return this; + } + + private Type sourceType_ = Type.MYSQL; + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +       ** 变更数据的来源*
      +       * 
      + */ + public boolean hasSourceType() { + return ((bitField0_ & 0x00000040) == 0x00000040); + } + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +       ** 变更数据的来源*
      +       * 
      + */ + public Type getSourceType() { + return sourceType_; + } + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +       ** 变更数据的来源*
      +       * 
      + */ + public Builder setSourceType(Type value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000040; + sourceType_ = value; + onChanged(); + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.Type sourceType = 7 [default = MYSQL]; + * + *
      +       ** 变更数据的来源*
      +       * 
      + */ + public Builder clearSourceType() { + bitField0_ = (bitField0_ & ~0x00000040); + sourceType_ = Type.MYSQL; + onChanged(); + return this; + } + + private Object schemaName_ = ""; + /** + * optional string schemaName = 8; + * + *
      +       ** 变更数据的schemaname*
      +       * 
      + */ + public boolean hasSchemaName() { + return ((bitField0_ & 0x00000080) == 0x00000080); + } + /** + * optional string schemaName = 8; + * + *
      +       ** 变更数据的schemaname*
      +       * 
      + */ + public String getSchemaName() { + Object ref = schemaName_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + schemaName_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string schemaName = 8; + * + *
      +       ** 变更数据的schemaname*
      +       * 
      + */ + public com.google.protobuf.ByteString + getSchemaNameBytes() { + Object ref = schemaName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + schemaName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string schemaName = 8; + * + *
      +       ** 变更数据的schemaname*
      +       * 
      + */ + public Builder setSchemaName( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000080; + schemaName_ = value; + onChanged(); + return this; + } + /** + * optional string schemaName = 8; + * + *
      +       ** 变更数据的schemaname*
      +       * 
      + */ + public Builder clearSchemaName() { + bitField0_ = (bitField0_ & ~0x00000080); + schemaName_ = getDefaultInstance().getSchemaName(); + onChanged(); + return this; + } + /** + * optional string schemaName = 8; + * + *
      +       ** 变更数据的schemaname*
      +       * 
      + */ + public Builder setSchemaNameBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000080; + schemaName_ = value; + onChanged(); + return this; + } + + private Object tableName_ = ""; + /** + * optional string tableName = 9; + * + *
      +       **变更数据的tablename*
      +       * 
      + */ + public boolean hasTableName() { + return ((bitField0_ & 0x00000100) == 0x00000100); + } + /** + * optional string tableName = 9; + * + *
      +       **变更数据的tablename*
      +       * 
      + */ + public String getTableName() { + Object ref = tableName_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + tableName_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string tableName = 9; + * + *
      +       **变更数据的tablename*
      +       * 
      + */ + public com.google.protobuf.ByteString + getTableNameBytes() { + Object ref = tableName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + tableName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string tableName = 9; + * + *
      +       **变更数据的tablename*
      +       * 
      + */ + public Builder setTableName( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000100; + tableName_ = value; + onChanged(); + return this; + } + /** + * optional string tableName = 9; + * + *
      +       **变更数据的tablename*
      +       * 
      + */ + public Builder clearTableName() { + bitField0_ = (bitField0_ & ~0x00000100); + tableName_ = getDefaultInstance().getTableName(); + onChanged(); + return this; + } + /** + * optional string tableName = 9; + * + *
      +       **变更数据的tablename*
      +       * 
      + */ + public Builder setTableNameBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000100; + tableName_ = value; + onChanged(); + return this; + } + + private long eventLength_ ; + /** + * optional int64 eventLength = 10; + * + *
      +       **每个event的长度*
      +       * 
      + */ + public boolean hasEventLength() { + return ((bitField0_ & 0x00000200) == 0x00000200); + } + /** + * optional int64 eventLength = 10; + * + *
      +       **每个event的长度*
      +       * 
      + */ + public long getEventLength() { + return eventLength_; + } + /** + * optional int64 eventLength = 10; + * + *
      +       **每个event的长度*
      +       * 
      + */ + public Builder setEventLength(long value) { + bitField0_ |= 0x00000200; + eventLength_ = value; + onChanged(); + return this; + } + /** + * optional int64 eventLength = 10; + * + *
      +       **每个event的长度*
      +       * 
      + */ + public Builder clearEventLength() { + bitField0_ = (bitField0_ & ~0x00000200); + eventLength_ = 0L; + onChanged(); + return this; + } + + private EventType eventType_ = EventType.UPDATE; + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public boolean hasEventType() { + return ((bitField0_ & 0x00000400) == 0x00000400); + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public EventType getEventType() { + return eventType_; + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public Builder setEventType(EventType value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000400; + eventType_ = value; + onChanged(); + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 11 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public Builder clearEventType() { + bitField0_ = (bitField0_ & ~0x00000400); + eventType_ = EventType.UPDATE; + onChanged(); + return this; + } + + private java.util.List props_ = + java.util.Collections.emptyList(); + private void ensurePropsIsMutable() { + if (!((bitField0_ & 0x00000800) == 0x00000800)) { + props_ = new java.util.ArrayList(props_); + bitField0_ |= 0x00000800; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> propsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List getPropsList() { + if (propsBuilder_ == null) { + return java.util.Collections.unmodifiableList(props_); + } else { + return propsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public int getPropsCount() { + if (propsBuilder_ == null) { + return props_.size(); + } else { + return propsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair getProps(int index) { + if (propsBuilder_ == null) { + return props_.get(index); + } else { + return propsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.set(index, value); + onChanged(); + } else { + propsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.set(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps(Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(value); + onChanged(); + } else { + propsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(index, value); + onChanged(); + } else { + propsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addAllProps( + Iterable values) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, props_); + onChanged(); + } else { + propsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder clearProps() { + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000800); + onChanged(); + } else { + propsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder removeProps(int index) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.remove(index); + onChanged(); + } else { + propsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder getPropsBuilder( + int index) { + return getPropsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + if (propsBuilder_ == null) { + return props_.get(index); } else { + return propsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsOrBuilderList() { + if (propsBuilder_ != null) { + return propsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(props_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder() { + return getPropsFieldBuilder().addBuilder( + Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder( + int index) { + return getPropsFieldBuilder().addBuilder( + index, Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 12; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsBuilderList() { + return getPropsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> + getPropsFieldBuilder() { + if (propsBuilder_ == null) { + propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder>( + props_, + ((bitField0_ & 0x00000800) == 0x00000800), + getParentForChildren(), + isClean()); + props_ = null; + } + return propsBuilder_; + } + + private Object gtid_ = ""; + /** + * optional string gtid = 13; + * + *
      +       **当前事务的gitd*
      +       * 
      + */ + public boolean hasGtid() { + return ((bitField0_ & 0x00001000) == 0x00001000); + } + /** + * optional string gtid = 13; + * + *
      +       **当前事务的gitd*
      +       * 
      + */ + public String getGtid() { + Object ref = gtid_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + gtid_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string gtid = 13; + * + *
      +       **当前事务的gitd*
      +       * 
      + */ + public com.google.protobuf.ByteString + getGtidBytes() { + Object ref = gtid_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + gtid_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string gtid = 13; + * + *
      +       **当前事务的gitd*
      +       * 
      + */ + public Builder setGtid( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00001000; + gtid_ = value; + onChanged(); + return this; + } + /** + * optional string gtid = 13; + * + *
      +       **当前事务的gitd*
      +       * 
      + */ + public Builder clearGtid() { + bitField0_ = (bitField0_ & ~0x00001000); + gtid_ = getDefaultInstance().getGtid(); + onChanged(); + return this; + } + /** + * optional string gtid = 13; + * + *
      +       **当前事务的gitd*
      +       * 
      + */ + public Builder setGtidBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00001000; + gtid_ = value; + onChanged(); + return this; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Header) } - public interface ColumnOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Column) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int32 index = 1; - * - *
      -         * *字段下标*
      -         * 
      - */ - boolean hasIndex(); - - /** - * optional int32 index = 1; - * - *
      -         * *字段下标*
      -         * 
      - */ - int getIndex(); - - /** - * optional int32 sqlType = 2; - * - *
      -         * *字段java中类型*
      -         * 
      - */ - boolean hasSqlType(); - - /** - * optional int32 sqlType = 2; - * - *
      -         * *字段java中类型*
      -         * 
      - */ - int getSqlType(); - - /** - * optional string name = 3; - * - *
      -         * *字段名称(忽略大小写),在mysql中是没有的*
      -         * 
      - */ - boolean hasName(); - - /** - * optional string name = 3; - * - *
      -         * *字段名称(忽略大小写),在mysql中是没有的*
      -         * 
      - */ - java.lang.String getName(); - - /** - * optional string name = 3; - * - *
      -         * *字段名称(忽略大小写),在mysql中是没有的*
      -         * 
      - */ - com.google.protobuf.ByteString getNameBytes(); - - /** - * optional bool isKey = 4; - * - *
      -         * *是否是主键*
      -         * 
      - */ - boolean hasIsKey(); - - /** - * optional bool isKey = 4; - * - *
      -         * *是否是主键*
      -         * 
      - */ - boolean getIsKey(); - - /** - * optional bool updated = 5; - * - *
      -         * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -         * 
      - */ - boolean hasUpdated(); - - /** - * optional bool updated = 5; - * - *
      -         * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -         * 
      - */ - boolean getUpdated(); - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -         * * 标识是否为空  *
      -         * 
      - */ - boolean hasIsNull(); - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -         * * 标识是否为空  *
      -         * 
      - */ - boolean getIsNull(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - int getPropsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index); - - /** - * optional string value = 8; - * - *
      -         * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -         * 
      - */ - boolean hasValue(); - - /** - * optional string value = 8; - * - *
      -         * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -         * 
      - */ - java.lang.String getValue(); - - /** - * optional string value = 8; - * - *
      -         * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -         * 
      - */ - com.google.protobuf.ByteString getValueBytes(); - - /** - * optional int32 length = 9; - * - *
      -         * * 对应数据对象原始长度 *
      -         * 
      - */ - boolean hasLength(); - - /** - * optional int32 length = 9; - * - *
      -         * * 对应数据对象原始长度 *
      -         * 
      - */ - int getLength(); - - /** - * optional string mysqlType = 10; - * - *
      -         * *字段mysql类型*
      -         * 
      - */ - boolean hasMysqlType(); - - /** - * optional string mysqlType = 10; - * - *
      -         * *字段mysql类型*
      -         * 
      - */ - java.lang.String getMysqlType(); - - /** - * optional string mysqlType = 10; - * - *
      -         * *字段mysql类型*
      -         * 
      - */ - com.google.protobuf.ByteString getMysqlTypeBytes(); + static { + defaultInstance = new Header(true); + defaultInstance.initFields(); } + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Header) + } + + public interface ColumnOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Column) + com.google.protobuf.MessageOrBuilder { + + /** + * optional int32 index = 1; + * + *
      +     **字段下标*
      +     * 
      + */ + boolean hasIndex(); + /** + * optional int32 index = 1; + * + *
      +     **字段下标*
      +     * 
      + */ + int getIndex(); + + /** + * optional int32 sqlType = 2; + * + *
      +     **字段java中类型*
      +     * 
      + */ + boolean hasSqlType(); + /** + * optional int32 sqlType = 2; + * + *
      +     **字段java中类型*
      +     * 
      + */ + int getSqlType(); + + /** + * optional string name = 3; + * + *
      +     **字段名称(忽略大小写),在mysql中是没有的*
      +     * 
      + */ + boolean hasName(); + /** + * optional string name = 3; + * + *
      +     **字段名称(忽略大小写),在mysql中是没有的*
      +     * 
      + */ + String getName(); + /** + * optional string name = 3; + * + *
      +     **字段名称(忽略大小写),在mysql中是没有的*
      +     * 
      + */ + com.google.protobuf.ByteString + getNameBytes(); + + /** + * optional bool isKey = 4; + * + *
      +     **是否是主键*
      +     * 
      + */ + boolean hasIsKey(); + /** + * optional bool isKey = 4; + * + *
      +     **是否是主键*
      +     * 
      + */ + boolean getIsKey(); + + /** + * optional bool updated = 5; + * + *
      +     **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +     * 
      + */ + boolean hasUpdated(); + /** + * optional bool updated = 5; + * + *
      +     **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +     * 
      + */ + boolean getUpdated(); + + /** + * optional bool isNull = 6 [default = false]; + * + *
      +     ** 标识是否为空  *
      +     * 
      + */ + boolean hasIsNull(); + /** + * optional bool isNull = 6 [default = false]; + * + *
      +     ** 标识是否为空  *
      +     * 
      + */ + boolean getIsNull(); + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + Pair getProps(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + int getPropsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + PairOrBuilder getPropsOrBuilder(int index); + + /** + * optional string value = 8; + * + *
      +     ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +     * 
      + */ + boolean hasValue(); + /** + * optional string value = 8; + * + *
      +     ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +     * 
      + */ + String getValue(); + /** + * optional string value = 8; + * + *
      +     ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +     * 
      + */ + com.google.protobuf.ByteString + getValueBytes(); + + /** + * optional int32 length = 9; + * + *
      +     ** 对应数据对象原始长度 *
      +     * 
      + */ + boolean hasLength(); + /** + * optional int32 length = 9; + * + *
      +     ** 对应数据对象原始长度 *
      +     * 
      + */ + int getLength(); + + /** + * optional string mysqlType = 10; + * + *
      +     **字段mysql类型*
      +     * 
      + */ + boolean hasMysqlType(); + /** + * optional string mysqlType = 10; + * + *
      +     **字段mysql类型*
      +     * 
      + */ + String getMysqlType(); + /** + * optional string mysqlType = 10; + * + *
      +     **字段mysql类型*
      +     * 
      + */ + com.google.protobuf.ByteString + getMysqlTypeBytes(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.Column} + * + *
      +   **每个字段的数据结构*
      +   * 
      + */ + public static final class Column extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Column) + ColumnOrBuilder { + // Use Column.newBuilder() to construct. + private Column(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private Column(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final Column defaultInstance; + public static Column getDefaultInstance() { + return defaultInstance; + } + + public Column getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Column( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 8: { + bitField0_ |= 0x00000001; + index_ = input.readInt32(); + break; + } + case 16: { + bitField0_ |= 0x00000002; + sqlType_ = input.readInt32(); + break; + } + case 26: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000004; + name_ = bs; + break; + } + case 32: { + bitField0_ |= 0x00000008; + isKey_ = input.readBool(); + break; + } + case 40: { + bitField0_ |= 0x00000010; + updated_ = input.readBool(); + break; + } + case 48: { + bitField0_ |= 0x00000020; + isNull_ = input.readBool(); + break; + } + case 58: { + if (!((mutable_bitField0_ & 0x00000040) == 0x00000040)) { + props_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000040; + } + props_.add(input.readMessage(Pair.PARSER, extensionRegistry)); + break; + } + case 66: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000040; + value_ = bs; + break; + } + case 72: { + bitField0_ |= 0x00000080; + length_ = input.readInt32(); + break; + } + case 82: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000100; + mysqlType_ = bs; + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + if (((mutable_bitField0_ & 0x00000040) == 0x00000040)) { + props_ = java.util.Collections.unmodifiableList(props_); + } + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Column.class, Builder.class); + } + + public static com.google.protobuf.Parser PARSER = + new com.google.protobuf.AbstractParser() { + public Column parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Column(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + private int bitField0_; + public static final int INDEX_FIELD_NUMBER = 1; + private int index_; + /** + * optional int32 index = 1; + * + *
      +     **字段下标*
      +     * 
      + */ + public boolean hasIndex() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int32 index = 1; + * + *
      +     **字段下标*
      +     * 
      + */ + public int getIndex() { + return index_; + } + + public static final int SQLTYPE_FIELD_NUMBER = 2; + private int sqlType_; + /** + * optional int32 sqlType = 2; + * + *
      +     **字段java中类型*
      +     * 
      + */ + public boolean hasSqlType() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional int32 sqlType = 2; + * + *
      +     **字段java中类型*
      +     * 
      + */ + public int getSqlType() { + return sqlType_; + } + + public static final int NAME_FIELD_NUMBER = 3; + private Object name_; + /** + * optional string name = 3; + * + *
      +     **字段名称(忽略大小写),在mysql中是没有的*
      +     * 
      + */ + public boolean hasName() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional string name = 3; + * + *
      +     **字段名称(忽略大小写),在mysql中是没有的*
      +     * 
      + */ + public String getName() { + Object ref = name_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + name_ = s; + } + return s; + } + } + /** + * optional string name = 3; + * + *
      +     **字段名称(忽略大小写),在mysql中是没有的*
      +     * 
      + */ + public com.google.protobuf.ByteString + getNameBytes() { + Object ref = name_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + name_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int ISKEY_FIELD_NUMBER = 4; + private boolean isKey_; + /** + * optional bool isKey = 4; + * + *
      +     **是否是主键*
      +     * 
      + */ + public boolean hasIsKey() { + return ((bitField0_ & 0x00000008) == 0x00000008); + } + /** + * optional bool isKey = 4; + * + *
      +     **是否是主键*
      +     * 
      + */ + public boolean getIsKey() { + return isKey_; + } + + public static final int UPDATED_FIELD_NUMBER = 5; + private boolean updated_; + /** + * optional bool updated = 5; + * + *
      +     **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +     * 
      + */ + public boolean hasUpdated() { + return ((bitField0_ & 0x00000010) == 0x00000010); + } + /** + * optional bool updated = 5; + * + *
      +     **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +     * 
      + */ + public boolean getUpdated() { + return updated_; + } + + public static final int ISNULL_FIELD_NUMBER = 6; + private boolean isNull_; + /** + * optional bool isNull = 6 [default = false]; + * + *
      +     ** 标识是否为空  *
      +     * 
      + */ + public boolean hasIsNull() { + return ((bitField0_ & 0x00000020) == 0x00000020); + } + /** + * optional bool isNull = 6 [default = false]; + * + *
      +     ** 标识是否为空  *
      +     * 
      + */ + public boolean getIsNull() { + return isNull_; + } + + public static final int PROPS_FIELD_NUMBER = 7; + private java.util.List props_; + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List getPropsList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List + getPropsOrBuilderList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + public int getPropsCount() { + return props_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + public Pair getProps(int index) { + return props_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +     **预留扩展*
      +     * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + return props_.get(index); + } + + public static final int VALUE_FIELD_NUMBER = 8; + private Object value_; + /** + * optional string value = 8; + * + *
      +     ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +     * 
      + */ + public boolean hasValue() { + return ((bitField0_ & 0x00000040) == 0x00000040); + } + /** + * optional string value = 8; + * + *
      +     ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +     * 
      + */ + public String getValue() { + Object ref = value_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + value_ = s; + } + return s; + } + } + /** + * optional string value = 8; + * + *
      +     ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +     * 
      + */ + public com.google.protobuf.ByteString + getValueBytes() { + Object ref = value_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + value_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int LENGTH_FIELD_NUMBER = 9; + private int length_; + /** + * optional int32 length = 9; + * + *
      +     ** 对应数据对象原始长度 *
      +     * 
      + */ + public boolean hasLength() { + return ((bitField0_ & 0x00000080) == 0x00000080); + } + /** + * optional int32 length = 9; + * + *
      +     ** 对应数据对象原始长度 *
      +     * 
      + */ + public int getLength() { + return length_; + } + + public static final int MYSQLTYPE_FIELD_NUMBER = 10; + private Object mysqlType_; + /** + * optional string mysqlType = 10; + * + *
      +     **字段mysql类型*
      +     * 
      + */ + public boolean hasMysqlType() { + return ((bitField0_ & 0x00000100) == 0x00000100); + } + /** + * optional string mysqlType = 10; + * + *
      +     **字段mysql类型*
      +     * 
      + */ + public String getMysqlType() { + Object ref = mysqlType_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + mysqlType_ = s; + } + return s; + } + } + /** + * optional string mysqlType = 10; + * + *
      +     **字段mysql类型*
      +     * 
      + */ + public com.google.protobuf.ByteString + getMysqlTypeBytes() { + Object ref = mysqlType_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + mysqlType_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + private void initFields() { + index_ = 0; + sqlType_ = 0; + name_ = ""; + isKey_ = false; + updated_ = false; + isNull_ = false; + props_ = java.util.Collections.emptyList(); + value_ = ""; + length_ = 0; + mysqlType_ = ""; + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + if (((bitField0_ & 0x00000001) == 0x00000001)) { + output.writeInt32(1, index_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + output.writeInt32(2, sqlType_); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + output.writeBytes(3, getNameBytes()); + } + if (((bitField0_ & 0x00000008) == 0x00000008)) { + output.writeBool(4, isKey_); + } + if (((bitField0_ & 0x00000010) == 0x00000010)) { + output.writeBool(5, updated_); + } + if (((bitField0_ & 0x00000020) == 0x00000020)) { + output.writeBool(6, isNull_); + } + for (int i = 0; i < props_.size(); i++) { + output.writeMessage(7, props_.get(i)); + } + if (((bitField0_ & 0x00000040) == 0x00000040)) { + output.writeBytes(8, getValueBytes()); + } + if (((bitField0_ & 0x00000080) == 0x00000080)) { + output.writeInt32(9, length_); + } + if (((bitField0_ & 0x00000100) == 0x00000100)) { + output.writeBytes(10, getMysqlTypeBytes()); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size(1, index_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size(2, sqlType_); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(3, getNameBytes()); + } + if (((bitField0_ & 0x00000008) == 0x00000008)) { + size += com.google.protobuf.CodedOutputStream + .computeBoolSize(4, isKey_); + } + if (((bitField0_ & 0x00000010) == 0x00000010)) { + size += com.google.protobuf.CodedOutputStream + .computeBoolSize(5, updated_); + } + if (((bitField0_ & 0x00000020) == 0x00000020)) { + size += com.google.protobuf.CodedOutputStream + .computeBoolSize(6, isNull_); + } + for (int i = 0; i < props_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(7, props_.get(i)); + } + if (((bitField0_ & 0x00000040) == 0x00000040)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(8, getValueBytes()); + } + if (((bitField0_ & 0x00000080) == 0x00000080)) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size(9, length_); + } + if (((bitField0_ & 0x00000100) == 0x00000100)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(10, getMysqlTypeBytes()); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static Column parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Column parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Column parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Column parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Column parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Column parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static Column parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static Column parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static Column parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Column parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(Column prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.Column} * *
      -     * *每个字段的数据结构*
      +     **每个字段的数据结构*
            * 
      */ - public static final class Column extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Column) - ColumnOrBuilder { - - // Use Column.newBuilder() to construct. - private Column(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Column(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Column defaultInstance; - - public static Column getDefaultInstance() { - return defaultInstance; - } - - public Column getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Column(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - index_ = input.readInt32(); - break; - } - case 16: { - bitField0_ |= 0x00000002; - sqlType_ = input.readInt32(); - break; - } - case 26: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000004; - name_ = bs; - break; - } - case 32: { - bitField0_ |= 0x00000008; - isKey_ = input.readBool(); - break; - } - case 40: { - bitField0_ |= 0x00000010; - updated_ = input.readBool(); - break; - } - case 48: { - bitField0_ |= 0x00000020; - isNull_ = input.readBool(); - break; - } - case 58: { - if (!((mutable_bitField0_ & 0x00000040) == 0x00000040)) { - props_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000040; - } - props_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Pair.PARSER, - extensionRegistry)); - break; - } - case 66: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000040; - value_ = bs; - break; - } - case 72: { - bitField0_ |= 0x00000080; - length_ = input.readInt32(); - break; - } - case 82: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000100; - mysqlType_ = bs; - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000040) == 0x00000040)) { - props_ = java.util.Collections.unmodifiableList(props_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Column.class, - com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Column parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Column(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int INDEX_FIELD_NUMBER = 1; - private int index_; - - /** - * optional int32 index = 1; - * - *
      -         * *字段下标*
      -         * 
      - */ - public boolean hasIndex() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 index = 1; - * - *
      -         * *字段下标*
      -         * 
      - */ - public int getIndex() { - return index_; - } - - public static final int SQLTYPE_FIELD_NUMBER = 2; - private int sqlType_; - - /** - * optional int32 sqlType = 2; - * - *
      -         * *字段java中类型*
      -         * 
      - */ - public boolean hasSqlType() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int32 sqlType = 2; - * - *
      -         * *字段java中类型*
      -         * 
      - */ - public int getSqlType() { - return sqlType_; - } - - public static final int NAME_FIELD_NUMBER = 3; - private java.lang.Object name_; - - /** - * optional string name = 3; - * - *
      -         * *字段名称(忽略大小写),在mysql中是没有的*
      -         * 
      - */ - public boolean hasName() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional string name = 3; - * - *
      -         * *字段名称(忽略大小写),在mysql中是没有的*
      -         * 
      - */ - public java.lang.String getName() { - java.lang.Object ref = name_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - name_ = s; - } - return s; - } - } - - /** - * optional string name = 3; - * - *
      -         * *字段名称(忽略大小写),在mysql中是没有的*
      -         * 
      - */ - public com.google.protobuf.ByteString getNameBytes() { - java.lang.Object ref = name_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - name_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int ISKEY_FIELD_NUMBER = 4; - private boolean isKey_; - - /** - * optional bool isKey = 4; - * - *
      -         * *是否是主键*
      -         * 
      - */ - public boolean hasIsKey() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional bool isKey = 4; - * - *
      -         * *是否是主键*
      -         * 
      - */ - public boolean getIsKey() { - return isKey_; - } - - public static final int UPDATED_FIELD_NUMBER = 5; - private boolean updated_; - - /** - * optional bool updated = 5; - * - *
      -         * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -         * 
      - */ - public boolean hasUpdated() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional bool updated = 5; - * - *
      -         * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -         * 
      - */ - public boolean getUpdated() { - return updated_; - } - - public static final int ISNULL_FIELD_NUMBER = 6; - private boolean isNull_; - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -         * * 标识是否为空  *
      -         * 
      - */ - public boolean hasIsNull() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -         * * 标识是否为空  *
      -         * 
      - */ - public boolean getIsNull() { - return isNull_; - } - - public static final int PROPS_FIELD_NUMBER = 7; - private java.util.List props_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsOrBuilderList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public int getPropsCount() { - return props_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - return props_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - return props_.get(index); - } - - public static final int VALUE_FIELD_NUMBER = 8; - private java.lang.Object value_; - - /** - * optional string value = 8; - * - *
      -         * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -         * 
      - */ - public boolean hasValue() { - return ((bitField0_ & 0x00000040) == 0x00000040); - } - - /** - * optional string value = 8; - * - *
      -         * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -         * 
      - */ - public java.lang.String getValue() { - java.lang.Object ref = value_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - value_ = s; - } - return s; - } - } - - /** - * optional string value = 8; - * - *
      -         * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -         * 
      - */ - public com.google.protobuf.ByteString getValueBytes() { - java.lang.Object ref = value_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - value_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int LENGTH_FIELD_NUMBER = 9; - private int length_; - - /** - * optional int32 length = 9; - * - *
      -         * * 对应数据对象原始长度 *
      -         * 
      - */ - public boolean hasLength() { - return ((bitField0_ & 0x00000080) == 0x00000080); - } - - /** - * optional int32 length = 9; - * - *
      -         * * 对应数据对象原始长度 *
      -         * 
      - */ - public int getLength() { - return length_; - } - - public static final int MYSQLTYPE_FIELD_NUMBER = 10; - private java.lang.Object mysqlType_; - - /** - * optional string mysqlType = 10; - * - *
      -         * *字段mysql类型*
      -         * 
      - */ - public boolean hasMysqlType() { - return ((bitField0_ & 0x00000100) == 0x00000100); - } - - /** - * optional string mysqlType = 10; - * - *
      -         * *字段mysql类型*
      -         * 
      - */ - public java.lang.String getMysqlType() { - java.lang.Object ref = mysqlType_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - mysqlType_ = s; - } - return s; - } - } - - /** - * optional string mysqlType = 10; - * - *
      -         * *字段mysql类型*
      -         * 
      - */ - public com.google.protobuf.ByteString getMysqlTypeBytes() { - java.lang.Object ref = mysqlType_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - mysqlType_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - private void initFields() { - index_ = 0; - sqlType_ = 0; - name_ = ""; - isKey_ = false; - updated_ = false; - isNull_ = false; - props_ = java.util.Collections.emptyList(); - value_ = ""; - length_ = 0; - mysqlType_ = ""; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt32(1, index_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeInt32(2, sqlType_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeBytes(3, getNameBytes()); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - output.writeBool(4, isKey_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - output.writeBool(5, updated_); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - output.writeBool(6, isNull_); - } - for (int i = 0; i < props_.size(); i++) { - output.writeMessage(7, props_.get(i)); - } - if (((bitField0_ & 0x00000040) == 0x00000040)) { - output.writeBytes(8, getValueBytes()); - } - if (((bitField0_ & 0x00000080) == 0x00000080)) { - output.writeInt32(9, length_); - } - if (((bitField0_ & 0x00000100) == 0x00000100)) { - output.writeBytes(10, getMysqlTypeBytes()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(1, index_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(2, sqlType_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(3, getNameBytes()); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - size += com.google.protobuf.CodedOutputStream.computeBoolSize(4, isKey_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - size += com.google.protobuf.CodedOutputStream.computeBoolSize(5, updated_); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - size += com.google.protobuf.CodedOutputStream.computeBoolSize(6, isNull_); - } - for (int i = 0; i < props_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(7, props_.get(i)); - } - if (((bitField0_ & 0x00000040) == 0x00000040)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(8, getValueBytes()); - } - if (((bitField0_ & 0x00000080) == 0x00000080)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(9, length_); - } - if (((bitField0_ & 0x00000100) == 0x00000100)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(10, getMysqlTypeBytes()); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Column parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Column prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Column} - * - *
      -         * *每个字段的数据结构*
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Column) - com.alibaba.otter.canal.protocol.CanalEntry.ColumnOrBuilder { - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Column.class, - com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder.class); - } - - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.Column.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - getPropsFieldBuilder(); - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - index_ = 0; - bitField0_ = (bitField0_ & ~0x00000001); - sqlType_ = 0; - bitField0_ = (bitField0_ & ~0x00000002); - name_ = ""; - bitField0_ = (bitField0_ & ~0x00000004); - isKey_ = false; - bitField0_ = (bitField0_ & ~0x00000008); - updated_ = false; - bitField0_ = (bitField0_ & ~0x00000010); - isNull_ = false; - bitField0_ = (bitField0_ & ~0x00000020); - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000040); - } else { - propsBuilder_.clear(); - } - value_ = ""; - bitField0_ = (bitField0_ & ~0x00000080); - length_ = 0; - bitField0_ = (bitField0_ & ~0x00000100); - mysqlType_ = ""; - bitField0_ = (bitField0_ & ~0x00000200); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Column getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.Column.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Column build() { - com.alibaba.otter.canal.protocol.CanalEntry.Column result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Column buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.Column result = new com.alibaba.otter.canal.protocol.CanalEntry.Column(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.index_ = index_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.sqlType_ = sqlType_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.name_ = name_; - if (((from_bitField0_ & 0x00000008) == 0x00000008)) { - to_bitField0_ |= 0x00000008; - } - result.isKey_ = isKey_; - if (((from_bitField0_ & 0x00000010) == 0x00000010)) { - to_bitField0_ |= 0x00000010; - } - result.updated_ = updated_; - if (((from_bitField0_ & 0x00000020) == 0x00000020)) { - to_bitField0_ |= 0x00000020; - } - result.isNull_ = isNull_; - if (propsBuilder_ == null) { - if (((bitField0_ & 0x00000040) == 0x00000040)) { - props_ = java.util.Collections.unmodifiableList(props_); - bitField0_ = (bitField0_ & ~0x00000040); - } - result.props_ = props_; - } else { - result.props_ = propsBuilder_.build(); - } - if (((from_bitField0_ & 0x00000080) == 0x00000080)) { - to_bitField0_ |= 0x00000040; - } - result.value_ = value_; - if (((from_bitField0_ & 0x00000100) == 0x00000100)) { - to_bitField0_ |= 0x00000080; - } - result.length_ = length_; - if (((from_bitField0_ & 0x00000200) == 0x00000200)) { - to_bitField0_ |= 0x00000100; - } - result.mysqlType_ = mysqlType_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.Column) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.Column) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.Column other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.Column.getDefaultInstance()) return this; - if (other.hasIndex()) { - setIndex(other.getIndex()); - } - if (other.hasSqlType()) { - setSqlType(other.getSqlType()); - } - if (other.hasName()) { - bitField0_ |= 0x00000004; - name_ = other.name_; - onChanged(); - } - if (other.hasIsKey()) { - setIsKey(other.getIsKey()); - } - if (other.hasUpdated()) { - setUpdated(other.getUpdated()); - } - if (other.hasIsNull()) { - setIsNull(other.getIsNull()); - } - if (propsBuilder_ == null) { - if (!other.props_.isEmpty()) { - if (props_.isEmpty()) { - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000040); - } else { - ensurePropsIsMutable(); - props_.addAll(other.props_); - } - onChanged(); - } - } else { - if (!other.props_.isEmpty()) { - if (propsBuilder_.isEmpty()) { - propsBuilder_.dispose(); - propsBuilder_ = null; - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000040); - propsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getPropsFieldBuilder() : null; - } else { - propsBuilder_.addAllMessages(other.props_); - } - } - } - if (other.hasValue()) { - bitField0_ |= 0x00000080; - value_ = other.value_; - onChanged(); - } - if (other.hasLength()) { - setLength(other.getLength()); - } - if (other.hasMysqlType()) { - bitField0_ |= 0x00000200; - mysqlType_ = other.mysqlType_; - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.Column parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.Column) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private int index_; - - /** - * optional int32 index = 1; - * - *
      -             * *字段下标*
      -             * 
      - */ - public boolean hasIndex() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 index = 1; - * - *
      -             * *字段下标*
      -             * 
      - */ - public int getIndex() { - return index_; - } - - /** - * optional int32 index = 1; - * - *
      -             * *字段下标*
      -             * 
      - */ - public Builder setIndex(int value) { - bitField0_ |= 0x00000001; - index_ = value; - onChanged(); - return this; - } - - /** - * optional int32 index = 1; - * - *
      -             * *字段下标*
      -             * 
      - */ - public Builder clearIndex() { - bitField0_ = (bitField0_ & ~0x00000001); - index_ = 0; - onChanged(); - return this; - } - - private int sqlType_; - - /** - * optional int32 sqlType = 2; - * - *
      -             * *字段java中类型*
      -             * 
      - */ - public boolean hasSqlType() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int32 sqlType = 2; - * - *
      -             * *字段java中类型*
      -             * 
      - */ - public int getSqlType() { - return sqlType_; - } - - /** - * optional int32 sqlType = 2; - * - *
      -             * *字段java中类型*
      -             * 
      - */ - public Builder setSqlType(int value) { - bitField0_ |= 0x00000002; - sqlType_ = value; - onChanged(); - return this; - } - - /** - * optional int32 sqlType = 2; - * - *
      -             * *字段java中类型*
      -             * 
      - */ - public Builder clearSqlType() { - bitField0_ = (bitField0_ & ~0x00000002); - sqlType_ = 0; - onChanged(); - return this; - } - - private java.lang.Object name_ = ""; - - /** - * optional string name = 3; - * - *
      -             * *字段名称(忽略大小写),在mysql中是没有的*
      -             * 
      - */ - public boolean hasName() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional string name = 3; - * - *
      -             * *字段名称(忽略大小写),在mysql中是没有的*
      -             * 
      - */ - public java.lang.String getName() { - java.lang.Object ref = name_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - name_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string name = 3; - * - *
      -             * *字段名称(忽略大小写),在mysql中是没有的*
      -             * 
      - */ - public com.google.protobuf.ByteString getNameBytes() { - java.lang.Object ref = name_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - name_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string name = 3; - * - *
      -             * *字段名称(忽略大小写),在mysql中是没有的*
      -             * 
      - */ - public Builder setName(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - name_ = value; - onChanged(); - return this; - } - - /** - * optional string name = 3; - * - *
      -             * *字段名称(忽略大小写),在mysql中是没有的*
      -             * 
      - */ - public Builder clearName() { - bitField0_ = (bitField0_ & ~0x00000004); - name_ = getDefaultInstance().getName(); - onChanged(); - return this; - } - - /** - * optional string name = 3; - * - *
      -             * *字段名称(忽略大小写),在mysql中是没有的*
      -             * 
      - */ - public Builder setNameBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - name_ = value; - onChanged(); - return this; - } - - private boolean isKey_; - - /** - * optional bool isKey = 4; - * - *
      -             * *是否是主键*
      -             * 
      - */ - public boolean hasIsKey() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional bool isKey = 4; - * - *
      -             * *是否是主键*
      -             * 
      - */ - public boolean getIsKey() { - return isKey_; - } - - /** - * optional bool isKey = 4; - * - *
      -             * *是否是主键*
      -             * 
      - */ - public Builder setIsKey(boolean value) { - bitField0_ |= 0x00000008; - isKey_ = value; - onChanged(); - return this; - } - - /** - * optional bool isKey = 4; - * - *
      -             * *是否是主键*
      -             * 
      - */ - public Builder clearIsKey() { - bitField0_ = (bitField0_ & ~0x00000008); - isKey_ = false; - onChanged(); - return this; - } - - private boolean updated_; - - /** - * optional bool updated = 5; - * - *
      -             * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -             * 
      - */ - public boolean hasUpdated() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional bool updated = 5; - * - *
      -             * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -             * 
      - */ - public boolean getUpdated() { - return updated_; - } - - /** - * optional bool updated = 5; - * - *
      -             * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -             * 
      - */ - public Builder setUpdated(boolean value) { - bitField0_ |= 0x00000010; - updated_ = value; - onChanged(); - return this; - } - - /** - * optional bool updated = 5; - * - *
      -             * *如果EventType=UPDATE,用于标识这个字段值是否有修改*
      -             * 
      - */ - public Builder clearUpdated() { - bitField0_ = (bitField0_ & ~0x00000010); - updated_ = false; - onChanged(); - return this; - } - - private boolean isNull_; - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -             * * 标识是否为空  *
      -             * 
      - */ - public boolean hasIsNull() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -             * * 标识是否为空  *
      -             * 
      - */ - public boolean getIsNull() { - return isNull_; - } - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -             * * 标识是否为空  *
      -             * 
      - */ - public Builder setIsNull(boolean value) { - bitField0_ |= 0x00000020; - isNull_ = value; - onChanged(); - return this; - } - - /** - * optional bool isNull = 6 [default = false]; - * - *
      -             * * 标识是否为空  *
      -             * 
      - */ - public Builder clearIsNull() { - bitField0_ = (bitField0_ & ~0x00000020); - isNull_ = false; - onChanged(); - return this; - } - - private java.util.List props_ = java.util.Collections.emptyList(); - - private void ensurePropsIsMutable() { - if (!((bitField0_ & 0x00000040) == 0x00000040)) { - props_ = new java.util.ArrayList(props_); - bitField0_ |= 0x00000040; - } - } - - private com.google.protobuf.RepeatedFieldBuilder propsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsList() { - if (propsBuilder_ == null) { - return java.util.Collections.unmodifiableList(props_); - } else { - return propsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public int getPropsCount() { - if (propsBuilder_ == null) { - return props_.size(); - } else { - return propsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.set(index, value); - onChanged(); - } else { - propsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.set(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(value); - onChanged(); - } else { - propsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(index, value); - onChanged(); - } else { - propsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addAllProps(java.lang.Iterable values) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, props_); - onChanged(); - } else { - propsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder clearProps() { - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000040); - onChanged(); - } else { - propsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder removeProps(int index) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.remove(index); - onChanged(); - } else { - propsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder getPropsBuilder(int index) { - return getPropsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsOrBuilderList() { - if (propsBuilder_ != null) { - return propsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(props_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder() { - return getPropsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder(int index) { - return getPropsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsBuilderList() { - return getPropsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getPropsFieldBuilder() { - if (propsBuilder_ == null) { - propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(props_, - ((bitField0_ & 0x00000040) == 0x00000040), - getParentForChildren(), - isClean()); - props_ = null; - } - return propsBuilder_; - } - - private java.lang.Object value_ = ""; - - /** - * optional string value = 8; - * - *
      -             * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -             * 
      - */ - public boolean hasValue() { - return ((bitField0_ & 0x00000080) == 0x00000080); - } - - /** - * optional string value = 8; - * - *
      -             * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -             * 
      - */ - public java.lang.String getValue() { - java.lang.Object ref = value_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - value_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string value = 8; - * - *
      -             * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -             * 
      - */ - public com.google.protobuf.ByteString getValueBytes() { - java.lang.Object ref = value_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - value_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string value = 8; - * - *
      -             * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -             * 
      - */ - public Builder setValue(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000080; - value_ = value; - onChanged(); - return this; - } - - /** - * optional string value = 8; - * - *
      -             * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -             * 
      - */ - public Builder clearValue() { - bitField0_ = (bitField0_ & ~0x00000080); - value_ = getDefaultInstance().getValue(); - onChanged(); - return this; - } - - /** - * optional string value = 8; - * - *
      -             * * 字段值,timestamp,Datetime是一个时间格式的文本 *
      -             * 
      - */ - public Builder setValueBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000080; - value_ = value; - onChanged(); - return this; - } - - private int length_; - - /** - * optional int32 length = 9; - * - *
      -             * * 对应数据对象原始长度 *
      -             * 
      - */ - public boolean hasLength() { - return ((bitField0_ & 0x00000100) == 0x00000100); - } - - /** - * optional int32 length = 9; - * - *
      -             * * 对应数据对象原始长度 *
      -             * 
      - */ - public int getLength() { - return length_; - } - - /** - * optional int32 length = 9; - * - *
      -             * * 对应数据对象原始长度 *
      -             * 
      - */ - public Builder setLength(int value) { - bitField0_ |= 0x00000100; - length_ = value; - onChanged(); - return this; - } - - /** - * optional int32 length = 9; - * - *
      -             * * 对应数据对象原始长度 *
      -             * 
      - */ - public Builder clearLength() { - bitField0_ = (bitField0_ & ~0x00000100); - length_ = 0; - onChanged(); - return this; - } - - private java.lang.Object mysqlType_ = ""; - - /** - * optional string mysqlType = 10; - * - *
      -             * *字段mysql类型*
      -             * 
      - */ - public boolean hasMysqlType() { - return ((bitField0_ & 0x00000200) == 0x00000200); - } - - /** - * optional string mysqlType = 10; - * - *
      -             * *字段mysql类型*
      -             * 
      - */ - public java.lang.String getMysqlType() { - java.lang.Object ref = mysqlType_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - mysqlType_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string mysqlType = 10; - * - *
      -             * *字段mysql类型*
      -             * 
      - */ - public com.google.protobuf.ByteString getMysqlTypeBytes() { - java.lang.Object ref = mysqlType_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - mysqlType_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string mysqlType = 10; - * - *
      -             * *字段mysql类型*
      -             * 
      - */ - public Builder setMysqlType(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000200; - mysqlType_ = value; - onChanged(); - return this; - } - - /** - * optional string mysqlType = 10; - * - *
      -             * *字段mysql类型*
      -             * 
      - */ - public Builder clearMysqlType() { - bitField0_ = (bitField0_ & ~0x00000200); - mysqlType_ = getDefaultInstance().getMysqlType(); - onChanged(); - return this; - } - - /** - * optional string mysqlType = 10; - * - *
      -             * *字段mysql类型*
      -             * 
      - */ - public Builder setMysqlTypeBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000200; - mysqlType_ = value; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Column) + ColumnOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Column.class, Builder.class); + } + + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.Column.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } + + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { + getPropsFieldBuilder(); } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new Column(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + index_ = 0; + bitField0_ = (bitField0_ & ~0x00000001); + sqlType_ = 0; + bitField0_ = (bitField0_ & ~0x00000002); + name_ = ""; + bitField0_ = (bitField0_ & ~0x00000004); + isKey_ = false; + bitField0_ = (bitField0_ & ~0x00000008); + updated_ = false; + bitField0_ = (bitField0_ & ~0x00000010); + isNull_ = false; + bitField0_ = (bitField0_ & ~0x00000020); + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000040); + } else { + propsBuilder_.clear(); } + value_ = ""; + bitField0_ = (bitField0_ & ~0x00000080); + length_ = 0; + bitField0_ = (bitField0_ & ~0x00000100); + mysqlType_ = ""; + bitField0_ = (bitField0_ & ~0x00000200); + return this; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Column) + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; + } + + public Column getDefaultInstanceForType() { + return Column.getDefaultInstance(); + } + + public Column build() { + Column result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); + } + return result; + } + + public Column buildPartial() { + Column result = new Column(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + if (((from_bitField0_ & 0x00000001) == 0x00000001)) { + to_bitField0_ |= 0x00000001; + } + result.index_ = index_; + if (((from_bitField0_ & 0x00000002) == 0x00000002)) { + to_bitField0_ |= 0x00000002; + } + result.sqlType_ = sqlType_; + if (((from_bitField0_ & 0x00000004) == 0x00000004)) { + to_bitField0_ |= 0x00000004; + } + result.name_ = name_; + if (((from_bitField0_ & 0x00000008) == 0x00000008)) { + to_bitField0_ |= 0x00000008; + } + result.isKey_ = isKey_; + if (((from_bitField0_ & 0x00000010) == 0x00000010)) { + to_bitField0_ |= 0x00000010; + } + result.updated_ = updated_; + if (((from_bitField0_ & 0x00000020) == 0x00000020)) { + to_bitField0_ |= 0x00000020; + } + result.isNull_ = isNull_; + if (propsBuilder_ == null) { + if (((bitField0_ & 0x00000040) == 0x00000040)) { + props_ = java.util.Collections.unmodifiableList(props_); + bitField0_ = (bitField0_ & ~0x00000040); + } + result.props_ = props_; + } else { + result.props_ = propsBuilder_.build(); + } + if (((from_bitField0_ & 0x00000080) == 0x00000080)) { + to_bitField0_ |= 0x00000040; + } + result.value_ = value_; + if (((from_bitField0_ & 0x00000100) == 0x00000100)) { + to_bitField0_ |= 0x00000080; + } + result.length_ = length_; + if (((from_bitField0_ & 0x00000200) == 0x00000200)) { + to_bitField0_ |= 0x00000100; + } + result.mysqlType_ = mysqlType_; + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof Column) { + return mergeFrom((Column)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(Column other) { + if (other == Column.getDefaultInstance()) return this; + if (other.hasIndex()) { + setIndex(other.getIndex()); + } + if (other.hasSqlType()) { + setSqlType(other.getSqlType()); + } + if (other.hasName()) { + bitField0_ |= 0x00000004; + name_ = other.name_; + onChanged(); + } + if (other.hasIsKey()) { + setIsKey(other.getIsKey()); + } + if (other.hasUpdated()) { + setUpdated(other.getUpdated()); + } + if (other.hasIsNull()) { + setIsNull(other.getIsNull()); + } + if (propsBuilder_ == null) { + if (!other.props_.isEmpty()) { + if (props_.isEmpty()) { + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000040); + } else { + ensurePropsIsMutable(); + props_.addAll(other.props_); + } + onChanged(); + } + } else { + if (!other.props_.isEmpty()) { + if (propsBuilder_.isEmpty()) { + propsBuilder_.dispose(); + propsBuilder_ = null; + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000040); + propsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getPropsFieldBuilder() : null; + } else { + propsBuilder_.addAllMessages(other.props_); + } + } + } + if (other.hasValue()) { + bitField0_ |= 0x00000080; + value_ = other.value_; + onChanged(); + } + if (other.hasLength()) { + setLength(other.getLength()); + } + if (other.hasMysqlType()) { + bitField0_ |= 0x00000200; + mysqlType_ = other.mysqlType_; + onChanged(); + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + Column parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (Column) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private int index_ ; + /** + * optional int32 index = 1; + * + *
      +       **字段下标*
      +       * 
      + */ + public boolean hasIndex() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int32 index = 1; + * + *
      +       **字段下标*
      +       * 
      + */ + public int getIndex() { + return index_; + } + /** + * optional int32 index = 1; + * + *
      +       **字段下标*
      +       * 
      + */ + public Builder setIndex(int value) { + bitField0_ |= 0x00000001; + index_ = value; + onChanged(); + return this; + } + /** + * optional int32 index = 1; + * + *
      +       **字段下标*
      +       * 
      + */ + public Builder clearIndex() { + bitField0_ = (bitField0_ & ~0x00000001); + index_ = 0; + onChanged(); + return this; + } + + private int sqlType_ ; + /** + * optional int32 sqlType = 2; + * + *
      +       **字段java中类型*
      +       * 
      + */ + public boolean hasSqlType() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional int32 sqlType = 2; + * + *
      +       **字段java中类型*
      +       * 
      + */ + public int getSqlType() { + return sqlType_; + } + /** + * optional int32 sqlType = 2; + * + *
      +       **字段java中类型*
      +       * 
      + */ + public Builder setSqlType(int value) { + bitField0_ |= 0x00000002; + sqlType_ = value; + onChanged(); + return this; + } + /** + * optional int32 sqlType = 2; + * + *
      +       **字段java中类型*
      +       * 
      + */ + public Builder clearSqlType() { + bitField0_ = (bitField0_ & ~0x00000002); + sqlType_ = 0; + onChanged(); + return this; + } + + private Object name_ = ""; + /** + * optional string name = 3; + * + *
      +       **字段名称(忽略大小写),在mysql中是没有的*
      +       * 
      + */ + public boolean hasName() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional string name = 3; + * + *
      +       **字段名称(忽略大小写),在mysql中是没有的*
      +       * 
      + */ + public String getName() { + Object ref = name_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + name_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string name = 3; + * + *
      +       **字段名称(忽略大小写),在mysql中是没有的*
      +       * 
      + */ + public com.google.protobuf.ByteString + getNameBytes() { + Object ref = name_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + name_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string name = 3; + * + *
      +       **字段名称(忽略大小写),在mysql中是没有的*
      +       * 
      + */ + public Builder setName( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000004; + name_ = value; + onChanged(); + return this; + } + /** + * optional string name = 3; + * + *
      +       **字段名称(忽略大小写),在mysql中是没有的*
      +       * 
      + */ + public Builder clearName() { + bitField0_ = (bitField0_ & ~0x00000004); + name_ = getDefaultInstance().getName(); + onChanged(); + return this; + } + /** + * optional string name = 3; + * + *
      +       **字段名称(忽略大小写),在mysql中是没有的*
      +       * 
      + */ + public Builder setNameBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000004; + name_ = value; + onChanged(); + return this; + } + + private boolean isKey_ ; + /** + * optional bool isKey = 4; + * + *
      +       **是否是主键*
      +       * 
      + */ + public boolean hasIsKey() { + return ((bitField0_ & 0x00000008) == 0x00000008); + } + /** + * optional bool isKey = 4; + * + *
      +       **是否是主键*
      +       * 
      + */ + public boolean getIsKey() { + return isKey_; + } + /** + * optional bool isKey = 4; + * + *
      +       **是否是主键*
      +       * 
      + */ + public Builder setIsKey(boolean value) { + bitField0_ |= 0x00000008; + isKey_ = value; + onChanged(); + return this; + } + /** + * optional bool isKey = 4; + * + *
      +       **是否是主键*
      +       * 
      + */ + public Builder clearIsKey() { + bitField0_ = (bitField0_ & ~0x00000008); + isKey_ = false; + onChanged(); + return this; + } + + private boolean updated_ ; + /** + * optional bool updated = 5; + * + *
      +       **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +       * 
      + */ + public boolean hasUpdated() { + return ((bitField0_ & 0x00000010) == 0x00000010); + } + /** + * optional bool updated = 5; + * + *
      +       **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +       * 
      + */ + public boolean getUpdated() { + return updated_; + } + /** + * optional bool updated = 5; + * + *
      +       **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +       * 
      + */ + public Builder setUpdated(boolean value) { + bitField0_ |= 0x00000010; + updated_ = value; + onChanged(); + return this; + } + /** + * optional bool updated = 5; + * + *
      +       **如果EventType=UPDATE,用于标识这个字段值是否有修改*
      +       * 
      + */ + public Builder clearUpdated() { + bitField0_ = (bitField0_ & ~0x00000010); + updated_ = false; + onChanged(); + return this; + } + + private boolean isNull_ ; + /** + * optional bool isNull = 6 [default = false]; + * + *
      +       ** 标识是否为空  *
      +       * 
      + */ + public boolean hasIsNull() { + return ((bitField0_ & 0x00000020) == 0x00000020); + } + /** + * optional bool isNull = 6 [default = false]; + * + *
      +       ** 标识是否为空  *
      +       * 
      + */ + public boolean getIsNull() { + return isNull_; + } + /** + * optional bool isNull = 6 [default = false]; + * + *
      +       ** 标识是否为空  *
      +       * 
      + */ + public Builder setIsNull(boolean value) { + bitField0_ |= 0x00000020; + isNull_ = value; + onChanged(); + return this; + } + /** + * optional bool isNull = 6 [default = false]; + * + *
      +       ** 标识是否为空  *
      +       * 
      + */ + public Builder clearIsNull() { + bitField0_ = (bitField0_ & ~0x00000020); + isNull_ = false; + onChanged(); + return this; + } + + private java.util.List props_ = + java.util.Collections.emptyList(); + private void ensurePropsIsMutable() { + if (!((bitField0_ & 0x00000040) == 0x00000040)) { + props_ = new java.util.ArrayList(props_); + bitField0_ |= 0x00000040; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> propsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List getPropsList() { + if (propsBuilder_ == null) { + return java.util.Collections.unmodifiableList(props_); + } else { + return propsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public int getPropsCount() { + if (propsBuilder_ == null) { + return props_.size(); + } else { + return propsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair getProps(int index) { + if (propsBuilder_ == null) { + return props_.get(index); + } else { + return propsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.set(index, value); + onChanged(); + } else { + propsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.set(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps(Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(value); + onChanged(); + } else { + propsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(index, value); + onChanged(); + } else { + propsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addAllProps( + Iterable values) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, props_); + onChanged(); + } else { + propsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder clearProps() { + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000040); + onChanged(); + } else { + propsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder removeProps(int index) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.remove(index); + onChanged(); + } else { + propsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder getPropsBuilder( + int index) { + return getPropsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + if (propsBuilder_ == null) { + return props_.get(index); } else { + return propsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsOrBuilderList() { + if (propsBuilder_ != null) { + return propsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(props_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder() { + return getPropsFieldBuilder().addBuilder( + Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder( + int index) { + return getPropsFieldBuilder().addBuilder( + index, Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 7; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsBuilderList() { + return getPropsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> + getPropsFieldBuilder() { + if (propsBuilder_ == null) { + propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder>( + props_, + ((bitField0_ & 0x00000040) == 0x00000040), + getParentForChildren(), + isClean()); + props_ = null; + } + return propsBuilder_; + } + + private Object value_ = ""; + /** + * optional string value = 8; + * + *
      +       ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +       * 
      + */ + public boolean hasValue() { + return ((bitField0_ & 0x00000080) == 0x00000080); + } + /** + * optional string value = 8; + * + *
      +       ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +       * 
      + */ + public String getValue() { + Object ref = value_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + value_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string value = 8; + * + *
      +       ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +       * 
      + */ + public com.google.protobuf.ByteString + getValueBytes() { + Object ref = value_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + value_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string value = 8; + * + *
      +       ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +       * 
      + */ + public Builder setValue( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000080; + value_ = value; + onChanged(); + return this; + } + /** + * optional string value = 8; + * + *
      +       ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +       * 
      + */ + public Builder clearValue() { + bitField0_ = (bitField0_ & ~0x00000080); + value_ = getDefaultInstance().getValue(); + onChanged(); + return this; + } + /** + * optional string value = 8; + * + *
      +       ** 字段值,timestamp,Datetime是一个时间格式的文本 *
      +       * 
      + */ + public Builder setValueBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000080; + value_ = value; + onChanged(); + return this; + } + + private int length_ ; + /** + * optional int32 length = 9; + * + *
      +       ** 对应数据对象原始长度 *
      +       * 
      + */ + public boolean hasLength() { + return ((bitField0_ & 0x00000100) == 0x00000100); + } + /** + * optional int32 length = 9; + * + *
      +       ** 对应数据对象原始长度 *
      +       * 
      + */ + public int getLength() { + return length_; + } + /** + * optional int32 length = 9; + * + *
      +       ** 对应数据对象原始长度 *
      +       * 
      + */ + public Builder setLength(int value) { + bitField0_ |= 0x00000100; + length_ = value; + onChanged(); + return this; + } + /** + * optional int32 length = 9; + * + *
      +       ** 对应数据对象原始长度 *
      +       * 
      + */ + public Builder clearLength() { + bitField0_ = (bitField0_ & ~0x00000100); + length_ = 0; + onChanged(); + return this; + } + + private Object mysqlType_ = ""; + /** + * optional string mysqlType = 10; + * + *
      +       **字段mysql类型*
      +       * 
      + */ + public boolean hasMysqlType() { + return ((bitField0_ & 0x00000200) == 0x00000200); + } + /** + * optional string mysqlType = 10; + * + *
      +       **字段mysql类型*
      +       * 
      + */ + public String getMysqlType() { + Object ref = mysqlType_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + mysqlType_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string mysqlType = 10; + * + *
      +       **字段mysql类型*
      +       * 
      + */ + public com.google.protobuf.ByteString + getMysqlTypeBytes() { + Object ref = mysqlType_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + mysqlType_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string mysqlType = 10; + * + *
      +       **字段mysql类型*
      +       * 
      + */ + public Builder setMysqlType( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000200; + mysqlType_ = value; + onChanged(); + return this; + } + /** + * optional string mysqlType = 10; + * + *
      +       **字段mysql类型*
      +       * 
      + */ + public Builder clearMysqlType() { + bitField0_ = (bitField0_ & ~0x00000200); + mysqlType_ = getDefaultInstance().getMysqlType(); + onChanged(); + return this; + } + /** + * optional string mysqlType = 10; + * + *
      +       **字段mysql类型*
      +       * 
      + */ + public Builder setMysqlTypeBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000200; + mysqlType_ = value; + onChanged(); + return this; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Column) } - public interface RowDataOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.RowData) - com.google.protobuf.MessageOrBuilder { - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - java.util.List getBeforeColumnsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Column getBeforeColumns(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - int getBeforeColumnsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - java.util.List getBeforeColumnsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.ColumnOrBuilder getBeforeColumnsOrBuilder(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - java.util.List getAfterColumnsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Column getAfterColumns(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - int getAfterColumnsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - java.util.List getAfterColumnsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.ColumnOrBuilder getAfterColumnsOrBuilder(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - int getPropsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index); + static { + defaultInstance = new Column(true); + defaultInstance.initFields(); } + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Column) + } + + public interface RowDataOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.RowData) + com.google.protobuf.MessageOrBuilder { + + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + java.util.List + getBeforeColumnsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + Column getBeforeColumns(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + int getBeforeColumnsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + java.util.List + getBeforeColumnsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + ColumnOrBuilder getBeforeColumnsOrBuilder(int index); + + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + java.util.List + getAfterColumnsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + Column getAfterColumns(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + int getAfterColumnsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + java.util.List + getAfterColumnsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + ColumnOrBuilder getAfterColumnsOrBuilder(int index); + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + Pair getProps(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + int getPropsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + PairOrBuilder getPropsOrBuilder(int index); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.RowData} + */ + public static final class RowData extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.RowData) + RowDataOrBuilder { + // Use RowData.newBuilder() to construct. + private RowData(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private RowData(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final RowData defaultInstance; + public static RowData getDefaultInstance() { + return defaultInstance; + } + + public RowData getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private RowData( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 10: { + if (!((mutable_bitField0_ & 0x00000001) == 0x00000001)) { + beforeColumns_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000001; + } + beforeColumns_.add(input.readMessage(Column.PARSER, extensionRegistry)); + break; + } + case 18: { + if (!((mutable_bitField0_ & 0x00000002) == 0x00000002)) { + afterColumns_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000002; + } + afterColumns_.add(input.readMessage(Column.PARSER, extensionRegistry)); + break; + } + case 26: { + if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { + props_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000004; + } + props_.add(input.readMessage(Pair.PARSER, extensionRegistry)); + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + if (((mutable_bitField0_ & 0x00000001) == 0x00000001)) { + beforeColumns_ = java.util.Collections.unmodifiableList(beforeColumns_); + } + if (((mutable_bitField0_ & 0x00000002) == 0x00000002)) { + afterColumns_ = java.util.Collections.unmodifiableList(afterColumns_); + } + if (((mutable_bitField0_ & 0x00000004) == 0x00000004)) { + props_ = java.util.Collections.unmodifiableList(props_); + } + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable + .ensureFieldAccessorsInitialized( + RowData.class, Builder.class); + } + + public static com.google.protobuf.Parser PARSER = + new com.google.protobuf.AbstractParser() { + public RowData parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new RowData(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + public static final int BEFORECOLUMNS_FIELD_NUMBER = 1; + private java.util.List beforeColumns_; + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + public java.util.List getBeforeColumnsList() { + return beforeColumns_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + public java.util.List + getBeforeColumnsOrBuilderList() { + return beforeColumns_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + public int getBeforeColumnsCount() { + return beforeColumns_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + public Column getBeforeColumns(int index) { + return beforeColumns_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +     ** 字段信息,增量数据(修改前,删除前) *
      +     * 
      + */ + public ColumnOrBuilder getBeforeColumnsOrBuilder( + int index) { + return beforeColumns_.get(index); + } + + public static final int AFTERCOLUMNS_FIELD_NUMBER = 2; + private java.util.List afterColumns_; + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + public java.util.List getAfterColumnsList() { + return afterColumns_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + public java.util.List + getAfterColumnsOrBuilderList() { + return afterColumns_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + public int getAfterColumnsCount() { + return afterColumns_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + public Column getAfterColumns(int index) { + return afterColumns_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +     ** 字段信息,增量数据(修改后,新增后)  *
      +     * 
      + */ + public ColumnOrBuilder getAfterColumnsOrBuilder( + int index) { + return afterColumns_.get(index); + } + + public static final int PROPS_FIELD_NUMBER = 3; + private java.util.List props_; + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List getPropsList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List + getPropsOrBuilderList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public int getPropsCount() { + return props_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public Pair getProps(int index) { + return props_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + return props_.get(index); + } + + private void initFields() { + beforeColumns_ = java.util.Collections.emptyList(); + afterColumns_ = java.util.Collections.emptyList(); + props_ = java.util.Collections.emptyList(); + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + for (int i = 0; i < beforeColumns_.size(); i++) { + output.writeMessage(1, beforeColumns_.get(i)); + } + for (int i = 0; i < afterColumns_.size(); i++) { + output.writeMessage(2, afterColumns_.get(i)); + } + for (int i = 0; i < props_.size(); i++) { + output.writeMessage(3, props_.get(i)); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + for (int i = 0; i < beforeColumns_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(1, beforeColumns_.get(i)); + } + for (int i = 0; i < afterColumns_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(2, afterColumns_.get(i)); + } + for (int i = 0; i < props_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(3, props_.get(i)); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static RowData parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static RowData parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static RowData parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static RowData parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static RowData parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static RowData parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static RowData parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static RowData parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static RowData parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static RowData parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(RowData prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.RowData} */ - public static final class RowData extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.RowData) - RowDataOrBuilder { - - // Use RowData.newBuilder() to construct. - private RowData(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private RowData(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final RowData defaultInstance; - - public static RowData getDefaultInstance() { - return defaultInstance; - } - - public RowData getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private RowData(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - if (!((mutable_bitField0_ & 0x00000001) == 0x00000001)) { - beforeColumns_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000001; - } - beforeColumns_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Column.PARSER, - extensionRegistry)); - break; - } - case 18: { - if (!((mutable_bitField0_ & 0x00000002) == 0x00000002)) { - afterColumns_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000002; - } - afterColumns_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Column.PARSER, - extensionRegistry)); - break; - } - case 26: { - if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - props_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000004; - } - props_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Pair.PARSER, - extensionRegistry)); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000001) == 0x00000001)) { - beforeColumns_ = java.util.Collections.unmodifiableList(beforeColumns_); - } - if (((mutable_bitField0_ & 0x00000002) == 0x00000002)) { - afterColumns_ = java.util.Collections.unmodifiableList(afterColumns_); - } - if (((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - props_ = java.util.Collections.unmodifiableList(props_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.RowData.class, - com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public RowData parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new RowData(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - public static final int BEFORECOLUMNS_FIELD_NUMBER = 1; - private java.util.List beforeColumns_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - public java.util.List getBeforeColumnsList() { - return beforeColumns_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - public java.util.List getBeforeColumnsOrBuilderList() { - return beforeColumns_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - public int getBeforeColumnsCount() { - return beforeColumns_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column getBeforeColumns(int index) { - return beforeColumns_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -         * * 字段信息,增量数据(修改前,删除前) *
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.ColumnOrBuilder getBeforeColumnsOrBuilder(int index) { - return beforeColumns_.get(index); - } - - public static final int AFTERCOLUMNS_FIELD_NUMBER = 2; - private java.util.List afterColumns_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - public java.util.List getAfterColumnsList() { - return afterColumns_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - public java.util.List getAfterColumnsOrBuilderList() { - return afterColumns_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - public int getAfterColumnsCount() { - return afterColumns_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column getAfterColumns(int index) { - return afterColumns_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -         * * 字段信息,增量数据(修改后,新增后)  *
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.ColumnOrBuilder getAfterColumnsOrBuilder(int index) { - return afterColumns_.get(index); - } - - public static final int PROPS_FIELD_NUMBER = 3; - private java.util.List props_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsOrBuilderList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public int getPropsCount() { - return props_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - return props_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - return props_.get(index); - } - - private void initFields() { - beforeColumns_ = java.util.Collections.emptyList(); - afterColumns_ = java.util.Collections.emptyList(); - props_ = java.util.Collections.emptyList(); - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - for (int i = 0; i < beforeColumns_.size(); i++) { - output.writeMessage(1, beforeColumns_.get(i)); - } - for (int i = 0; i < afterColumns_.size(); i++) { - output.writeMessage(2, afterColumns_.get(i)); - } - for (int i = 0; i < props_.size(); i++) { - output.writeMessage(3, props_.get(i)); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - for (int i = 0; i < beforeColumns_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(1, beforeColumns_.get(i)); - } - for (int i = 0; i < afterColumns_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(2, afterColumns_.get(i)); - } - for (int i = 0; i < props_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(3, props_.get(i)); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowData parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.RowData prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.RowData} - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.RowData) - com.alibaba.otter.canal.protocol.CanalEntry.RowDataOrBuilder { - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.RowData.class, - com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder.class); - } - - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.RowData.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - getBeforeColumnsFieldBuilder(); - getAfterColumnsFieldBuilder(); - getPropsFieldBuilder(); - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - if (beforeColumnsBuilder_ == null) { - beforeColumns_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000001); - } else { - beforeColumnsBuilder_.clear(); - } - if (afterColumnsBuilder_ == null) { - afterColumns_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000002); - } else { - afterColumnsBuilder_.clear(); - } - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - } else { - propsBuilder_.clear(); - } - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.RowData getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.RowData.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.RowData build() { - com.alibaba.otter.canal.protocol.CanalEntry.RowData result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.RowData buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.RowData result = new com.alibaba.otter.canal.protocol.CanalEntry.RowData(this); - int from_bitField0_ = bitField0_; - if (beforeColumnsBuilder_ == null) { - if (((bitField0_ & 0x00000001) == 0x00000001)) { - beforeColumns_ = java.util.Collections.unmodifiableList(beforeColumns_); - bitField0_ = (bitField0_ & ~0x00000001); - } - result.beforeColumns_ = beforeColumns_; - } else { - result.beforeColumns_ = beforeColumnsBuilder_.build(); - } - if (afterColumnsBuilder_ == null) { - if (((bitField0_ & 0x00000002) == 0x00000002)) { - afterColumns_ = java.util.Collections.unmodifiableList(afterColumns_); - bitField0_ = (bitField0_ & ~0x00000002); - } - result.afterColumns_ = afterColumns_; - } else { - result.afterColumns_ = afterColumnsBuilder_.build(); - } - if (propsBuilder_ == null) { - if (((bitField0_ & 0x00000004) == 0x00000004)) { - props_ = java.util.Collections.unmodifiableList(props_); - bitField0_ = (bitField0_ & ~0x00000004); - } - result.props_ = props_; - } else { - result.props_ = propsBuilder_.build(); - } - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.RowData) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.RowData) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.RowData other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.RowData.getDefaultInstance()) return this; - if (beforeColumnsBuilder_ == null) { - if (!other.beforeColumns_.isEmpty()) { - if (beforeColumns_.isEmpty()) { - beforeColumns_ = other.beforeColumns_; - bitField0_ = (bitField0_ & ~0x00000001); - } else { - ensureBeforeColumnsIsMutable(); - beforeColumns_.addAll(other.beforeColumns_); - } - onChanged(); - } - } else { - if (!other.beforeColumns_.isEmpty()) { - if (beforeColumnsBuilder_.isEmpty()) { - beforeColumnsBuilder_.dispose(); - beforeColumnsBuilder_ = null; - beforeColumns_ = other.beforeColumns_; - bitField0_ = (bitField0_ & ~0x00000001); - beforeColumnsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getBeforeColumnsFieldBuilder() : null; - } else { - beforeColumnsBuilder_.addAllMessages(other.beforeColumns_); - } - } - } - if (afterColumnsBuilder_ == null) { - if (!other.afterColumns_.isEmpty()) { - if (afterColumns_.isEmpty()) { - afterColumns_ = other.afterColumns_; - bitField0_ = (bitField0_ & ~0x00000002); - } else { - ensureAfterColumnsIsMutable(); - afterColumns_.addAll(other.afterColumns_); - } - onChanged(); - } - } else { - if (!other.afterColumns_.isEmpty()) { - if (afterColumnsBuilder_.isEmpty()) { - afterColumnsBuilder_.dispose(); - afterColumnsBuilder_ = null; - afterColumns_ = other.afterColumns_; - bitField0_ = (bitField0_ & ~0x00000002); - afterColumnsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getAfterColumnsFieldBuilder() : null; - } else { - afterColumnsBuilder_.addAllMessages(other.afterColumns_); - } - } - } - if (propsBuilder_ == null) { - if (!other.props_.isEmpty()) { - if (props_.isEmpty()) { - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000004); - } else { - ensurePropsIsMutable(); - props_.addAll(other.props_); - } - onChanged(); - } - } else { - if (!other.props_.isEmpty()) { - if (propsBuilder_.isEmpty()) { - propsBuilder_.dispose(); - propsBuilder_ = null; - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000004); - propsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getPropsFieldBuilder() : null; - } else { - propsBuilder_.addAllMessages(other.props_); - } - } - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.RowData parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.RowData) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.util.List beforeColumns_ = java.util.Collections.emptyList(); - - private void ensureBeforeColumnsIsMutable() { - if (!((bitField0_ & 0x00000001) == 0x00000001)) { - beforeColumns_ = new java.util.ArrayList(beforeColumns_); - bitField0_ |= 0x00000001; - } - } - - private com.google.protobuf.RepeatedFieldBuilder beforeColumnsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public java.util.List getBeforeColumnsList() { - if (beforeColumnsBuilder_ == null) { - return java.util.Collections.unmodifiableList(beforeColumns_); - } else { - return beforeColumnsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public int getBeforeColumnsCount() { - if (beforeColumnsBuilder_ == null) { - return beforeColumns_.size(); - } else { - return beforeColumnsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column getBeforeColumns(int index) { - if (beforeColumnsBuilder_ == null) { - return beforeColumns_.get(index); - } else { - return beforeColumnsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder setBeforeColumns(int index, com.alibaba.otter.canal.protocol.CanalEntry.Column value) { - if (beforeColumnsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureBeforeColumnsIsMutable(); - beforeColumns_.set(index, value); - onChanged(); - } else { - beforeColumnsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder setBeforeColumns(int index, - com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder builderForValue) { - if (beforeColumnsBuilder_ == null) { - ensureBeforeColumnsIsMutable(); - beforeColumns_.set(index, builderForValue.build()); - onChanged(); - } else { - beforeColumnsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder addBeforeColumns(com.alibaba.otter.canal.protocol.CanalEntry.Column value) { - if (beforeColumnsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureBeforeColumnsIsMutable(); - beforeColumns_.add(value); - onChanged(); - } else { - beforeColumnsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder addBeforeColumns(int index, com.alibaba.otter.canal.protocol.CanalEntry.Column value) { - if (beforeColumnsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureBeforeColumnsIsMutable(); - beforeColumns_.add(index, value); - onChanged(); - } else { - beforeColumnsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder addBeforeColumns(com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder builderForValue) { - if (beforeColumnsBuilder_ == null) { - ensureBeforeColumnsIsMutable(); - beforeColumns_.add(builderForValue.build()); - onChanged(); - } else { - beforeColumnsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder addBeforeColumns(int index, - com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder builderForValue) { - if (beforeColumnsBuilder_ == null) { - ensureBeforeColumnsIsMutable(); - beforeColumns_.add(index, builderForValue.build()); - onChanged(); - } else { - beforeColumnsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder addAllBeforeColumns(java.lang.Iterable values) { - if (beforeColumnsBuilder_ == null) { - ensureBeforeColumnsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, beforeColumns_); - onChanged(); - } else { - beforeColumnsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder clearBeforeColumns() { - if (beforeColumnsBuilder_ == null) { - beforeColumns_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000001); - onChanged(); - } else { - beforeColumnsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public Builder removeBeforeColumns(int index) { - if (beforeColumnsBuilder_ == null) { - ensureBeforeColumnsIsMutable(); - beforeColumns_.remove(index); - onChanged(); - } else { - beforeColumnsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder getBeforeColumnsBuilder(int index) { - return getBeforeColumnsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.ColumnOrBuilder getBeforeColumnsOrBuilder(int index) { - if (beforeColumnsBuilder_ == null) { - return beforeColumns_.get(index); - } else { - return beforeColumnsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public java.util.List getBeforeColumnsOrBuilderList() { - if (beforeColumnsBuilder_ != null) { - return beforeColumnsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(beforeColumns_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder addBeforeColumnsBuilder() { - return getBeforeColumnsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Column.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder addBeforeColumnsBuilder(int index) { - return getBeforeColumnsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Column.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; - * - *
      -             * * 字段信息,增量数据(修改前,删除前) *
      -             * 
      - */ - public java.util.List getBeforeColumnsBuilderList() { - return getBeforeColumnsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getBeforeColumnsFieldBuilder() { - if (beforeColumnsBuilder_ == null) { - beforeColumnsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(beforeColumns_, - ((bitField0_ & 0x00000001) == 0x00000001), - getParentForChildren(), - isClean()); - beforeColumns_ = null; - } - return beforeColumnsBuilder_; - } - - private java.util.List afterColumns_ = java.util.Collections.emptyList(); - - private void ensureAfterColumnsIsMutable() { - if (!((bitField0_ & 0x00000002) == 0x00000002)) { - afterColumns_ = new java.util.ArrayList(afterColumns_); - bitField0_ |= 0x00000002; - } - } - - private com.google.protobuf.RepeatedFieldBuilder afterColumnsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public java.util.List getAfterColumnsList() { - if (afterColumnsBuilder_ == null) { - return java.util.Collections.unmodifiableList(afterColumns_); - } else { - return afterColumnsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public int getAfterColumnsCount() { - if (afterColumnsBuilder_ == null) { - return afterColumns_.size(); - } else { - return afterColumnsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column getAfterColumns(int index) { - if (afterColumnsBuilder_ == null) { - return afterColumns_.get(index); - } else { - return afterColumnsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder setAfterColumns(int index, com.alibaba.otter.canal.protocol.CanalEntry.Column value) { - if (afterColumnsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureAfterColumnsIsMutable(); - afterColumns_.set(index, value); - onChanged(); - } else { - afterColumnsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder setAfterColumns(int index, - com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder builderForValue) { - if (afterColumnsBuilder_ == null) { - ensureAfterColumnsIsMutable(); - afterColumns_.set(index, builderForValue.build()); - onChanged(); - } else { - afterColumnsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder addAfterColumns(com.alibaba.otter.canal.protocol.CanalEntry.Column value) { - if (afterColumnsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureAfterColumnsIsMutable(); - afterColumns_.add(value); - onChanged(); - } else { - afterColumnsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder addAfterColumns(int index, com.alibaba.otter.canal.protocol.CanalEntry.Column value) { - if (afterColumnsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureAfterColumnsIsMutable(); - afterColumns_.add(index, value); - onChanged(); - } else { - afterColumnsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder addAfterColumns(com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder builderForValue) { - if (afterColumnsBuilder_ == null) { - ensureAfterColumnsIsMutable(); - afterColumns_.add(builderForValue.build()); - onChanged(); - } else { - afterColumnsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder addAfterColumns(int index, - com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder builderForValue) { - if (afterColumnsBuilder_ == null) { - ensureAfterColumnsIsMutable(); - afterColumns_.add(index, builderForValue.build()); - onChanged(); - } else { - afterColumnsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder addAllAfterColumns(java.lang.Iterable values) { - if (afterColumnsBuilder_ == null) { - ensureAfterColumnsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, afterColumns_); - onChanged(); - } else { - afterColumnsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder clearAfterColumns() { - if (afterColumnsBuilder_ == null) { - afterColumns_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000002); - onChanged(); - } else { - afterColumnsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public Builder removeAfterColumns(int index) { - if (afterColumnsBuilder_ == null) { - ensureAfterColumnsIsMutable(); - afterColumns_.remove(index); - onChanged(); - } else { - afterColumnsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder getAfterColumnsBuilder(int index) { - return getAfterColumnsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.ColumnOrBuilder getAfterColumnsOrBuilder(int index) { - if (afterColumnsBuilder_ == null) { - return afterColumns_.get(index); - } else { - return afterColumnsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public java.util.List getAfterColumnsOrBuilderList() { - if (afterColumnsBuilder_ != null) { - return afterColumnsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(afterColumns_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder addAfterColumnsBuilder() { - return getAfterColumnsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Column.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Column.Builder addAfterColumnsBuilder(int index) { - return getAfterColumnsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Column.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; - * - *
      -             * * 字段信息,增量数据(修改后,新增后)  *
      -             * 
      - */ - public java.util.List getAfterColumnsBuilderList() { - return getAfterColumnsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getAfterColumnsFieldBuilder() { - if (afterColumnsBuilder_ == null) { - afterColumnsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(afterColumns_, - ((bitField0_ & 0x00000002) == 0x00000002), - getParentForChildren(), - isClean()); - afterColumns_ = null; - } - return afterColumnsBuilder_; - } - - private java.util.List props_ = java.util.Collections.emptyList(); - - private void ensurePropsIsMutable() { - if (!((bitField0_ & 0x00000004) == 0x00000004)) { - props_ = new java.util.ArrayList(props_); - bitField0_ |= 0x00000004; - } - } - - private com.google.protobuf.RepeatedFieldBuilder propsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsList() { - if (propsBuilder_ == null) { - return java.util.Collections.unmodifiableList(props_); - } else { - return propsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public int getPropsCount() { - if (propsBuilder_ == null) { - return props_.size(); - } else { - return propsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.set(index, value); - onChanged(); - } else { - propsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.set(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(value); - onChanged(); - } else { - propsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(index, value); - onChanged(); - } else { - propsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addAllProps(java.lang.Iterable values) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, props_); - onChanged(); - } else { - propsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder clearProps() { - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - onChanged(); - } else { - propsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder removeProps(int index) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.remove(index); - onChanged(); - } else { - propsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder getPropsBuilder(int index) { - return getPropsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsOrBuilderList() { - if (propsBuilder_ != null) { - return propsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(props_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder() { - return getPropsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder(int index) { - return getPropsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsBuilderList() { - return getPropsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getPropsFieldBuilder() { - if (propsBuilder_ == null) { - propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(props_, - ((bitField0_ & 0x00000004) == 0x00000004), - getParentForChildren(), - isClean()); - props_ = null; - } - return propsBuilder_; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.RowData) + RowDataOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable + .ensureFieldAccessorsInitialized( + RowData.class, Builder.class); + } + + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.RowData.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } + + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { + getBeforeColumnsFieldBuilder(); + getAfterColumnsFieldBuilder(); + getPropsFieldBuilder(); } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new RowData(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + if (beforeColumnsBuilder_ == null) { + beforeColumns_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000001); + } else { + beforeColumnsBuilder_.clear(); } + if (afterColumnsBuilder_ == null) { + afterColumns_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000002); + } else { + afterColumnsBuilder_.clear(); + } + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000004); + } else { + propsBuilder_.clear(); + } + return this; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.RowData) + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; + } + + public RowData getDefaultInstanceForType() { + return RowData.getDefaultInstance(); + } + + public RowData build() { + RowData result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); + } + return result; + } + + public RowData buildPartial() { + RowData result = new RowData(this); + int from_bitField0_ = bitField0_; + if (beforeColumnsBuilder_ == null) { + if (((bitField0_ & 0x00000001) == 0x00000001)) { + beforeColumns_ = java.util.Collections.unmodifiableList(beforeColumns_); + bitField0_ = (bitField0_ & ~0x00000001); + } + result.beforeColumns_ = beforeColumns_; + } else { + result.beforeColumns_ = beforeColumnsBuilder_.build(); + } + if (afterColumnsBuilder_ == null) { + if (((bitField0_ & 0x00000002) == 0x00000002)) { + afterColumns_ = java.util.Collections.unmodifiableList(afterColumns_); + bitField0_ = (bitField0_ & ~0x00000002); + } + result.afterColumns_ = afterColumns_; + } else { + result.afterColumns_ = afterColumnsBuilder_.build(); + } + if (propsBuilder_ == null) { + if (((bitField0_ & 0x00000004) == 0x00000004)) { + props_ = java.util.Collections.unmodifiableList(props_); + bitField0_ = (bitField0_ & ~0x00000004); + } + result.props_ = props_; + } else { + result.props_ = propsBuilder_.build(); + } + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof RowData) { + return mergeFrom((RowData)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(RowData other) { + if (other == RowData.getDefaultInstance()) return this; + if (beforeColumnsBuilder_ == null) { + if (!other.beforeColumns_.isEmpty()) { + if (beforeColumns_.isEmpty()) { + beforeColumns_ = other.beforeColumns_; + bitField0_ = (bitField0_ & ~0x00000001); + } else { + ensureBeforeColumnsIsMutable(); + beforeColumns_.addAll(other.beforeColumns_); + } + onChanged(); + } + } else { + if (!other.beforeColumns_.isEmpty()) { + if (beforeColumnsBuilder_.isEmpty()) { + beforeColumnsBuilder_.dispose(); + beforeColumnsBuilder_ = null; + beforeColumns_ = other.beforeColumns_; + bitField0_ = (bitField0_ & ~0x00000001); + beforeColumnsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getBeforeColumnsFieldBuilder() : null; + } else { + beforeColumnsBuilder_.addAllMessages(other.beforeColumns_); + } + } + } + if (afterColumnsBuilder_ == null) { + if (!other.afterColumns_.isEmpty()) { + if (afterColumns_.isEmpty()) { + afterColumns_ = other.afterColumns_; + bitField0_ = (bitField0_ & ~0x00000002); + } else { + ensureAfterColumnsIsMutable(); + afterColumns_.addAll(other.afterColumns_); + } + onChanged(); + } + } else { + if (!other.afterColumns_.isEmpty()) { + if (afterColumnsBuilder_.isEmpty()) { + afterColumnsBuilder_.dispose(); + afterColumnsBuilder_ = null; + afterColumns_ = other.afterColumns_; + bitField0_ = (bitField0_ & ~0x00000002); + afterColumnsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getAfterColumnsFieldBuilder() : null; + } else { + afterColumnsBuilder_.addAllMessages(other.afterColumns_); + } + } + } + if (propsBuilder_ == null) { + if (!other.props_.isEmpty()) { + if (props_.isEmpty()) { + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000004); + } else { + ensurePropsIsMutable(); + props_.addAll(other.props_); + } + onChanged(); + } + } else { + if (!other.props_.isEmpty()) { + if (propsBuilder_.isEmpty()) { + propsBuilder_.dispose(); + propsBuilder_ = null; + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000004); + propsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getPropsFieldBuilder() : null; + } else { + propsBuilder_.addAllMessages(other.props_); + } + } + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + RowData parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (RowData) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private java.util.List beforeColumns_ = + java.util.Collections.emptyList(); + private void ensureBeforeColumnsIsMutable() { + if (!((bitField0_ & 0x00000001) == 0x00000001)) { + beforeColumns_ = new java.util.ArrayList(beforeColumns_); + bitField0_ |= 0x00000001; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Column, Column.Builder, ColumnOrBuilder> beforeColumnsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public java.util.List getBeforeColumnsList() { + if (beforeColumnsBuilder_ == null) { + return java.util.Collections.unmodifiableList(beforeColumns_); + } else { + return beforeColumnsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public int getBeforeColumnsCount() { + if (beforeColumnsBuilder_ == null) { + return beforeColumns_.size(); + } else { + return beforeColumnsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Column getBeforeColumns(int index) { + if (beforeColumnsBuilder_ == null) { + return beforeColumns_.get(index); + } else { + return beforeColumnsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder setBeforeColumns( + int index, Column value) { + if (beforeColumnsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureBeforeColumnsIsMutable(); + beforeColumns_.set(index, value); + onChanged(); + } else { + beforeColumnsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder setBeforeColumns( + int index, Column.Builder builderForValue) { + if (beforeColumnsBuilder_ == null) { + ensureBeforeColumnsIsMutable(); + beforeColumns_.set(index, builderForValue.build()); + onChanged(); + } else { + beforeColumnsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder addBeforeColumns(Column value) { + if (beforeColumnsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureBeforeColumnsIsMutable(); + beforeColumns_.add(value); + onChanged(); + } else { + beforeColumnsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder addBeforeColumns( + int index, Column value) { + if (beforeColumnsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureBeforeColumnsIsMutable(); + beforeColumns_.add(index, value); + onChanged(); + } else { + beforeColumnsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder addBeforeColumns( + Column.Builder builderForValue) { + if (beforeColumnsBuilder_ == null) { + ensureBeforeColumnsIsMutable(); + beforeColumns_.add(builderForValue.build()); + onChanged(); + } else { + beforeColumnsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder addBeforeColumns( + int index, Column.Builder builderForValue) { + if (beforeColumnsBuilder_ == null) { + ensureBeforeColumnsIsMutable(); + beforeColumns_.add(index, builderForValue.build()); + onChanged(); + } else { + beforeColumnsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder addAllBeforeColumns( + Iterable values) { + if (beforeColumnsBuilder_ == null) { + ensureBeforeColumnsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, beforeColumns_); + onChanged(); + } else { + beforeColumnsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder clearBeforeColumns() { + if (beforeColumnsBuilder_ == null) { + beforeColumns_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000001); + onChanged(); + } else { + beforeColumnsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Builder removeBeforeColumns(int index) { + if (beforeColumnsBuilder_ == null) { + ensureBeforeColumnsIsMutable(); + beforeColumns_.remove(index); + onChanged(); + } else { + beforeColumnsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Column.Builder getBeforeColumnsBuilder( + int index) { + return getBeforeColumnsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public ColumnOrBuilder getBeforeColumnsOrBuilder( + int index) { + if (beforeColumnsBuilder_ == null) { + return beforeColumns_.get(index); } else { + return beforeColumnsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public java.util.List + getBeforeColumnsOrBuilderList() { + if (beforeColumnsBuilder_ != null) { + return beforeColumnsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(beforeColumns_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Column.Builder addBeforeColumnsBuilder() { + return getBeforeColumnsFieldBuilder().addBuilder( + Column.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public Column.Builder addBeforeColumnsBuilder( + int index) { + return getBeforeColumnsFieldBuilder().addBuilder( + index, Column.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column beforeColumns = 1; + * + *
      +       ** 字段信息,增量数据(修改前,删除前) *
      +       * 
      + */ + public java.util.List + getBeforeColumnsBuilderList() { + return getBeforeColumnsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Column, Column.Builder, ColumnOrBuilder> + getBeforeColumnsFieldBuilder() { + if (beforeColumnsBuilder_ == null) { + beforeColumnsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Column, Column.Builder, ColumnOrBuilder>( + beforeColumns_, + ((bitField0_ & 0x00000001) == 0x00000001), + getParentForChildren(), + isClean()); + beforeColumns_ = null; + } + return beforeColumnsBuilder_; + } + + private java.util.List afterColumns_ = + java.util.Collections.emptyList(); + private void ensureAfterColumnsIsMutable() { + if (!((bitField0_ & 0x00000002) == 0x00000002)) { + afterColumns_ = new java.util.ArrayList(afterColumns_); + bitField0_ |= 0x00000002; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Column, Column.Builder, ColumnOrBuilder> afterColumnsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public java.util.List getAfterColumnsList() { + if (afterColumnsBuilder_ == null) { + return java.util.Collections.unmodifiableList(afterColumns_); + } else { + return afterColumnsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public int getAfterColumnsCount() { + if (afterColumnsBuilder_ == null) { + return afterColumns_.size(); + } else { + return afterColumnsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Column getAfterColumns(int index) { + if (afterColumnsBuilder_ == null) { + return afterColumns_.get(index); + } else { + return afterColumnsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder setAfterColumns( + int index, Column value) { + if (afterColumnsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureAfterColumnsIsMutable(); + afterColumns_.set(index, value); + onChanged(); + } else { + afterColumnsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder setAfterColumns( + int index, Column.Builder builderForValue) { + if (afterColumnsBuilder_ == null) { + ensureAfterColumnsIsMutable(); + afterColumns_.set(index, builderForValue.build()); + onChanged(); + } else { + afterColumnsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder addAfterColumns(Column value) { + if (afterColumnsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureAfterColumnsIsMutable(); + afterColumns_.add(value); + onChanged(); + } else { + afterColumnsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder addAfterColumns( + int index, Column value) { + if (afterColumnsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureAfterColumnsIsMutable(); + afterColumns_.add(index, value); + onChanged(); + } else { + afterColumnsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder addAfterColumns( + Column.Builder builderForValue) { + if (afterColumnsBuilder_ == null) { + ensureAfterColumnsIsMutable(); + afterColumns_.add(builderForValue.build()); + onChanged(); + } else { + afterColumnsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder addAfterColumns( + int index, Column.Builder builderForValue) { + if (afterColumnsBuilder_ == null) { + ensureAfterColumnsIsMutable(); + afterColumns_.add(index, builderForValue.build()); + onChanged(); + } else { + afterColumnsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder addAllAfterColumns( + Iterable values) { + if (afterColumnsBuilder_ == null) { + ensureAfterColumnsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, afterColumns_); + onChanged(); + } else { + afterColumnsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder clearAfterColumns() { + if (afterColumnsBuilder_ == null) { + afterColumns_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000002); + onChanged(); + } else { + afterColumnsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Builder removeAfterColumns(int index) { + if (afterColumnsBuilder_ == null) { + ensureAfterColumnsIsMutable(); + afterColumns_.remove(index); + onChanged(); + } else { + afterColumnsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Column.Builder getAfterColumnsBuilder( + int index) { + return getAfterColumnsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public ColumnOrBuilder getAfterColumnsOrBuilder( + int index) { + if (afterColumnsBuilder_ == null) { + return afterColumns_.get(index); } else { + return afterColumnsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public java.util.List + getAfterColumnsOrBuilderList() { + if (afterColumnsBuilder_ != null) { + return afterColumnsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(afterColumns_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Column.Builder addAfterColumnsBuilder() { + return getAfterColumnsFieldBuilder().addBuilder( + Column.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public Column.Builder addAfterColumnsBuilder( + int index) { + return getAfterColumnsFieldBuilder().addBuilder( + index, Column.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Column afterColumns = 2; + * + *
      +       ** 字段信息,增量数据(修改后,新增后)  *
      +       * 
      + */ + public java.util.List + getAfterColumnsBuilderList() { + return getAfterColumnsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Column, Column.Builder, ColumnOrBuilder> + getAfterColumnsFieldBuilder() { + if (afterColumnsBuilder_ == null) { + afterColumnsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Column, Column.Builder, ColumnOrBuilder>( + afterColumns_, + ((bitField0_ & 0x00000002) == 0x00000002), + getParentForChildren(), + isClean()); + afterColumns_ = null; + } + return afterColumnsBuilder_; + } + + private java.util.List props_ = + java.util.Collections.emptyList(); + private void ensurePropsIsMutable() { + if (!((bitField0_ & 0x00000004) == 0x00000004)) { + props_ = new java.util.ArrayList(props_); + bitField0_ |= 0x00000004; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> propsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List getPropsList() { + if (propsBuilder_ == null) { + return java.util.Collections.unmodifiableList(props_); + } else { + return propsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public int getPropsCount() { + if (propsBuilder_ == null) { + return props_.size(); + } else { + return propsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair getProps(int index) { + if (propsBuilder_ == null) { + return props_.get(index); + } else { + return propsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.set(index, value); + onChanged(); + } else { + propsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.set(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps(Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(value); + onChanged(); + } else { + propsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(index, value); + onChanged(); + } else { + propsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addAllProps( + Iterable values) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, props_); + onChanged(); + } else { + propsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder clearProps() { + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000004); + onChanged(); + } else { + propsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder removeProps(int index) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.remove(index); + onChanged(); + } else { + propsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder getPropsBuilder( + int index) { + return getPropsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + if (propsBuilder_ == null) { + return props_.get(index); } else { + return propsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsOrBuilderList() { + if (propsBuilder_ != null) { + return propsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(props_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder() { + return getPropsFieldBuilder().addBuilder( + Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder( + int index) { + return getPropsFieldBuilder().addBuilder( + index, Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsBuilderList() { + return getPropsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> + getPropsFieldBuilder() { + if (propsBuilder_ == null) { + propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder>( + props_, + ((bitField0_ & 0x00000004) == 0x00000004), + getParentForChildren(), + isClean()); + props_ = null; + } + return propsBuilder_; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.RowData) } - public interface RowChangeOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.RowChange) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int64 tableId = 1; - * - *
      -         * *tableId,由数据库产生*
      -         * 
      - */ - boolean hasTableId(); - - /** - * optional int64 tableId = 1; - * - *
      -         * *tableId,由数据库产生*
      -         * 
      - */ - long getTableId(); - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - boolean hasEventType(); - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.EventType getEventType(); - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -         * * 标识是否是ddl语句  *
      -         * 
      - */ - boolean hasIsDdl(); - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -         * * 标识是否是ddl语句  *
      -         * 
      - */ - boolean getIsDdl(); - - /** - * optional string sql = 11; - * - *
      -         * * ddl/query的sql语句  *
      -         * 
      - */ - boolean hasSql(); - - /** - * optional string sql = 11; - * - *
      -         * * ddl/query的sql语句  *
      -         * 
      - */ - java.lang.String getSql(); - - /** - * optional string sql = 11; - * - *
      -         * * ddl/query的sql语句  *
      -         * 
      - */ - com.google.protobuf.ByteString getSqlBytes(); - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - java.util.List getRowDatasList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.RowData getRowDatas(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - int getRowDatasCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - java.util.List getRowDatasOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.RowDataOrBuilder getRowDatasOrBuilder(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - int getPropsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index); - - /** - * optional string ddlSchemaName = 14; - * - *
      -         * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -         * 
      - */ - boolean hasDdlSchemaName(); - - /** - * optional string ddlSchemaName = 14; - * - *
      -         * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -         * 
      - */ - java.lang.String getDdlSchemaName(); - - /** - * optional string ddlSchemaName = 14; - * - *
      -         * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -         * 
      - */ - com.google.protobuf.ByteString getDdlSchemaNameBytes(); + static { + defaultInstance = new RowData(true); + defaultInstance.initFields(); } + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.RowData) + } + + public interface RowChangeOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.RowChange) + com.google.protobuf.MessageOrBuilder { + + /** + * optional int64 tableId = 1; + * + *
      +     **tableId,由数据库产生*
      +     * 
      + */ + boolean hasTableId(); + /** + * optional int64 tableId = 1; + * + *
      +     **tableId,由数据库产生*
      +     * 
      + */ + long getTableId(); + + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + boolean hasEventType(); + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + EventType getEventType(); + + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +     ** 标识是否是ddl语句  *
      +     * 
      + */ + boolean hasIsDdl(); + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +     ** 标识是否是ddl语句  *
      +     * 
      + */ + boolean getIsDdl(); + + /** + * optional string sql = 11; + * + *
      +     ** ddl/query的sql语句  *
      +     * 
      + */ + boolean hasSql(); + /** + * optional string sql = 11; + * + *
      +     ** ddl/query的sql语句  *
      +     * 
      + */ + String getSql(); + /** + * optional string sql = 11; + * + *
      +     ** ddl/query的sql语句  *
      +     * 
      + */ + com.google.protobuf.ByteString + getSqlBytes(); + + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + java.util.List + getRowDatasList(); + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + RowData getRowDatas(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + int getRowDatasCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + java.util.List + getRowDatasOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + RowDataOrBuilder getRowDatasOrBuilder(int index); + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + Pair getProps(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + int getPropsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + PairOrBuilder getPropsOrBuilder(int index); + + /** + * optional string ddlSchemaName = 14; + * + *
      +     ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +     * 
      + */ + boolean hasDdlSchemaName(); + /** + * optional string ddlSchemaName = 14; + * + *
      +     ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +     * 
      + */ + String getDdlSchemaName(); + /** + * optional string ddlSchemaName = 14; + * + *
      +     ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +     * 
      + */ + com.google.protobuf.ByteString + getDdlSchemaNameBytes(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.RowChange} + * + *
      +   **message row 每行变更数据的数据结构*
      +   * 
      + */ + public static final class RowChange extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.RowChange) + RowChangeOrBuilder { + // Use RowChange.newBuilder() to construct. + private RowChange(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private RowChange(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final RowChange defaultInstance; + public static RowChange getDefaultInstance() { + return defaultInstance; + } + + public RowChange getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private RowChange( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 8: { + bitField0_ |= 0x00000001; + tableId_ = input.readInt64(); + break; + } + case 16: { + int rawValue = input.readEnum(); + EventType value = EventType.valueOf(rawValue); + if (value == null) { + unknownFields.mergeVarintField(2, rawValue); + } else { + bitField0_ |= 0x00000002; + eventType_ = value; + } + break; + } + case 80: { + bitField0_ |= 0x00000004; + isDdl_ = input.readBool(); + break; + } + case 90: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000008; + sql_ = bs; + break; + } + case 98: { + if (!((mutable_bitField0_ & 0x00000010) == 0x00000010)) { + rowDatas_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000010; + } + rowDatas_.add(input.readMessage(RowData.PARSER, extensionRegistry)); + break; + } + case 106: { + if (!((mutable_bitField0_ & 0x00000020) == 0x00000020)) { + props_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000020; + } + props_.add(input.readMessage(Pair.PARSER, extensionRegistry)); + break; + } + case 114: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000010; + ddlSchemaName_ = bs; + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + if (((mutable_bitField0_ & 0x00000010) == 0x00000010)) { + rowDatas_ = java.util.Collections.unmodifiableList(rowDatas_); + } + if (((mutable_bitField0_ & 0x00000020) == 0x00000020)) { + props_ = java.util.Collections.unmodifiableList(props_); + } + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable + .ensureFieldAccessorsInitialized( + RowChange.class, Builder.class); + } + + public static com.google.protobuf.Parser PARSER = + new com.google.protobuf.AbstractParser() { + public RowChange parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new RowChange(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + private int bitField0_; + public static final int TABLEID_FIELD_NUMBER = 1; + private long tableId_; + /** + * optional int64 tableId = 1; + * + *
      +     **tableId,由数据库产生*
      +     * 
      + */ + public boolean hasTableId() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int64 tableId = 1; + * + *
      +     **tableId,由数据库产生*
      +     * 
      + */ + public long getTableId() { + return tableId_; + } + + public static final int EVENTTYPE_FIELD_NUMBER = 2; + private EventType eventType_; + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + public boolean hasEventType() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +     **数据变更类型*
      +     * 
      + */ + public EventType getEventType() { + return eventType_; + } + + public static final int ISDDL_FIELD_NUMBER = 10; + private boolean isDdl_; + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +     ** 标识是否是ddl语句  *
      +     * 
      + */ + public boolean hasIsDdl() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +     ** 标识是否是ddl语句  *
      +     * 
      + */ + public boolean getIsDdl() { + return isDdl_; + } + + public static final int SQL_FIELD_NUMBER = 11; + private Object sql_; + /** + * optional string sql = 11; + * + *
      +     ** ddl/query的sql语句  *
      +     * 
      + */ + public boolean hasSql() { + return ((bitField0_ & 0x00000008) == 0x00000008); + } + /** + * optional string sql = 11; + * + *
      +     ** ddl/query的sql语句  *
      +     * 
      + */ + public String getSql() { + Object ref = sql_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + sql_ = s; + } + return s; + } + } + /** + * optional string sql = 11; + * + *
      +     ** ddl/query的sql语句  *
      +     * 
      + */ + public com.google.protobuf.ByteString + getSqlBytes() { + Object ref = sql_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + sql_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int ROWDATAS_FIELD_NUMBER = 12; + private java.util.List rowDatas_; + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + public java.util.List getRowDatasList() { + return rowDatas_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + public java.util.List + getRowDatasOrBuilderList() { + return rowDatas_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + public int getRowDatasCount() { + return rowDatas_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + public RowData getRowDatas(int index) { + return rowDatas_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +     ** 一次数据库变更可能存在多行  *
      +     * 
      + */ + public RowDataOrBuilder getRowDatasOrBuilder( + int index) { + return rowDatas_.get(index); + } + + public static final int PROPS_FIELD_NUMBER = 13; + private java.util.List props_; + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List getPropsList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List + getPropsOrBuilderList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + public int getPropsCount() { + return props_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + public Pair getProps(int index) { + return props_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +     **预留扩展*
      +     * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + return props_.get(index); + } + + public static final int DDLSCHEMANAME_FIELD_NUMBER = 14; + private Object ddlSchemaName_; + /** + * optional string ddlSchemaName = 14; + * + *
      +     ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +     * 
      + */ + public boolean hasDdlSchemaName() { + return ((bitField0_ & 0x00000010) == 0x00000010); + } + /** + * optional string ddlSchemaName = 14; + * + *
      +     ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +     * 
      + */ + public String getDdlSchemaName() { + Object ref = ddlSchemaName_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + ddlSchemaName_ = s; + } + return s; + } + } + /** + * optional string ddlSchemaName = 14; + * + *
      +     ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +     * 
      + */ + public com.google.protobuf.ByteString + getDdlSchemaNameBytes() { + Object ref = ddlSchemaName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + ddlSchemaName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + private void initFields() { + tableId_ = 0L; + eventType_ = EventType.UPDATE; + isDdl_ = false; + sql_ = ""; + rowDatas_ = java.util.Collections.emptyList(); + props_ = java.util.Collections.emptyList(); + ddlSchemaName_ = ""; + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + if (((bitField0_ & 0x00000001) == 0x00000001)) { + output.writeInt64(1, tableId_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + output.writeEnum(2, eventType_.getNumber()); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + output.writeBool(10, isDdl_); + } + if (((bitField0_ & 0x00000008) == 0x00000008)) { + output.writeBytes(11, getSqlBytes()); + } + for (int i = 0; i < rowDatas_.size(); i++) { + output.writeMessage(12, rowDatas_.get(i)); + } + for (int i = 0; i < props_.size(); i++) { + output.writeMessage(13, props_.get(i)); + } + if (((bitField0_ & 0x00000010) == 0x00000010)) { + output.writeBytes(14, getDdlSchemaNameBytes()); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(1, tableId_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + size += com.google.protobuf.CodedOutputStream + .computeEnumSize(2, eventType_.getNumber()); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + size += com.google.protobuf.CodedOutputStream + .computeBoolSize(10, isDdl_); + } + if (((bitField0_ & 0x00000008) == 0x00000008)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(11, getSqlBytes()); + } + for (int i = 0; i < rowDatas_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(12, rowDatas_.get(i)); + } + for (int i = 0; i < props_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(13, props_.get(i)); + } + if (((bitField0_ & 0x00000010) == 0x00000010)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(14, getDdlSchemaNameBytes()); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static RowChange parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static RowChange parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static RowChange parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static RowChange parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static RowChange parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static RowChange parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static RowChange parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static RowChange parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static RowChange parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static RowChange parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(RowChange prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.RowChange} * *
      -     * *message row 每行变更数据的数据结构*
      +     **message row 每行变更数据的数据结构*
            * 
      */ - public static final class RowChange extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.RowChange) - RowChangeOrBuilder { - - // Use RowChange.newBuilder() to construct. - private RowChange(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private RowChange(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final RowChange defaultInstance; - - public static RowChange getDefaultInstance() { - return defaultInstance; - } - - public RowChange getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private RowChange(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - tableId_ = input.readInt64(); - break; - } - case 16: { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalEntry.EventType value = com.alibaba.otter.canal.protocol.CanalEntry.EventType.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(2, rawValue); - } else { - bitField0_ |= 0x00000002; - eventType_ = value; - } - break; - } - case 80: { - bitField0_ |= 0x00000004; - isDdl_ = input.readBool(); - break; - } - case 90: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000008; - sql_ = bs; - break; - } - case 98: { - if (!((mutable_bitField0_ & 0x00000010) == 0x00000010)) { - rowDatas_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000010; - } - rowDatas_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.RowData.PARSER, - extensionRegistry)); - break; - } - case 106: { - if (!((mutable_bitField0_ & 0x00000020) == 0x00000020)) { - props_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000020; - } - props_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Pair.PARSER, - extensionRegistry)); - break; - } - case 114: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000010; - ddlSchemaName_ = bs; - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000010) == 0x00000010)) { - rowDatas_ = java.util.Collections.unmodifiableList(rowDatas_); - } - if (((mutable_bitField0_ & 0x00000020) == 0x00000020)) { - props_ = java.util.Collections.unmodifiableList(props_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.RowChange.class, - com.alibaba.otter.canal.protocol.CanalEntry.RowChange.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public RowChange parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new RowChange(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int TABLEID_FIELD_NUMBER = 1; - private long tableId_; - - /** - * optional int64 tableId = 1; - * - *
      -         * *tableId,由数据库产生*
      -         * 
      - */ - public boolean hasTableId() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 tableId = 1; - * - *
      -         * *tableId,由数据库产生*
      -         * 
      - */ - public long getTableId() { - return tableId_; - } - - public static final int EVENTTYPE_FIELD_NUMBER = 2; - private com.alibaba.otter.canal.protocol.CanalEntry.EventType eventType_; - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - public boolean hasEventType() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -         * *数据变更类型*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.EventType getEventType() { - return eventType_; - } - - public static final int ISDDL_FIELD_NUMBER = 10; - private boolean isDdl_; - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -         * * 标识是否是ddl语句  *
      -         * 
      - */ - public boolean hasIsDdl() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -         * * 标识是否是ddl语句  *
      -         * 
      - */ - public boolean getIsDdl() { - return isDdl_; - } - - public static final int SQL_FIELD_NUMBER = 11; - private java.lang.Object sql_; - - /** - * optional string sql = 11; - * - *
      -         * * ddl/query的sql语句  *
      -         * 
      - */ - public boolean hasSql() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional string sql = 11; - * - *
      -         * * ddl/query的sql语句  *
      -         * 
      - */ - public java.lang.String getSql() { - java.lang.Object ref = sql_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - sql_ = s; - } - return s; - } - } - - /** - * optional string sql = 11; - * - *
      -         * * ddl/query的sql语句  *
      -         * 
      - */ - public com.google.protobuf.ByteString getSqlBytes() { - java.lang.Object ref = sql_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - sql_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int ROWDATAS_FIELD_NUMBER = 12; - private java.util.List rowDatas_; - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - public java.util.List getRowDatasList() { - return rowDatas_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - public java.util.List getRowDatasOrBuilderList() { - return rowDatas_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - public int getRowDatasCount() { - return rowDatas_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.RowData getRowDatas(int index) { - return rowDatas_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -         * * 一次数据库变更可能存在多行  *
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.RowDataOrBuilder getRowDatasOrBuilder(int index) { - return rowDatas_.get(index); - } - - public static final int PROPS_FIELD_NUMBER = 13; - private java.util.List props_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsOrBuilderList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public int getPropsCount() { - return props_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - return props_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - return props_.get(index); - } - - public static final int DDLSCHEMANAME_FIELD_NUMBER = 14; - private java.lang.Object ddlSchemaName_; - - /** - * optional string ddlSchemaName = 14; - * - *
      -         * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -         * 
      - */ - public boolean hasDdlSchemaName() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional string ddlSchemaName = 14; - * - *
      -         * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -         * 
      - */ - public java.lang.String getDdlSchemaName() { - java.lang.Object ref = ddlSchemaName_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - ddlSchemaName_ = s; - } - return s; - } - } - - /** - * optional string ddlSchemaName = 14; - * - *
      -         * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -         * 
      - */ - public com.google.protobuf.ByteString getDdlSchemaNameBytes() { - java.lang.Object ref = ddlSchemaName_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - ddlSchemaName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - private void initFields() { - tableId_ = 0L; - eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - isDdl_ = false; - sql_ = ""; - rowDatas_ = java.util.Collections.emptyList(); - props_ = java.util.Collections.emptyList(); - ddlSchemaName_ = ""; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt64(1, tableId_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeEnum(2, eventType_.getNumber()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeBool(10, isDdl_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - output.writeBytes(11, getSqlBytes()); - } - for (int i = 0; i < rowDatas_.size(); i++) { - output.writeMessage(12, rowDatas_.get(i)); - } - for (int i = 0; i < props_.size(); i++) { - output.writeMessage(13, props_.get(i)); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - output.writeBytes(14, getDdlSchemaNameBytes()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(1, tableId_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeEnumSize(2, eventType_.getNumber()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeBoolSize(10, isDdl_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(11, getSqlBytes()); - } - for (int i = 0; i < rowDatas_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(12, rowDatas_.get(i)); - } - for (int i = 0; i < props_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(13, props_.get(i)); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(14, getDdlSchemaNameBytes()); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.RowChange parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.RowChange prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.RowChange} - * - *
      -         * *message row 每行变更数据的数据结构*
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.RowChange) - com.alibaba.otter.canal.protocol.CanalEntry.RowChangeOrBuilder { - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.RowChange.class, - com.alibaba.otter.canal.protocol.CanalEntry.RowChange.Builder.class); - } - - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.RowChange.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - getRowDatasFieldBuilder(); - getPropsFieldBuilder(); - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - tableId_ = 0L; - bitField0_ = (bitField0_ & ~0x00000001); - eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - bitField0_ = (bitField0_ & ~0x00000002); - isDdl_ = false; - bitField0_ = (bitField0_ & ~0x00000004); - sql_ = ""; - bitField0_ = (bitField0_ & ~0x00000008); - if (rowDatasBuilder_ == null) { - rowDatas_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000010); - } else { - rowDatasBuilder_.clear(); - } - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000020); - } else { - propsBuilder_.clear(); - } - ddlSchemaName_ = ""; - bitField0_ = (bitField0_ & ~0x00000040); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.RowChange getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.RowChange.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.RowChange build() { - com.alibaba.otter.canal.protocol.CanalEntry.RowChange result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.RowChange buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.RowChange result = new com.alibaba.otter.canal.protocol.CanalEntry.RowChange(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.tableId_ = tableId_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.eventType_ = eventType_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.isDdl_ = isDdl_; - if (((from_bitField0_ & 0x00000008) == 0x00000008)) { - to_bitField0_ |= 0x00000008; - } - result.sql_ = sql_; - if (rowDatasBuilder_ == null) { - if (((bitField0_ & 0x00000010) == 0x00000010)) { - rowDatas_ = java.util.Collections.unmodifiableList(rowDatas_); - bitField0_ = (bitField0_ & ~0x00000010); - } - result.rowDatas_ = rowDatas_; - } else { - result.rowDatas_ = rowDatasBuilder_.build(); - } - if (propsBuilder_ == null) { - if (((bitField0_ & 0x00000020) == 0x00000020)) { - props_ = java.util.Collections.unmodifiableList(props_); - bitField0_ = (bitField0_ & ~0x00000020); - } - result.props_ = props_; - } else { - result.props_ = propsBuilder_.build(); - } - if (((from_bitField0_ & 0x00000040) == 0x00000040)) { - to_bitField0_ |= 0x00000010; - } - result.ddlSchemaName_ = ddlSchemaName_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.RowChange) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.RowChange) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.RowChange other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.RowChange.getDefaultInstance()) return this; - if (other.hasTableId()) { - setTableId(other.getTableId()); - } - if (other.hasEventType()) { - setEventType(other.getEventType()); - } - if (other.hasIsDdl()) { - setIsDdl(other.getIsDdl()); - } - if (other.hasSql()) { - bitField0_ |= 0x00000008; - sql_ = other.sql_; - onChanged(); - } - if (rowDatasBuilder_ == null) { - if (!other.rowDatas_.isEmpty()) { - if (rowDatas_.isEmpty()) { - rowDatas_ = other.rowDatas_; - bitField0_ = (bitField0_ & ~0x00000010); - } else { - ensureRowDatasIsMutable(); - rowDatas_.addAll(other.rowDatas_); - } - onChanged(); - } - } else { - if (!other.rowDatas_.isEmpty()) { - if (rowDatasBuilder_.isEmpty()) { - rowDatasBuilder_.dispose(); - rowDatasBuilder_ = null; - rowDatas_ = other.rowDatas_; - bitField0_ = (bitField0_ & ~0x00000010); - rowDatasBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getRowDatasFieldBuilder() : null; - } else { - rowDatasBuilder_.addAllMessages(other.rowDatas_); - } - } - } - if (propsBuilder_ == null) { - if (!other.props_.isEmpty()) { - if (props_.isEmpty()) { - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000020); - } else { - ensurePropsIsMutable(); - props_.addAll(other.props_); - } - onChanged(); - } - } else { - if (!other.props_.isEmpty()) { - if (propsBuilder_.isEmpty()) { - propsBuilder_.dispose(); - propsBuilder_ = null; - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000020); - propsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getPropsFieldBuilder() : null; - } else { - propsBuilder_.addAllMessages(other.props_); - } - } - } - if (other.hasDdlSchemaName()) { - bitField0_ |= 0x00000040; - ddlSchemaName_ = other.ddlSchemaName_; - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.RowChange parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.RowChange) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private long tableId_; - - /** - * optional int64 tableId = 1; - * - *
      -             * *tableId,由数据库产生*
      -             * 
      - */ - public boolean hasTableId() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 tableId = 1; - * - *
      -             * *tableId,由数据库产生*
      -             * 
      - */ - public long getTableId() { - return tableId_; - } - - /** - * optional int64 tableId = 1; - * - *
      -             * *tableId,由数据库产生*
      -             * 
      - */ - public Builder setTableId(long value) { - bitField0_ |= 0x00000001; - tableId_ = value; - onChanged(); - return this; - } - - /** - * optional int64 tableId = 1; - * - *
      -             * *tableId,由数据库产生*
      -             * 
      - */ - public Builder clearTableId() { - bitField0_ = (bitField0_ & ~0x00000001); - tableId_ = 0L; - onChanged(); - return this; - } - - private com.alibaba.otter.canal.protocol.CanalEntry.EventType eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public boolean hasEventType() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.EventType getEventType() { - return eventType_; - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public Builder setEventType(com.alibaba.otter.canal.protocol.CanalEntry.EventType value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - eventType_ = value; - onChanged(); - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; - * - *
      -             * *数据变更类型*
      -             * 
      - */ - public Builder clearEventType() { - bitField0_ = (bitField0_ & ~0x00000002); - eventType_ = com.alibaba.otter.canal.protocol.CanalEntry.EventType.UPDATE; - onChanged(); - return this; - } - - private boolean isDdl_; - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -             * * 标识是否是ddl语句  *
      -             * 
      - */ - public boolean hasIsDdl() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -             * * 标识是否是ddl语句  *
      -             * 
      - */ - public boolean getIsDdl() { - return isDdl_; - } - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -             * * 标识是否是ddl语句  *
      -             * 
      - */ - public Builder setIsDdl(boolean value) { - bitField0_ |= 0x00000004; - isDdl_ = value; - onChanged(); - return this; - } - - /** - * optional bool isDdl = 10 [default = false]; - * - *
      -             * * 标识是否是ddl语句  *
      -             * 
      - */ - public Builder clearIsDdl() { - bitField0_ = (bitField0_ & ~0x00000004); - isDdl_ = false; - onChanged(); - return this; - } - - private java.lang.Object sql_ = ""; - - /** - * optional string sql = 11; - * - *
      -             * * ddl/query的sql语句  *
      -             * 
      - */ - public boolean hasSql() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional string sql = 11; - * - *
      -             * * ddl/query的sql语句  *
      -             * 
      - */ - public java.lang.String getSql() { - java.lang.Object ref = sql_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - sql_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string sql = 11; - * - *
      -             * * ddl/query的sql语句  *
      -             * 
      - */ - public com.google.protobuf.ByteString getSqlBytes() { - java.lang.Object ref = sql_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - sql_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string sql = 11; - * - *
      -             * * ddl/query的sql语句  *
      -             * 
      - */ - public Builder setSql(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000008; - sql_ = value; - onChanged(); - return this; - } - - /** - * optional string sql = 11; - * - *
      -             * * ddl/query的sql语句  *
      -             * 
      - */ - public Builder clearSql() { - bitField0_ = (bitField0_ & ~0x00000008); - sql_ = getDefaultInstance().getSql(); - onChanged(); - return this; - } - - /** - * optional string sql = 11; - * - *
      -             * * ddl/query的sql语句  *
      -             * 
      - */ - public Builder setSqlBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000008; - sql_ = value; - onChanged(); - return this; - } - - private java.util.List rowDatas_ = java.util.Collections.emptyList(); - - private void ensureRowDatasIsMutable() { - if (!((bitField0_ & 0x00000010) == 0x00000010)) { - rowDatas_ = new java.util.ArrayList(rowDatas_); - bitField0_ |= 0x00000010; - } - } - - private com.google.protobuf.RepeatedFieldBuilder rowDatasBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public java.util.List getRowDatasList() { - if (rowDatasBuilder_ == null) { - return java.util.Collections.unmodifiableList(rowDatas_); - } else { - return rowDatasBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public int getRowDatasCount() { - if (rowDatasBuilder_ == null) { - return rowDatas_.size(); - } else { - return rowDatasBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.RowData getRowDatas(int index) { - if (rowDatasBuilder_ == null) { - return rowDatas_.get(index); - } else { - return rowDatasBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder setRowDatas(int index, com.alibaba.otter.canal.protocol.CanalEntry.RowData value) { - if (rowDatasBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureRowDatasIsMutable(); - rowDatas_.set(index, value); - onChanged(); - } else { - rowDatasBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder setRowDatas(int index, - com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder builderForValue) { - if (rowDatasBuilder_ == null) { - ensureRowDatasIsMutable(); - rowDatas_.set(index, builderForValue.build()); - onChanged(); - } else { - rowDatasBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder addRowDatas(com.alibaba.otter.canal.protocol.CanalEntry.RowData value) { - if (rowDatasBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureRowDatasIsMutable(); - rowDatas_.add(value); - onChanged(); - } else { - rowDatasBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder addRowDatas(int index, com.alibaba.otter.canal.protocol.CanalEntry.RowData value) { - if (rowDatasBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensureRowDatasIsMutable(); - rowDatas_.add(index, value); - onChanged(); - } else { - rowDatasBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder addRowDatas(com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder builderForValue) { - if (rowDatasBuilder_ == null) { - ensureRowDatasIsMutable(); - rowDatas_.add(builderForValue.build()); - onChanged(); - } else { - rowDatasBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder addRowDatas(int index, - com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder builderForValue) { - if (rowDatasBuilder_ == null) { - ensureRowDatasIsMutable(); - rowDatas_.add(index, builderForValue.build()); - onChanged(); - } else { - rowDatasBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder addAllRowDatas(java.lang.Iterable values) { - if (rowDatasBuilder_ == null) { - ensureRowDatasIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, rowDatas_); - onChanged(); - } else { - rowDatasBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder clearRowDatas() { - if (rowDatasBuilder_ == null) { - rowDatas_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000010); - onChanged(); - } else { - rowDatasBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public Builder removeRowDatas(int index) { - if (rowDatasBuilder_ == null) { - ensureRowDatasIsMutable(); - rowDatas_.remove(index); - onChanged(); - } else { - rowDatasBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder getRowDatasBuilder(int index) { - return getRowDatasFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.RowDataOrBuilder getRowDatasOrBuilder(int index) { - if (rowDatasBuilder_ == null) { - return rowDatas_.get(index); - } else { - return rowDatasBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public java.util.List getRowDatasOrBuilderList() { - if (rowDatasBuilder_ != null) { - return rowDatasBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(rowDatas_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder addRowDatasBuilder() { - return getRowDatasFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.RowData.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.RowData.Builder addRowDatasBuilder(int index) { - return getRowDatasFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.RowData.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; - * - *
      -             * * 一次数据库变更可能存在多行  *
      -             * 
      - */ - public java.util.List getRowDatasBuilderList() { - return getRowDatasFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getRowDatasFieldBuilder() { - if (rowDatasBuilder_ == null) { - rowDatasBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(rowDatas_, - ((bitField0_ & 0x00000010) == 0x00000010), - getParentForChildren(), - isClean()); - rowDatas_ = null; - } - return rowDatasBuilder_; - } - - private java.util.List props_ = java.util.Collections.emptyList(); - - private void ensurePropsIsMutable() { - if (!((bitField0_ & 0x00000020) == 0x00000020)) { - props_ = new java.util.ArrayList(props_); - bitField0_ |= 0x00000020; - } - } - - private com.google.protobuf.RepeatedFieldBuilder propsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsList() { - if (propsBuilder_ == null) { - return java.util.Collections.unmodifiableList(props_); - } else { - return propsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public int getPropsCount() { - if (propsBuilder_ == null) { - return props_.size(); - } else { - return propsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.set(index, value); - onChanged(); - } else { - propsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.set(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(value); - onChanged(); - } else { - propsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(index, value); - onChanged(); - } else { - propsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addAllProps(java.lang.Iterable values) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, props_); - onChanged(); - } else { - propsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder clearProps() { - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000020); - onChanged(); - } else { - propsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder removeProps(int index) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.remove(index); - onChanged(); - } else { - propsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder getPropsBuilder(int index) { - return getPropsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsOrBuilderList() { - if (propsBuilder_ != null) { - return propsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(props_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder() { - return getPropsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder(int index) { - return getPropsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsBuilderList() { - return getPropsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getPropsFieldBuilder() { - if (propsBuilder_ == null) { - propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(props_, - ((bitField0_ & 0x00000020) == 0x00000020), - getParentForChildren(), - isClean()); - props_ = null; - } - return propsBuilder_; - } - - private java.lang.Object ddlSchemaName_ = ""; - - /** - * optional string ddlSchemaName = 14; - * - *
      -             * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -             * 
      - */ - public boolean hasDdlSchemaName() { - return ((bitField0_ & 0x00000040) == 0x00000040); - } - - /** - * optional string ddlSchemaName = 14; - * - *
      -             * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -             * 
      - */ - public java.lang.String getDdlSchemaName() { - java.lang.Object ref = ddlSchemaName_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - ddlSchemaName_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string ddlSchemaName = 14; - * - *
      -             * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -             * 
      - */ - public com.google.protobuf.ByteString getDdlSchemaNameBytes() { - java.lang.Object ref = ddlSchemaName_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - ddlSchemaName_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string ddlSchemaName = 14; - * - *
      -             * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -             * 
      - */ - public Builder setDdlSchemaName(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000040; - ddlSchemaName_ = value; - onChanged(); - return this; - } - - /** - * optional string ddlSchemaName = 14; - * - *
      -             * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -             * 
      - */ - public Builder clearDdlSchemaName() { - bitField0_ = (bitField0_ & ~0x00000040); - ddlSchemaName_ = getDefaultInstance().getDdlSchemaName(); - onChanged(); - return this; - } - - /** - * optional string ddlSchemaName = 14; - * - *
      -             * * ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      -             * 
      - */ - public Builder setDdlSchemaNameBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000040; - ddlSchemaName_ = value; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.RowChange) + RowChangeOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable + .ensureFieldAccessorsInitialized( + RowChange.class, Builder.class); + } + + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.RowChange.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } + + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { + getRowDatasFieldBuilder(); + getPropsFieldBuilder(); } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new RowChange(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + tableId_ = 0L; + bitField0_ = (bitField0_ & ~0x00000001); + eventType_ = EventType.UPDATE; + bitField0_ = (bitField0_ & ~0x00000002); + isDdl_ = false; + bitField0_ = (bitField0_ & ~0x00000004); + sql_ = ""; + bitField0_ = (bitField0_ & ~0x00000008); + if (rowDatasBuilder_ == null) { + rowDatas_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000010); + } else { + rowDatasBuilder_.clear(); } + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000020); + } else { + propsBuilder_.clear(); + } + ddlSchemaName_ = ""; + bitField0_ = (bitField0_ & ~0x00000040); + return this; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.RowChange) + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; + } + + public RowChange getDefaultInstanceForType() { + return RowChange.getDefaultInstance(); + } + + public RowChange build() { + RowChange result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); + } + return result; + } + + public RowChange buildPartial() { + RowChange result = new RowChange(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + if (((from_bitField0_ & 0x00000001) == 0x00000001)) { + to_bitField0_ |= 0x00000001; + } + result.tableId_ = tableId_; + if (((from_bitField0_ & 0x00000002) == 0x00000002)) { + to_bitField0_ |= 0x00000002; + } + result.eventType_ = eventType_; + if (((from_bitField0_ & 0x00000004) == 0x00000004)) { + to_bitField0_ |= 0x00000004; + } + result.isDdl_ = isDdl_; + if (((from_bitField0_ & 0x00000008) == 0x00000008)) { + to_bitField0_ |= 0x00000008; + } + result.sql_ = sql_; + if (rowDatasBuilder_ == null) { + if (((bitField0_ & 0x00000010) == 0x00000010)) { + rowDatas_ = java.util.Collections.unmodifiableList(rowDatas_); + bitField0_ = (bitField0_ & ~0x00000010); + } + result.rowDatas_ = rowDatas_; + } else { + result.rowDatas_ = rowDatasBuilder_.build(); + } + if (propsBuilder_ == null) { + if (((bitField0_ & 0x00000020) == 0x00000020)) { + props_ = java.util.Collections.unmodifiableList(props_); + bitField0_ = (bitField0_ & ~0x00000020); + } + result.props_ = props_; + } else { + result.props_ = propsBuilder_.build(); + } + if (((from_bitField0_ & 0x00000040) == 0x00000040)) { + to_bitField0_ |= 0x00000010; + } + result.ddlSchemaName_ = ddlSchemaName_; + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof RowChange) { + return mergeFrom((RowChange)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(RowChange other) { + if (other == RowChange.getDefaultInstance()) return this; + if (other.hasTableId()) { + setTableId(other.getTableId()); + } + if (other.hasEventType()) { + setEventType(other.getEventType()); + } + if (other.hasIsDdl()) { + setIsDdl(other.getIsDdl()); + } + if (other.hasSql()) { + bitField0_ |= 0x00000008; + sql_ = other.sql_; + onChanged(); + } + if (rowDatasBuilder_ == null) { + if (!other.rowDatas_.isEmpty()) { + if (rowDatas_.isEmpty()) { + rowDatas_ = other.rowDatas_; + bitField0_ = (bitField0_ & ~0x00000010); + } else { + ensureRowDatasIsMutable(); + rowDatas_.addAll(other.rowDatas_); + } + onChanged(); + } + } else { + if (!other.rowDatas_.isEmpty()) { + if (rowDatasBuilder_.isEmpty()) { + rowDatasBuilder_.dispose(); + rowDatasBuilder_ = null; + rowDatas_ = other.rowDatas_; + bitField0_ = (bitField0_ & ~0x00000010); + rowDatasBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getRowDatasFieldBuilder() : null; + } else { + rowDatasBuilder_.addAllMessages(other.rowDatas_); + } + } + } + if (propsBuilder_ == null) { + if (!other.props_.isEmpty()) { + if (props_.isEmpty()) { + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000020); + } else { + ensurePropsIsMutable(); + props_.addAll(other.props_); + } + onChanged(); + } + } else { + if (!other.props_.isEmpty()) { + if (propsBuilder_.isEmpty()) { + propsBuilder_.dispose(); + propsBuilder_ = null; + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000020); + propsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getPropsFieldBuilder() : null; + } else { + propsBuilder_.addAllMessages(other.props_); + } + } + } + if (other.hasDdlSchemaName()) { + bitField0_ |= 0x00000040; + ddlSchemaName_ = other.ddlSchemaName_; + onChanged(); + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + RowChange parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (RowChange) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private long tableId_ ; + /** + * optional int64 tableId = 1; + * + *
      +       **tableId,由数据库产生*
      +       * 
      + */ + public boolean hasTableId() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int64 tableId = 1; + * + *
      +       **tableId,由数据库产生*
      +       * 
      + */ + public long getTableId() { + return tableId_; + } + /** + * optional int64 tableId = 1; + * + *
      +       **tableId,由数据库产生*
      +       * 
      + */ + public Builder setTableId(long value) { + bitField0_ |= 0x00000001; + tableId_ = value; + onChanged(); + return this; + } + /** + * optional int64 tableId = 1; + * + *
      +       **tableId,由数据库产生*
      +       * 
      + */ + public Builder clearTableId() { + bitField0_ = (bitField0_ & ~0x00000001); + tableId_ = 0L; + onChanged(); + return this; + } + + private EventType eventType_ = EventType.UPDATE; + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public boolean hasEventType() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public EventType getEventType() { + return eventType_; + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public Builder setEventType(EventType value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + eventType_ = value; + onChanged(); + return this; + } + /** + * optional .com.alibaba.otter.canal.protocol.EventType eventType = 2 [default = UPDATE]; + * + *
      +       **数据变更类型*
      +       * 
      + */ + public Builder clearEventType() { + bitField0_ = (bitField0_ & ~0x00000002); + eventType_ = EventType.UPDATE; + onChanged(); + return this; + } + + private boolean isDdl_ ; + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +       ** 标识是否是ddl语句  *
      +       * 
      + */ + public boolean hasIsDdl() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +       ** 标识是否是ddl语句  *
      +       * 
      + */ + public boolean getIsDdl() { + return isDdl_; + } + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +       ** 标识是否是ddl语句  *
      +       * 
      + */ + public Builder setIsDdl(boolean value) { + bitField0_ |= 0x00000004; + isDdl_ = value; + onChanged(); + return this; + } + /** + * optional bool isDdl = 10 [default = false]; + * + *
      +       ** 标识是否是ddl语句  *
      +       * 
      + */ + public Builder clearIsDdl() { + bitField0_ = (bitField0_ & ~0x00000004); + isDdl_ = false; + onChanged(); + return this; + } + + private Object sql_ = ""; + /** + * optional string sql = 11; + * + *
      +       ** ddl/query的sql语句  *
      +       * 
      + */ + public boolean hasSql() { + return ((bitField0_ & 0x00000008) == 0x00000008); + } + /** + * optional string sql = 11; + * + *
      +       ** ddl/query的sql语句  *
      +       * 
      + */ + public String getSql() { + Object ref = sql_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + sql_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string sql = 11; + * + *
      +       ** ddl/query的sql语句  *
      +       * 
      + */ + public com.google.protobuf.ByteString + getSqlBytes() { + Object ref = sql_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + sql_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string sql = 11; + * + *
      +       ** ddl/query的sql语句  *
      +       * 
      + */ + public Builder setSql( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000008; + sql_ = value; + onChanged(); + return this; + } + /** + * optional string sql = 11; + * + *
      +       ** ddl/query的sql语句  *
      +       * 
      + */ + public Builder clearSql() { + bitField0_ = (bitField0_ & ~0x00000008); + sql_ = getDefaultInstance().getSql(); + onChanged(); + return this; + } + /** + * optional string sql = 11; + * + *
      +       ** ddl/query的sql语句  *
      +       * 
      + */ + public Builder setSqlBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000008; + sql_ = value; + onChanged(); + return this; + } + + private java.util.List rowDatas_ = + java.util.Collections.emptyList(); + private void ensureRowDatasIsMutable() { + if (!((bitField0_ & 0x00000010) == 0x00000010)) { + rowDatas_ = new java.util.ArrayList(rowDatas_); + bitField0_ |= 0x00000010; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + RowData, RowData.Builder, RowDataOrBuilder> rowDatasBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public java.util.List getRowDatasList() { + if (rowDatasBuilder_ == null) { + return java.util.Collections.unmodifiableList(rowDatas_); + } else { + return rowDatasBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public int getRowDatasCount() { + if (rowDatasBuilder_ == null) { + return rowDatas_.size(); + } else { + return rowDatasBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public RowData getRowDatas(int index) { + if (rowDatasBuilder_ == null) { + return rowDatas_.get(index); + } else { + return rowDatasBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder setRowDatas( + int index, RowData value) { + if (rowDatasBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureRowDatasIsMutable(); + rowDatas_.set(index, value); + onChanged(); + } else { + rowDatasBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder setRowDatas( + int index, RowData.Builder builderForValue) { + if (rowDatasBuilder_ == null) { + ensureRowDatasIsMutable(); + rowDatas_.set(index, builderForValue.build()); + onChanged(); + } else { + rowDatasBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder addRowDatas(RowData value) { + if (rowDatasBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureRowDatasIsMutable(); + rowDatas_.add(value); + onChanged(); + } else { + rowDatasBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder addRowDatas( + int index, RowData value) { + if (rowDatasBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensureRowDatasIsMutable(); + rowDatas_.add(index, value); + onChanged(); + } else { + rowDatasBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder addRowDatas( + RowData.Builder builderForValue) { + if (rowDatasBuilder_ == null) { + ensureRowDatasIsMutable(); + rowDatas_.add(builderForValue.build()); + onChanged(); + } else { + rowDatasBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder addRowDatas( + int index, RowData.Builder builderForValue) { + if (rowDatasBuilder_ == null) { + ensureRowDatasIsMutable(); + rowDatas_.add(index, builderForValue.build()); + onChanged(); + } else { + rowDatasBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder addAllRowDatas( + Iterable values) { + if (rowDatasBuilder_ == null) { + ensureRowDatasIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, rowDatas_); + onChanged(); + } else { + rowDatasBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder clearRowDatas() { + if (rowDatasBuilder_ == null) { + rowDatas_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000010); + onChanged(); + } else { + rowDatasBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public Builder removeRowDatas(int index) { + if (rowDatasBuilder_ == null) { + ensureRowDatasIsMutable(); + rowDatas_.remove(index); + onChanged(); + } else { + rowDatasBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public RowData.Builder getRowDatasBuilder( + int index) { + return getRowDatasFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public RowDataOrBuilder getRowDatasOrBuilder( + int index) { + if (rowDatasBuilder_ == null) { + return rowDatas_.get(index); } else { + return rowDatasBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public java.util.List + getRowDatasOrBuilderList() { + if (rowDatasBuilder_ != null) { + return rowDatasBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(rowDatas_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public RowData.Builder addRowDatasBuilder() { + return getRowDatasFieldBuilder().addBuilder( + RowData.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public RowData.Builder addRowDatasBuilder( + int index) { + return getRowDatasFieldBuilder().addBuilder( + index, RowData.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.RowData rowDatas = 12; + * + *
      +       ** 一次数据库变更可能存在多行  *
      +       * 
      + */ + public java.util.List + getRowDatasBuilderList() { + return getRowDatasFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + RowData, RowData.Builder, RowDataOrBuilder> + getRowDatasFieldBuilder() { + if (rowDatasBuilder_ == null) { + rowDatasBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + RowData, RowData.Builder, RowDataOrBuilder>( + rowDatas_, + ((bitField0_ & 0x00000010) == 0x00000010), + getParentForChildren(), + isClean()); + rowDatas_ = null; + } + return rowDatasBuilder_; + } + + private java.util.List props_ = + java.util.Collections.emptyList(); + private void ensurePropsIsMutable() { + if (!((bitField0_ & 0x00000020) == 0x00000020)) { + props_ = new java.util.ArrayList(props_); + bitField0_ |= 0x00000020; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> propsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List getPropsList() { + if (propsBuilder_ == null) { + return java.util.Collections.unmodifiableList(props_); + } else { + return propsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public int getPropsCount() { + if (propsBuilder_ == null) { + return props_.size(); + } else { + return propsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair getProps(int index) { + if (propsBuilder_ == null) { + return props_.get(index); + } else { + return propsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.set(index, value); + onChanged(); + } else { + propsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.set(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps(Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(value); + onChanged(); + } else { + propsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(index, value); + onChanged(); + } else { + propsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addAllProps( + Iterable values) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, props_); + onChanged(); + } else { + propsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder clearProps() { + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000020); + onChanged(); + } else { + propsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder removeProps(int index) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.remove(index); + onChanged(); + } else { + propsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder getPropsBuilder( + int index) { + return getPropsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + if (propsBuilder_ == null) { + return props_.get(index); } else { + return propsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsOrBuilderList() { + if (propsBuilder_ != null) { + return propsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(props_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder() { + return getPropsFieldBuilder().addBuilder( + Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder( + int index) { + return getPropsFieldBuilder().addBuilder( + index, Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 13; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsBuilderList() { + return getPropsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> + getPropsFieldBuilder() { + if (propsBuilder_ == null) { + propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder>( + props_, + ((bitField0_ & 0x00000020) == 0x00000020), + getParentForChildren(), + isClean()); + props_ = null; + } + return propsBuilder_; + } + + private Object ddlSchemaName_ = ""; + /** + * optional string ddlSchemaName = 14; + * + *
      +       ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +       * 
      + */ + public boolean hasDdlSchemaName() { + return ((bitField0_ & 0x00000040) == 0x00000040); + } + /** + * optional string ddlSchemaName = 14; + * + *
      +       ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +       * 
      + */ + public String getDdlSchemaName() { + Object ref = ddlSchemaName_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + ddlSchemaName_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string ddlSchemaName = 14; + * + *
      +       ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +       * 
      + */ + public com.google.protobuf.ByteString + getDdlSchemaNameBytes() { + Object ref = ddlSchemaName_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + ddlSchemaName_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string ddlSchemaName = 14; + * + *
      +       ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +       * 
      + */ + public Builder setDdlSchemaName( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000040; + ddlSchemaName_ = value; + onChanged(); + return this; + } + /** + * optional string ddlSchemaName = 14; + * + *
      +       ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +       * 
      + */ + public Builder clearDdlSchemaName() { + bitField0_ = (bitField0_ & ~0x00000040); + ddlSchemaName_ = getDefaultInstance().getDdlSchemaName(); + onChanged(); + return this; + } + /** + * optional string ddlSchemaName = 14; + * + *
      +       ** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName  *
      +       * 
      + */ + public Builder setDdlSchemaNameBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000040; + ddlSchemaName_ = value; + onChanged(); + return this; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.RowChange) } - public interface TransactionBeginOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.TransactionBegin) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - boolean hasExecuteTime(); - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - long getExecuteTime(); - - /** - * optional string transactionId = 2; - * - *
      -         * *已废弃,Begin里不提供事务id*
      -         * 
      - */ - boolean hasTransactionId(); - - /** - * optional string transactionId = 2; - * - *
      -         * *已废弃,Begin里不提供事务id*
      -         * 
      - */ - java.lang.String getTransactionId(); - - /** - * optional string transactionId = 2; - * - *
      -         * *已废弃,Begin里不提供事务id*
      -         * 
      - */ - com.google.protobuf.ByteString getTransactionIdBytes(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - int getPropsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index); - - /** - * optional int64 threadId = 4; - * - *
      -         * *执行的thread Id*
      -         * 
      - */ - boolean hasThreadId(); - - /** - * optional int64 threadId = 4; - * - *
      -         * *执行的thread Id*
      -         * 
      - */ - long getThreadId(); + static { + defaultInstance = new RowChange(true); + defaultInstance.initFields(); } + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.RowChange) + } + + public interface TransactionBeginOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.TransactionBegin) + com.google.protobuf.MessageOrBuilder { + + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + boolean hasExecuteTime(); + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + long getExecuteTime(); + + /** + * optional string transactionId = 2; + * + *
      +     **已废弃,Begin里不提供事务id*
      +     * 
      + */ + boolean hasTransactionId(); + /** + * optional string transactionId = 2; + * + *
      +     **已废弃,Begin里不提供事务id*
      +     * 
      + */ + String getTransactionId(); + /** + * optional string transactionId = 2; + * + *
      +     **已废弃,Begin里不提供事务id*
      +     * 
      + */ + com.google.protobuf.ByteString + getTransactionIdBytes(); + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + Pair getProps(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + int getPropsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + PairOrBuilder getPropsOrBuilder(int index); + + /** + * optional int64 threadId = 4; + * + *
      +     **执行的thread Id*
      +     * 
      + */ + boolean hasThreadId(); + /** + * optional int64 threadId = 4; + * + *
      +     **执行的thread Id*
      +     * 
      + */ + long getThreadId(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.TransactionBegin} + * + *
      +   **开始事务的一些信息*
      +   * 
      + */ + public static final class TransactionBegin extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.TransactionBegin) + TransactionBeginOrBuilder { + // Use TransactionBegin.newBuilder() to construct. + private TransactionBegin(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private TransactionBegin(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final TransactionBegin defaultInstance; + public static TransactionBegin getDefaultInstance() { + return defaultInstance; + } + + public TransactionBegin getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private TransactionBegin( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 8: { + bitField0_ |= 0x00000001; + executeTime_ = input.readInt64(); + break; + } + case 18: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000002; + transactionId_ = bs; + break; + } + case 26: { + if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { + props_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000004; + } + props_.add(input.readMessage(Pair.PARSER, extensionRegistry)); + break; + } + case 32: { + bitField0_ |= 0x00000004; + threadId_ = input.readInt64(); + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + if (((mutable_bitField0_ & 0x00000004) == 0x00000004)) { + props_ = java.util.Collections.unmodifiableList(props_); + } + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable + .ensureFieldAccessorsInitialized( + TransactionBegin.class, Builder.class); + } + + public static com.google.protobuf.Parser PARSER = + new com.google.protobuf.AbstractParser() { + public TransactionBegin parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new TransactionBegin(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + private int bitField0_; + public static final int EXECUTETIME_FIELD_NUMBER = 1; + private long executeTime_; + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + public boolean hasExecuteTime() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + public long getExecuteTime() { + return executeTime_; + } + + public static final int TRANSACTIONID_FIELD_NUMBER = 2; + private Object transactionId_; + /** + * optional string transactionId = 2; + * + *
      +     **已废弃,Begin里不提供事务id*
      +     * 
      + */ + public boolean hasTransactionId() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string transactionId = 2; + * + *
      +     **已废弃,Begin里不提供事务id*
      +     * 
      + */ + public String getTransactionId() { + Object ref = transactionId_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + transactionId_ = s; + } + return s; + } + } + /** + * optional string transactionId = 2; + * + *
      +     **已废弃,Begin里不提供事务id*
      +     * 
      + */ + public com.google.protobuf.ByteString + getTransactionIdBytes() { + Object ref = transactionId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + transactionId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int PROPS_FIELD_NUMBER = 3; + private java.util.List props_; + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List getPropsList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List + getPropsOrBuilderList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public int getPropsCount() { + return props_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public Pair getProps(int index) { + return props_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + return props_.get(index); + } + + public static final int THREADID_FIELD_NUMBER = 4; + private long threadId_; + /** + * optional int64 threadId = 4; + * + *
      +     **执行的thread Id*
      +     * 
      + */ + public boolean hasThreadId() { + return ((bitField0_ & 0x00000004) == 0x00000004); + } + /** + * optional int64 threadId = 4; + * + *
      +     **执行的thread Id*
      +     * 
      + */ + public long getThreadId() { + return threadId_; + } + + private void initFields() { + executeTime_ = 0L; + transactionId_ = ""; + props_ = java.util.Collections.emptyList(); + threadId_ = 0L; + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + if (((bitField0_ & 0x00000001) == 0x00000001)) { + output.writeInt64(1, executeTime_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + output.writeBytes(2, getTransactionIdBytes()); + } + for (int i = 0; i < props_.size(); i++) { + output.writeMessage(3, props_.get(i)); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + output.writeInt64(4, threadId_); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(1, executeTime_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(2, getTransactionIdBytes()); + } + for (int i = 0; i < props_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(3, props_.get(i)); + } + if (((bitField0_ & 0x00000004) == 0x00000004)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(4, threadId_); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static TransactionBegin parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static TransactionBegin parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static TransactionBegin parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static TransactionBegin parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static TransactionBegin parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static TransactionBegin parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static TransactionBegin parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static TransactionBegin parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static TransactionBegin parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static TransactionBegin parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(TransactionBegin prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.TransactionBegin} * *
      -     * *开始事务的一些信息*
      +     **开始事务的一些信息*
            * 
      */ - public static final class TransactionBegin extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.TransactionBegin) - TransactionBeginOrBuilder { - - // Use TransactionBegin.newBuilder() to construct. - private TransactionBegin(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private TransactionBegin(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final TransactionBegin defaultInstance; - - public static TransactionBegin getDefaultInstance() { - return defaultInstance; - } - - public TransactionBegin getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private TransactionBegin(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - executeTime_ = input.readInt64(); - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - transactionId_ = bs; - break; - } - case 26: { - if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - props_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000004; - } - props_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Pair.PARSER, - extensionRegistry)); - break; - } - case 32: { - bitField0_ |= 0x00000004; - threadId_ = input.readInt64(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - props_ = java.util.Collections.unmodifiableList(props_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.class, - com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public TransactionBegin parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new TransactionBegin(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int EXECUTETIME_FIELD_NUMBER = 1; - private long executeTime_; - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - public boolean hasExecuteTime() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - public long getExecuteTime() { - return executeTime_; - } - - public static final int TRANSACTIONID_FIELD_NUMBER = 2; - private java.lang.Object transactionId_; - - /** - * optional string transactionId = 2; - * - *
      -         * *已废弃,Begin里不提供事务id*
      -         * 
      - */ - public boolean hasTransactionId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string transactionId = 2; - * - *
      -         * *已废弃,Begin里不提供事务id*
      -         * 
      - */ - public java.lang.String getTransactionId() { - java.lang.Object ref = transactionId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - transactionId_ = s; - } - return s; - } - } - - /** - * optional string transactionId = 2; - * - *
      -         * *已废弃,Begin里不提供事务id*
      -         * 
      - */ - public com.google.protobuf.ByteString getTransactionIdBytes() { - java.lang.Object ref = transactionId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - transactionId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int PROPS_FIELD_NUMBER = 3; - private java.util.List props_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsOrBuilderList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public int getPropsCount() { - return props_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - return props_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - return props_.get(index); - } - - public static final int THREADID_FIELD_NUMBER = 4; - private long threadId_; - - /** - * optional int64 threadId = 4; - * - *
      -         * *执行的thread Id*
      -         * 
      - */ - public boolean hasThreadId() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 threadId = 4; - * - *
      -         * *执行的thread Id*
      -         * 
      - */ - public long getThreadId() { - return threadId_; - } - - private void initFields() { - executeTime_ = 0L; - transactionId_ = ""; - props_ = java.util.Collections.emptyList(); - threadId_ = 0L; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt64(1, executeTime_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getTransactionIdBytes()); - } - for (int i = 0; i < props_.size(); i++) { - output.writeMessage(3, props_.get(i)); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeInt64(4, threadId_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(1, executeTime_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getTransactionIdBytes()); - } - for (int i = 0; i < props_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(3, props_.get(i)); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(4, threadId_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type - * {@code com.alibaba.otter.canal.protocol.TransactionBegin} - * - *
      -         * *开始事务的一些信息*
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.TransactionBegin) - com.alibaba.otter.canal.protocol.CanalEntry.TransactionBeginOrBuilder { + TransactionBeginOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; - } + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable + .ensureFieldAccessorsInitialized( + TransactionBegin.class, Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.class, - com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - getPropsFieldBuilder(); - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - executeTime_ = 0L; - bitField0_ = (bitField0_ & ~0x00000001); - transactionId_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - } else { - propsBuilder_.clear(); - } - threadId_ = 0L; - bitField0_ = (bitField0_ & ~0x00000008); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin build() { - com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin result = new com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.executeTime_ = executeTime_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.transactionId_ = transactionId_; - if (propsBuilder_ == null) { - if (((bitField0_ & 0x00000004) == 0x00000004)) { - props_ = java.util.Collections.unmodifiableList(props_); - bitField0_ = (bitField0_ & ~0x00000004); - } - result.props_ = props_; - } else { - result.props_ = propsBuilder_.build(); - } - if (((from_bitField0_ & 0x00000008) == 0x00000008)) { - to_bitField0_ |= 0x00000004; - } - result.threadId_ = threadId_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin.getDefaultInstance()) return this; - if (other.hasExecuteTime()) { - setExecuteTime(other.getExecuteTime()); - } - if (other.hasTransactionId()) { - bitField0_ |= 0x00000002; - transactionId_ = other.transactionId_; - onChanged(); - } - if (propsBuilder_ == null) { - if (!other.props_.isEmpty()) { - if (props_.isEmpty()) { - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000004); - } else { - ensurePropsIsMutable(); - props_.addAll(other.props_); - } - onChanged(); - } - } else { - if (!other.props_.isEmpty()) { - if (propsBuilder_.isEmpty()) { - propsBuilder_.dispose(); - propsBuilder_ = null; - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000004); - propsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getPropsFieldBuilder() : null; - } else { - propsBuilder_.addAllMessages(other.props_); - } - } - } - if (other.hasThreadId()) { - setThreadId(other.getThreadId()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.TransactionBegin) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private long executeTime_; - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public boolean hasExecuteTime() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public long getExecuteTime() { - return executeTime_; - } - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public Builder setExecuteTime(long value) { - bitField0_ |= 0x00000001; - executeTime_ = value; - onChanged(); - return this; - } - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public Builder clearExecuteTime() { - bitField0_ = (bitField0_ & ~0x00000001); - executeTime_ = 0L; - onChanged(); - return this; - } - - private java.lang.Object transactionId_ = ""; - - /** - * optional string transactionId = 2; - * - *
      -             * *已废弃,Begin里不提供事务id*
      -             * 
      - */ - public boolean hasTransactionId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string transactionId = 2; - * - *
      -             * *已废弃,Begin里不提供事务id*
      -             * 
      - */ - public java.lang.String getTransactionId() { - java.lang.Object ref = transactionId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - transactionId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string transactionId = 2; - * - *
      -             * *已废弃,Begin里不提供事务id*
      -             * 
      - */ - public com.google.protobuf.ByteString getTransactionIdBytes() { - java.lang.Object ref = transactionId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - transactionId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string transactionId = 2; - * - *
      -             * *已废弃,Begin里不提供事务id*
      -             * 
      - */ - public Builder setTransactionId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - transactionId_ = value; - onChanged(); - return this; - } - - /** - * optional string transactionId = 2; - * - *
      -             * *已废弃,Begin里不提供事务id*
      -             * 
      - */ - public Builder clearTransactionId() { - bitField0_ = (bitField0_ & ~0x00000002); - transactionId_ = getDefaultInstance().getTransactionId(); - onChanged(); - return this; - } - - /** - * optional string transactionId = 2; - * - *
      -             * *已废弃,Begin里不提供事务id*
      -             * 
      - */ - public Builder setTransactionIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - transactionId_ = value; - onChanged(); - return this; - } - - private java.util.List props_ = java.util.Collections.emptyList(); - - private void ensurePropsIsMutable() { - if (!((bitField0_ & 0x00000004) == 0x00000004)) { - props_ = new java.util.ArrayList(props_); - bitField0_ |= 0x00000004; - } - } - - private com.google.protobuf.RepeatedFieldBuilder propsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsList() { - if (propsBuilder_ == null) { - return java.util.Collections.unmodifiableList(props_); - } else { - return propsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public int getPropsCount() { - if (propsBuilder_ == null) { - return props_.size(); - } else { - return propsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.set(index, value); - onChanged(); - } else { - propsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.set(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(value); - onChanged(); - } else { - propsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(index, value); - onChanged(); - } else { - propsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addAllProps(java.lang.Iterable values) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, props_); - onChanged(); - } else { - propsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder clearProps() { - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - onChanged(); - } else { - propsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder removeProps(int index) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.remove(index); - onChanged(); - } else { - propsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder getPropsBuilder(int index) { - return getPropsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsOrBuilderList() { - if (propsBuilder_ != null) { - return propsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(props_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder() { - return getPropsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder(int index) { - return getPropsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsBuilderList() { - return getPropsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getPropsFieldBuilder() { - if (propsBuilder_ == null) { - propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(props_, - ((bitField0_ & 0x00000004) == 0x00000004), - getParentForChildren(), - isClean()); - props_ = null; - } - return propsBuilder_; - } - - private long threadId_; - - /** - * optional int64 threadId = 4; - * - *
      -             * *执行的thread Id*
      -             * 
      - */ - public boolean hasThreadId() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional int64 threadId = 4; - * - *
      -             * *执行的thread Id*
      -             * 
      - */ - public long getThreadId() { - return threadId_; - } - - /** - * optional int64 threadId = 4; - * - *
      -             * *执行的thread Id*
      -             * 
      - */ - public Builder setThreadId(long value) { - bitField0_ |= 0x00000008; - threadId_ = value; - onChanged(); - return this; - } - - /** - * optional int64 threadId = 4; - * - *
      -             * *执行的thread Id*
      -             * 
      - */ - public Builder clearThreadId() { - bitField0_ = (bitField0_ & ~0x00000008); - threadId_ = 0L; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.TransactionBegin) + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { + getPropsFieldBuilder(); } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new TransactionBegin(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + executeTime_ = 0L; + bitField0_ = (bitField0_ & ~0x00000001); + transactionId_ = ""; + bitField0_ = (bitField0_ & ~0x00000002); + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000004); + } else { + propsBuilder_.clear(); } + threadId_ = 0L; + bitField0_ = (bitField0_ & ~0x00000008); + return this; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.TransactionBegin) + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; + } + + public TransactionBegin getDefaultInstanceForType() { + return TransactionBegin.getDefaultInstance(); + } + + public TransactionBegin build() { + TransactionBegin result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); + } + return result; + } + + public TransactionBegin buildPartial() { + TransactionBegin result = new TransactionBegin(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + if (((from_bitField0_ & 0x00000001) == 0x00000001)) { + to_bitField0_ |= 0x00000001; + } + result.executeTime_ = executeTime_; + if (((from_bitField0_ & 0x00000002) == 0x00000002)) { + to_bitField0_ |= 0x00000002; + } + result.transactionId_ = transactionId_; + if (propsBuilder_ == null) { + if (((bitField0_ & 0x00000004) == 0x00000004)) { + props_ = java.util.Collections.unmodifiableList(props_); + bitField0_ = (bitField0_ & ~0x00000004); + } + result.props_ = props_; + } else { + result.props_ = propsBuilder_.build(); + } + if (((from_bitField0_ & 0x00000008) == 0x00000008)) { + to_bitField0_ |= 0x00000004; + } + result.threadId_ = threadId_; + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof TransactionBegin) { + return mergeFrom((TransactionBegin)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(TransactionBegin other) { + if (other == TransactionBegin.getDefaultInstance()) return this; + if (other.hasExecuteTime()) { + setExecuteTime(other.getExecuteTime()); + } + if (other.hasTransactionId()) { + bitField0_ |= 0x00000002; + transactionId_ = other.transactionId_; + onChanged(); + } + if (propsBuilder_ == null) { + if (!other.props_.isEmpty()) { + if (props_.isEmpty()) { + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000004); + } else { + ensurePropsIsMutable(); + props_.addAll(other.props_); + } + onChanged(); + } + } else { + if (!other.props_.isEmpty()) { + if (propsBuilder_.isEmpty()) { + propsBuilder_.dispose(); + propsBuilder_ = null; + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000004); + propsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getPropsFieldBuilder() : null; + } else { + propsBuilder_.addAllMessages(other.props_); + } + } + } + if (other.hasThreadId()) { + setThreadId(other.getThreadId()); + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + TransactionBegin parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (TransactionBegin) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private long executeTime_ ; + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public boolean hasExecuteTime() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public long getExecuteTime() { + return executeTime_; + } + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public Builder setExecuteTime(long value) { + bitField0_ |= 0x00000001; + executeTime_ = value; + onChanged(); + return this; + } + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public Builder clearExecuteTime() { + bitField0_ = (bitField0_ & ~0x00000001); + executeTime_ = 0L; + onChanged(); + return this; + } + + private Object transactionId_ = ""; + /** + * optional string transactionId = 2; + * + *
      +       **已废弃,Begin里不提供事务id*
      +       * 
      + */ + public boolean hasTransactionId() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string transactionId = 2; + * + *
      +       **已废弃,Begin里不提供事务id*
      +       * 
      + */ + public String getTransactionId() { + Object ref = transactionId_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + transactionId_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string transactionId = 2; + * + *
      +       **已废弃,Begin里不提供事务id*
      +       * 
      + */ + public com.google.protobuf.ByteString + getTransactionIdBytes() { + Object ref = transactionId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + transactionId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string transactionId = 2; + * + *
      +       **已废弃,Begin里不提供事务id*
      +       * 
      + */ + public Builder setTransactionId( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + transactionId_ = value; + onChanged(); + return this; + } + /** + * optional string transactionId = 2; + * + *
      +       **已废弃,Begin里不提供事务id*
      +       * 
      + */ + public Builder clearTransactionId() { + bitField0_ = (bitField0_ & ~0x00000002); + transactionId_ = getDefaultInstance().getTransactionId(); + onChanged(); + return this; + } + /** + * optional string transactionId = 2; + * + *
      +       **已废弃,Begin里不提供事务id*
      +       * 
      + */ + public Builder setTransactionIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + transactionId_ = value; + onChanged(); + return this; + } + + private java.util.List props_ = + java.util.Collections.emptyList(); + private void ensurePropsIsMutable() { + if (!((bitField0_ & 0x00000004) == 0x00000004)) { + props_ = new java.util.ArrayList(props_); + bitField0_ |= 0x00000004; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> propsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List getPropsList() { + if (propsBuilder_ == null) { + return java.util.Collections.unmodifiableList(props_); + } else { + return propsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public int getPropsCount() { + if (propsBuilder_ == null) { + return props_.size(); + } else { + return propsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair getProps(int index) { + if (propsBuilder_ == null) { + return props_.get(index); + } else { + return propsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.set(index, value); + onChanged(); + } else { + propsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.set(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps(Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(value); + onChanged(); + } else { + propsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(index, value); + onChanged(); + } else { + propsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addAllProps( + Iterable values) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, props_); + onChanged(); + } else { + propsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder clearProps() { + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000004); + onChanged(); + } else { + propsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder removeProps(int index) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.remove(index); + onChanged(); + } else { + propsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder getPropsBuilder( + int index) { + return getPropsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + if (propsBuilder_ == null) { + return props_.get(index); } else { + return propsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsOrBuilderList() { + if (propsBuilder_ != null) { + return propsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(props_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder() { + return getPropsFieldBuilder().addBuilder( + Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder( + int index) { + return getPropsFieldBuilder().addBuilder( + index, Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsBuilderList() { + return getPropsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> + getPropsFieldBuilder() { + if (propsBuilder_ == null) { + propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder>( + props_, + ((bitField0_ & 0x00000004) == 0x00000004), + getParentForChildren(), + isClean()); + props_ = null; + } + return propsBuilder_; + } + + private long threadId_ ; + /** + * optional int64 threadId = 4; + * + *
      +       **执行的thread Id*
      +       * 
      + */ + public boolean hasThreadId() { + return ((bitField0_ & 0x00000008) == 0x00000008); + } + /** + * optional int64 threadId = 4; + * + *
      +       **执行的thread Id*
      +       * 
      + */ + public long getThreadId() { + return threadId_; + } + /** + * optional int64 threadId = 4; + * + *
      +       **执行的thread Id*
      +       * 
      + */ + public Builder setThreadId(long value) { + bitField0_ |= 0x00000008; + threadId_ = value; + onChanged(); + return this; + } + /** + * optional int64 threadId = 4; + * + *
      +       **执行的thread Id*
      +       * 
      + */ + public Builder clearThreadId() { + bitField0_ = (bitField0_ & ~0x00000008); + threadId_ = 0L; + onChanged(); + return this; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.TransactionBegin) } - public interface TransactionEndOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.TransactionEnd) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - boolean hasExecuteTime(); - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - long getExecuteTime(); - - /** - * optional string transactionId = 2; - * - *
      -         * *事务号*
      -         * 
      - */ - boolean hasTransactionId(); - - /** - * optional string transactionId = 2; - * - *
      -         * *事务号*
      -         * 
      - */ - java.lang.String getTransactionId(); - - /** - * optional string transactionId = 2; - * - *
      -         * *事务号*
      -         * 
      - */ - com.google.protobuf.ByteString getTransactionIdBytes(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - int getPropsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - java.util.List getPropsOrBuilderList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index); + static { + defaultInstance = new TransactionBegin(true); + defaultInstance.initFields(); } + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.TransactionBegin) + } + + public interface TransactionEndOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.TransactionEnd) + com.google.protobuf.MessageOrBuilder { + + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + boolean hasExecuteTime(); + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + long getExecuteTime(); + + /** + * optional string transactionId = 2; + * + *
      +     **事务号*
      +     * 
      + */ + boolean hasTransactionId(); + /** + * optional string transactionId = 2; + * + *
      +     **事务号*
      +     * 
      + */ + String getTransactionId(); + /** + * optional string transactionId = 2; + * + *
      +     **事务号*
      +     * 
      + */ + com.google.protobuf.ByteString + getTransactionIdBytes(); + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + Pair getProps(int index); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + int getPropsCount(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + java.util.List + getPropsOrBuilderList(); + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + PairOrBuilder getPropsOrBuilder(int index); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.TransactionEnd} + * + *
      +   **结束事务的一些信息*
      +   * 
      + */ + public static final class TransactionEnd extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.TransactionEnd) + TransactionEndOrBuilder { + // Use TransactionEnd.newBuilder() to construct. + private TransactionEnd(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private TransactionEnd(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final TransactionEnd defaultInstance; + public static TransactionEnd getDefaultInstance() { + return defaultInstance; + } + + public TransactionEnd getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private TransactionEnd( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 8: { + bitField0_ |= 0x00000001; + executeTime_ = input.readInt64(); + break; + } + case 18: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000002; + transactionId_ = bs; + break; + } + case 26: { + if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { + props_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000004; + } + props_.add(input.readMessage(Pair.PARSER, extensionRegistry)); + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + if (((mutable_bitField0_ & 0x00000004) == 0x00000004)) { + props_ = java.util.Collections.unmodifiableList(props_); + } + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable + .ensureFieldAccessorsInitialized( + TransactionEnd.class, Builder.class); + } + + public static com.google.protobuf.Parser PARSER = + new com.google.protobuf.AbstractParser() { + public TransactionEnd parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new TransactionEnd(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + private int bitField0_; + public static final int EXECUTETIME_FIELD_NUMBER = 1; + private long executeTime_; + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + public boolean hasExecuteTime() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int64 executeTime = 1; + * + *
      +     **已废弃,请使用header里的executeTime*
      +     * 
      + */ + public long getExecuteTime() { + return executeTime_; + } + + public static final int TRANSACTIONID_FIELD_NUMBER = 2; + private Object transactionId_; + /** + * optional string transactionId = 2; + * + *
      +     **事务号*
      +     * 
      + */ + public boolean hasTransactionId() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string transactionId = 2; + * + *
      +     **事务号*
      +     * 
      + */ + public String getTransactionId() { + Object ref = transactionId_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + transactionId_ = s; + } + return s; + } + } + /** + * optional string transactionId = 2; + * + *
      +     **事务号*
      +     * 
      + */ + public com.google.protobuf.ByteString + getTransactionIdBytes() { + Object ref = transactionId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + transactionId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int PROPS_FIELD_NUMBER = 3; + private java.util.List props_; + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List getPropsList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public java.util.List + getPropsOrBuilderList() { + return props_; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public int getPropsCount() { + return props_.size(); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public Pair getProps(int index) { + return props_.get(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +     **预留扩展*
      +     * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + return props_.get(index); + } + + private void initFields() { + executeTime_ = 0L; + transactionId_ = ""; + props_ = java.util.Collections.emptyList(); + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + if (((bitField0_ & 0x00000001) == 0x00000001)) { + output.writeInt64(1, executeTime_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + output.writeBytes(2, getTransactionIdBytes()); + } + for (int i = 0; i < props_.size(); i++) { + output.writeMessage(3, props_.get(i)); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(1, executeTime_); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(2, getTransactionIdBytes()); + } + for (int i = 0; i < props_.size(); i++) { + size += com.google.protobuf.CodedOutputStream + .computeMessageSize(3, props_.get(i)); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static TransactionEnd parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static TransactionEnd parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static TransactionEnd parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static TransactionEnd parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static TransactionEnd parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static TransactionEnd parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static TransactionEnd parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static TransactionEnd parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static TransactionEnd parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static TransactionEnd parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(TransactionEnd prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.TransactionEnd} * *
      -     * *结束事务的一些信息*
      +     **结束事务的一些信息*
            * 
      */ - public static final class TransactionEnd extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.TransactionEnd) - TransactionEndOrBuilder { - - // Use TransactionEnd.newBuilder() to construct. - private TransactionEnd(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private TransactionEnd(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final TransactionEnd defaultInstance; - - public static TransactionEnd getDefaultInstance() { - return defaultInstance; - } - - public TransactionEnd getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private TransactionEnd(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - executeTime_ = input.readInt64(); - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - transactionId_ = bs; - break; - } - case 26: { - if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - props_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000004; - } - props_.add(input.readMessage(com.alibaba.otter.canal.protocol.CanalEntry.Pair.PARSER, - extensionRegistry)); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - props_ = java.util.Collections.unmodifiableList(props_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.class, - com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public TransactionEnd parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new TransactionEnd(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int EXECUTETIME_FIELD_NUMBER = 1; - private long executeTime_; - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - public boolean hasExecuteTime() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 executeTime = 1; - * - *
      -         * *已废弃,请使用header里的executeTime*
      -         * 
      - */ - public long getExecuteTime() { - return executeTime_; - } - - public static final int TRANSACTIONID_FIELD_NUMBER = 2; - private java.lang.Object transactionId_; - - /** - * optional string transactionId = 2; - * - *
      -         * *事务号*
      -         * 
      - */ - public boolean hasTransactionId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string transactionId = 2; - * - *
      -         * *事务号*
      -         * 
      - */ - public java.lang.String getTransactionId() { - java.lang.Object ref = transactionId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - transactionId_ = s; - } - return s; - } - } - - /** - * optional string transactionId = 2; - * - *
      -         * *事务号*
      -         * 
      - */ - public com.google.protobuf.ByteString getTransactionIdBytes() { - java.lang.Object ref = transactionId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - transactionId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int PROPS_FIELD_NUMBER = 3; - private java.util.List props_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public java.util.List getPropsOrBuilderList() { - return props_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public int getPropsCount() { - return props_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - return props_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -         * *预留扩展*
      -         * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - return props_.get(index); - } - - private void initFields() { - executeTime_ = 0L; - transactionId_ = ""; - props_ = java.util.Collections.emptyList(); - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt64(1, executeTime_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getTransactionIdBytes()); - } - for (int i = 0; i < props_.size(); i++) { - output.writeMessage(3, props_.get(i)); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(1, executeTime_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getTransactionIdBytes()); - } - for (int i = 0; i < props_.size(); i++) { - size += com.google.protobuf.CodedOutputStream.computeMessageSize(3, props_.get(i)); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.TransactionEnd} - * - *
      -         * *结束事务的一些信息*
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.TransactionEnd) - com.alibaba.otter.canal.protocol.CanalEntry.TransactionEndOrBuilder { + TransactionEndOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; - } + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable + .ensureFieldAccessorsInitialized( + TransactionEnd.class, Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.class, - com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - getPropsFieldBuilder(); - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - executeTime_ = 0L; - bitField0_ = (bitField0_ & ~0x00000001); - transactionId_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - } else { - propsBuilder_.clear(); - } - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd build() { - com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd result = new com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.executeTime_ = executeTime_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.transactionId_ = transactionId_; - if (propsBuilder_ == null) { - if (((bitField0_ & 0x00000004) == 0x00000004)) { - props_ = java.util.Collections.unmodifiableList(props_); - bitField0_ = (bitField0_ & ~0x00000004); - } - result.props_ = props_; - } else { - result.props_ = propsBuilder_.build(); - } - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd.getDefaultInstance()) return this; - if (other.hasExecuteTime()) { - setExecuteTime(other.getExecuteTime()); - } - if (other.hasTransactionId()) { - bitField0_ |= 0x00000002; - transactionId_ = other.transactionId_; - onChanged(); - } - if (propsBuilder_ == null) { - if (!other.props_.isEmpty()) { - if (props_.isEmpty()) { - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000004); - } else { - ensurePropsIsMutable(); - props_.addAll(other.props_); - } - onChanged(); - } - } else { - if (!other.props_.isEmpty()) { - if (propsBuilder_.isEmpty()) { - propsBuilder_.dispose(); - propsBuilder_ = null; - props_ = other.props_; - bitField0_ = (bitField0_ & ~0x00000004); - propsBuilder_ = com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? getPropsFieldBuilder() : null; - } else { - propsBuilder_.addAllMessages(other.props_); - } - } - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.TransactionEnd) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private long executeTime_; - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public boolean hasExecuteTime() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public long getExecuteTime() { - return executeTime_; - } - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public Builder setExecuteTime(long value) { - bitField0_ |= 0x00000001; - executeTime_ = value; - onChanged(); - return this; - } - - /** - * optional int64 executeTime = 1; - * - *
      -             * *已废弃,请使用header里的executeTime*
      -             * 
      - */ - public Builder clearExecuteTime() { - bitField0_ = (bitField0_ & ~0x00000001); - executeTime_ = 0L; - onChanged(); - return this; - } - - private java.lang.Object transactionId_ = ""; - - /** - * optional string transactionId = 2; - * - *
      -             * *事务号*
      -             * 
      - */ - public boolean hasTransactionId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string transactionId = 2; - * - *
      -             * *事务号*
      -             * 
      - */ - public java.lang.String getTransactionId() { - java.lang.Object ref = transactionId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - transactionId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string transactionId = 2; - * - *
      -             * *事务号*
      -             * 
      - */ - public com.google.protobuf.ByteString getTransactionIdBytes() { - java.lang.Object ref = transactionId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - transactionId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string transactionId = 2; - * - *
      -             * *事务号*
      -             * 
      - */ - public Builder setTransactionId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - transactionId_ = value; - onChanged(); - return this; - } - - /** - * optional string transactionId = 2; - * - *
      -             * *事务号*
      -             * 
      - */ - public Builder clearTransactionId() { - bitField0_ = (bitField0_ & ~0x00000002); - transactionId_ = getDefaultInstance().getTransactionId(); - onChanged(); - return this; - } - - /** - * optional string transactionId = 2; - * - *
      -             * *事务号*
      -             * 
      - */ - public Builder setTransactionIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - transactionId_ = value; - onChanged(); - return this; - } - - private java.util.List props_ = java.util.Collections.emptyList(); - - private void ensurePropsIsMutable() { - if (!((bitField0_ & 0x00000004) == 0x00000004)) { - props_ = new java.util.ArrayList(props_); - bitField0_ |= 0x00000004; - } - } - - private com.google.protobuf.RepeatedFieldBuilder propsBuilder_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsList() { - if (propsBuilder_ == null) { - return java.util.Collections.unmodifiableList(props_); - } else { - return propsBuilder_.getMessageList(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public int getPropsCount() { - if (propsBuilder_ == null) { - return props_.size(); - } else { - return propsBuilder_.getCount(); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getProps(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessage(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.set(index, value); - onChanged(); - } else { - propsBuilder_.setMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder setProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.set(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.setMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(value); - onChanged(); - } else { - propsBuilder_.addMessage(value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair value) { - if (propsBuilder_ == null) { - if (value == null) { - throw new NullPointerException(); - } - ensurePropsIsMutable(); - props_.add(index, value); - onChanged(); - } else { - propsBuilder_.addMessage(index, value); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addProps(int index, com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder builderForValue) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.add(index, builderForValue.build()); - onChanged(); - } else { - propsBuilder_.addMessage(index, builderForValue.build()); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder addAllProps(java.lang.Iterable values) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, props_); - onChanged(); - } else { - propsBuilder_.addAllMessages(values); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder clearProps() { - if (propsBuilder_ == null) { - props_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - onChanged(); - } else { - propsBuilder_.clear(); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public Builder removeProps(int index) { - if (propsBuilder_ == null) { - ensurePropsIsMutable(); - props_.remove(index); - onChanged(); - } else { - propsBuilder_.remove(index); - } - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder getPropsBuilder(int index) { - return getPropsFieldBuilder().getBuilder(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder getPropsOrBuilder(int index) { - if (propsBuilder_ == null) { - return props_.get(index); - } else { - return propsBuilder_.getMessageOrBuilder(index); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsOrBuilderList() { - if (propsBuilder_ != null) { - return propsBuilder_.getMessageOrBuilderList(); - } else { - return java.util.Collections.unmodifiableList(props_); - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder() { - return getPropsFieldBuilder().addBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder addPropsBuilder(int index) { - return getPropsFieldBuilder().addBuilder(index, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; - * - *
      -             * *预留扩展*
      -             * 
      - */ - public java.util.List getPropsBuilderList() { - return getPropsFieldBuilder().getBuilderList(); - } - - private com.google.protobuf.RepeatedFieldBuilder getPropsFieldBuilder() { - if (propsBuilder_ == null) { - propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder(props_, - ((bitField0_ & 0x00000004) == 0x00000004), - getParentForChildren(), - isClean()); - props_ = null; - } - return propsBuilder_; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.TransactionEnd) + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { + getPropsFieldBuilder(); } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new TransactionEnd(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + executeTime_ = 0L; + bitField0_ = (bitField0_ & ~0x00000001); + transactionId_ = ""; + bitField0_ = (bitField0_ & ~0x00000002); + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000004); + } else { + propsBuilder_.clear(); } + return this; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.TransactionEnd) + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; + } + + public TransactionEnd getDefaultInstanceForType() { + return TransactionEnd.getDefaultInstance(); + } + + public TransactionEnd build() { + TransactionEnd result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); + } + return result; + } + + public TransactionEnd buildPartial() { + TransactionEnd result = new TransactionEnd(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + if (((from_bitField0_ & 0x00000001) == 0x00000001)) { + to_bitField0_ |= 0x00000001; + } + result.executeTime_ = executeTime_; + if (((from_bitField0_ & 0x00000002) == 0x00000002)) { + to_bitField0_ |= 0x00000002; + } + result.transactionId_ = transactionId_; + if (propsBuilder_ == null) { + if (((bitField0_ & 0x00000004) == 0x00000004)) { + props_ = java.util.Collections.unmodifiableList(props_); + bitField0_ = (bitField0_ & ~0x00000004); + } + result.props_ = props_; + } else { + result.props_ = propsBuilder_.build(); + } + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof TransactionEnd) { + return mergeFrom((TransactionEnd)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(TransactionEnd other) { + if (other == TransactionEnd.getDefaultInstance()) return this; + if (other.hasExecuteTime()) { + setExecuteTime(other.getExecuteTime()); + } + if (other.hasTransactionId()) { + bitField0_ |= 0x00000002; + transactionId_ = other.transactionId_; + onChanged(); + } + if (propsBuilder_ == null) { + if (!other.props_.isEmpty()) { + if (props_.isEmpty()) { + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000004); + } else { + ensurePropsIsMutable(); + props_.addAll(other.props_); + } + onChanged(); + } + } else { + if (!other.props_.isEmpty()) { + if (propsBuilder_.isEmpty()) { + propsBuilder_.dispose(); + propsBuilder_ = null; + props_ = other.props_; + bitField0_ = (bitField0_ & ~0x00000004); + propsBuilder_ = + com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders ? + getPropsFieldBuilder() : null; + } else { + propsBuilder_.addAllMessages(other.props_); + } + } + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + TransactionEnd parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (TransactionEnd) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private long executeTime_ ; + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public boolean hasExecuteTime() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public long getExecuteTime() { + return executeTime_; + } + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public Builder setExecuteTime(long value) { + bitField0_ |= 0x00000001; + executeTime_ = value; + onChanged(); + return this; + } + /** + * optional int64 executeTime = 1; + * + *
      +       **已废弃,请使用header里的executeTime*
      +       * 
      + */ + public Builder clearExecuteTime() { + bitField0_ = (bitField0_ & ~0x00000001); + executeTime_ = 0L; + onChanged(); + return this; + } + + private Object transactionId_ = ""; + /** + * optional string transactionId = 2; + * + *
      +       **事务号*
      +       * 
      + */ + public boolean hasTransactionId() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string transactionId = 2; + * + *
      +       **事务号*
      +       * 
      + */ + public String getTransactionId() { + Object ref = transactionId_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + transactionId_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string transactionId = 2; + * + *
      +       **事务号*
      +       * 
      + */ + public com.google.protobuf.ByteString + getTransactionIdBytes() { + Object ref = transactionId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + transactionId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string transactionId = 2; + * + *
      +       **事务号*
      +       * 
      + */ + public Builder setTransactionId( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + transactionId_ = value; + onChanged(); + return this; + } + /** + * optional string transactionId = 2; + * + *
      +       **事务号*
      +       * 
      + */ + public Builder clearTransactionId() { + bitField0_ = (bitField0_ & ~0x00000002); + transactionId_ = getDefaultInstance().getTransactionId(); + onChanged(); + return this; + } + /** + * optional string transactionId = 2; + * + *
      +       **事务号*
      +       * 
      + */ + public Builder setTransactionIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + transactionId_ = value; + onChanged(); + return this; + } + + private java.util.List props_ = + java.util.Collections.emptyList(); + private void ensurePropsIsMutable() { + if (!((bitField0_ & 0x00000004) == 0x00000004)) { + props_ = new java.util.ArrayList(props_); + bitField0_ |= 0x00000004; + } + } + + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> propsBuilder_; + + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List getPropsList() { + if (propsBuilder_ == null) { + return java.util.Collections.unmodifiableList(props_); + } else { + return propsBuilder_.getMessageList(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public int getPropsCount() { + if (propsBuilder_ == null) { + return props_.size(); + } else { + return propsBuilder_.getCount(); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair getProps(int index) { + if (propsBuilder_ == null) { + return props_.get(index); + } else { + return propsBuilder_.getMessage(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.set(index, value); + onChanged(); + } else { + propsBuilder_.setMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder setProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.set(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.setMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps(Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(value); + onChanged(); + } else { + propsBuilder_.addMessage(value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair value) { + if (propsBuilder_ == null) { + if (value == null) { + throw new NullPointerException(); + } + ensurePropsIsMutable(); + props_.add(index, value); + onChanged(); + } else { + propsBuilder_.addMessage(index, value); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addProps( + int index, Pair.Builder builderForValue) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.add(index, builderForValue.build()); + onChanged(); + } else { + propsBuilder_.addMessage(index, builderForValue.build()); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder addAllProps( + Iterable values) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, props_); + onChanged(); + } else { + propsBuilder_.addAllMessages(values); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder clearProps() { + if (propsBuilder_ == null) { + props_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000004); + onChanged(); + } else { + propsBuilder_.clear(); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Builder removeProps(int index) { + if (propsBuilder_ == null) { + ensurePropsIsMutable(); + props_.remove(index); + onChanged(); + } else { + propsBuilder_.remove(index); + } + return this; + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder getPropsBuilder( + int index) { + return getPropsFieldBuilder().getBuilder(index); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public PairOrBuilder getPropsOrBuilder( + int index) { + if (propsBuilder_ == null) { + return props_.get(index); } else { + return propsBuilder_.getMessageOrBuilder(index); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsOrBuilderList() { + if (propsBuilder_ != null) { + return propsBuilder_.getMessageOrBuilderList(); + } else { + return java.util.Collections.unmodifiableList(props_); + } + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder() { + return getPropsFieldBuilder().addBuilder( + Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public Pair.Builder addPropsBuilder( + int index) { + return getPropsFieldBuilder().addBuilder( + index, Pair.getDefaultInstance()); + } + /** + * repeated .com.alibaba.otter.canal.protocol.Pair props = 3; + * + *
      +       **预留扩展*
      +       * 
      + */ + public java.util.List + getPropsBuilderList() { + return getPropsFieldBuilder().getBuilderList(); + } + private com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder> + getPropsFieldBuilder() { + if (propsBuilder_ == null) { + propsBuilder_ = new com.google.protobuf.RepeatedFieldBuilder< + Pair, Pair.Builder, PairOrBuilder>( + props_, + ((bitField0_ & 0x00000004) == 0x00000004), + getParentForChildren(), + isClean()); + props_ = null; + } + return propsBuilder_; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.TransactionEnd) } - public interface PairOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Pair) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string key = 1; - */ - boolean hasKey(); - - /** - * optional string key = 1; - */ - java.lang.String getKey(); - - /** - * optional string key = 1; - */ - com.google.protobuf.ByteString getKeyBytes(); - - /** - * optional string value = 2; - */ - boolean hasValue(); - - /** - * optional string value = 2; - */ - java.lang.String getValue(); - - /** - * optional string value = 2; - */ - com.google.protobuf.ByteString getValueBytes(); + static { + defaultInstance = new TransactionEnd(true); + defaultInstance.initFields(); } + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.TransactionEnd) + } + + public interface PairOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Pair) + com.google.protobuf.MessageOrBuilder { + + /** + * optional string key = 1; + */ + boolean hasKey(); + /** + * optional string key = 1; + */ + String getKey(); + /** + * optional string key = 1; + */ + com.google.protobuf.ByteString + getKeyBytes(); + + /** + * optional string value = 2; + */ + boolean hasValue(); + /** + * optional string value = 2; + */ + String getValue(); + /** + * optional string value = 2; + */ + com.google.protobuf.ByteString + getValueBytes(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.Pair} + * + *
      +   **预留扩展*
      +   * 
      + */ + public static final class Pair extends + com.google.protobuf.GeneratedMessage implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Pair) + PairOrBuilder { + // Use Pair.newBuilder() to construct. + private Pair(com.google.protobuf.GeneratedMessage.Builder builder) { + super(builder); + this.unknownFields = builder.getUnknownFields(); + } + private Pair(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); } + + private static final Pair defaultInstance; + public static Pair getDefaultInstance() { + return defaultInstance; + } + + public Pair getDefaultInstanceForType() { + return defaultInstance; + } + + private final com.google.protobuf.UnknownFieldSet unknownFields; + @Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Pair( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + initFields(); + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + default: { + if (!parseUnknownField(input, unknownFields, + extensionRegistry, tag)) { + done = true; + } + break; + } + case 10: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000001; + key_ = bs; + break; + } + case 18: { + com.google.protobuf.ByteString bs = input.readBytes(); + bitField0_ |= 0x00000002; + value_ = bs; + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e.getMessage()).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; + } + + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Pair.class, Builder.class); + } + + public static com.google.protobuf.Parser PARSER = + new com.google.protobuf.AbstractParser() { + public Pair parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Pair(input, extensionRegistry); + } + }; + + @Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + private int bitField0_; + public static final int KEY_FIELD_NUMBER = 1; + private Object key_; + /** + * optional string key = 1; + */ + public boolean hasKey() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional string key = 1; + */ + public String getKey() { + Object ref = key_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + key_ = s; + } + return s; + } + } + /** + * optional string key = 1; + */ + public com.google.protobuf.ByteString + getKeyBytes() { + Object ref = key_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + key_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int VALUE_FIELD_NUMBER = 2; + private Object value_; + /** + * optional string value = 2; + */ + public boolean hasValue() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string value = 2; + */ + public String getValue() { + Object ref = value_; + if (ref instanceof String) { + return (String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + value_ = s; + } + return s; + } + } + /** + * optional string value = 2; + */ + public com.google.protobuf.ByteString + getValueBytes() { + Object ref = value_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + value_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + private void initFields() { + key_ = ""; + value_ = ""; + } + private byte memoizedIsInitialized = -1; + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + getSerializedSize(); + if (((bitField0_ & 0x00000001) == 0x00000001)) { + output.writeBytes(1, getKeyBytes()); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + output.writeBytes(2, getValueBytes()); + } + getUnknownFields().writeTo(output); + } + + private int memoizedSerializedSize = -1; + public int getSerializedSize() { + int size = memoizedSerializedSize; + if (size != -1) return size; + + size = 0; + if (((bitField0_ & 0x00000001) == 0x00000001)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(1, getKeyBytes()); + } + if (((bitField0_ & 0x00000002) == 0x00000002)) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(2, getValueBytes()); + } + size += getUnknownFields().getSerializedSize(); + memoizedSerializedSize = size; + return size; + } + + private static final long serialVersionUID = 0L; + @Override + protected Object writeReplace() + throws java.io.ObjectStreamException { + return super.writeReplace(); + } + + public static Pair parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Pair parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Pair parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static Pair parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static Pair parseFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Pair parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + public static Pair parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input); + } + public static Pair parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseDelimitedFrom(input, extensionRegistry); + } + public static Pair parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return PARSER.parseFrom(input); + } + public static Pair parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return PARSER.parseFrom(input, extensionRegistry); + } + + public static Builder newBuilder() { return Builder.create(); } + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder(Pair prototype) { + return newBuilder().mergeFrom(prototype); + } + public Builder toBuilder() { return newBuilder(this); } + + @Override + protected Builder newBuilderForType( + BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.Pair} * *
      -     * *预留扩展*
      +     **预留扩展*
            * 
      */ - public static final class Pair extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Pair) - PairOrBuilder { - - // Use Pair.newBuilder() to construct. - private Pair(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Pair(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Pair defaultInstance; - - public static Pair getDefaultInstance() { - return defaultInstance; - } - - public Pair getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Pair(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - key_ = bs; - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - value_ = bs; - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Pair.class, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Pair parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Pair(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int KEY_FIELD_NUMBER = 1; - private java.lang.Object key_; - - /** - * optional string key = 1; - */ - public boolean hasKey() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string key = 1; - */ - public java.lang.String getKey() { - java.lang.Object ref = key_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - key_ = s; - } - return s; - } - } - - /** - * optional string key = 1; - */ - public com.google.protobuf.ByteString getKeyBytes() { - java.lang.Object ref = key_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - key_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int VALUE_FIELD_NUMBER = 2; - private java.lang.Object value_; - - /** - * optional string value = 2; - */ - public boolean hasValue() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string value = 2; - */ - public java.lang.String getValue() { - java.lang.Object ref = value_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - value_ = s; - } - return s; - } - } - - /** - * optional string value = 2; - */ - public com.google.protobuf.ByteString getValueBytes() { - java.lang.Object ref = value_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - value_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - private void initFields() { - key_ = ""; - value_ = ""; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getKeyBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getValueBytes()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getKeyBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getValueBytes()); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalEntry.Pair parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalEntry.Pair prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Pair} - * - *
      -         * *预留扩展*
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessage.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Pair) - com.alibaba.otter.canal.protocol.CanalEntry.PairOrBuilder { + PairOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; - } + protected FieldAccessorTable + internalGetFieldAccessorTable() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable + .ensureFieldAccessorsInitialized( + Pair.class, Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalEntry.Pair.class, - com.alibaba.otter.canal.protocol.CanalEntry.Pair.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalEntry.Pair.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalEntry.Pair.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - key_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - value_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Pair getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Pair build() { - com.alibaba.otter.canal.protocol.CanalEntry.Pair result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalEntry.Pair buildPartial() { - com.alibaba.otter.canal.protocol.CanalEntry.Pair result = new com.alibaba.otter.canal.protocol.CanalEntry.Pair(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.key_ = key_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.value_ = value_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalEntry.Pair) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalEntry.Pair) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalEntry.Pair other) { - if (other == com.alibaba.otter.canal.protocol.CanalEntry.Pair.getDefaultInstance()) return this; - if (other.hasKey()) { - bitField0_ |= 0x00000001; - key_ = other.key_; - onChanged(); - } - if (other.hasValue()) { - bitField0_ |= 0x00000002; - value_ = other.value_; - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalEntry.Pair parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalEntry.Pair) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object key_ = ""; - - /** - * optional string key = 1; - */ - public boolean hasKey() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string key = 1; - */ - public java.lang.String getKey() { - java.lang.Object ref = key_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - key_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string key = 1; - */ - public com.google.protobuf.ByteString getKeyBytes() { - java.lang.Object ref = key_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - key_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string key = 1; - */ - public Builder setKey(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - key_ = value; - onChanged(); - return this; - } - - /** - * optional string key = 1; - */ - public Builder clearKey() { - bitField0_ = (bitField0_ & ~0x00000001); - key_ = getDefaultInstance().getKey(); - onChanged(); - return this; - } - - /** - * optional string key = 1; - */ - public Builder setKeyBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - key_ = value; - onChanged(); - return this; - } - - private java.lang.Object value_ = ""; - - /** - * optional string value = 2; - */ - public boolean hasValue() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string value = 2; - */ - public java.lang.String getValue() { - java.lang.Object ref = value_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - value_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string value = 2; - */ - public com.google.protobuf.ByteString getValueBytes() { - java.lang.Object ref = value_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - value_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string value = 2; - */ - public Builder setValue(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - value_ = value; - onChanged(); - return this; - } - - /** - * optional string value = 2; - */ - public Builder clearValue() { - bitField0_ = (bitField0_ & ~0x00000002); - value_ = getDefaultInstance().getValue(); - onChanged(); - return this; - } - - /** - * optional string value = 2; - */ - public Builder setValueBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - value_ = value; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Pair) + private Builder( + BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { } + } + private static Builder create() { + return new Builder(); + } - static { - defaultInstance = new Pair(true); - defaultInstance.initFields(); + public Builder clear() { + super.clear(); + key_ = ""; + bitField0_ = (bitField0_ & ~0x00000001); + value_ = ""; + bitField0_ = (bitField0_ & ~0x00000002); + return this; + } + + public Builder clone() { + return create().mergeFrom(buildPartial()); + } + + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return CanalEntry.internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; + } + + public Pair getDefaultInstanceForType() { + return Pair.getDefaultInstance(); + } + + public Pair build() { + Pair result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Pair) + public Pair buildPartial() { + Pair result = new Pair(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + if (((from_bitField0_ & 0x00000001) == 0x00000001)) { + to_bitField0_ |= 0x00000001; + } + result.key_ = key_; + if (((from_bitField0_ & 0x00000002) == 0x00000002)) { + to_bitField0_ |= 0x00000002; + } + result.value_ = value_; + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof Pair) { + return mergeFrom((Pair)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(Pair other) { + if (other == Pair.getDefaultInstance()) return this; + if (other.hasKey()) { + bitField0_ |= 0x00000001; + key_ = other.key_; + onChanged(); + } + if (other.hasValue()) { + bitField0_ |= 0x00000002; + value_ = other.value_; + onChanged(); + } + this.mergeUnknownFields(other.getUnknownFields()); + return this; + } + + public final boolean isInitialized() { + return true; + } + + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + Pair parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (Pair) e.getUnfinishedMessage(); + throw e; + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private Object key_ = ""; + /** + * optional string key = 1; + */ + public boolean hasKey() { + return ((bitField0_ & 0x00000001) == 0x00000001); + } + /** + * optional string key = 1; + */ + public String getKey() { + Object ref = key_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + key_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string key = 1; + */ + public com.google.protobuf.ByteString + getKeyBytes() { + Object ref = key_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + key_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string key = 1; + */ + public Builder setKey( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000001; + key_ = value; + onChanged(); + return this; + } + /** + * optional string key = 1; + */ + public Builder clearKey() { + bitField0_ = (bitField0_ & ~0x00000001); + key_ = getDefaultInstance().getKey(); + onChanged(); + return this; + } + /** + * optional string key = 1; + */ + public Builder setKeyBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000001; + key_ = value; + onChanged(); + return this; + } + + private Object value_ = ""; + /** + * optional string value = 2; + */ + public boolean hasValue() { + return ((bitField0_ & 0x00000002) == 0x00000002); + } + /** + * optional string value = 2; + */ + public String getValue() { + Object ref = value_; + if (!(ref instanceof String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + String s = bs.toStringUtf8(); + if (bs.isValidUtf8()) { + value_ = s; + } + return s; + } else { + return (String) ref; + } + } + /** + * optional string value = 2; + */ + public com.google.protobuf.ByteString + getValueBytes() { + Object ref = value_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (String) ref); + value_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * optional string value = 2; + */ + public Builder setValue( + String value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + value_ = value; + onChanged(); + return this; + } + /** + * optional string value = 2; + */ + public Builder clearValue() { + bitField0_ = (bitField0_ & ~0x00000002); + value_ = getDefaultInstance().getValue(); + onChanged(); + return this; + } + /** + * optional string value = 2; + */ + public Builder setValueBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + bitField0_ |= 0x00000002; + value_ = value; + onChanged(); + return this; + } + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Pair) } - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable; - - public static com.google.protobuf.Descriptors.FileDescriptor getDescriptor() { - return descriptor; - } - - private static com.google.protobuf.Descriptors.FileDescriptor descriptor; static { - java.lang.String[] descriptorData = { - "\n\023EntryProtocol.proto\022 com.alibaba.otter" - + ".canal.protocol\"\236\001\n\005Entry\0228\n\006header\030\001 \001(" - + "\0132(.com.alibaba.otter.canal.protocol.Hea" - + "der\022G\n\tentryType\030\002 \001(\0162+.com.alibaba.ott" - + "er.canal.protocol.EntryType:\007ROWDATA\022\022\n\n" - + "storeValue\030\003 \001(\014\"\221\003\n\006Header\022\022\n\007version\030\001" - + " \001(\005:\0011\022\023\n\013logfileName\030\002 \001(\t\022\025\n\rlogfileO" - + "ffset\030\003 \001(\003\022\020\n\010serverId\030\004 \001(\003\022\024\n\014servere" - + "nCode\030\005 \001(\t\022\023\n\013executeTime\030\006 \001(\003\022A\n\nsour" - + "ceType\030\007 \001(\0162&.com.alibaba.otter.canal.p", - "rotocol.Type:\005MYSQL\022\022\n\nschemaName\030\010 \001(\t\022" - + "\021\n\ttableName\030\t \001(\t\022\023\n\013eventLength\030\n \001(\003\022" - + "F\n\teventType\030\013 \001(\0162+.com.alibaba.otter.c" - + "anal.protocol.EventType:\006UPDATE\0225\n\005props" - + "\030\014 \003(\0132&.com.alibaba.otter.canal.protoco" - + "l.Pair\022\014\n\004gtid\030\r \001(\t\"\326\001\n\006Column\022\r\n\005index" - + "\030\001 \001(\005\022\017\n\007sqlType\030\002 \001(\005\022\014\n\004name\030\003 \001(\t\022\r\n" - + "\005isKey\030\004 \001(\010\022\017\n\007updated\030\005 \001(\010\022\025\n\006isNull\030" - + "\006 \001(\010:\005false\0225\n\005props\030\007 \003(\0132&.com.alibab" - + "a.otter.canal.protocol.Pair\022\r\n\005value\030\010 \001", - "(\t\022\016\n\006length\030\t \001(\005\022\021\n\tmysqlType\030\n \001(\t\"\301\001" - + "\n\007RowData\022?\n\rbeforeColumns\030\001 \003(\0132(.com.a" - + "libaba.otter.canal.protocol.Column\022>\n\014af" - + "terColumns\030\002 \003(\0132(.com.alibaba.otter.can" - + "al.protocol.Column\0225\n\005props\030\003 \003(\0132&.com." - + "alibaba.otter.canal.protocol.Pair\"\222\002\n\tRo" - + "wChange\022\017\n\007tableId\030\001 \001(\003\022F\n\teventType\030\002 " - + "\001(\0162+.com.alibaba.otter.canal.protocol.E" - + "ventType:\006UPDATE\022\024\n\005isDdl\030\n \001(\010:\005false\022\013" - + "\n\003sql\030\013 \001(\t\022;\n\010rowDatas\030\014 \003(\0132).com.alib", - "aba.otter.canal.protocol.RowData\0225\n\005prop" + "s\030\r \003(\0132&.com.alibaba.otter.canal.protoc" - + "ol.Pair\022\025\n\rddlSchemaName\030\016 \001(\t\"\207\001\n\020Trans" - + "actionBegin\022\023\n\013executeTime\030\001 \001(\003\022\025\n\rtran" - + "sactionId\030\002 \001(\t\0225\n\005props\030\003 \003(\0132&.com.ali" - + "baba.otter.canal.protocol.Pair\022\020\n\010thread" - + "Id\030\004 \001(\003\"s\n\016TransactionEnd\022\023\n\013executeTim" - + "e\030\001 \001(\003\022\025\n\rtransactionId\030\002 \001(\t\0225\n\005props\030" - + "\003 \003(\0132&.com.alibaba.otter.canal.protocol" - + ".Pair\"\"\n\004Pair\022\013\n\003key\030\001 \001(\t\022\r\n\005value\030\002 \001(", - "\t*^\n\tEntryType\022\024\n\020TRANSACTIONBEGIN\020\001\022\013\n\007" - + "ROWDATA\020\002\022\022\n\016TRANSACTIONEND\020\003\022\r\n\tHEARTBE" - + "AT\020\004\022\013\n\007GTIDLOG\020\005*\316\001\n\tEventType\022\n\n\006INSER" - + "T\020\001\022\n\n\006UPDATE\020\002\022\n\n\006DELETE\020\003\022\n\n\006CREATE\020\004\022" - + "\t\n\005ALTER\020\005\022\t\n\005ERASE\020\006\022\t\n\005QUERY\020\007\022\014\n\010TRUN" - + "CATE\020\010\022\n\n\006RENAME\020\t\022\n\n\006CINDEX\020\n\022\n\n\006DINDEX" - + "\020\013\022\010\n\004GTID\020\014\022\013\n\007XASTART\020\r\022\t\n\005XAEND\020\016\022\014\n\010" - + "XACOMMIT\020\017\022\016\n\nXAROLLBACK\020\020*(\n\004Type\022\n\n\006OR" - + "ACLE\020\001\022\t\n\005MYSQL\020\002\022\t\n\005PGSQL\020\003B0\n com.alib" - + "aba.otter.canal.protocolB\nCanalEntryH\001" }; - com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner = new com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner() { - - public com.google.protobuf.ExtensionRegistry assignDescriptors(com.google.protobuf.Descriptors.FileDescriptor root) { - descriptor = root; - return null; - } - }; - com.google.protobuf.Descriptors.FileDescriptor.internalBuildGeneratedFileFrom(descriptorData, - new com.google.protobuf.Descriptors.FileDescriptor[] {}, - assigner); - internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor = getDescriptor().getMessageTypes().get(0); - internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor, - new java.lang.String[] { "Header", "EntryType", "StoreValue", }); - internal_static_com_alibaba_otter_canal_protocol_Header_descriptor = getDescriptor().getMessageTypes().get(1); - internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Header_descriptor, - new java.lang.String[] { "Version", "LogfileName", "LogfileOffset", "ServerId", "ServerenCode", - "ExecuteTime", "SourceType", "SchemaName", "TableName", "EventLength", "EventType", "Props", "Gtid", }); - internal_static_com_alibaba_otter_canal_protocol_Column_descriptor = getDescriptor().getMessageTypes().get(2); - internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Column_descriptor, - new java.lang.String[] { "Index", "SqlType", "Name", "IsKey", "Updated", "IsNull", "Props", "Value", - "Length", "MysqlType", }); - internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor = getDescriptor().getMessageTypes().get(3); - internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor, - new java.lang.String[] { "BeforeColumns", "AfterColumns", "Props", }); - internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor = getDescriptor().getMessageTypes() - .get(4); - internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor, - new java.lang.String[] { "TableId", "EventType", "IsDdl", "Sql", "RowDatas", "Props", "DdlSchemaName", }); - internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor = getDescriptor().getMessageTypes() - .get(5); - internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor, - new java.lang.String[] { "ExecuteTime", "TransactionId", "Props", "ThreadId", }); - internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor = getDescriptor().getMessageTypes() - .get(6); - internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor, - new java.lang.String[] { "ExecuteTime", "TransactionId", "Props", }); - internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor = getDescriptor().getMessageTypes().get(7); - internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor, - new java.lang.String[] { "Key", "Value", }); + defaultInstance = new Pair(true); + defaultInstance.initFields(); } - // @@protoc_insertion_point(outer_class_scope) + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Pair) + } + + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Header_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Column_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor; + private static + com.google.protobuf.GeneratedMessage.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable; + + public static com.google.protobuf.Descriptors.FileDescriptor + getDescriptor() { + return descriptor; + } + private static com.google.protobuf.Descriptors.FileDescriptor + descriptor; + static { + String[] descriptorData = { + "\n\023EntryProtocol.proto\022 com.alibaba.otter" + + ".canal.protocol\"\236\001\n\005Entry\0228\n\006header\030\001 \001(" + + "\0132(.com.alibaba.otter.canal.protocol.Hea" + + "der\022G\n\tentryType\030\002 \001(\0162+.com.alibaba.ott" + + "er.canal.protocol.EntryType:\007ROWDATA\022\022\n\n" + + "storeValue\030\003 \001(\014\"\221\003\n\006Header\022\022\n\007version\030\001" + + " \001(\005:\0011\022\023\n\013logfileName\030\002 \001(\t\022\025\n\rlogfileO" + + "ffset\030\003 \001(\003\022\020\n\010serverId\030\004 \001(\003\022\024\n\014servere" + + "nCode\030\005 \001(\t\022\023\n\013executeTime\030\006 \001(\003\022A\n\nsour" + + "ceType\030\007 \001(\0162&.com.alibaba.otter.canal.p", + "rotocol.Type:\005MYSQL\022\022\n\nschemaName\030\010 \001(\t\022" + + "\021\n\ttableName\030\t \001(\t\022\023\n\013eventLength\030\n \001(\003\022" + + "F\n\teventType\030\013 \001(\0162+.com.alibaba.otter.c" + + "anal.protocol.EventType:\006UPDATE\0225\n\005props" + + "\030\014 \003(\0132&.com.alibaba.otter.canal.protoco" + + "l.Pair\022\014\n\004gtid\030\r \001(\t\"\326\001\n\006Column\022\r\n\005index" + + "\030\001 \001(\005\022\017\n\007sqlType\030\002 \001(\005\022\014\n\004name\030\003 \001(\t\022\r\n" + + "\005isKey\030\004 \001(\010\022\017\n\007updated\030\005 \001(\010\022\025\n\006isNull\030" + + "\006 \001(\010:\005false\0225\n\005props\030\007 \003(\0132&.com.alibab" + + "a.otter.canal.protocol.Pair\022\r\n\005value\030\010 \001", + "(\t\022\016\n\006length\030\t \001(\005\022\021\n\tmysqlType\030\n \001(\t\"\301\001" + + "\n\007RowData\022?\n\rbeforeColumns\030\001 \003(\0132(.com.a" + + "libaba.otter.canal.protocol.Column\022>\n\014af" + + "terColumns\030\002 \003(\0132(.com.alibaba.otter.can" + + "al.protocol.Column\0225\n\005props\030\003 \003(\0132&.com." + + "alibaba.otter.canal.protocol.Pair\"\222\002\n\tRo" + + "wChange\022\017\n\007tableId\030\001 \001(\003\022F\n\teventType\030\002 " + + "\001(\0162+.com.alibaba.otter.canal.protocol.E" + + "ventType:\006UPDATE\022\024\n\005isDdl\030\n \001(\010:\005false\022\013" + + "\n\003sql\030\013 \001(\t\022;\n\010rowDatas\030\014 \003(\0132).com.alib", + "aba.otter.canal.protocol.RowData\0225\n\005prop" + + "s\030\r \003(\0132&.com.alibaba.otter.canal.protoc" + + "ol.Pair\022\025\n\rddlSchemaName\030\016 \001(\t\"\207\001\n\020Trans" + + "actionBegin\022\023\n\013executeTime\030\001 \001(\003\022\025\n\rtran" + + "sactionId\030\002 \001(\t\0225\n\005props\030\003 \003(\0132&.com.ali" + + "baba.otter.canal.protocol.Pair\022\020\n\010thread" + + "Id\030\004 \001(\003\"s\n\016TransactionEnd\022\023\n\013executeTim" + + "e\030\001 \001(\003\022\025\n\rtransactionId\030\002 \001(\t\0225\n\005props\030" + + "\003 \003(\0132&.com.alibaba.otter.canal.protocol" + + ".Pair\"\"\n\004Pair\022\013\n\003key\030\001 \001(\t\022\r\n\005value\030\002 \001(", + "\t*^\n\tEntryType\022\024\n\020TRANSACTIONBEGIN\020\001\022\013\n\007" + + "ROWDATA\020\002\022\022\n\016TRANSACTIONEND\020\003\022\r\n\tHEARTBE" + + "AT\020\004\022\013\n\007GTIDLOG\020\005*\306\001\n\tEventType\022\n\n\006INSER" + + "T\020\001\022\n\n\006UPDATE\020\002\022\n\n\006DELETE\020\003\022\n\n\006CREATE\020\004\022" + + "\t\n\005ALTER\020\005\022\t\n\005ERASE\020\006\022\t\n\005QUERY\020\007\022\014\n\010TRUN" + + "CATE\020\010\022\n\n\006RENAME\020\t\022\n\n\006CINDEX\020\n\022\n\n\006DINDEX" + + "\020\013\022\010\n\004GTID\020\014\022\014\n\010XACOMMIT\020\r\022\016\n\nXAROLLBACK" + + "\020\016\022\016\n\nMHEARTBEAT\020\017*(\n\004Type\022\n\n\006ORACLE\020\001\022\t" + + "\n\005MYSQL\020\002\022\t\n\005PGSQL\020\003B0\n com.alibaba.otte" + + "r.canal.protocolB\nCanalEntryH\001" + }; + com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner = + new com.google.protobuf.Descriptors.FileDescriptor. InternalDescriptorAssigner() { + public com.google.protobuf.ExtensionRegistry assignDescriptors( + com.google.protobuf.Descriptors.FileDescriptor root) { + descriptor = root; + return null; + } + }; + com.google.protobuf.Descriptors.FileDescriptor + .internalBuildGeneratedFileFrom(descriptorData, + new com.google.protobuf.Descriptors.FileDescriptor[] { + }, assigner); + internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor = + getDescriptor().getMessageTypes().get(0); + internal_static_com_alibaba_otter_canal_protocol_Entry_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Entry_descriptor, + new String[] { "Header", "EntryType", "StoreValue", }); + internal_static_com_alibaba_otter_canal_protocol_Header_descriptor = + getDescriptor().getMessageTypes().get(1); + internal_static_com_alibaba_otter_canal_protocol_Header_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Header_descriptor, + new String[] { "Version", "LogfileName", "LogfileOffset", "ServerId", "ServerenCode", "ExecuteTime", "SourceType", "SchemaName", "TableName", "EventLength", "EventType", "Props", "Gtid", }); + internal_static_com_alibaba_otter_canal_protocol_Column_descriptor = + getDescriptor().getMessageTypes().get(2); + internal_static_com_alibaba_otter_canal_protocol_Column_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Column_descriptor, + new String[] { "Index", "SqlType", "Name", "IsKey", "Updated", "IsNull", "Props", "Value", "Length", "MysqlType", }); + internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor = + getDescriptor().getMessageTypes().get(3); + internal_static_com_alibaba_otter_canal_protocol_RowData_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_RowData_descriptor, + new String[] { "BeforeColumns", "AfterColumns", "Props", }); + internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor = + getDescriptor().getMessageTypes().get(4); + internal_static_com_alibaba_otter_canal_protocol_RowChange_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_RowChange_descriptor, + new String[] { "TableId", "EventType", "IsDdl", "Sql", "RowDatas", "Props", "DdlSchemaName", }); + internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor = + getDescriptor().getMessageTypes().get(5); + internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_TransactionBegin_descriptor, + new String[] { "ExecuteTime", "TransactionId", "Props", "ThreadId", }); + internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor = + getDescriptor().getMessageTypes().get(6); + internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_TransactionEnd_descriptor, + new String[] { "ExecuteTime", "TransactionId", "Props", }); + internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor = + getDescriptor().getMessageTypes().get(7); + internal_static_com_alibaba_otter_canal_protocol_Pair_fieldAccessorTable = new + com.google.protobuf.GeneratedMessage.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Pair_descriptor, + new String[] { "Key", "Value", }); + } + + // @@protoc_insertion_point(outer_class_scope) } diff --git a/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalPacket.java b/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalPacket.java index 3909668a..1e7e4e53 100644 --- a/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalPacket.java +++ b/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalPacket.java @@ -4,9847 +4,10990 @@ package com.alibaba.otter.canal.protocol; public final class CanalPacket { + private CanalPacket() {} + public static void registerAllExtensions( + com.google.protobuf.ExtensionRegistryLite registry) { + } - private CanalPacket(){ - } + public static void registerAllExtensions( + com.google.protobuf.ExtensionRegistry registry) { + registerAllExtensions( + (com.google.protobuf.ExtensionRegistryLite) registry); + } + /** + * Protobuf enum {@code com.alibaba.otter.canal.protocol.Compression} + */ + public enum Compression + implements com.google.protobuf.ProtocolMessageEnum { + /** + * COMPRESSIONCOMPATIBLEPROTO2 = 0; + */ + COMPRESSIONCOMPATIBLEPROTO2(0), + /** + * NONE = 1; + */ + NONE(1), + /** + * ZLIB = 2; + */ + ZLIB(2), + /** + * GZIP = 3; + */ + GZIP(3), + /** + * LZF = 4; + */ + LZF(4), + UNRECOGNIZED(-1), + ; - public static void registerAllExtensions(com.google.protobuf.ExtensionRegistry registry) { + /** + * COMPRESSIONCOMPATIBLEPROTO2 = 0; + */ + public static final int COMPRESSIONCOMPATIBLEPROTO2_VALUE = 0; + /** + * NONE = 1; + */ + public static final int NONE_VALUE = 1; + /** + * ZLIB = 2; + */ + public static final int ZLIB_VALUE = 2; + /** + * GZIP = 3; + */ + public static final int GZIP_VALUE = 3; + /** + * LZF = 4; + */ + public static final int LZF_VALUE = 4; + + + public final int getNumber() { + if (this == UNRECOGNIZED) { + throw new java.lang.IllegalArgumentException( + "Can't get the number of an unknown enum value."); + } + return value; } /** - * Protobuf enum {@code com.alibaba.otter.canal.protocol.Compression} + * @deprecated Use {@link #forNumber(int)} instead. */ - public enum Compression implements com.google.protobuf.ProtocolMessageEnum { - /** - * NONE = 1; - */ - NONE(0, 1), - /** - * ZLIB = 2; - */ - ZLIB(1, 2), - /** - * GZIP = 3; - */ - GZIP(2, 3), - /** - * LZF = 4; - */ - LZF(3, 4), ; + @java.lang.Deprecated + public static Compression valueOf(int value) { + return forNumber(value); + } - /** - * NONE = 1; - */ - public static final int NONE_VALUE = 1; - /** - * ZLIB = 2; - */ - public static final int ZLIB_VALUE = 2; - /** - * GZIP = 3; - */ - public static final int GZIP_VALUE = 3; - /** - * LZF = 4; - */ - public static final int LZF_VALUE = 4; + public static Compression forNumber(int value) { + switch (value) { + case 0: return COMPRESSIONCOMPATIBLEPROTO2; + case 1: return NONE; + case 2: return ZLIB; + case 3: return GZIP; + case 4: return LZF; + default: return null; + } + } - public final int getNumber() { - return value; - } - - public static Compression valueOf(int value) { - switch (value) { - case 1: - return NONE; - case 2: - return ZLIB; - case 3: - return GZIP; - case 4: - return LZF; - default: - return null; + public static com.google.protobuf.Internal.EnumLiteMap + internalGetValueMap() { + return internalValueMap; + } + private static final com.google.protobuf.Internal.EnumLiteMap< + Compression> internalValueMap = + new com.google.protobuf.Internal.EnumLiteMap() { + public Compression findValueByNumber(int number) { + return Compression.forNumber(number); } - } + }; - public static com.google.protobuf.Internal.EnumLiteMap internalGetValueMap() { - return internalValueMap; - } + public final com.google.protobuf.Descriptors.EnumValueDescriptor + getValueDescriptor() { + return getDescriptor().getValues().get(ordinal()); + } + public final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptorForType() { + return getDescriptor(); + } + public static final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.getDescriptor().getEnumTypes().get(0); + } - private static com.google.protobuf.Internal.EnumLiteMap internalValueMap = new com.google.protobuf.Internal.EnumLiteMap() { + private static final Compression[] VALUES = values(); - public Compression findValueByNumber(int number) { - return Compression.valueOf(number); - } - }; + public static Compression valueOf( + com.google.protobuf.Descriptors.EnumValueDescriptor desc) { + if (desc.getType() != getDescriptor()) { + throw new java.lang.IllegalArgumentException( + "EnumValueDescriptor is not for this type."); + } + if (desc.getIndex() == -1) { + return UNRECOGNIZED; + } + return VALUES[desc.getIndex()]; + } - public final com.google.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() { - return getDescriptor().getValues().get(index); - } + private final int value; - public final com.google.protobuf.Descriptors.EnumDescriptor getDescriptorForType() { - return getDescriptor(); - } + private Compression(int value) { + this.value = value; + } - public static final com.google.protobuf.Descriptors.EnumDescriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.getDescriptor().getEnumTypes().get(0); - } + // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.Compression) + } - private static final Compression[] VALUES = values(); + /** + * Protobuf enum {@code com.alibaba.otter.canal.protocol.PacketType} + */ + public enum PacketType + implements com.google.protobuf.ProtocolMessageEnum { + /** + *
      +     *compatible
      +     * 
      + * + * PACKAGETYPECOMPATIBLEPROTO2 = 0; + */ + PACKAGETYPECOMPATIBLEPROTO2(0), + /** + * HANDSHAKE = 1; + */ + HANDSHAKE(1), + /** + * CLIENTAUTHENTICATION = 2; + */ + CLIENTAUTHENTICATION(2), + /** + * ACK = 3; + */ + ACK(3), + /** + * SUBSCRIPTION = 4; + */ + SUBSCRIPTION(4), + /** + * UNSUBSCRIPTION = 5; + */ + UNSUBSCRIPTION(5), + /** + * GET = 6; + */ + GET(6), + /** + * MESSAGES = 7; + */ + MESSAGES(7), + /** + * CLIENTACK = 8; + */ + CLIENTACK(8), + /** + *
      +     * management part
      +     * 
      + * + * SHUTDOWN = 9; + */ + SHUTDOWN(9), + /** + *
      +     * integration
      +     * 
      + * + * DUMP = 10; + */ + DUMP(10), + /** + * HEARTBEAT = 11; + */ + HEARTBEAT(11), + /** + * CLIENTROLLBACK = 12; + */ + CLIENTROLLBACK(12), + UNRECOGNIZED(-1), + ; - public static Compression valueOf(com.google.protobuf.Descriptors.EnumValueDescriptor desc) { - if (desc.getType() != getDescriptor()) { - throw new java.lang.IllegalArgumentException("EnumValueDescriptor is not for this type."); - } - return VALUES[desc.getIndex()]; - } + /** + *
      +     *compatible
      +     * 
      + * + * PACKAGETYPECOMPATIBLEPROTO2 = 0; + */ + public static final int PACKAGETYPECOMPATIBLEPROTO2_VALUE = 0; + /** + * HANDSHAKE = 1; + */ + public static final int HANDSHAKE_VALUE = 1; + /** + * CLIENTAUTHENTICATION = 2; + */ + public static final int CLIENTAUTHENTICATION_VALUE = 2; + /** + * ACK = 3; + */ + public static final int ACK_VALUE = 3; + /** + * SUBSCRIPTION = 4; + */ + public static final int SUBSCRIPTION_VALUE = 4; + /** + * UNSUBSCRIPTION = 5; + */ + public static final int UNSUBSCRIPTION_VALUE = 5; + /** + * GET = 6; + */ + public static final int GET_VALUE = 6; + /** + * MESSAGES = 7; + */ + public static final int MESSAGES_VALUE = 7; + /** + * CLIENTACK = 8; + */ + public static final int CLIENTACK_VALUE = 8; + /** + *
      +     * management part
      +     * 
      + * + * SHUTDOWN = 9; + */ + public static final int SHUTDOWN_VALUE = 9; + /** + *
      +     * integration
      +     * 
      + * + * DUMP = 10; + */ + public static final int DUMP_VALUE = 10; + /** + * HEARTBEAT = 11; + */ + public static final int HEARTBEAT_VALUE = 11; + /** + * CLIENTROLLBACK = 12; + */ + public static final int CLIENTROLLBACK_VALUE = 12; - private final int index; - private final int value; - private Compression(int index, int value){ - this.index = index; - this.value = value; - } - - // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.Compression) + public final int getNumber() { + if (this == UNRECOGNIZED) { + throw new java.lang.IllegalArgumentException( + "Can't get the number of an unknown enum value."); + } + return value; } /** - * Protobuf enum {@code com.alibaba.otter.canal.protocol.PacketType} + * @deprecated Use {@link #forNumber(int)} instead. */ - public enum PacketType implements com.google.protobuf.ProtocolMessageEnum { - /** - * HANDSHAKE = 1; - */ - HANDSHAKE(0, 1), - /** - * CLIENTAUTHENTICATION = 2; - */ - CLIENTAUTHENTICATION(1, 2), - /** - * ACK = 3; - */ - ACK(2, 3), - /** - * SUBSCRIPTION = 4; - */ - SUBSCRIPTION(3, 4), - /** - * UNSUBSCRIPTION = 5; - */ - UNSUBSCRIPTION(4, 5), - /** - * GET = 6; - */ - GET(5, 6), - /** - * MESSAGES = 7; - */ - MESSAGES(6, 7), - /** - * CLIENTACK = 8; - */ - CLIENTACK(7, 8), - /** - * SHUTDOWN = 9; - * - *
      -         * management part
      -         * 
      - */ - SHUTDOWN(8, 9), - /** - * DUMP = 10; - * - *
      -         * integration
      -         * 
      - */ - DUMP(9, 10), - /** - * HEARTBEAT = 11; - */ - HEARTBEAT(10, 11), - /** - * CLIENTROLLBACK = 12; - */ - CLIENTROLLBACK(11, 12), ; - - /** - * HANDSHAKE = 1; - */ - public static final int HANDSHAKE_VALUE = 1; - /** - * CLIENTAUTHENTICATION = 2; - */ - public static final int CLIENTAUTHENTICATION_VALUE = 2; - /** - * ACK = 3; - */ - public static final int ACK_VALUE = 3; - /** - * SUBSCRIPTION = 4; - */ - public static final int SUBSCRIPTION_VALUE = 4; - /** - * UNSUBSCRIPTION = 5; - */ - public static final int UNSUBSCRIPTION_VALUE = 5; - /** - * GET = 6; - */ - public static final int GET_VALUE = 6; - /** - * MESSAGES = 7; - */ - public static final int MESSAGES_VALUE = 7; - /** - * CLIENTACK = 8; - */ - public static final int CLIENTACK_VALUE = 8; - /** - * SHUTDOWN = 9; - * - *
      -         * management part
      -         * 
      - */ - public static final int SHUTDOWN_VALUE = 9; - /** - * DUMP = 10; - * - *
      -         * integration
      -         * 
      - */ - public static final int DUMP_VALUE = 10; - /** - * HEARTBEAT = 11; - */ - public static final int HEARTBEAT_VALUE = 11; - /** - * CLIENTROLLBACK = 12; - */ - public static final int CLIENTROLLBACK_VALUE = 12; - - public final int getNumber() { - return value; - } - - public static PacketType valueOf(int value) { - switch (value) { - case 1: - return HANDSHAKE; - case 2: - return CLIENTAUTHENTICATION; - case 3: - return ACK; - case 4: - return SUBSCRIPTION; - case 5: - return UNSUBSCRIPTION; - case 6: - return GET; - case 7: - return MESSAGES; - case 8: - return CLIENTACK; - case 9: - return SHUTDOWN; - case 10: - return DUMP; - case 11: - return HEARTBEAT; - case 12: - return CLIENTROLLBACK; - default: - return null; - } - } - - public static com.google.protobuf.Internal.EnumLiteMap internalGetValueMap() { - return internalValueMap; - } - - private static com.google.protobuf.Internal.EnumLiteMap internalValueMap = new com.google.protobuf.Internal.EnumLiteMap() { - - public PacketType findValueByNumber(int number) { - return PacketType.valueOf(number); - } - }; - - public final com.google.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() { - return getDescriptor().getValues().get(index); - } - - public final com.google.protobuf.Descriptors.EnumDescriptor getDescriptorForType() { - return getDescriptor(); - } - - public static final com.google.protobuf.Descriptors.EnumDescriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.getDescriptor().getEnumTypes().get(1); - } - - private static final PacketType[] VALUES = values(); - - public static PacketType valueOf(com.google.protobuf.Descriptors.EnumValueDescriptor desc) { - if (desc.getType() != getDescriptor()) { - throw new java.lang.IllegalArgumentException("EnumValueDescriptor is not for this type."); - } - return VALUES[desc.getIndex()]; - } - - private final int index; - private final int value; - - private PacketType(int index, int value){ - this.index = index; - this.value = value; - } - - // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.PacketType) + @java.lang.Deprecated + public static PacketType valueOf(int value) { + return forNumber(value); } - public interface PacketOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Packet) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - boolean hasMagicNumber(); - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - int getMagicNumber(); - - /** - * optional int32 version = 2 [default = 1]; - */ - boolean hasVersion(); - - /** - * optional int32 version = 2 [default = 1]; - */ - int getVersion(); - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - boolean hasType(); - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - com.alibaba.otter.canal.protocol.CanalPacket.PacketType getType(); - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - boolean hasCompression(); - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - com.alibaba.otter.canal.protocol.CanalPacket.Compression getCompression(); - - /** - * optional bytes body = 5; - */ - boolean hasBody(); - - /** - * optional bytes body = 5; - */ - com.google.protobuf.ByteString getBody(); + public static PacketType forNumber(int value) { + switch (value) { + case 0: return PACKAGETYPECOMPATIBLEPROTO2; + case 1: return HANDSHAKE; + case 2: return CLIENTAUTHENTICATION; + case 3: return ACK; + case 4: return SUBSCRIPTION; + case 5: return UNSUBSCRIPTION; + case 6: return GET; + case 7: return MESSAGES; + case 8: return CLIENTACK; + case 9: return SHUTDOWN; + case 10: return DUMP; + case 11: return HEARTBEAT; + case 12: return CLIENTROLLBACK; + default: return null; + } } + public static com.google.protobuf.Internal.EnumLiteMap + internalGetValueMap() { + return internalValueMap; + } + private static final com.google.protobuf.Internal.EnumLiteMap< + PacketType> internalValueMap = + new com.google.protobuf.Internal.EnumLiteMap() { + public PacketType findValueByNumber(int number) { + return PacketType.forNumber(number); + } + }; + + public final com.google.protobuf.Descriptors.EnumValueDescriptor + getValueDescriptor() { + return getDescriptor().getValues().get(ordinal()); + } + public final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptorForType() { + return getDescriptor(); + } + public static final com.google.protobuf.Descriptors.EnumDescriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.getDescriptor().getEnumTypes().get(1); + } + + private static final PacketType[] VALUES = values(); + + public static PacketType valueOf( + com.google.protobuf.Descriptors.EnumValueDescriptor desc) { + if (desc.getType() != getDescriptor()) { + throw new java.lang.IllegalArgumentException( + "EnumValueDescriptor is not for this type."); + } + if (desc.getIndex() == -1) { + return UNRECOGNIZED; + } + return VALUES[desc.getIndex()]; + } + + private final int value; + + private PacketType(int value) { + this.value = value; + } + + // @@protoc_insertion_point(enum_scope:com.alibaba.otter.canal.protocol.PacketType) + } + + public interface PacketOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Packet) + com.google.protobuf.MessageOrBuilder { + + /** + * int32 magic_number = 1; + */ + int getMagicNumber(); + + /** + * int32 version = 2; + */ + int getVersion(); + + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + int getTypeValue(); + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + com.alibaba.otter.canal.protocol.CanalPacket.PacketType getType(); + + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + int getCompressionValue(); + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + com.alibaba.otter.canal.protocol.CanalPacket.Compression getCompression(); + + /** + * bytes body = 5; + */ + com.google.protobuf.ByteString getBody(); + + public com.alibaba.otter.canal.protocol.CanalPacket.Packet.MagicNumberPresentCase getMagicNumberPresentCase(); + + public com.alibaba.otter.canal.protocol.CanalPacket.Packet.VersionPresentCase getVersionPresentCase(); + + public com.alibaba.otter.canal.protocol.CanalPacket.Packet.CompressionPresentCase getCompressionPresentCase(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.Packet} + */ + public static final class Packet extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Packet) + PacketOrBuilder { + private static final long serialVersionUID = 0L; + // Use Packet.newBuilder() to construct. + private Packet(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Packet() { + type_ = 0; + body_ = com.google.protobuf.ByteString.EMPTY; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Packet( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 8: { + magicNumberPresentCase_ = 1; + magicNumberPresent_ = input.readInt32(); + break; + } + case 16: { + versionPresentCase_ = 2; + versionPresent_ = input.readInt32(); + break; + } + case 24: { + int rawValue = input.readEnum(); + + type_ = rawValue; + break; + } + case 32: { + int rawValue = input.readEnum(); + compressionPresentCase_ = 4; + compressionPresent_ = rawValue; + break; + } + case 42: { + + body_ = input.readBytes(); + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Packet.class, com.alibaba.otter.canal.protocol.CanalPacket.Packet.Builder.class); + } + + private int magicNumberPresentCase_ = 0; + private java.lang.Object magicNumberPresent_; + public enum MagicNumberPresentCase + implements com.google.protobuf.Internal.EnumLite { + MAGIC_NUMBER(1), + MAGICNUMBERPRESENT_NOT_SET(0); + private final int value; + private MagicNumberPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static MagicNumberPresentCase valueOf(int value) { + return forNumber(value); + } + + public static MagicNumberPresentCase forNumber(int value) { + switch (value) { + case 1: return MAGIC_NUMBER; + case 0: return MAGICNUMBERPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public MagicNumberPresentCase + getMagicNumberPresentCase() { + return MagicNumberPresentCase.forNumber( + magicNumberPresentCase_); + } + + private int versionPresentCase_ = 0; + private java.lang.Object versionPresent_; + public enum VersionPresentCase + implements com.google.protobuf.Internal.EnumLite { + VERSION(2), + VERSIONPRESENT_NOT_SET(0); + private final int value; + private VersionPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static VersionPresentCase valueOf(int value) { + return forNumber(value); + } + + public static VersionPresentCase forNumber(int value) { + switch (value) { + case 2: return VERSION; + case 0: return VERSIONPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public VersionPresentCase + getVersionPresentCase() { + return VersionPresentCase.forNumber( + versionPresentCase_); + } + + private int compressionPresentCase_ = 0; + private java.lang.Object compressionPresent_; + public enum CompressionPresentCase + implements com.google.protobuf.Internal.EnumLite { + COMPRESSION(4), + COMPRESSIONPRESENT_NOT_SET(0); + private final int value; + private CompressionPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static CompressionPresentCase valueOf(int value) { + return forNumber(value); + } + + public static CompressionPresentCase forNumber(int value) { + switch (value) { + case 4: return COMPRESSION; + case 0: return COMPRESSIONPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public CompressionPresentCase + getCompressionPresentCase() { + return CompressionPresentCase.forNumber( + compressionPresentCase_); + } + + public static final int MAGIC_NUMBER_FIELD_NUMBER = 1; + /** + * int32 magic_number = 1; + */ + public int getMagicNumber() { + if (magicNumberPresentCase_ == 1) { + return (java.lang.Integer) magicNumberPresent_; + } + return 0; + } + + public static final int VERSION_FIELD_NUMBER = 2; + /** + * int32 version = 2; + */ + public int getVersion() { + if (versionPresentCase_ == 2) { + return (java.lang.Integer) versionPresent_; + } + return 1; + } + + public static final int TYPE_FIELD_NUMBER = 3; + private int type_; + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + public int getTypeValue() { + return type_; + } + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + public com.alibaba.otter.canal.protocol.CanalPacket.PacketType getType() { + @SuppressWarnings("deprecation") + com.alibaba.otter.canal.protocol.CanalPacket.PacketType result = com.alibaba.otter.canal.protocol.CanalPacket.PacketType.valueOf(type_); + return result == null ? com.alibaba.otter.canal.protocol.CanalPacket.PacketType.UNRECOGNIZED : result; + } + + public static final int COMPRESSION_FIELD_NUMBER = 4; + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + public int getCompressionValue() { + if (compressionPresentCase_ == 4) { + return (java.lang.Integer) compressionPresent_; + } + return Compression.NONE_VALUE; + } + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + public com.alibaba.otter.canal.protocol.CanalPacket.Compression getCompression() { + if (compressionPresentCase_ == 4) { + @SuppressWarnings("deprecation") + com.alibaba.otter.canal.protocol.CanalPacket.Compression result = com.alibaba.otter.canal.protocol.CanalPacket.Compression.valueOf( + (java.lang.Integer) compressionPresent_); + return result == null ? com.alibaba.otter.canal.protocol.CanalPacket.Compression.UNRECOGNIZED : result; + } + return com.alibaba.otter.canal.protocol.CanalPacket.Compression.COMPRESSIONCOMPATIBLEPROTO2; + } + + public static final int BODY_FIELD_NUMBER = 5; + private com.google.protobuf.ByteString body_; + /** + * bytes body = 5; + */ + public com.google.protobuf.ByteString getBody() { + return body_; + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (magicNumberPresentCase_ == 1) { + output.writeInt32( + 1, (int)((java.lang.Integer) magicNumberPresent_)); + } + if (versionPresentCase_ == 2) { + output.writeInt32( + 2, (int)((java.lang.Integer) versionPresent_)); + } + if (type_ != com.alibaba.otter.canal.protocol.CanalPacket.PacketType.PACKAGETYPECOMPATIBLEPROTO2.getNumber()) { + output.writeEnum(3, type_); + } + if (compressionPresentCase_ == 4) { + output.writeEnum(4, ((java.lang.Integer) compressionPresent_)); + } + if (!body_.isEmpty()) { + output.writeBytes(5, body_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (magicNumberPresentCase_ == 1) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size( + 1, (int)((java.lang.Integer) magicNumberPresent_)); + } + if (versionPresentCase_ == 2) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size( + 2, (int)((java.lang.Integer) versionPresent_)); + } + if (type_ != com.alibaba.otter.canal.protocol.CanalPacket.PacketType.PACKAGETYPECOMPATIBLEPROTO2.getNumber()) { + size += com.google.protobuf.CodedOutputStream + .computeEnumSize(3, type_); + } + if (compressionPresentCase_ == 4) { + size += com.google.protobuf.CodedOutputStream + .computeEnumSize(4, ((java.lang.Integer) compressionPresent_)); + } + if (!body_.isEmpty()) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(5, body_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Packet)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Packet other = (com.alibaba.otter.canal.protocol.CanalPacket.Packet) obj; + + boolean result = true; + result = result && type_ == other.type_; + result = result && getBody() + .equals(other.getBody()); + result = result && getMagicNumberPresentCase().equals( + other.getMagicNumberPresentCase()); + if (!result) return false; + switch (magicNumberPresentCase_) { + case 1: + result = result && (getMagicNumber() + == other.getMagicNumber()); + break; + case 0: + default: + } + result = result && getVersionPresentCase().equals( + other.getVersionPresentCase()); + if (!result) return false; + switch (versionPresentCase_) { + case 2: + result = result && (getVersion() + == other.getVersion()); + break; + case 0: + default: + } + result = result && getCompressionPresentCase().equals( + other.getCompressionPresentCase()); + if (!result) return false; + switch (compressionPresentCase_) { + case 4: + result = result && getCompressionValue() + == other.getCompressionValue(); + break; + case 0: + default: + } + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + TYPE_FIELD_NUMBER; + hash = (53 * hash) + type_; + hash = (37 * hash) + BODY_FIELD_NUMBER; + hash = (53 * hash) + getBody().hashCode(); + switch (magicNumberPresentCase_) { + case 1: + hash = (37 * hash) + MAGIC_NUMBER_FIELD_NUMBER; + hash = (53 * hash) + getMagicNumber(); + break; + case 0: + default: + } + switch (versionPresentCase_) { + case 2: + hash = (37 * hash) + VERSION_FIELD_NUMBER; + hash = (53 * hash) + getVersion(); + break; + case 0: + default: + } + switch (compressionPresentCase_) { + case 4: + hash = (37 * hash) + COMPRESSION_FIELD_NUMBER; + hash = (53 * hash) + getCompressionValue(); + break; + case 0: + default: + } + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Packet prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.Packet} */ - public static final class Packet extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Packet) - PacketOrBuilder { - - // Use Packet.newBuilder() to construct. - private Packet(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Packet(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Packet defaultInstance; - - public static Packet getDefaultInstance() { - return defaultInstance; - } - - public Packet getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Packet(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - magicNumber_ = input.readInt32(); - break; - } - case 16: { - bitField0_ |= 0x00000002; - version_ = input.readInt32(); - break; - } - case 24: { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalPacket.PacketType value = com.alibaba.otter.canal.protocol.CanalPacket.PacketType.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(3, rawValue); - } else { - bitField0_ |= 0x00000004; - type_ = value; - } - break; - } - case 32: { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalPacket.Compression value = com.alibaba.otter.canal.protocol.CanalPacket.Compression.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(4, rawValue); - } else { - bitField0_ |= 0x00000008; - compression_ = value; - } - break; - } - case 42: { - bitField0_ |= 0x00000010; - body_ = input.readBytes(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Packet.class, - com.alibaba.otter.canal.protocol.CanalPacket.Packet.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Packet parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Packet(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int MAGIC_NUMBER_FIELD_NUMBER = 1; - private int magicNumber_; - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - public boolean hasMagicNumber() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - public int getMagicNumber() { - return magicNumber_; - } - - public static final int VERSION_FIELD_NUMBER = 2; - private int version_; - - /** - * optional int32 version = 2 [default = 1]; - */ - public boolean hasVersion() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int32 version = 2 [default = 1]; - */ - public int getVersion() { - return version_; - } - - public static final int TYPE_FIELD_NUMBER = 3; - private com.alibaba.otter.canal.protocol.CanalPacket.PacketType type_; - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - public boolean hasType() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - public com.alibaba.otter.canal.protocol.CanalPacket.PacketType getType() { - return type_; - } - - public static final int COMPRESSION_FIELD_NUMBER = 4; - private com.alibaba.otter.canal.protocol.CanalPacket.Compression compression_; - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - public boolean hasCompression() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - public com.alibaba.otter.canal.protocol.CanalPacket.Compression getCompression() { - return compression_; - } - - public static final int BODY_FIELD_NUMBER = 5; - private com.google.protobuf.ByteString body_; - - /** - * optional bytes body = 5; - */ - public boolean hasBody() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional bytes body = 5; - */ - public com.google.protobuf.ByteString getBody() { - return body_; - } - - private void initFields() { - magicNumber_ = 17; - version_ = 1; - type_ = com.alibaba.otter.canal.protocol.CanalPacket.PacketType.HANDSHAKE; - compression_ = com.alibaba.otter.canal.protocol.CanalPacket.Compression.NONE; - body_ = com.google.protobuf.ByteString.EMPTY; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt32(1, magicNumber_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeInt32(2, version_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeEnum(3, type_.getNumber()); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - output.writeEnum(4, compression_.getNumber()); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - output.writeBytes(5, body_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(1, magicNumber_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(2, version_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeEnumSize(3, type_.getNumber()); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - size += com.google.protobuf.CodedOutputStream.computeEnumSize(4, compression_.getNumber()); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(5, body_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Packet parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Packet prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Packet} - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Packet) com.alibaba.otter.canal.protocol.CanalPacket.PacketOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Packet.class, com.alibaba.otter.canal.protocol.CanalPacket.Packet.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Packet.class, - com.alibaba.otter.canal.protocol.CanalPacket.Packet.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Packet.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Packet.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - magicNumber_ = 17; - bitField0_ = (bitField0_ & ~0x00000001); - version_ = 1; - bitField0_ = (bitField0_ & ~0x00000002); - type_ = com.alibaba.otter.canal.protocol.CanalPacket.PacketType.HANDSHAKE; - bitField0_ = (bitField0_ & ~0x00000004); - compression_ = com.alibaba.otter.canal.protocol.CanalPacket.Compression.NONE; - bitField0_ = (bitField0_ & ~0x00000008); - body_ = com.google.protobuf.ByteString.EMPTY; - bitField0_ = (bitField0_ & ~0x00000010); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Packet getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Packet.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Packet build() { - com.alibaba.otter.canal.protocol.CanalPacket.Packet result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Packet buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Packet result = new com.alibaba.otter.canal.protocol.CanalPacket.Packet(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.magicNumber_ = magicNumber_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.version_ = version_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.type_ = type_; - if (((from_bitField0_ & 0x00000008) == 0x00000008)) { - to_bitField0_ |= 0x00000008; - } - result.compression_ = compression_; - if (((from_bitField0_ & 0x00000010) == 0x00000010)) { - to_bitField0_ |= 0x00000010; - } - result.body_ = body_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Packet) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Packet) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Packet other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Packet.getDefaultInstance()) return this; - if (other.hasMagicNumber()) { - setMagicNumber(other.getMagicNumber()); - } - if (other.hasVersion()) { - setVersion(other.getVersion()); - } - if (other.hasType()) { - setType(other.getType()); - } - if (other.hasCompression()) { - setCompression(other.getCompression()); - } - if (other.hasBody()) { - setBody(other.getBody()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Packet parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Packet) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private int magicNumber_ = 17; - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - public boolean hasMagicNumber() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - public int getMagicNumber() { - return magicNumber_; - } - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - public Builder setMagicNumber(int value) { - bitField0_ |= 0x00000001; - magicNumber_ = value; - onChanged(); - return this; - } - - /** - * optional int32 magic_number = 1 [default = 17]; - */ - public Builder clearMagicNumber() { - bitField0_ = (bitField0_ & ~0x00000001); - magicNumber_ = 17; - onChanged(); - return this; - } - - private int version_ = 1; - - /** - * optional int32 version = 2 [default = 1]; - */ - public boolean hasVersion() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int32 version = 2 [default = 1]; - */ - public int getVersion() { - return version_; - } - - /** - * optional int32 version = 2 [default = 1]; - */ - public Builder setVersion(int value) { - bitField0_ |= 0x00000002; - version_ = value; - onChanged(); - return this; - } - - /** - * optional int32 version = 2 [default = 1]; - */ - public Builder clearVersion() { - bitField0_ = (bitField0_ & ~0x00000002); - version_ = 1; - onChanged(); - return this; - } - - private com.alibaba.otter.canal.protocol.CanalPacket.PacketType type_ = com.alibaba.otter.canal.protocol.CanalPacket.PacketType.HANDSHAKE; - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - public boolean hasType() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - public com.alibaba.otter.canal.protocol.CanalPacket.PacketType getType() { - return type_; - } - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - public Builder setType(com.alibaba.otter.canal.protocol.CanalPacket.PacketType value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - type_ = value; - onChanged(); - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.PacketType type = 3; - */ - public Builder clearType() { - bitField0_ = (bitField0_ & ~0x00000004); - type_ = com.alibaba.otter.canal.protocol.CanalPacket.PacketType.HANDSHAKE; - onChanged(); - return this; - } - - private com.alibaba.otter.canal.protocol.CanalPacket.Compression compression_ = com.alibaba.otter.canal.protocol.CanalPacket.Compression.NONE; - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - public boolean hasCompression() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - public com.alibaba.otter.canal.protocol.CanalPacket.Compression getCompression() { - return compression_; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - public Builder setCompression(com.alibaba.otter.canal.protocol.CanalPacket.Compression value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000008; - compression_ = value; - onChanged(); - return this; - } - - /** - * optional .com.alibaba.otter.canal.protocol.Compression compression = 4 [default = NONE]; - */ - public Builder clearCompression() { - bitField0_ = (bitField0_ & ~0x00000008); - compression_ = com.alibaba.otter.canal.protocol.CanalPacket.Compression.NONE; - onChanged(); - return this; - } - - private com.google.protobuf.ByteString body_ = com.google.protobuf.ByteString.EMPTY; - - /** - * optional bytes body = 5; - */ - public boolean hasBody() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional bytes body = 5; - */ - public com.google.protobuf.ByteString getBody() { - return body_; - } - - /** - * optional bytes body = 5; - */ - public Builder setBody(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000010; - body_ = value; - onChanged(); - return this; - } - - /** - * optional bytes body = 5; - */ - public Builder clearBody() { - bitField0_ = (bitField0_ & ~0x00000010); - body_ = getDefaultInstance().getBody(); - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Packet) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + type_ = 0; - static { - defaultInstance = new Packet(true); - defaultInstance.initFields(); + body_ = com.google.protobuf.ByteString.EMPTY; + + magicNumberPresentCase_ = 0; + magicNumberPresent_ = null; + versionPresentCase_ = 0; + versionPresent_ = null; + compressionPresentCase_ = 0; + compressionPresent_ = null; + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Packet getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Packet.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Packet build() { + com.alibaba.otter.canal.protocol.CanalPacket.Packet result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Packet) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Packet buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Packet result = new com.alibaba.otter.canal.protocol.CanalPacket.Packet(this); + if (magicNumberPresentCase_ == 1) { + result.magicNumberPresent_ = magicNumberPresent_; + } + if (versionPresentCase_ == 2) { + result.versionPresent_ = versionPresent_; + } + result.type_ = type_; + if (compressionPresentCase_ == 4) { + result.compressionPresent_ = compressionPresent_; + } + result.body_ = body_; + result.magicNumberPresentCase_ = magicNumberPresentCase_; + result.versionPresentCase_ = versionPresentCase_; + result.compressionPresentCase_ = compressionPresentCase_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Packet) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Packet)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Packet other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Packet.getDefaultInstance()) return this; + if (other.type_ != 0) { + setTypeValue(other.getTypeValue()); + } + if (other.getBody() != com.google.protobuf.ByteString.EMPTY) { + setBody(other.getBody()); + } + switch (other.getMagicNumberPresentCase()) { + case MAGIC_NUMBER: { + setMagicNumber(other.getMagicNumber()); + break; + } + case MAGICNUMBERPRESENT_NOT_SET: { + break; + } + } + switch (other.getVersionPresentCase()) { + case VERSION: { + setVersion(other.getVersion()); + break; + } + case VERSIONPRESENT_NOT_SET: { + break; + } + } + switch (other.getCompressionPresentCase()) { + case COMPRESSION: { + setCompressionValue(other.getCompressionValue()); + break; + } + case COMPRESSIONPRESENT_NOT_SET: { + break; + } + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Packet parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Packet) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int magicNumberPresentCase_ = 0; + private java.lang.Object magicNumberPresent_; + public MagicNumberPresentCase + getMagicNumberPresentCase() { + return MagicNumberPresentCase.forNumber( + magicNumberPresentCase_); + } + + public Builder clearMagicNumberPresent() { + magicNumberPresentCase_ = 0; + magicNumberPresent_ = null; + onChanged(); + return this; + } + + private int versionPresentCase_ = 0; + private java.lang.Object versionPresent_; + public VersionPresentCase + getVersionPresentCase() { + return VersionPresentCase.forNumber( + versionPresentCase_); + } + + public Builder clearVersionPresent() { + versionPresentCase_ = 0; + versionPresent_ = null; + onChanged(); + return this; + } + + private int compressionPresentCase_ = 0; + private java.lang.Object compressionPresent_; + public CompressionPresentCase + getCompressionPresentCase() { + return CompressionPresentCase.forNumber( + compressionPresentCase_); + } + + public Builder clearCompressionPresent() { + compressionPresentCase_ = 0; + compressionPresent_ = null; + onChanged(); + return this; + } + + + /** + * int32 magic_number = 1; + */ + public int getMagicNumber() { + if (magicNumberPresentCase_ == 1) { + return (java.lang.Integer) magicNumberPresent_; + } + return 17; + } + /** + * int32 magic_number = 1; + */ + public Builder setMagicNumber(int value) { + magicNumberPresentCase_ = 1; + magicNumberPresent_ = value; + onChanged(); + return this; + } + /** + * int32 magic_number = 1; + */ + public Builder clearMagicNumber() { + if (magicNumberPresentCase_ == 1) { + magicNumberPresentCase_ = 0; + magicNumberPresent_ = null; + onChanged(); + } + return this; + } + + /** + * int32 version = 2; + */ + public int getVersion() { + if (versionPresentCase_ == 2) { + return (java.lang.Integer) versionPresent_; + } + return 0; + } + /** + * int32 version = 2; + */ + public Builder setVersion(int value) { + versionPresentCase_ = 2; + versionPresent_ = value; + onChanged(); + return this; + } + /** + * int32 version = 2; + */ + public Builder clearVersion() { + if (versionPresentCase_ == 2) { + versionPresentCase_ = 0; + versionPresent_ = null; + onChanged(); + } + return this; + } + + private int type_ = 0; + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + public int getTypeValue() { + return type_; + } + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + public Builder setTypeValue(int value) { + type_ = value; + onChanged(); + return this; + } + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + public com.alibaba.otter.canal.protocol.CanalPacket.PacketType getType() { + @SuppressWarnings("deprecation") + com.alibaba.otter.canal.protocol.CanalPacket.PacketType result = com.alibaba.otter.canal.protocol.CanalPacket.PacketType.valueOf(type_); + return result == null ? com.alibaba.otter.canal.protocol.CanalPacket.PacketType.UNRECOGNIZED : result; + } + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + public Builder setType(com.alibaba.otter.canal.protocol.CanalPacket.PacketType value) { + if (value == null) { + throw new NullPointerException(); + } + + type_ = value.getNumber(); + onChanged(); + return this; + } + /** + * .com.alibaba.otter.canal.protocol.PacketType type = 3; + */ + public Builder clearType() { + + type_ = 0; + onChanged(); + return this; + } + + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + public int getCompressionValue() { + if (compressionPresentCase_ == 4) { + return ((java.lang.Integer) compressionPresent_).intValue(); + } + return 0; + } + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + public Builder setCompressionValue(int value) { + compressionPresentCase_ = 4; + compressionPresent_ = value; + onChanged(); + return this; + } + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + public com.alibaba.otter.canal.protocol.CanalPacket.Compression getCompression() { + if (compressionPresentCase_ == 4) { + @SuppressWarnings("deprecation") + com.alibaba.otter.canal.protocol.CanalPacket.Compression result = com.alibaba.otter.canal.protocol.CanalPacket.Compression.valueOf( + (java.lang.Integer) compressionPresent_); + return result == null ? com.alibaba.otter.canal.protocol.CanalPacket.Compression.UNRECOGNIZED : result; + } + return com.alibaba.otter.canal.protocol.CanalPacket.Compression.COMPRESSIONCOMPATIBLEPROTO2; + } + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + public Builder setCompression(com.alibaba.otter.canal.protocol.CanalPacket.Compression value) { + if (value == null) { + throw new NullPointerException(); + } + compressionPresentCase_ = 4; + compressionPresent_ = value.getNumber(); + onChanged(); + return this; + } + /** + * .com.alibaba.otter.canal.protocol.Compression compression = 4; + */ + public Builder clearCompression() { + if (compressionPresentCase_ == 4) { + compressionPresentCase_ = 0; + compressionPresent_ = null; + onChanged(); + } + return this; + } + + private com.google.protobuf.ByteString body_ = com.google.protobuf.ByteString.EMPTY; + /** + * bytes body = 5; + */ + public com.google.protobuf.ByteString getBody() { + return body_; + } + /** + * bytes body = 5; + */ + public Builder setBody(com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + + body_ = value; + onChanged(); + return this; + } + /** + * bytes body = 5; + */ + public Builder clearBody() { + + body_ = getDefaultInstance().getBody(); + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Packet) } - public interface HeartBeatOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.HeartBeat) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int64 send_timestamp = 1; - */ - boolean hasSendTimestamp(); - - /** - * optional int64 send_timestamp = 1; - */ - long getSendTimestamp(); - - /** - * optional int64 start_timestamp = 2; - */ - boolean hasStartTimestamp(); - - /** - * optional int64 start_timestamp = 2; - */ - long getStartTimestamp(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Packet) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Packet DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Packet(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Packet getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Packet parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Packet(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Packet getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface HeartBeatOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.HeartBeat) + com.google.protobuf.MessageOrBuilder { + + /** + * int64 send_timestamp = 1; + */ + long getSendTimestamp(); + + /** + * int64 start_timestamp = 2; + */ + long getStartTimestamp(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.HeartBeat} + */ + public static final class HeartBeat extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.HeartBeat) + HeartBeatOrBuilder { + private static final long serialVersionUID = 0L; + // Use HeartBeat.newBuilder() to construct. + private HeartBeat(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private HeartBeat() { + sendTimestamp_ = 0L; + startTimestamp_ = 0L; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private HeartBeat( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 8: { + + sendTimestamp_ = input.readInt64(); + break; + } + case 16: { + + startTimestamp_ = input.readInt64(); + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.class, com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.Builder.class); + } + + public static final int SEND_TIMESTAMP_FIELD_NUMBER = 1; + private long sendTimestamp_; + /** + * int64 send_timestamp = 1; + */ + public long getSendTimestamp() { + return sendTimestamp_; + } + + public static final int START_TIMESTAMP_FIELD_NUMBER = 2; + private long startTimestamp_; + /** + * int64 start_timestamp = 2; + */ + public long getStartTimestamp() { + return startTimestamp_; + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (sendTimestamp_ != 0L) { + output.writeInt64(1, sendTimestamp_); + } + if (startTimestamp_ != 0L) { + output.writeInt64(2, startTimestamp_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (sendTimestamp_ != 0L) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(1, sendTimestamp_); + } + if (startTimestamp_ != 0L) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(2, startTimestamp_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat other = (com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat) obj; + + boolean result = true; + result = result && (getSendTimestamp() + == other.getSendTimestamp()); + result = result && (getStartTimestamp() + == other.getStartTimestamp()); + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + SEND_TIMESTAMP_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getSendTimestamp()); + hash = (37 * hash) + START_TIMESTAMP_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getStartTimestamp()); + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.HeartBeat} */ - public static final class HeartBeat extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.HeartBeat) - HeartBeatOrBuilder { - - // Use HeartBeat.newBuilder() to construct. - private HeartBeat(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private HeartBeat(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final HeartBeat defaultInstance; - - public static HeartBeat getDefaultInstance() { - return defaultInstance; - } - - public HeartBeat getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private HeartBeat(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - sendTimestamp_ = input.readInt64(); - break; - } - case 16: { - bitField0_ |= 0x00000002; - startTimestamp_ = input.readInt64(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.class, - com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public HeartBeat parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new HeartBeat(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int SEND_TIMESTAMP_FIELD_NUMBER = 1; - private long sendTimestamp_; - - /** - * optional int64 send_timestamp = 1; - */ - public boolean hasSendTimestamp() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 send_timestamp = 1; - */ - public long getSendTimestamp() { - return sendTimestamp_; - } - - public static final int START_TIMESTAMP_FIELD_NUMBER = 2; - private long startTimestamp_; - - /** - * optional int64 start_timestamp = 2; - */ - public boolean hasStartTimestamp() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int64 start_timestamp = 2; - */ - public long getStartTimestamp() { - return startTimestamp_; - } - - private void initFields() { - sendTimestamp_ = 0L; - startTimestamp_ = 0L; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt64(1, sendTimestamp_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeInt64(2, startTimestamp_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(1, sendTimestamp_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(2, startTimestamp_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.HeartBeat} - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.HeartBeat) com.alibaba.otter.canal.protocol.CanalPacket.HeartBeatOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.class, com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.class, - com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - sendTimestamp_ = 0L; - bitField0_ = (bitField0_ & ~0x00000001); - startTimestamp_ = 0L; - bitField0_ = (bitField0_ & ~0x00000002); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat build() { - com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat result = new com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.sendTimestamp_ = sendTimestamp_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.startTimestamp_ = startTimestamp_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.getDefaultInstance()) return this; - if (other.hasSendTimestamp()) { - setSendTimestamp(other.getSendTimestamp()); - } - if (other.hasStartTimestamp()) { - setStartTimestamp(other.getStartTimestamp()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private long sendTimestamp_; - - /** - * optional int64 send_timestamp = 1; - */ - public boolean hasSendTimestamp() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 send_timestamp = 1; - */ - public long getSendTimestamp() { - return sendTimestamp_; - } - - /** - * optional int64 send_timestamp = 1; - */ - public Builder setSendTimestamp(long value) { - bitField0_ |= 0x00000001; - sendTimestamp_ = value; - onChanged(); - return this; - } - - /** - * optional int64 send_timestamp = 1; - */ - public Builder clearSendTimestamp() { - bitField0_ = (bitField0_ & ~0x00000001); - sendTimestamp_ = 0L; - onChanged(); - return this; - } - - private long startTimestamp_; - - /** - * optional int64 start_timestamp = 2; - */ - public boolean hasStartTimestamp() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int64 start_timestamp = 2; - */ - public long getStartTimestamp() { - return startTimestamp_; - } - - /** - * optional int64 start_timestamp = 2; - */ - public Builder setStartTimestamp(long value) { - bitField0_ |= 0x00000002; - startTimestamp_ = value; - onChanged(); - return this; - } - - /** - * optional int64 start_timestamp = 2; - */ - public Builder clearStartTimestamp() { - bitField0_ = (bitField0_ & ~0x00000002); - startTimestamp_ = 0L; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.HeartBeat) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + sendTimestamp_ = 0L; - static { - defaultInstance = new HeartBeat(true); - defaultInstance.initFields(); + startTimestamp_ = 0L; + + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat build() { + com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.HeartBeat) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat result = new com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat(this); + result.sendTimestamp_ = sendTimestamp_; + result.startTimestamp_ = startTimestamp_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat.getDefaultInstance()) return this; + if (other.getSendTimestamp() != 0L) { + setSendTimestamp(other.getSendTimestamp()); + } + if (other.getStartTimestamp() != 0L) { + setStartTimestamp(other.getStartTimestamp()); + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + + private long sendTimestamp_ ; + /** + * int64 send_timestamp = 1; + */ + public long getSendTimestamp() { + return sendTimestamp_; + } + /** + * int64 send_timestamp = 1; + */ + public Builder setSendTimestamp(long value) { + + sendTimestamp_ = value; + onChanged(); + return this; + } + /** + * int64 send_timestamp = 1; + */ + public Builder clearSendTimestamp() { + + sendTimestamp_ = 0L; + onChanged(); + return this; + } + + private long startTimestamp_ ; + /** + * int64 start_timestamp = 2; + */ + public long getStartTimestamp() { + return startTimestamp_; + } + /** + * int64 start_timestamp = 2; + */ + public Builder setStartTimestamp(long value) { + + startTimestamp_ = value; + onChanged(); + return this; + } + /** + * int64 start_timestamp = 2; + */ + public Builder clearStartTimestamp() { + + startTimestamp_ = 0L; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.HeartBeat) } - public interface HandshakeOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Handshake) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - boolean hasCommunicationEncoding(); - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - java.lang.String getCommunicationEncoding(); - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - com.google.protobuf.ByteString getCommunicationEncodingBytes(); - - /** - * optional bytes seeds = 2; - */ - boolean hasSeeds(); - - /** - * optional bytes seeds = 2; - */ - com.google.protobuf.ByteString getSeeds(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - java.util.List getSupportedCompressionsList(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - int getSupportedCompressionsCount(); - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - com.alibaba.otter.canal.protocol.CanalPacket.Compression getSupportedCompressions(int index); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.HeartBeat) + private static final com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public HeartBeat parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new HeartBeat(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.HeartBeat getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface HandshakeOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Handshake) + com.google.protobuf.MessageOrBuilder { + + /** + * string communication_encoding = 1; + */ + java.lang.String getCommunicationEncoding(); + /** + * string communication_encoding = 1; + */ + com.google.protobuf.ByteString + getCommunicationEncodingBytes(); + + /** + * bytes seeds = 2; + */ + com.google.protobuf.ByteString getSeeds(); + + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + int getSupportedCompressionsValue(); + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + com.alibaba.otter.canal.protocol.CanalPacket.Compression getSupportedCompressions(); + + public com.alibaba.otter.canal.protocol.CanalPacket.Handshake.CommunicationEncodingPresentCase getCommunicationEncodingPresentCase(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.Handshake} + */ + public static final class Handshake extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Handshake) + HandshakeOrBuilder { + private static final long serialVersionUID = 0L; + // Use Handshake.newBuilder() to construct. + private Handshake(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Handshake() { + seeds_ = com.google.protobuf.ByteString.EMPTY; + supportedCompressions_ = 0; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Handshake( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + communicationEncodingPresentCase_ = 1; + communicationEncodingPresent_ = s; + break; + } + case 18: { + + seeds_ = input.readBytes(); + break; + } + case 24: { + int rawValue = input.readEnum(); + + supportedCompressions_ = rawValue; + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Handshake.class, com.alibaba.otter.canal.protocol.CanalPacket.Handshake.Builder.class); + } + + private int communicationEncodingPresentCase_ = 0; + private java.lang.Object communicationEncodingPresent_; + public enum CommunicationEncodingPresentCase + implements com.google.protobuf.Internal.EnumLite { + COMMUNICATION_ENCODING(1), + COMMUNICATIONENCODINGPRESENT_NOT_SET(0); + private final int value; + private CommunicationEncodingPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static CommunicationEncodingPresentCase valueOf(int value) { + return forNumber(value); + } + + public static CommunicationEncodingPresentCase forNumber(int value) { + switch (value) { + case 1: return COMMUNICATION_ENCODING; + case 0: return COMMUNICATIONENCODINGPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public CommunicationEncodingPresentCase + getCommunicationEncodingPresentCase() { + return CommunicationEncodingPresentCase.forNumber( + communicationEncodingPresentCase_); + } + + public static final int COMMUNICATION_ENCODING_FIELD_NUMBER = 1; + /** + * string communication_encoding = 1; + */ + public java.lang.String getCommunicationEncoding() { + java.lang.Object ref = ""; + if (communicationEncodingPresentCase_ == 1) { + ref = communicationEncodingPresent_; + } + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + if (communicationEncodingPresentCase_ == 1) { + communicationEncodingPresent_ = s; + } + return s; + } + } + /** + * string communication_encoding = 1; + */ + public com.google.protobuf.ByteString + getCommunicationEncodingBytes() { + java.lang.Object ref = ""; + if (communicationEncodingPresentCase_ == 1) { + ref = communicationEncodingPresent_; + } + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + if (communicationEncodingPresentCase_ == 1) { + communicationEncodingPresent_ = b; + } + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int SEEDS_FIELD_NUMBER = 2; + private com.google.protobuf.ByteString seeds_; + /** + * bytes seeds = 2; + */ + public com.google.protobuf.ByteString getSeeds() { + return seeds_; + } + + public static final int SUPPORTED_COMPRESSIONS_FIELD_NUMBER = 3; + private int supportedCompressions_; + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + public int getSupportedCompressionsValue() { + return supportedCompressions_; + } + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + public com.alibaba.otter.canal.protocol.CanalPacket.Compression getSupportedCompressions() { + @SuppressWarnings("deprecation") + com.alibaba.otter.canal.protocol.CanalPacket.Compression result = com.alibaba.otter.canal.protocol.CanalPacket.Compression.valueOf(supportedCompressions_); + return result == null ? com.alibaba.otter.canal.protocol.CanalPacket.Compression.UNRECOGNIZED : result; + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (communicationEncodingPresentCase_ == 1) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, communicationEncodingPresent_); + } + if (!seeds_.isEmpty()) { + output.writeBytes(2, seeds_); + } + if (supportedCompressions_ != com.alibaba.otter.canal.protocol.CanalPacket.Compression.COMPRESSIONCOMPATIBLEPROTO2.getNumber()) { + output.writeEnum(3, supportedCompressions_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (communicationEncodingPresentCase_ == 1) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, communicationEncodingPresent_); + } + if (!seeds_.isEmpty()) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(2, seeds_); + } + if (supportedCompressions_ != com.alibaba.otter.canal.protocol.CanalPacket.Compression.COMPRESSIONCOMPATIBLEPROTO2.getNumber()) { + size += com.google.protobuf.CodedOutputStream + .computeEnumSize(3, supportedCompressions_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Handshake)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Handshake other = (com.alibaba.otter.canal.protocol.CanalPacket.Handshake) obj; + + boolean result = true; + result = result && getSeeds() + .equals(other.getSeeds()); + result = result && supportedCompressions_ == other.supportedCompressions_; + result = result && getCommunicationEncodingPresentCase().equals( + other.getCommunicationEncodingPresentCase()); + if (!result) return false; + switch (communicationEncodingPresentCase_) { + case 1: + result = result && getCommunicationEncoding() + .equals(other.getCommunicationEncoding()); + break; + case 0: + default: + } + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + SEEDS_FIELD_NUMBER; + hash = (53 * hash) + getSeeds().hashCode(); + hash = (37 * hash) + SUPPORTED_COMPRESSIONS_FIELD_NUMBER; + hash = (53 * hash) + supportedCompressions_; + switch (communicationEncodingPresentCase_) { + case 1: + hash = (37 * hash) + COMMUNICATION_ENCODING_FIELD_NUMBER; + hash = (53 * hash) + getCommunicationEncoding().hashCode(); + break; + case 0: + default: + } + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Handshake prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.Handshake} */ - public static final class Handshake extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Handshake) - HandshakeOrBuilder { - - // Use Handshake.newBuilder() to construct. - private Handshake(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Handshake(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Handshake defaultInstance; - - public static Handshake getDefaultInstance() { - return defaultInstance; - } - - public Handshake getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Handshake(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - communicationEncoding_ = bs; - break; - } - case 18: { - bitField0_ |= 0x00000002; - seeds_ = input.readBytes(); - break; - } - case 24: { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalPacket.Compression value = com.alibaba.otter.canal.protocol.CanalPacket.Compression.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(3, rawValue); - } else { - if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - supportedCompressions_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000004; - } - supportedCompressions_.add(value); - } - break; - } - case 26: { - int length = input.readRawVarint32(); - int oldLimit = input.pushLimit(length); - while (input.getBytesUntilLimit() > 0) { - int rawValue = input.readEnum(); - com.alibaba.otter.canal.protocol.CanalPacket.Compression value = com.alibaba.otter.canal.protocol.CanalPacket.Compression.valueOf(rawValue); - if (value == null) { - unknownFields.mergeVarintField(3, rawValue); - } else { - if (!((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - supportedCompressions_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000004; - } - supportedCompressions_.add(value); - } - } - input.popLimit(oldLimit); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000004) == 0x00000004)) { - supportedCompressions_ = java.util.Collections.unmodifiableList(supportedCompressions_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Handshake.class, - com.alibaba.otter.canal.protocol.CanalPacket.Handshake.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Handshake parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Handshake(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int COMMUNICATION_ENCODING_FIELD_NUMBER = 1; - private java.lang.Object communicationEncoding_; - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public boolean hasCommunicationEncoding() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public java.lang.String getCommunicationEncoding() { - java.lang.Object ref = communicationEncoding_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - communicationEncoding_ = s; - } - return s; - } - } - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public com.google.protobuf.ByteString getCommunicationEncodingBytes() { - java.lang.Object ref = communicationEncoding_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - communicationEncoding_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int SEEDS_FIELD_NUMBER = 2; - private com.google.protobuf.ByteString seeds_; - - /** - * optional bytes seeds = 2; - */ - public boolean hasSeeds() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional bytes seeds = 2; - */ - public com.google.protobuf.ByteString getSeeds() { - return seeds_; - } - - public static final int SUPPORTED_COMPRESSIONS_FIELD_NUMBER = 3; - private java.util.List supportedCompressions_; - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public java.util.List getSupportedCompressionsList() { - return supportedCompressions_; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public int getSupportedCompressionsCount() { - return supportedCompressions_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public com.alibaba.otter.canal.protocol.CanalPacket.Compression getSupportedCompressions(int index) { - return supportedCompressions_.get(index); - } - - private void initFields() { - communicationEncoding_ = "utf8"; - seeds_ = com.google.protobuf.ByteString.EMPTY; - supportedCompressions_ = java.util.Collections.emptyList(); - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getCommunicationEncodingBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, seeds_); - } - for (int i = 0; i < supportedCompressions_.size(); i++) { - output.writeEnum(3, supportedCompressions_.get(i).getNumber()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getCommunicationEncodingBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, seeds_); - } - { - int dataSize = 0; - for (int i = 0; i < supportedCompressions_.size(); i++) { - dataSize += com.google.protobuf.CodedOutputStream.computeEnumSizeNoTag(supportedCompressions_.get(i) - .getNumber()); - } - size += dataSize; - size += 1 * supportedCompressions_.size(); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Handshake prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Handshake} - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Handshake) com.alibaba.otter.canal.protocol.CanalPacket.HandshakeOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Handshake.class, com.alibaba.otter.canal.protocol.CanalPacket.Handshake.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Handshake.class, - com.alibaba.otter.canal.protocol.CanalPacket.Handshake.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Handshake.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Handshake.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - communicationEncoding_ = "utf8"; - bitField0_ = (bitField0_ & ~0x00000001); - seeds_ = com.google.protobuf.ByteString.EMPTY; - bitField0_ = (bitField0_ & ~0x00000002); - supportedCompressions_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Handshake getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Handshake.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Handshake build() { - com.alibaba.otter.canal.protocol.CanalPacket.Handshake result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Handshake buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Handshake result = new com.alibaba.otter.canal.protocol.CanalPacket.Handshake(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.communicationEncoding_ = communicationEncoding_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.seeds_ = seeds_; - if (((bitField0_ & 0x00000004) == 0x00000004)) { - supportedCompressions_ = java.util.Collections.unmodifiableList(supportedCompressions_); - bitField0_ = (bitField0_ & ~0x00000004); - } - result.supportedCompressions_ = supportedCompressions_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Handshake) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Handshake) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Handshake other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Handshake.getDefaultInstance()) return this; - if (other.hasCommunicationEncoding()) { - bitField0_ |= 0x00000001; - communicationEncoding_ = other.communicationEncoding_; - onChanged(); - } - if (other.hasSeeds()) { - setSeeds(other.getSeeds()); - } - if (!other.supportedCompressions_.isEmpty()) { - if (supportedCompressions_.isEmpty()) { - supportedCompressions_ = other.supportedCompressions_; - bitField0_ = (bitField0_ & ~0x00000004); - } else { - ensureSupportedCompressionsIsMutable(); - supportedCompressions_.addAll(other.supportedCompressions_); - } - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Handshake parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Handshake) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object communicationEncoding_ = "utf8"; - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public boolean hasCommunicationEncoding() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public java.lang.String getCommunicationEncoding() { - java.lang.Object ref = communicationEncoding_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - communicationEncoding_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public com.google.protobuf.ByteString getCommunicationEncodingBytes() { - java.lang.Object ref = communicationEncoding_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - communicationEncoding_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public Builder setCommunicationEncoding(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - communicationEncoding_ = value; - onChanged(); - return this; - } - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public Builder clearCommunicationEncoding() { - bitField0_ = (bitField0_ & ~0x00000001); - communicationEncoding_ = getDefaultInstance().getCommunicationEncoding(); - onChanged(); - return this; - } - - /** - * optional string communication_encoding = 1 [default = "utf8"]; - */ - public Builder setCommunicationEncodingBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - communicationEncoding_ = value; - onChanged(); - return this; - } - - private com.google.protobuf.ByteString seeds_ = com.google.protobuf.ByteString.EMPTY; - - /** - * optional bytes seeds = 2; - */ - public boolean hasSeeds() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional bytes seeds = 2; - */ - public com.google.protobuf.ByteString getSeeds() { - return seeds_; - } - - /** - * optional bytes seeds = 2; - */ - public Builder setSeeds(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - seeds_ = value; - onChanged(); - return this; - } - - /** - * optional bytes seeds = 2; - */ - public Builder clearSeeds() { - bitField0_ = (bitField0_ & ~0x00000002); - seeds_ = getDefaultInstance().getSeeds(); - onChanged(); - return this; - } - - private java.util.List supportedCompressions_ = java.util.Collections.emptyList(); - - private void ensureSupportedCompressionsIsMutable() { - if (!((bitField0_ & 0x00000004) == 0x00000004)) { - supportedCompressions_ = new java.util.ArrayList(supportedCompressions_); - bitField0_ |= 0x00000004; - } - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public java.util.List getSupportedCompressionsList() { - return java.util.Collections.unmodifiableList(supportedCompressions_); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public int getSupportedCompressionsCount() { - return supportedCompressions_.size(); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public com.alibaba.otter.canal.protocol.CanalPacket.Compression getSupportedCompressions(int index) { - return supportedCompressions_.get(index); - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public Builder setSupportedCompressions(int index, - com.alibaba.otter.canal.protocol.CanalPacket.Compression value) { - if (value == null) { - throw new NullPointerException(); - } - ensureSupportedCompressionsIsMutable(); - supportedCompressions_.set(index, value); - onChanged(); - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public Builder addSupportedCompressions(com.alibaba.otter.canal.protocol.CanalPacket.Compression value) { - if (value == null) { - throw new NullPointerException(); - } - ensureSupportedCompressionsIsMutable(); - supportedCompressions_.add(value); - onChanged(); - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public Builder addAllSupportedCompressions(java.lang.Iterable values) { - ensureSupportedCompressionsIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, supportedCompressions_); - onChanged(); - return this; - } - - /** - * repeated .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; - */ - public Builder clearSupportedCompressions() { - supportedCompressions_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000004); - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Handshake) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + seeds_ = com.google.protobuf.ByteString.EMPTY; - static { - defaultInstance = new Handshake(true); - defaultInstance.initFields(); + supportedCompressions_ = 0; + + communicationEncodingPresentCase_ = 0; + communicationEncodingPresent_ = null; + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Handshake getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Handshake.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Handshake build() { + com.alibaba.otter.canal.protocol.CanalPacket.Handshake result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Handshake) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Handshake buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Handshake result = new com.alibaba.otter.canal.protocol.CanalPacket.Handshake(this); + if (communicationEncodingPresentCase_ == 1) { + result.communicationEncodingPresent_ = communicationEncodingPresent_; + } + result.seeds_ = seeds_; + result.supportedCompressions_ = supportedCompressions_; + result.communicationEncodingPresentCase_ = communicationEncodingPresentCase_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Handshake) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Handshake)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Handshake other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Handshake.getDefaultInstance()) return this; + if (other.getSeeds() != com.google.protobuf.ByteString.EMPTY) { + setSeeds(other.getSeeds()); + } + if (other.supportedCompressions_ != 0) { + setSupportedCompressionsValue(other.getSupportedCompressionsValue()); + } + switch (other.getCommunicationEncodingPresentCase()) { + case COMMUNICATION_ENCODING: { + communicationEncodingPresentCase_ = 1; + communicationEncodingPresent_ = other.communicationEncodingPresent_; + onChanged(); + break; + } + case COMMUNICATIONENCODINGPRESENT_NOT_SET: { + break; + } + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Handshake parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Handshake) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int communicationEncodingPresentCase_ = 0; + private java.lang.Object communicationEncodingPresent_; + public CommunicationEncodingPresentCase + getCommunicationEncodingPresentCase() { + return CommunicationEncodingPresentCase.forNumber( + communicationEncodingPresentCase_); + } + + public Builder clearCommunicationEncodingPresent() { + communicationEncodingPresentCase_ = 0; + communicationEncodingPresent_ = null; + onChanged(); + return this; + } + + + /** + * string communication_encoding = 1; + */ + public java.lang.String getCommunicationEncoding() { + java.lang.Object ref = ""; + if (communicationEncodingPresentCase_ == 1) { + ref = communicationEncodingPresent_; + } + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + if (communicationEncodingPresentCase_ == 1) { + communicationEncodingPresent_ = s; + } + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string communication_encoding = 1; + */ + public com.google.protobuf.ByteString + getCommunicationEncodingBytes() { + java.lang.Object ref = ""; + if (communicationEncodingPresentCase_ == 1) { + ref = communicationEncodingPresent_; + } + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + if (communicationEncodingPresentCase_ == 1) { + communicationEncodingPresent_ = b; + } + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string communication_encoding = 1; + */ + public Builder setCommunicationEncoding( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + communicationEncodingPresentCase_ = 1; + communicationEncodingPresent_ = value; + onChanged(); + return this; + } + /** + * string communication_encoding = 1; + */ + public Builder clearCommunicationEncoding() { + if (communicationEncodingPresentCase_ == 1) { + communicationEncodingPresentCase_ = 0; + communicationEncodingPresent_ = null; + onChanged(); + } + return this; + } + /** + * string communication_encoding = 1; + */ + public Builder setCommunicationEncodingBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + communicationEncodingPresentCase_ = 1; + communicationEncodingPresent_ = value; + onChanged(); + return this; + } + + private com.google.protobuf.ByteString seeds_ = com.google.protobuf.ByteString.EMPTY; + /** + * bytes seeds = 2; + */ + public com.google.protobuf.ByteString getSeeds() { + return seeds_; + } + /** + * bytes seeds = 2; + */ + public Builder setSeeds(com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + + seeds_ = value; + onChanged(); + return this; + } + /** + * bytes seeds = 2; + */ + public Builder clearSeeds() { + + seeds_ = getDefaultInstance().getSeeds(); + onChanged(); + return this; + } + + private int supportedCompressions_ = 0; + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + public int getSupportedCompressionsValue() { + return supportedCompressions_; + } + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + public Builder setSupportedCompressionsValue(int value) { + supportedCompressions_ = value; + onChanged(); + return this; + } + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + public com.alibaba.otter.canal.protocol.CanalPacket.Compression getSupportedCompressions() { + @SuppressWarnings("deprecation") + com.alibaba.otter.canal.protocol.CanalPacket.Compression result = com.alibaba.otter.canal.protocol.CanalPacket.Compression.valueOf(supportedCompressions_); + return result == null ? com.alibaba.otter.canal.protocol.CanalPacket.Compression.UNRECOGNIZED : result; + } + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + public Builder setSupportedCompressions(com.alibaba.otter.canal.protocol.CanalPacket.Compression value) { + if (value == null) { + throw new NullPointerException(); + } + + supportedCompressions_ = value.getNumber(); + onChanged(); + return this; + } + /** + * .com.alibaba.otter.canal.protocol.Compression supported_compressions = 3; + */ + public Builder clearSupportedCompressions() { + + supportedCompressions_ = 0; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Handshake) } - public interface ClientAuthOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.ClientAuth) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string username = 1; - */ - boolean hasUsername(); - - /** - * optional string username = 1; - */ - java.lang.String getUsername(); - - /** - * optional string username = 1; - */ - com.google.protobuf.ByteString getUsernameBytes(); - - /** - * optional bytes password = 2; - * - *
      -         * hashed password with seeds from Handshake message
      -         * 
      - */ - boolean hasPassword(); - - /** - * optional bytes password = 2; - * - *
      -         * hashed password with seeds from Handshake message
      -         * 
      - */ - com.google.protobuf.ByteString getPassword(); - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - boolean hasNetReadTimeout(); - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - int getNetReadTimeout(); - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - boolean hasNetWriteTimeout(); - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - int getNetWriteTimeout(); - - /** - * optional string destination = 5; - */ - boolean hasDestination(); - - /** - * optional string destination = 5; - */ - java.lang.String getDestination(); - - /** - * optional string destination = 5; - */ - com.google.protobuf.ByteString getDestinationBytes(); - - /** - * optional string client_id = 6; - */ - boolean hasClientId(); - - /** - * optional string client_id = 6; - */ - java.lang.String getClientId(); - - /** - * optional string client_id = 6; - */ - com.google.protobuf.ByteString getClientIdBytes(); - - /** - * optional string filter = 7; - */ - boolean hasFilter(); - - /** - * optional string filter = 7; - */ - java.lang.String getFilter(); - - /** - * optional string filter = 7; - */ - com.google.protobuf.ByteString getFilterBytes(); - - /** - * optional int64 start_timestamp = 8; - */ - boolean hasStartTimestamp(); - - /** - * optional int64 start_timestamp = 8; - */ - long getStartTimestamp(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Handshake) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Handshake DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Handshake(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Handshake getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Handshake parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Handshake(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Handshake getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface ClientAuthOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.ClientAuth) + com.google.protobuf.MessageOrBuilder { + /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientAuth} + * string username = 1; + */ + java.lang.String getUsername(); + /** + * string username = 1; + */ + com.google.protobuf.ByteString + getUsernameBytes(); + + /** + *
      +     * hashed password with seeds from Handshake message
      +     * 
      * + * bytes password = 2; + */ + com.google.protobuf.ByteString getPassword(); + + /** + *
      +     * in seconds
      +     * 
      + * + * int32 net_read_timeout = 3; + */ + int getNetReadTimeout(); + + /** + *
      +     * in seconds
      +     * 
      + * + * int32 net_write_timeout = 4; + */ + int getNetWriteTimeout(); + + /** + * string destination = 5; + */ + java.lang.String getDestination(); + /** + * string destination = 5; + */ + com.google.protobuf.ByteString + getDestinationBytes(); + + /** + * string client_id = 6; + */ + java.lang.String getClientId(); + /** + * string client_id = 6; + */ + com.google.protobuf.ByteString + getClientIdBytes(); + + /** + * string filter = 7; + */ + java.lang.String getFilter(); + /** + * string filter = 7; + */ + com.google.protobuf.ByteString + getFilterBytes(); + + /** + * int64 start_timestamp = 8; + */ + long getStartTimestamp(); + + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.NetReadTimeoutPresentCase getNetReadTimeoutPresentCase(); + + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.NetWriteTimeoutPresentCase getNetWriteTimeoutPresentCase(); + } + /** + *
      +   * client authentication
      +   * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientAuth} + */ + public static final class ClientAuth extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.ClientAuth) + ClientAuthOrBuilder { + private static final long serialVersionUID = 0L; + // Use ClientAuth.newBuilder() to construct. + private ClientAuth(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private ClientAuth() { + username_ = ""; + password_ = com.google.protobuf.ByteString.EMPTY; + destination_ = ""; + clientId_ = ""; + filter_ = ""; + startTimestamp_ = 0L; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private ClientAuth( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + + username_ = s; + break; + } + case 18: { + + password_ = input.readBytes(); + break; + } + case 24: { + netReadTimeoutPresentCase_ = 3; + netReadTimeoutPresent_ = input.readInt32(); + break; + } + case 32: { + netWriteTimeoutPresentCase_ = 4; + netWriteTimeoutPresent_ = input.readInt32(); + break; + } + case 42: { + java.lang.String s = input.readStringRequireUtf8(); + + destination_ = s; + break; + } + case 50: { + java.lang.String s = input.readStringRequireUtf8(); + + clientId_ = s; + break; + } + case 58: { + java.lang.String s = input.readStringRequireUtf8(); + + filter_ = s; + break; + } + case 64: { + + startTimestamp_ = input.readInt64(); + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.class, com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.Builder.class); + } + + private int netReadTimeoutPresentCase_ = 0; + private java.lang.Object netReadTimeoutPresent_; + public enum NetReadTimeoutPresentCase + implements com.google.protobuf.Internal.EnumLite { + NET_READ_TIMEOUT(3), + NETREADTIMEOUTPRESENT_NOT_SET(0); + private final int value; + private NetReadTimeoutPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static NetReadTimeoutPresentCase valueOf(int value) { + return forNumber(value); + } + + public static NetReadTimeoutPresentCase forNumber(int value) { + switch (value) { + case 3: return NET_READ_TIMEOUT; + case 0: return NETREADTIMEOUTPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public NetReadTimeoutPresentCase + getNetReadTimeoutPresentCase() { + return NetReadTimeoutPresentCase.forNumber( + netReadTimeoutPresentCase_); + } + + private int netWriteTimeoutPresentCase_ = 0; + private java.lang.Object netWriteTimeoutPresent_; + public enum NetWriteTimeoutPresentCase + implements com.google.protobuf.Internal.EnumLite { + NET_WRITE_TIMEOUT(4), + NETWRITETIMEOUTPRESENT_NOT_SET(0); + private final int value; + private NetWriteTimeoutPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static NetWriteTimeoutPresentCase valueOf(int value) { + return forNumber(value); + } + + public static NetWriteTimeoutPresentCase forNumber(int value) { + switch (value) { + case 4: return NET_WRITE_TIMEOUT; + case 0: return NETWRITETIMEOUTPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public NetWriteTimeoutPresentCase + getNetWriteTimeoutPresentCase() { + return NetWriteTimeoutPresentCase.forNumber( + netWriteTimeoutPresentCase_); + } + + public static final int USERNAME_FIELD_NUMBER = 1; + private volatile java.lang.Object username_; + /** + * string username = 1; + */ + public java.lang.String getUsername() { + java.lang.Object ref = username_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + username_ = s; + return s; + } + } + /** + * string username = 1; + */ + public com.google.protobuf.ByteString + getUsernameBytes() { + java.lang.Object ref = username_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + username_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int PASSWORD_FIELD_NUMBER = 2; + private com.google.protobuf.ByteString password_; + /** + *
      +     * hashed password with seeds from Handshake message
      +     * 
      + * + * bytes password = 2; + */ + public com.google.protobuf.ByteString getPassword() { + return password_; + } + + public static final int NET_READ_TIMEOUT_FIELD_NUMBER = 3; + /** + *
      +     * in seconds
      +     * 
      + * + * int32 net_read_timeout = 3; + */ + public int getNetReadTimeout() { + if (netReadTimeoutPresentCase_ == 3) { + return (java.lang.Integer) netReadTimeoutPresent_; + } + return 0; + } + + public static final int NET_WRITE_TIMEOUT_FIELD_NUMBER = 4; + /** + *
      +     * in seconds
      +     * 
      + * + * int32 net_write_timeout = 4; + */ + public int getNetWriteTimeout() { + if (netWriteTimeoutPresentCase_ == 4) { + return (java.lang.Integer) netWriteTimeoutPresent_; + } + return 0; + } + + public static final int DESTINATION_FIELD_NUMBER = 5; + private volatile java.lang.Object destination_; + /** + * string destination = 5; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } + } + /** + * string destination = 5; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int CLIENT_ID_FIELD_NUMBER = 6; + private volatile java.lang.Object clientId_; + /** + * string client_id = 6; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } + } + /** + * string client_id = 6; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int FILTER_FIELD_NUMBER = 7; + private volatile java.lang.Object filter_; + /** + * string filter = 7; + */ + public java.lang.String getFilter() { + java.lang.Object ref = filter_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + filter_ = s; + return s; + } + } + /** + * string filter = 7; + */ + public com.google.protobuf.ByteString + getFilterBytes() { + java.lang.Object ref = filter_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + filter_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int START_TIMESTAMP_FIELD_NUMBER = 8; + private long startTimestamp_; + /** + * int64 start_timestamp = 8; + */ + public long getStartTimestamp() { + return startTimestamp_; + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (!getUsernameBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, username_); + } + if (!password_.isEmpty()) { + output.writeBytes(2, password_); + } + if (netReadTimeoutPresentCase_ == 3) { + output.writeInt32( + 3, (int)((java.lang.Integer) netReadTimeoutPresent_)); + } + if (netWriteTimeoutPresentCase_ == 4) { + output.writeInt32( + 4, (int)((java.lang.Integer) netWriteTimeoutPresent_)); + } + if (!getDestinationBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 5, destination_); + } + if (!getClientIdBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 6, clientId_); + } + if (!getFilterBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 7, filter_); + } + if (startTimestamp_ != 0L) { + output.writeInt64(8, startTimestamp_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (!getUsernameBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, username_); + } + if (!password_.isEmpty()) { + size += com.google.protobuf.CodedOutputStream + .computeBytesSize(2, password_); + } + if (netReadTimeoutPresentCase_ == 3) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size( + 3, (int)((java.lang.Integer) netReadTimeoutPresent_)); + } + if (netWriteTimeoutPresentCase_ == 4) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size( + 4, (int)((java.lang.Integer) netWriteTimeoutPresent_)); + } + if (!getDestinationBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(5, destination_); + } + if (!getClientIdBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(6, clientId_); + } + if (!getFilterBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(7, filter_); + } + if (startTimestamp_ != 0L) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(8, startTimestamp_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth other = (com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth) obj; + + boolean result = true; + result = result && getUsername() + .equals(other.getUsername()); + result = result && getPassword() + .equals(other.getPassword()); + result = result && getDestination() + .equals(other.getDestination()); + result = result && getClientId() + .equals(other.getClientId()); + result = result && getFilter() + .equals(other.getFilter()); + result = result && (getStartTimestamp() + == other.getStartTimestamp()); + result = result && getNetReadTimeoutPresentCase().equals( + other.getNetReadTimeoutPresentCase()); + if (!result) return false; + switch (netReadTimeoutPresentCase_) { + case 3: + result = result && (getNetReadTimeout() + == other.getNetReadTimeout()); + break; + case 0: + default: + } + result = result && getNetWriteTimeoutPresentCase().equals( + other.getNetWriteTimeoutPresentCase()); + if (!result) return false; + switch (netWriteTimeoutPresentCase_) { + case 4: + result = result && (getNetWriteTimeout() + == other.getNetWriteTimeout()); + break; + case 0: + default: + } + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + USERNAME_FIELD_NUMBER; + hash = (53 * hash) + getUsername().hashCode(); + hash = (37 * hash) + PASSWORD_FIELD_NUMBER; + hash = (53 * hash) + getPassword().hashCode(); + hash = (37 * hash) + DESTINATION_FIELD_NUMBER; + hash = (53 * hash) + getDestination().hashCode(); + hash = (37 * hash) + CLIENT_ID_FIELD_NUMBER; + hash = (53 * hash) + getClientId().hashCode(); + hash = (37 * hash) + FILTER_FIELD_NUMBER; + hash = (53 * hash) + getFilter().hashCode(); + hash = (37 * hash) + START_TIMESTAMP_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getStartTimestamp()); + switch (netReadTimeoutPresentCase_) { + case 3: + hash = (37 * hash) + NET_READ_TIMEOUT_FIELD_NUMBER; + hash = (53 * hash) + getNetReadTimeout(); + break; + case 0: + default: + } + switch (netWriteTimeoutPresentCase_) { + case 4: + hash = (37 * hash) + NET_WRITE_TIMEOUT_FIELD_NUMBER; + hash = (53 * hash) + getNetWriteTimeout(); + break; + case 0: + default: + } + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } + /** *
            * client authentication
            * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientAuth} */ - public static final class ClientAuth extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.ClientAuth) - ClientAuthOrBuilder { - - // Use ClientAuth.newBuilder() to construct. - private ClientAuth(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private ClientAuth(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final ClientAuth defaultInstance; - - public static ClientAuth getDefaultInstance() { - return defaultInstance; - } - - public ClientAuth getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private ClientAuth(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - username_ = bs; - break; - } - case 18: { - bitField0_ |= 0x00000002; - password_ = input.readBytes(); - break; - } - case 24: { - bitField0_ |= 0x00000004; - netReadTimeout_ = input.readInt32(); - break; - } - case 32: { - bitField0_ |= 0x00000008; - netWriteTimeout_ = input.readInt32(); - break; - } - case 42: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000010; - destination_ = bs; - break; - } - case 50: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000020; - clientId_ = bs; - break; - } - case 58: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000040; - filter_ = bs; - break; - } - case 64: { - bitField0_ |= 0x00000080; - startTimestamp_ = input.readInt64(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.class, - com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public ClientAuth parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new ClientAuth(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int USERNAME_FIELD_NUMBER = 1; - private java.lang.Object username_; - - /** - * optional string username = 1; - */ - public boolean hasUsername() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string username = 1; - */ - public java.lang.String getUsername() { - java.lang.Object ref = username_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - username_ = s; - } - return s; - } - } - - /** - * optional string username = 1; - */ - public com.google.protobuf.ByteString getUsernameBytes() { - java.lang.Object ref = username_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - username_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int PASSWORD_FIELD_NUMBER = 2; - private com.google.protobuf.ByteString password_; - - /** - * optional bytes password = 2; - * - *
      -         * hashed password with seeds from Handshake message
      -         * 
      - */ - public boolean hasPassword() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional bytes password = 2; - * - *
      -         * hashed password with seeds from Handshake message
      -         * 
      - */ - public com.google.protobuf.ByteString getPassword() { - return password_; - } - - public static final int NET_READ_TIMEOUT_FIELD_NUMBER = 3; - private int netReadTimeout_; - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - public boolean hasNetReadTimeout() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - public int getNetReadTimeout() { - return netReadTimeout_; - } - - public static final int NET_WRITE_TIMEOUT_FIELD_NUMBER = 4; - private int netWriteTimeout_; - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - public boolean hasNetWriteTimeout() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -         * in seconds
      -         * 
      - */ - public int getNetWriteTimeout() { - return netWriteTimeout_; - } - - public static final int DESTINATION_FIELD_NUMBER = 5; - private java.lang.Object destination_; - - /** - * optional string destination = 5; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional string destination = 5; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } - } - - /** - * optional string destination = 5; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int CLIENT_ID_FIELD_NUMBER = 6; - private java.lang.Object clientId_; - - /** - * optional string client_id = 6; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional string client_id = 6; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } - } - - /** - * optional string client_id = 6; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int FILTER_FIELD_NUMBER = 7; - private java.lang.Object filter_; - - /** - * optional string filter = 7; - */ - public boolean hasFilter() { - return ((bitField0_ & 0x00000040) == 0x00000040); - } - - /** - * optional string filter = 7; - */ - public java.lang.String getFilter() { - java.lang.Object ref = filter_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - filter_ = s; - } - return s; - } - } - - /** - * optional string filter = 7; - */ - public com.google.protobuf.ByteString getFilterBytes() { - java.lang.Object ref = filter_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - filter_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int START_TIMESTAMP_FIELD_NUMBER = 8; - private long startTimestamp_; - - /** - * optional int64 start_timestamp = 8; - */ - public boolean hasStartTimestamp() { - return ((bitField0_ & 0x00000080) == 0x00000080); - } - - /** - * optional int64 start_timestamp = 8; - */ - public long getStartTimestamp() { - return startTimestamp_; - } - - private void initFields() { - username_ = ""; - password_ = com.google.protobuf.ByteString.EMPTY; - netReadTimeout_ = 0; - netWriteTimeout_ = 0; - destination_ = ""; - clientId_ = ""; - filter_ = ""; - startTimestamp_ = 0L; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getUsernameBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, password_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeInt32(3, netReadTimeout_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - output.writeInt32(4, netWriteTimeout_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - output.writeBytes(5, getDestinationBytes()); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - output.writeBytes(6, getClientIdBytes()); - } - if (((bitField0_ & 0x00000040) == 0x00000040)) { - output.writeBytes(7, getFilterBytes()); - } - if (((bitField0_ & 0x00000080) == 0x00000080)) { - output.writeInt64(8, startTimestamp_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getUsernameBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, password_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(3, netReadTimeout_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(4, netWriteTimeout_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(5, getDestinationBytes()); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(6, getClientIdBytes()); - } - if (((bitField0_ & 0x00000040) == 0x00000040)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(7, getFilterBytes()); - } - if (((bitField0_ & 0x00000080) == 0x00000080)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(8, startTimestamp_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientAuth} - * - *
      -         * client authentication
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.ClientAuth) com.alibaba.otter.canal.protocol.CanalPacket.ClientAuthOrBuilder { - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.class, - com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.Builder.class); - } - - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - username_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - password_ = com.google.protobuf.ByteString.EMPTY; - bitField0_ = (bitField0_ & ~0x00000002); - netReadTimeout_ = 0; - bitField0_ = (bitField0_ & ~0x00000004); - netWriteTimeout_ = 0; - bitField0_ = (bitField0_ & ~0x00000008); - destination_ = ""; - bitField0_ = (bitField0_ & ~0x00000010); - clientId_ = ""; - bitField0_ = (bitField0_ & ~0x00000020); - filter_ = ""; - bitField0_ = (bitField0_ & ~0x00000040); - startTimestamp_ = 0L; - bitField0_ = (bitField0_ & ~0x00000080); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth build() { - com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth result = new com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.username_ = username_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.password_ = password_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.netReadTimeout_ = netReadTimeout_; - if (((from_bitField0_ & 0x00000008) == 0x00000008)) { - to_bitField0_ |= 0x00000008; - } - result.netWriteTimeout_ = netWriteTimeout_; - if (((from_bitField0_ & 0x00000010) == 0x00000010)) { - to_bitField0_ |= 0x00000010; - } - result.destination_ = destination_; - if (((from_bitField0_ & 0x00000020) == 0x00000020)) { - to_bitField0_ |= 0x00000020; - } - result.clientId_ = clientId_; - if (((from_bitField0_ & 0x00000040) == 0x00000040)) { - to_bitField0_ |= 0x00000040; - } - result.filter_ = filter_; - if (((from_bitField0_ & 0x00000080) == 0x00000080)) { - to_bitField0_ |= 0x00000080; - } - result.startTimestamp_ = startTimestamp_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.getDefaultInstance()) return this; - if (other.hasUsername()) { - bitField0_ |= 0x00000001; - username_ = other.username_; - onChanged(); - } - if (other.hasPassword()) { - setPassword(other.getPassword()); - } - if (other.hasNetReadTimeout()) { - setNetReadTimeout(other.getNetReadTimeout()); - } - if (other.hasNetWriteTimeout()) { - setNetWriteTimeout(other.getNetWriteTimeout()); - } - if (other.hasDestination()) { - bitField0_ |= 0x00000010; - destination_ = other.destination_; - onChanged(); - } - if (other.hasClientId()) { - bitField0_ |= 0x00000020; - clientId_ = other.clientId_; - onChanged(); - } - if (other.hasFilter()) { - bitField0_ |= 0x00000040; - filter_ = other.filter_; - onChanged(); - } - if (other.hasStartTimestamp()) { - setStartTimestamp(other.getStartTimestamp()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object username_ = ""; - - /** - * optional string username = 1; - */ - public boolean hasUsername() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string username = 1; - */ - public java.lang.String getUsername() { - java.lang.Object ref = username_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - username_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string username = 1; - */ - public com.google.protobuf.ByteString getUsernameBytes() { - java.lang.Object ref = username_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - username_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string username = 1; - */ - public Builder setUsername(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - username_ = value; - onChanged(); - return this; - } - - /** - * optional string username = 1; - */ - public Builder clearUsername() { - bitField0_ = (bitField0_ & ~0x00000001); - username_ = getDefaultInstance().getUsername(); - onChanged(); - return this; - } - - /** - * optional string username = 1; - */ - public Builder setUsernameBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - username_ = value; - onChanged(); - return this; - } - - private com.google.protobuf.ByteString password_ = com.google.protobuf.ByteString.EMPTY; - - /** - * optional bytes password = 2; - * - *
      -             * hashed password with seeds from Handshake message
      -             * 
      - */ - public boolean hasPassword() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional bytes password = 2; - * - *
      -             * hashed password with seeds from Handshake message
      -             * 
      - */ - public com.google.protobuf.ByteString getPassword() { - return password_; - } - - /** - * optional bytes password = 2; - * - *
      -             * hashed password with seeds from Handshake message
      -             * 
      - */ - public Builder setPassword(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - password_ = value; - onChanged(); - return this; - } - - /** - * optional bytes password = 2; - * - *
      -             * hashed password with seeds from Handshake message
      -             * 
      - */ - public Builder clearPassword() { - bitField0_ = (bitField0_ & ~0x00000002); - password_ = getDefaultInstance().getPassword(); - onChanged(); - return this; - } - - private int netReadTimeout_; - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public boolean hasNetReadTimeout() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public int getNetReadTimeout() { - return netReadTimeout_; - } - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public Builder setNetReadTimeout(int value) { - bitField0_ |= 0x00000004; - netReadTimeout_ = value; - onChanged(); - return this; - } - - /** - * optional int32 net_read_timeout = 3 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public Builder clearNetReadTimeout() { - bitField0_ = (bitField0_ & ~0x00000004); - netReadTimeout_ = 0; - onChanged(); - return this; - } - - private int netWriteTimeout_; - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public boolean hasNetWriteTimeout() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public int getNetWriteTimeout() { - return netWriteTimeout_; - } - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public Builder setNetWriteTimeout(int value) { - bitField0_ |= 0x00000008; - netWriteTimeout_ = value; - onChanged(); - return this; - } - - /** - * optional int32 net_write_timeout = 4 [default = 0]; - * - *
      -             * in seconds
      -             * 
      - */ - public Builder clearNetWriteTimeout() { - bitField0_ = (bitField0_ & ~0x00000008); - netWriteTimeout_ = 0; - onChanged(); - return this; - } - - private java.lang.Object destination_ = ""; - - /** - * optional string destination = 5; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional string destination = 5; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string destination = 5; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string destination = 5; - */ - public Builder setDestination(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000010; - destination_ = value; - onChanged(); - return this; - } - - /** - * optional string destination = 5; - */ - public Builder clearDestination() { - bitField0_ = (bitField0_ & ~0x00000010); - destination_ = getDefaultInstance().getDestination(); - onChanged(); - return this; - } - - /** - * optional string destination = 5; - */ - public Builder setDestinationBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000010; - destination_ = value; - onChanged(); - return this; - } - - private java.lang.Object clientId_ = ""; - - /** - * optional string client_id = 6; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional string client_id = 6; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string client_id = 6; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string client_id = 6; - */ - public Builder setClientId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000020; - clientId_ = value; - onChanged(); - return this; - } - - /** - * optional string client_id = 6; - */ - public Builder clearClientId() { - bitField0_ = (bitField0_ & ~0x00000020); - clientId_ = getDefaultInstance().getClientId(); - onChanged(); - return this; - } - - /** - * optional string client_id = 6; - */ - public Builder setClientIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000020; - clientId_ = value; - onChanged(); - return this; - } - - private java.lang.Object filter_ = ""; - - /** - * optional string filter = 7; - */ - public boolean hasFilter() { - return ((bitField0_ & 0x00000040) == 0x00000040); - } - - /** - * optional string filter = 7; - */ - public java.lang.String getFilter() { - java.lang.Object ref = filter_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - filter_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string filter = 7; - */ - public com.google.protobuf.ByteString getFilterBytes() { - java.lang.Object ref = filter_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - filter_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string filter = 7; - */ - public Builder setFilter(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000040; - filter_ = value; - onChanged(); - return this; - } - - /** - * optional string filter = 7; - */ - public Builder clearFilter() { - bitField0_ = (bitField0_ & ~0x00000040); - filter_ = getDefaultInstance().getFilter(); - onChanged(); - return this; - } - - /** - * optional string filter = 7; - */ - public Builder setFilterBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000040; - filter_ = value; - onChanged(); - return this; - } - - private long startTimestamp_; - - /** - * optional int64 start_timestamp = 8; - */ - public boolean hasStartTimestamp() { - return ((bitField0_ & 0x00000080) == 0x00000080); - } - - /** - * optional int64 start_timestamp = 8; - */ - public long getStartTimestamp() { - return startTimestamp_; - } - - /** - * optional int64 start_timestamp = 8; - */ - public Builder setStartTimestamp(long value) { - bitField0_ |= 0x00000080; - startTimestamp_ = value; - onChanged(); - return this; - } - - /** - * optional int64 start_timestamp = 8; - */ - public Builder clearStartTimestamp() { - bitField0_ = (bitField0_ & ~0x00000080); - startTimestamp_ = 0L; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.ClientAuth) + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.class, com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.Builder.class); + } + + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } + + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + username_ = ""; - static { - defaultInstance = new ClientAuth(true); - defaultInstance.initFields(); + password_ = com.google.protobuf.ByteString.EMPTY; + + destination_ = ""; + + clientId_ = ""; + + filter_ = ""; + + startTimestamp_ = 0L; + + netReadTimeoutPresentCase_ = 0; + netReadTimeoutPresent_ = null; + netWriteTimeoutPresentCase_ = 0; + netWriteTimeoutPresent_ = null; + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth build() { + com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.ClientAuth) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth result = new com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth(this); + result.username_ = username_; + result.password_ = password_; + if (netReadTimeoutPresentCase_ == 3) { + result.netReadTimeoutPresent_ = netReadTimeoutPresent_; + } + if (netWriteTimeoutPresentCase_ == 4) { + result.netWriteTimeoutPresent_ = netWriteTimeoutPresent_; + } + result.destination_ = destination_; + result.clientId_ = clientId_; + result.filter_ = filter_; + result.startTimestamp_ = startTimestamp_; + result.netReadTimeoutPresentCase_ = netReadTimeoutPresentCase_; + result.netWriteTimeoutPresentCase_ = netWriteTimeoutPresentCase_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth.getDefaultInstance()) return this; + if (!other.getUsername().isEmpty()) { + username_ = other.username_; + onChanged(); + } + if (other.getPassword() != com.google.protobuf.ByteString.EMPTY) { + setPassword(other.getPassword()); + } + if (!other.getDestination().isEmpty()) { + destination_ = other.destination_; + onChanged(); + } + if (!other.getClientId().isEmpty()) { + clientId_ = other.clientId_; + onChanged(); + } + if (!other.getFilter().isEmpty()) { + filter_ = other.filter_; + onChanged(); + } + if (other.getStartTimestamp() != 0L) { + setStartTimestamp(other.getStartTimestamp()); + } + switch (other.getNetReadTimeoutPresentCase()) { + case NET_READ_TIMEOUT: { + setNetReadTimeout(other.getNetReadTimeout()); + break; + } + case NETREADTIMEOUTPRESENT_NOT_SET: { + break; + } + } + switch (other.getNetWriteTimeoutPresentCase()) { + case NET_WRITE_TIMEOUT: { + setNetWriteTimeout(other.getNetWriteTimeout()); + break; + } + case NETWRITETIMEOUTPRESENT_NOT_SET: { + break; + } + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int netReadTimeoutPresentCase_ = 0; + private java.lang.Object netReadTimeoutPresent_; + public NetReadTimeoutPresentCase + getNetReadTimeoutPresentCase() { + return NetReadTimeoutPresentCase.forNumber( + netReadTimeoutPresentCase_); + } + + public Builder clearNetReadTimeoutPresent() { + netReadTimeoutPresentCase_ = 0; + netReadTimeoutPresent_ = null; + onChanged(); + return this; + } + + private int netWriteTimeoutPresentCase_ = 0; + private java.lang.Object netWriteTimeoutPresent_; + public NetWriteTimeoutPresentCase + getNetWriteTimeoutPresentCase() { + return NetWriteTimeoutPresentCase.forNumber( + netWriteTimeoutPresentCase_); + } + + public Builder clearNetWriteTimeoutPresent() { + netWriteTimeoutPresentCase_ = 0; + netWriteTimeoutPresent_ = null; + onChanged(); + return this; + } + + + private java.lang.Object username_ = ""; + /** + * string username = 1; + */ + public java.lang.String getUsername() { + java.lang.Object ref = username_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + username_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string username = 1; + */ + public com.google.protobuf.ByteString + getUsernameBytes() { + java.lang.Object ref = username_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + username_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string username = 1; + */ + public Builder setUsername( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + username_ = value; + onChanged(); + return this; + } + /** + * string username = 1; + */ + public Builder clearUsername() { + + username_ = getDefaultInstance().getUsername(); + onChanged(); + return this; + } + /** + * string username = 1; + */ + public Builder setUsernameBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + username_ = value; + onChanged(); + return this; + } + + private com.google.protobuf.ByteString password_ = com.google.protobuf.ByteString.EMPTY; + /** + *
      +       * hashed password with seeds from Handshake message
      +       * 
      + * + * bytes password = 2; + */ + public com.google.protobuf.ByteString getPassword() { + return password_; + } + /** + *
      +       * hashed password with seeds from Handshake message
      +       * 
      + * + * bytes password = 2; + */ + public Builder setPassword(com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + + password_ = value; + onChanged(); + return this; + } + /** + *
      +       * hashed password with seeds from Handshake message
      +       * 
      + * + * bytes password = 2; + */ + public Builder clearPassword() { + + password_ = getDefaultInstance().getPassword(); + onChanged(); + return this; + } + + /** + *
      +       * in seconds
      +       * 
      + * + * int32 net_read_timeout = 3; + */ + public int getNetReadTimeout() { + if (netReadTimeoutPresentCase_ == 3) { + return (java.lang.Integer) netReadTimeoutPresent_; + } + return 0; + } + /** + *
      +       * in seconds
      +       * 
      + * + * int32 net_read_timeout = 3; + */ + public Builder setNetReadTimeout(int value) { + netReadTimeoutPresentCase_ = 3; + netReadTimeoutPresent_ = value; + onChanged(); + return this; + } + /** + *
      +       * in seconds
      +       * 
      + * + * int32 net_read_timeout = 3; + */ + public Builder clearNetReadTimeout() { + if (netReadTimeoutPresentCase_ == 3) { + netReadTimeoutPresentCase_ = 0; + netReadTimeoutPresent_ = null; + onChanged(); + } + return this; + } + + /** + *
      +       * in seconds
      +       * 
      + * + * int32 net_write_timeout = 4; + */ + public int getNetWriteTimeout() { + if (netWriteTimeoutPresentCase_ == 4) { + return (java.lang.Integer) netWriteTimeoutPresent_; + } + return 0; + } + /** + *
      +       * in seconds
      +       * 
      + * + * int32 net_write_timeout = 4; + */ + public Builder setNetWriteTimeout(int value) { + netWriteTimeoutPresentCase_ = 4; + netWriteTimeoutPresent_ = value; + onChanged(); + return this; + } + /** + *
      +       * in seconds
      +       * 
      + * + * int32 net_write_timeout = 4; + */ + public Builder clearNetWriteTimeout() { + if (netWriteTimeoutPresentCase_ == 4) { + netWriteTimeoutPresentCase_ = 0; + netWriteTimeoutPresent_ = null; + onChanged(); + } + return this; + } + + private java.lang.Object destination_ = ""; + /** + * string destination = 5; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string destination = 5; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string destination = 5; + */ + public Builder setDestination( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + destination_ = value; + onChanged(); + return this; + } + /** + * string destination = 5; + */ + public Builder clearDestination() { + + destination_ = getDefaultInstance().getDestination(); + onChanged(); + return this; + } + /** + * string destination = 5; + */ + public Builder setDestinationBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + destination_ = value; + onChanged(); + return this; + } + + private java.lang.Object clientId_ = ""; + /** + * string client_id = 6; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string client_id = 6; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string client_id = 6; + */ + public Builder setClientId( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + clientId_ = value; + onChanged(); + return this; + } + /** + * string client_id = 6; + */ + public Builder clearClientId() { + + clientId_ = getDefaultInstance().getClientId(); + onChanged(); + return this; + } + /** + * string client_id = 6; + */ + public Builder setClientIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + clientId_ = value; + onChanged(); + return this; + } + + private java.lang.Object filter_ = ""; + /** + * string filter = 7; + */ + public java.lang.String getFilter() { + java.lang.Object ref = filter_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + filter_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string filter = 7; + */ + public com.google.protobuf.ByteString + getFilterBytes() { + java.lang.Object ref = filter_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + filter_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string filter = 7; + */ + public Builder setFilter( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + filter_ = value; + onChanged(); + return this; + } + /** + * string filter = 7; + */ + public Builder clearFilter() { + + filter_ = getDefaultInstance().getFilter(); + onChanged(); + return this; + } + /** + * string filter = 7; + */ + public Builder setFilterBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + filter_ = value; + onChanged(); + return this; + } + + private long startTimestamp_ ; + /** + * int64 start_timestamp = 8; + */ + public long getStartTimestamp() { + return startTimestamp_; + } + /** + * int64 start_timestamp = 8; + */ + public Builder setStartTimestamp(long value) { + + startTimestamp_ = value; + onChanged(); + return this; + } + /** + * int64 start_timestamp = 8; + */ + public Builder clearStartTimestamp() { + + startTimestamp_ = 0L; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.ClientAuth) } - public interface AckOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Ack) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int32 error_code = 1 [default = 0]; - */ - boolean hasErrorCode(); - - /** - * optional int32 error_code = 1 [default = 0]; - */ - int getErrorCode(); - - /** - * optional string error_message = 2; - * - *
      -         * if something like compression is not supported, erorr_message will tell about it.
      -         * 
      - */ - boolean hasErrorMessage(); - - /** - * optional string error_message = 2; - * - *
      -         * if something like compression is not supported, erorr_message will tell about it.
      -         * 
      - */ - java.lang.String getErrorMessage(); - - /** - * optional string error_message = 2; - * - *
      -         * if something like compression is not supported, erorr_message will tell about it.
      -         * 
      - */ - com.google.protobuf.ByteString getErrorMessageBytes(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.ClientAuth) + private static final com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public ClientAuth parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new ClientAuth(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAuth getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface AckOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Ack) + com.google.protobuf.MessageOrBuilder { + + /** + * int32 error_code = 1; + */ + int getErrorCode(); + + /** + *
      +     * if something like compression is not supported, erorr_message will tell about it.
      +     * 
      + * + * string error_message = 2; + */ + java.lang.String getErrorMessage(); + /** + *
      +     * if something like compression is not supported, erorr_message will tell about it.
      +     * 
      + * + * string error_message = 2; + */ + com.google.protobuf.ByteString + getErrorMessageBytes(); + + public com.alibaba.otter.canal.protocol.CanalPacket.Ack.ErrorCodePresentCase getErrorCodePresentCase(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.Ack} + */ + public static final class Ack extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Ack) + AckOrBuilder { + private static final long serialVersionUID = 0L; + // Use Ack.newBuilder() to construct. + private Ack(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Ack() { + errorMessage_ = ""; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Ack( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 8: { + errorCodePresentCase_ = 1; + errorCodePresent_ = input.readInt32(); + break; + } + case 18: { + java.lang.String s = input.readStringRequireUtf8(); + + errorMessage_ = s; + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Ack.class, com.alibaba.otter.canal.protocol.CanalPacket.Ack.Builder.class); + } + + private int errorCodePresentCase_ = 0; + private java.lang.Object errorCodePresent_; + public enum ErrorCodePresentCase + implements com.google.protobuf.Internal.EnumLite { + ERROR_CODE(1), + ERRORCODEPRESENT_NOT_SET(0); + private final int value; + private ErrorCodePresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static ErrorCodePresentCase valueOf(int value) { + return forNumber(value); + } + + public static ErrorCodePresentCase forNumber(int value) { + switch (value) { + case 1: return ERROR_CODE; + case 0: return ERRORCODEPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public ErrorCodePresentCase + getErrorCodePresentCase() { + return ErrorCodePresentCase.forNumber( + errorCodePresentCase_); + } + + public static final int ERROR_CODE_FIELD_NUMBER = 1; + /** + * int32 error_code = 1; + */ + public int getErrorCode() { + if (errorCodePresentCase_ == 1) { + return (java.lang.Integer) errorCodePresent_; + } + return 0; + } + + public static final int ERROR_MESSAGE_FIELD_NUMBER = 2; + private volatile java.lang.Object errorMessage_; + /** + *
      +     * if something like compression is not supported, erorr_message will tell about it.
      +     * 
      + * + * string error_message = 2; + */ + public java.lang.String getErrorMessage() { + java.lang.Object ref = errorMessage_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + errorMessage_ = s; + return s; + } + } + /** + *
      +     * if something like compression is not supported, erorr_message will tell about it.
      +     * 
      + * + * string error_message = 2; + */ + public com.google.protobuf.ByteString + getErrorMessageBytes() { + java.lang.Object ref = errorMessage_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + errorMessage_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (errorCodePresentCase_ == 1) { + output.writeInt32( + 1, (int)((java.lang.Integer) errorCodePresent_)); + } + if (!getErrorMessageBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 2, errorMessage_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (errorCodePresentCase_ == 1) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size( + 1, (int)((java.lang.Integer) errorCodePresent_)); + } + if (!getErrorMessageBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(2, errorMessage_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Ack)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Ack other = (com.alibaba.otter.canal.protocol.CanalPacket.Ack) obj; + + boolean result = true; + result = result && getErrorMessage() + .equals(other.getErrorMessage()); + result = result && getErrorCodePresentCase().equals( + other.getErrorCodePresentCase()); + if (!result) return false; + switch (errorCodePresentCase_) { + case 1: + result = result && (getErrorCode() + == other.getErrorCode()); + break; + case 0: + default: + } + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + ERROR_MESSAGE_FIELD_NUMBER; + hash = (53 * hash) + getErrorMessage().hashCode(); + switch (errorCodePresentCase_) { + case 1: + hash = (37 * hash) + ERROR_CODE_FIELD_NUMBER; + hash = (53 * hash) + getErrorCode(); + break; + case 0: + default: + } + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Ack prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.Ack} */ - public static final class Ack extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Ack) - AckOrBuilder { - - // Use Ack.newBuilder() to construct. - private Ack(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Ack(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Ack defaultInstance; - - public static Ack getDefaultInstance() { - return defaultInstance; - } - - public Ack getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Ack(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - errorCode_ = input.readInt32(); - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - errorMessage_ = bs; - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Ack.class, - com.alibaba.otter.canal.protocol.CanalPacket.Ack.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Ack parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Ack(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int ERROR_CODE_FIELD_NUMBER = 1; - private int errorCode_; - - /** - * optional int32 error_code = 1 [default = 0]; - */ - public boolean hasErrorCode() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 error_code = 1 [default = 0]; - */ - public int getErrorCode() { - return errorCode_; - } - - public static final int ERROR_MESSAGE_FIELD_NUMBER = 2; - private java.lang.Object errorMessage_; - - /** - * optional string error_message = 2; - * - *
      -         * if something like compression is not supported, erorr_message will tell about it.
      -         * 
      - */ - public boolean hasErrorMessage() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string error_message = 2; - * - *
      -         * if something like compression is not supported, erorr_message will tell about it.
      -         * 
      - */ - public java.lang.String getErrorMessage() { - java.lang.Object ref = errorMessage_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - errorMessage_ = s; - } - return s; - } - } - - /** - * optional string error_message = 2; - * - *
      -         * if something like compression is not supported, erorr_message will tell about it.
      -         * 
      - */ - public com.google.protobuf.ByteString getErrorMessageBytes() { - java.lang.Object ref = errorMessage_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - errorMessage_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - private void initFields() { - errorCode_ = 0; - errorMessage_ = ""; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt32(1, errorCode_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getErrorMessageBytes()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(1, errorCode_); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getErrorMessageBytes()); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Ack parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Ack prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Ack} - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Ack) com.alibaba.otter.canal.protocol.CanalPacket.AckOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Ack.class, com.alibaba.otter.canal.protocol.CanalPacket.Ack.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Ack.class, - com.alibaba.otter.canal.protocol.CanalPacket.Ack.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Ack.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Ack.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - errorCode_ = 0; - bitField0_ = (bitField0_ & ~0x00000001); - errorMessage_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Ack getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Ack.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Ack build() { - com.alibaba.otter.canal.protocol.CanalPacket.Ack result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Ack buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Ack result = new com.alibaba.otter.canal.protocol.CanalPacket.Ack(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.errorCode_ = errorCode_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.errorMessage_ = errorMessage_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Ack) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Ack) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Ack other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Ack.getDefaultInstance()) return this; - if (other.hasErrorCode()) { - setErrorCode(other.getErrorCode()); - } - if (other.hasErrorMessage()) { - bitField0_ |= 0x00000002; - errorMessage_ = other.errorMessage_; - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Ack parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Ack) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private int errorCode_; - - /** - * optional int32 error_code = 1 [default = 0]; - */ - public boolean hasErrorCode() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int32 error_code = 1 [default = 0]; - */ - public int getErrorCode() { - return errorCode_; - } - - /** - * optional int32 error_code = 1 [default = 0]; - */ - public Builder setErrorCode(int value) { - bitField0_ |= 0x00000001; - errorCode_ = value; - onChanged(); - return this; - } - - /** - * optional int32 error_code = 1 [default = 0]; - */ - public Builder clearErrorCode() { - bitField0_ = (bitField0_ & ~0x00000001); - errorCode_ = 0; - onChanged(); - return this; - } - - private java.lang.Object errorMessage_ = ""; - - /** - * optional string error_message = 2; - * - *
      -             * if something like compression is not supported, erorr_message will tell about it.
      -             * 
      - */ - public boolean hasErrorMessage() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string error_message = 2; - * - *
      -             * if something like compression is not supported, erorr_message will tell about it.
      -             * 
      - */ - public java.lang.String getErrorMessage() { - java.lang.Object ref = errorMessage_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - errorMessage_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string error_message = 2; - * - *
      -             * if something like compression is not supported, erorr_message will tell about it.
      -             * 
      - */ - public com.google.protobuf.ByteString getErrorMessageBytes() { - java.lang.Object ref = errorMessage_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - errorMessage_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string error_message = 2; - * - *
      -             * if something like compression is not supported, erorr_message will tell about it.
      -             * 
      - */ - public Builder setErrorMessage(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - errorMessage_ = value; - onChanged(); - return this; - } - - /** - * optional string error_message = 2; - * - *
      -             * if something like compression is not supported, erorr_message will tell about it.
      -             * 
      - */ - public Builder clearErrorMessage() { - bitField0_ = (bitField0_ & ~0x00000002); - errorMessage_ = getDefaultInstance().getErrorMessage(); - onChanged(); - return this; - } - - /** - * optional string error_message = 2; - * - *
      -             * if something like compression is not supported, erorr_message will tell about it.
      -             * 
      - */ - public Builder setErrorMessageBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - errorMessage_ = value; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Ack) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + errorMessage_ = ""; - static { - defaultInstance = new Ack(true); - defaultInstance.initFields(); + errorCodePresentCase_ = 0; + errorCodePresent_ = null; + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Ack getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Ack.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Ack build() { + com.alibaba.otter.canal.protocol.CanalPacket.Ack result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Ack) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Ack buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Ack result = new com.alibaba.otter.canal.protocol.CanalPacket.Ack(this); + if (errorCodePresentCase_ == 1) { + result.errorCodePresent_ = errorCodePresent_; + } + result.errorMessage_ = errorMessage_; + result.errorCodePresentCase_ = errorCodePresentCase_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Ack) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Ack)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Ack other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Ack.getDefaultInstance()) return this; + if (!other.getErrorMessage().isEmpty()) { + errorMessage_ = other.errorMessage_; + onChanged(); + } + switch (other.getErrorCodePresentCase()) { + case ERROR_CODE: { + setErrorCode(other.getErrorCode()); + break; + } + case ERRORCODEPRESENT_NOT_SET: { + break; + } + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Ack parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Ack) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int errorCodePresentCase_ = 0; + private java.lang.Object errorCodePresent_; + public ErrorCodePresentCase + getErrorCodePresentCase() { + return ErrorCodePresentCase.forNumber( + errorCodePresentCase_); + } + + public Builder clearErrorCodePresent() { + errorCodePresentCase_ = 0; + errorCodePresent_ = null; + onChanged(); + return this; + } + + + /** + * int32 error_code = 1; + */ + public int getErrorCode() { + if (errorCodePresentCase_ == 1) { + return (java.lang.Integer) errorCodePresent_; + } + return 0; + } + /** + * int32 error_code = 1; + */ + public Builder setErrorCode(int value) { + errorCodePresentCase_ = 1; + errorCodePresent_ = value; + onChanged(); + return this; + } + /** + * int32 error_code = 1; + */ + public Builder clearErrorCode() { + if (errorCodePresentCase_ == 1) { + errorCodePresentCase_ = 0; + errorCodePresent_ = null; + onChanged(); + } + return this; + } + + private java.lang.Object errorMessage_ = ""; + /** + *
      +       * if something like compression is not supported, erorr_message will tell about it.
      +       * 
      + * + * string error_message = 2; + */ + public java.lang.String getErrorMessage() { + java.lang.Object ref = errorMessage_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + errorMessage_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + *
      +       * if something like compression is not supported, erorr_message will tell about it.
      +       * 
      + * + * string error_message = 2; + */ + public com.google.protobuf.ByteString + getErrorMessageBytes() { + java.lang.Object ref = errorMessage_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + errorMessage_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + *
      +       * if something like compression is not supported, erorr_message will tell about it.
      +       * 
      + * + * string error_message = 2; + */ + public Builder setErrorMessage( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + errorMessage_ = value; + onChanged(); + return this; + } + /** + *
      +       * if something like compression is not supported, erorr_message will tell about it.
      +       * 
      + * + * string error_message = 2; + */ + public Builder clearErrorMessage() { + + errorMessage_ = getDefaultInstance().getErrorMessage(); + onChanged(); + return this; + } + /** + *
      +       * if something like compression is not supported, erorr_message will tell about it.
      +       * 
      + * + * string error_message = 2; + */ + public Builder setErrorMessageBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + errorMessage_ = value; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Ack) } - public interface ClientAckOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.ClientAck) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string destination = 1; - */ - boolean hasDestination(); - - /** - * optional string destination = 1; - */ - java.lang.String getDestination(); - - /** - * optional string destination = 1; - */ - com.google.protobuf.ByteString getDestinationBytes(); - - /** - * optional string client_id = 2; - */ - boolean hasClientId(); - - /** - * optional string client_id = 2; - */ - java.lang.String getClientId(); - - /** - * optional string client_id = 2; - */ - com.google.protobuf.ByteString getClientIdBytes(); - - /** - * optional int64 batch_id = 3; - */ - boolean hasBatchId(); - - /** - * optional int64 batch_id = 3; - */ - long getBatchId(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Ack) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Ack DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Ack(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Ack getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Ack parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Ack(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Ack getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface ClientAckOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.ClientAck) + com.google.protobuf.MessageOrBuilder { + + /** + * string destination = 1; + */ + java.lang.String getDestination(); + /** + * string destination = 1; + */ + com.google.protobuf.ByteString + getDestinationBytes(); + + /** + * string client_id = 2; + */ + java.lang.String getClientId(); + /** + * string client_id = 2; + */ + com.google.protobuf.ByteString + getClientIdBytes(); + + /** + * int64 batch_id = 3; + */ + long getBatchId(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientAck} + */ + public static final class ClientAck extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.ClientAck) + ClientAckOrBuilder { + private static final long serialVersionUID = 0L; + // Use ClientAck.newBuilder() to construct. + private ClientAck(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private ClientAck() { + destination_ = ""; + clientId_ = ""; + batchId_ = 0L; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private ClientAck( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + + destination_ = s; + break; + } + case 18: { + java.lang.String s = input.readStringRequireUtf8(); + + clientId_ = s; + break; + } + case 24: { + + batchId_ = input.readInt64(); + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.class, com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.Builder.class); + } + + public static final int DESTINATION_FIELD_NUMBER = 1; + private volatile java.lang.Object destination_; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int CLIENT_ID_FIELD_NUMBER = 2; + private volatile java.lang.Object clientId_; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int BATCH_ID_FIELD_NUMBER = 3; + private long batchId_; + /** + * int64 batch_id = 3; + */ + public long getBatchId() { + return batchId_; + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (!getDestinationBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 2, clientId_); + } + if (batchId_ != 0L) { + output.writeInt64(3, batchId_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (!getDestinationBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(2, clientId_); + } + if (batchId_ != 0L) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(3, batchId_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientAck)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.ClientAck other = (com.alibaba.otter.canal.protocol.CanalPacket.ClientAck) obj; + + boolean result = true; + result = result && getDestination() + .equals(other.getDestination()); + result = result && getClientId() + .equals(other.getClientId()); + result = result && (getBatchId() + == other.getBatchId()); + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + DESTINATION_FIELD_NUMBER; + hash = (53 * hash) + getDestination().hashCode(); + hash = (37 * hash) + CLIENT_ID_FIELD_NUMBER; + hash = (53 * hash) + getClientId().hashCode(); + hash = (37 * hash) + BATCH_ID_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getBatchId()); + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.ClientAck prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientAck} */ - public static final class ClientAck extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.ClientAck) - ClientAckOrBuilder { - - // Use ClientAck.newBuilder() to construct. - private ClientAck(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private ClientAck(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final ClientAck defaultInstance; - - public static ClientAck getDefaultInstance() { - return defaultInstance; - } - - public ClientAck getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private ClientAck(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - destination_ = bs; - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - clientId_ = bs; - break; - } - case 24: { - bitField0_ |= 0x00000004; - batchId_ = input.readInt64(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.class, - com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public ClientAck parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new ClientAck(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int DESTINATION_FIELD_NUMBER = 1; - private java.lang.Object destination_; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int CLIENT_ID_FIELD_NUMBER = 2; - private java.lang.Object clientId_; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int BATCH_ID_FIELD_NUMBER = 3; - private long batchId_; - - /** - * optional int64 batch_id = 3; - */ - public boolean hasBatchId() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 batch_id = 3; - */ - public long getBatchId() { - return batchId_; - } - - private void initFields() { - destination_ = ""; - clientId_ = ""; - batchId_ = 0L; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeInt64(3, batchId_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(3, batchId_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.ClientAck prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientAck} - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.ClientAck) com.alibaba.otter.canal.protocol.CanalPacket.ClientAckOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.class, com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.class, - com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - destination_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - clientId_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - batchId_ = 0L; - bitField0_ = (bitField0_ & ~0x00000004); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientAck getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientAck build() { - com.alibaba.otter.canal.protocol.CanalPacket.ClientAck result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientAck buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.ClientAck result = new com.alibaba.otter.canal.protocol.CanalPacket.ClientAck(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.destination_ = destination_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.clientId_ = clientId_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.batchId_ = batchId_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientAck) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.ClientAck) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.ClientAck other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.getDefaultInstance()) return this; - if (other.hasDestination()) { - bitField0_ |= 0x00000001; - destination_ = other.destination_; - onChanged(); - } - if (other.hasClientId()) { - bitField0_ |= 0x00000002; - clientId_ = other.clientId_; - onChanged(); - } - if (other.hasBatchId()) { - setBatchId(other.getBatchId()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.ClientAck) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object destination_ = ""; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string destination = 1; - */ - public Builder setDestination(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder clearDestination() { - bitField0_ = (bitField0_ & ~0x00000001); - destination_ = getDefaultInstance().getDestination(); - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder setDestinationBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - private java.lang.Object clientId_ = ""; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string client_id = 2; - */ - public Builder setClientId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder clearClientId() { - bitField0_ = (bitField0_ & ~0x00000002); - clientId_ = getDefaultInstance().getClientId(); - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder setClientIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - private long batchId_; - - /** - * optional int64 batch_id = 3; - */ - public boolean hasBatchId() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 batch_id = 3; - */ - public long getBatchId() { - return batchId_; - } - - /** - * optional int64 batch_id = 3; - */ - public Builder setBatchId(long value) { - bitField0_ |= 0x00000004; - batchId_ = value; - onChanged(); - return this; - } - - /** - * optional int64 batch_id = 3; - */ - public Builder clearBatchId() { - bitField0_ = (bitField0_ & ~0x00000004); - batchId_ = 0L; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.ClientAck) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + destination_ = ""; - static { - defaultInstance = new ClientAck(true); - defaultInstance.initFields(); + clientId_ = ""; + + batchId_ = 0L; + + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAck getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAck build() { + com.alibaba.otter.canal.protocol.CanalPacket.ClientAck result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.ClientAck) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAck buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.ClientAck result = new com.alibaba.otter.canal.protocol.CanalPacket.ClientAck(this); + result.destination_ = destination_; + result.clientId_ = clientId_; + result.batchId_ = batchId_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientAck) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.ClientAck)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.ClientAck other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.ClientAck.getDefaultInstance()) return this; + if (!other.getDestination().isEmpty()) { + destination_ = other.destination_; + onChanged(); + } + if (!other.getClientId().isEmpty()) { + clientId_ = other.clientId_; + onChanged(); + } + if (other.getBatchId() != 0L) { + setBatchId(other.getBatchId()); + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.ClientAck parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.ClientAck) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + + private java.lang.Object destination_ = ""; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string destination = 1; + */ + public Builder setDestination( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + destination_ = value; + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder clearDestination() { + + destination_ = getDefaultInstance().getDestination(); + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder setDestinationBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + destination_ = value; + onChanged(); + return this; + } + + private java.lang.Object clientId_ = ""; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string client_id = 2; + */ + public Builder setClientId( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + clientId_ = value; + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder clearClientId() { + + clientId_ = getDefaultInstance().getClientId(); + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder setClientIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + clientId_ = value; + onChanged(); + return this; + } + + private long batchId_ ; + /** + * int64 batch_id = 3; + */ + public long getBatchId() { + return batchId_; + } + /** + * int64 batch_id = 3; + */ + public Builder setBatchId(long value) { + + batchId_ = value; + onChanged(); + return this; + } + /** + * int64 batch_id = 3; + */ + public Builder clearBatchId() { + + batchId_ = 0L; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.ClientAck) } - public interface SubOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Sub) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string destination = 1; - */ - boolean hasDestination(); - - /** - * optional string destination = 1; - */ - java.lang.String getDestination(); - - /** - * optional string destination = 1; - */ - com.google.protobuf.ByteString getDestinationBytes(); - - /** - * optional string client_id = 2; - */ - boolean hasClientId(); - - /** - * optional string client_id = 2; - */ - java.lang.String getClientId(); - - /** - * optional string client_id = 2; - */ - com.google.protobuf.ByteString getClientIdBytes(); - - /** - * optional string filter = 7; - */ - boolean hasFilter(); - - /** - * optional string filter = 7; - */ - java.lang.String getFilter(); - - /** - * optional string filter = 7; - */ - com.google.protobuf.ByteString getFilterBytes(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.ClientAck) + private static final com.alibaba.otter.canal.protocol.CanalPacket.ClientAck DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.ClientAck(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientAck getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public ClientAck parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new ClientAck(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientAck getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface SubOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Sub) + com.google.protobuf.MessageOrBuilder { + + /** + * string destination = 1; + */ + java.lang.String getDestination(); + /** + * string destination = 1; + */ + com.google.protobuf.ByteString + getDestinationBytes(); + + /** + * string client_id = 2; + */ + java.lang.String getClientId(); + /** + * string client_id = 2; + */ + com.google.protobuf.ByteString + getClientIdBytes(); + + /** + * string filter = 7; + */ + java.lang.String getFilter(); + /** + * string filter = 7; + */ + com.google.protobuf.ByteString + getFilterBytes(); + } + /** + *
      +   * subscription
      +   * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Sub} + */ + public static final class Sub extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Sub) + SubOrBuilder { + private static final long serialVersionUID = 0L; + // Use Sub.newBuilder() to construct. + private Sub(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Sub() { + destination_ = ""; + clientId_ = ""; + filter_ = ""; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Sub( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + + destination_ = s; + break; + } + case 18: { + java.lang.String s = input.readStringRequireUtf8(); + + clientId_ = s; + break; + } + case 58: { + java.lang.String s = input.readStringRequireUtf8(); + + filter_ = s; + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Sub.class, com.alibaba.otter.canal.protocol.CanalPacket.Sub.Builder.class); + } + + public static final int DESTINATION_FIELD_NUMBER = 1; + private volatile java.lang.Object destination_; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int CLIENT_ID_FIELD_NUMBER = 2; + private volatile java.lang.Object clientId_; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int FILTER_FIELD_NUMBER = 7; + private volatile java.lang.Object filter_; + /** + * string filter = 7; + */ + public java.lang.String getFilter() { + java.lang.Object ref = filter_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + filter_ = s; + return s; + } + } + /** + * string filter = 7; + */ + public com.google.protobuf.ByteString + getFilterBytes() { + java.lang.Object ref = filter_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + filter_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (!getDestinationBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 2, clientId_); + } + if (!getFilterBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 7, filter_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (!getDestinationBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(2, clientId_); + } + if (!getFilterBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(7, filter_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Sub)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Sub other = (com.alibaba.otter.canal.protocol.CanalPacket.Sub) obj; + + boolean result = true; + result = result && getDestination() + .equals(other.getDestination()); + result = result && getClientId() + .equals(other.getClientId()); + result = result && getFilter() + .equals(other.getFilter()); + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + DESTINATION_FIELD_NUMBER; + hash = (53 * hash) + getDestination().hashCode(); + hash = (37 * hash) + CLIENT_ID_FIELD_NUMBER; + hash = (53 * hash) + getClientId().hashCode(); + hash = (37 * hash) + FILTER_FIELD_NUMBER; + hash = (53 * hash) + getFilter().hashCode(); + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Sub prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Sub} - * *
            * subscription
            * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Sub} */ - public static final class Sub extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Sub) - SubOrBuilder { - - // Use Sub.newBuilder() to construct. - private Sub(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Sub(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Sub defaultInstance; - - public static Sub getDefaultInstance() { - return defaultInstance; - } - - public Sub getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Sub(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - destination_ = bs; - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - clientId_ = bs; - break; - } - case 58: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000004; - filter_ = bs; - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Sub.class, - com.alibaba.otter.canal.protocol.CanalPacket.Sub.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Sub parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Sub(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int DESTINATION_FIELD_NUMBER = 1; - private java.lang.Object destination_; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int CLIENT_ID_FIELD_NUMBER = 2; - private java.lang.Object clientId_; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int FILTER_FIELD_NUMBER = 7; - private java.lang.Object filter_; - - /** - * optional string filter = 7; - */ - public boolean hasFilter() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional string filter = 7; - */ - public java.lang.String getFilter() { - java.lang.Object ref = filter_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - filter_ = s; - } - return s; - } - } - - /** - * optional string filter = 7; - */ - public com.google.protobuf.ByteString getFilterBytes() { - java.lang.Object ref = filter_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - filter_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - private void initFields() { - destination_ = ""; - clientId_ = ""; - filter_ = ""; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeBytes(7, getFilterBytes()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(7, getFilterBytes()); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Sub parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Sub prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Sub} - * - *
      -         * subscription
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Sub) com.alibaba.otter.canal.protocol.CanalPacket.SubOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Sub.class, com.alibaba.otter.canal.protocol.CanalPacket.Sub.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Sub.class, - com.alibaba.otter.canal.protocol.CanalPacket.Sub.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Sub.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Sub.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - destination_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - clientId_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - filter_ = ""; - bitField0_ = (bitField0_ & ~0x00000004); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Sub getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Sub.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Sub build() { - com.alibaba.otter.canal.protocol.CanalPacket.Sub result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Sub buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Sub result = new com.alibaba.otter.canal.protocol.CanalPacket.Sub(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.destination_ = destination_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.clientId_ = clientId_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.filter_ = filter_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Sub) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Sub) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Sub other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Sub.getDefaultInstance()) return this; - if (other.hasDestination()) { - bitField0_ |= 0x00000001; - destination_ = other.destination_; - onChanged(); - } - if (other.hasClientId()) { - bitField0_ |= 0x00000002; - clientId_ = other.clientId_; - onChanged(); - } - if (other.hasFilter()) { - bitField0_ |= 0x00000004; - filter_ = other.filter_; - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Sub parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Sub) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object destination_ = ""; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string destination = 1; - */ - public Builder setDestination(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder clearDestination() { - bitField0_ = (bitField0_ & ~0x00000001); - destination_ = getDefaultInstance().getDestination(); - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder setDestinationBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - private java.lang.Object clientId_ = ""; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string client_id = 2; - */ - public Builder setClientId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder clearClientId() { - bitField0_ = (bitField0_ & ~0x00000002); - clientId_ = getDefaultInstance().getClientId(); - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder setClientIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - private java.lang.Object filter_ = ""; - - /** - * optional string filter = 7; - */ - public boolean hasFilter() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional string filter = 7; - */ - public java.lang.String getFilter() { - java.lang.Object ref = filter_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - filter_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string filter = 7; - */ - public com.google.protobuf.ByteString getFilterBytes() { - java.lang.Object ref = filter_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - filter_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string filter = 7; - */ - public Builder setFilter(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - filter_ = value; - onChanged(); - return this; - } - - /** - * optional string filter = 7; - */ - public Builder clearFilter() { - bitField0_ = (bitField0_ & ~0x00000004); - filter_ = getDefaultInstance().getFilter(); - onChanged(); - return this; - } - - /** - * optional string filter = 7; - */ - public Builder setFilterBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - filter_ = value; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Sub) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + destination_ = ""; - static { - defaultInstance = new Sub(true); - defaultInstance.initFields(); + clientId_ = ""; + + filter_ = ""; + + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Sub getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Sub.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Sub build() { + com.alibaba.otter.canal.protocol.CanalPacket.Sub result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Sub) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Sub buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Sub result = new com.alibaba.otter.canal.protocol.CanalPacket.Sub(this); + result.destination_ = destination_; + result.clientId_ = clientId_; + result.filter_ = filter_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Sub) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Sub)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Sub other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Sub.getDefaultInstance()) return this; + if (!other.getDestination().isEmpty()) { + destination_ = other.destination_; + onChanged(); + } + if (!other.getClientId().isEmpty()) { + clientId_ = other.clientId_; + onChanged(); + } + if (!other.getFilter().isEmpty()) { + filter_ = other.filter_; + onChanged(); + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Sub parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Sub) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + + private java.lang.Object destination_ = ""; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string destination = 1; + */ + public Builder setDestination( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + destination_ = value; + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder clearDestination() { + + destination_ = getDefaultInstance().getDestination(); + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder setDestinationBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + destination_ = value; + onChanged(); + return this; + } + + private java.lang.Object clientId_ = ""; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string client_id = 2; + */ + public Builder setClientId( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + clientId_ = value; + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder clearClientId() { + + clientId_ = getDefaultInstance().getClientId(); + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder setClientIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + clientId_ = value; + onChanged(); + return this; + } + + private java.lang.Object filter_ = ""; + /** + * string filter = 7; + */ + public java.lang.String getFilter() { + java.lang.Object ref = filter_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + filter_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string filter = 7; + */ + public com.google.protobuf.ByteString + getFilterBytes() { + java.lang.Object ref = filter_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + filter_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string filter = 7; + */ + public Builder setFilter( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + filter_ = value; + onChanged(); + return this; + } + /** + * string filter = 7; + */ + public Builder clearFilter() { + + filter_ = getDefaultInstance().getFilter(); + onChanged(); + return this; + } + /** + * string filter = 7; + */ + public Builder setFilterBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + filter_ = value; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Sub) } - public interface UnsubOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Unsub) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string destination = 1; - */ - boolean hasDestination(); - - /** - * optional string destination = 1; - */ - java.lang.String getDestination(); - - /** - * optional string destination = 1; - */ - com.google.protobuf.ByteString getDestinationBytes(); - - /** - * optional string client_id = 2; - */ - boolean hasClientId(); - - /** - * optional string client_id = 2; - */ - java.lang.String getClientId(); - - /** - * optional string client_id = 2; - */ - com.google.protobuf.ByteString getClientIdBytes(); - - /** - * optional string filter = 7; - */ - boolean hasFilter(); - - /** - * optional string filter = 7; - */ - java.lang.String getFilter(); - - /** - * optional string filter = 7; - */ - com.google.protobuf.ByteString getFilterBytes(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Sub) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Sub DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Sub(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Sub getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Sub parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Sub(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Sub getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface UnsubOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Unsub) + com.google.protobuf.MessageOrBuilder { + + /** + * string destination = 1; + */ + java.lang.String getDestination(); + /** + * string destination = 1; + */ + com.google.protobuf.ByteString + getDestinationBytes(); + + /** + * string client_id = 2; + */ + java.lang.String getClientId(); + /** + * string client_id = 2; + */ + com.google.protobuf.ByteString + getClientIdBytes(); + + /** + * string filter = 7; + */ + java.lang.String getFilter(); + /** + * string filter = 7; + */ + com.google.protobuf.ByteString + getFilterBytes(); + } + /** + *
      +   * Unsubscription
      +   * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Unsub} + */ + public static final class Unsub extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Unsub) + UnsubOrBuilder { + private static final long serialVersionUID = 0L; + // Use Unsub.newBuilder() to construct. + private Unsub(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Unsub() { + destination_ = ""; + clientId_ = ""; + filter_ = ""; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Unsub( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + + destination_ = s; + break; + } + case 18: { + java.lang.String s = input.readStringRequireUtf8(); + + clientId_ = s; + break; + } + case 58: { + java.lang.String s = input.readStringRequireUtf8(); + + filter_ = s; + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Unsub.class, com.alibaba.otter.canal.protocol.CanalPacket.Unsub.Builder.class); + } + + public static final int DESTINATION_FIELD_NUMBER = 1; + private volatile java.lang.Object destination_; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int CLIENT_ID_FIELD_NUMBER = 2; + private volatile java.lang.Object clientId_; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int FILTER_FIELD_NUMBER = 7; + private volatile java.lang.Object filter_; + /** + * string filter = 7; + */ + public java.lang.String getFilter() { + java.lang.Object ref = filter_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + filter_ = s; + return s; + } + } + /** + * string filter = 7; + */ + public com.google.protobuf.ByteString + getFilterBytes() { + java.lang.Object ref = filter_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + filter_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (!getDestinationBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 2, clientId_); + } + if (!getFilterBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 7, filter_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (!getDestinationBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(2, clientId_); + } + if (!getFilterBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(7, filter_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Unsub)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Unsub other = (com.alibaba.otter.canal.protocol.CanalPacket.Unsub) obj; + + boolean result = true; + result = result && getDestination() + .equals(other.getDestination()); + result = result && getClientId() + .equals(other.getClientId()); + result = result && getFilter() + .equals(other.getFilter()); + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + DESTINATION_FIELD_NUMBER; + hash = (53 * hash) + getDestination().hashCode(); + hash = (37 * hash) + CLIENT_ID_FIELD_NUMBER; + hash = (53 * hash) + getClientId().hashCode(); + hash = (37 * hash) + FILTER_FIELD_NUMBER; + hash = (53 * hash) + getFilter().hashCode(); + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Unsub prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Unsub} - * *
            * Unsubscription
            * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Unsub} */ - public static final class Unsub extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Unsub) - UnsubOrBuilder { - - // Use Unsub.newBuilder() to construct. - private Unsub(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Unsub(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Unsub defaultInstance; - - public static Unsub getDefaultInstance() { - return defaultInstance; - } - - public Unsub getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Unsub(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - destination_ = bs; - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - clientId_ = bs; - break; - } - case 58: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000004; - filter_ = bs; - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Unsub.class, - com.alibaba.otter.canal.protocol.CanalPacket.Unsub.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Unsub parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Unsub(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int DESTINATION_FIELD_NUMBER = 1; - private java.lang.Object destination_; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int CLIENT_ID_FIELD_NUMBER = 2; - private java.lang.Object clientId_; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int FILTER_FIELD_NUMBER = 7; - private java.lang.Object filter_; - - /** - * optional string filter = 7; - */ - public boolean hasFilter() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional string filter = 7; - */ - public java.lang.String getFilter() { - java.lang.Object ref = filter_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - filter_ = s; - } - return s; - } - } - - /** - * optional string filter = 7; - */ - public com.google.protobuf.ByteString getFilterBytes() { - java.lang.Object ref = filter_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - filter_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - private void initFields() { - destination_ = ""; - clientId_ = ""; - filter_ = ""; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeBytes(7, getFilterBytes()); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(7, getFilterBytes()); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Unsub prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Unsub} - * - *
      -         * Unsubscription
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Unsub) com.alibaba.otter.canal.protocol.CanalPacket.UnsubOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Unsub.class, com.alibaba.otter.canal.protocol.CanalPacket.Unsub.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Unsub.class, - com.alibaba.otter.canal.protocol.CanalPacket.Unsub.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Unsub.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Unsub.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - destination_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - clientId_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - filter_ = ""; - bitField0_ = (bitField0_ & ~0x00000004); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Unsub getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Unsub.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Unsub build() { - com.alibaba.otter.canal.protocol.CanalPacket.Unsub result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Unsub buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Unsub result = new com.alibaba.otter.canal.protocol.CanalPacket.Unsub(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.destination_ = destination_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.clientId_ = clientId_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.filter_ = filter_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Unsub) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Unsub) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Unsub other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Unsub.getDefaultInstance()) return this; - if (other.hasDestination()) { - bitField0_ |= 0x00000001; - destination_ = other.destination_; - onChanged(); - } - if (other.hasClientId()) { - bitField0_ |= 0x00000002; - clientId_ = other.clientId_; - onChanged(); - } - if (other.hasFilter()) { - bitField0_ |= 0x00000004; - filter_ = other.filter_; - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Unsub parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Unsub) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object destination_ = ""; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string destination = 1; - */ - public Builder setDestination(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder clearDestination() { - bitField0_ = (bitField0_ & ~0x00000001); - destination_ = getDefaultInstance().getDestination(); - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder setDestinationBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - private java.lang.Object clientId_ = ""; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string client_id = 2; - */ - public Builder setClientId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder clearClientId() { - bitField0_ = (bitField0_ & ~0x00000002); - clientId_ = getDefaultInstance().getClientId(); - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder setClientIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - private java.lang.Object filter_ = ""; - - /** - * optional string filter = 7; - */ - public boolean hasFilter() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional string filter = 7; - */ - public java.lang.String getFilter() { - java.lang.Object ref = filter_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - filter_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string filter = 7; - */ - public com.google.protobuf.ByteString getFilterBytes() { - java.lang.Object ref = filter_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - filter_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string filter = 7; - */ - public Builder setFilter(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - filter_ = value; - onChanged(); - return this; - } - - /** - * optional string filter = 7; - */ - public Builder clearFilter() { - bitField0_ = (bitField0_ & ~0x00000004); - filter_ = getDefaultInstance().getFilter(); - onChanged(); - return this; - } - - /** - * optional string filter = 7; - */ - public Builder setFilterBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000004; - filter_ = value; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Unsub) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + destination_ = ""; - static { - defaultInstance = new Unsub(true); - defaultInstance.initFields(); + clientId_ = ""; + + filter_ = ""; + + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Unsub getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Unsub.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Unsub build() { + com.alibaba.otter.canal.protocol.CanalPacket.Unsub result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Unsub) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Unsub buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Unsub result = new com.alibaba.otter.canal.protocol.CanalPacket.Unsub(this); + result.destination_ = destination_; + result.clientId_ = clientId_; + result.filter_ = filter_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Unsub) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Unsub)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Unsub other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Unsub.getDefaultInstance()) return this; + if (!other.getDestination().isEmpty()) { + destination_ = other.destination_; + onChanged(); + } + if (!other.getClientId().isEmpty()) { + clientId_ = other.clientId_; + onChanged(); + } + if (!other.getFilter().isEmpty()) { + filter_ = other.filter_; + onChanged(); + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Unsub parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Unsub) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + + private java.lang.Object destination_ = ""; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string destination = 1; + */ + public Builder setDestination( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + destination_ = value; + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder clearDestination() { + + destination_ = getDefaultInstance().getDestination(); + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder setDestinationBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + destination_ = value; + onChanged(); + return this; + } + + private java.lang.Object clientId_ = ""; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string client_id = 2; + */ + public Builder setClientId( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + clientId_ = value; + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder clearClientId() { + + clientId_ = getDefaultInstance().getClientId(); + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder setClientIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + clientId_ = value; + onChanged(); + return this; + } + + private java.lang.Object filter_ = ""; + /** + * string filter = 7; + */ + public java.lang.String getFilter() { + java.lang.Object ref = filter_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + filter_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string filter = 7; + */ + public com.google.protobuf.ByteString + getFilterBytes() { + java.lang.Object ref = filter_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + filter_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string filter = 7; + */ + public Builder setFilter( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + filter_ = value; + onChanged(); + return this; + } + /** + * string filter = 7; + */ + public Builder clearFilter() { + + filter_ = getDefaultInstance().getFilter(); + onChanged(); + return this; + } + /** + * string filter = 7; + */ + public Builder setFilterBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + filter_ = value; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Unsub) } - public interface GetOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Get) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string destination = 1; - */ - boolean hasDestination(); - - /** - * optional string destination = 1; - */ - java.lang.String getDestination(); - - /** - * optional string destination = 1; - */ - com.google.protobuf.ByteString getDestinationBytes(); - - /** - * optional string client_id = 2; - */ - boolean hasClientId(); - - /** - * optional string client_id = 2; - */ - java.lang.String getClientId(); - - /** - * optional string client_id = 2; - */ - com.google.protobuf.ByteString getClientIdBytes(); - - /** - * optional int32 fetch_size = 3; - */ - boolean hasFetchSize(); - - /** - * optional int32 fetch_size = 3; - */ - int getFetchSize(); - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -         * 默认-1时代表不控制
      -         * 
      - */ - boolean hasTimeout(); - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -         * 默认-1时代表不控制
      -         * 
      - */ - long getTimeout(); - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -         * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -         * 
      - */ - boolean hasUnit(); - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -         * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -         * 
      - */ - int getUnit(); - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -         * 是否自动ack
      -         * 
      - */ - boolean hasAutoAck(); - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -         * 是否自动ack
      -         * 
      - */ - boolean getAutoAck(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Unsub) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Unsub DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Unsub(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Unsub getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Unsub parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Unsub(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Unsub getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface GetOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Get) + com.google.protobuf.MessageOrBuilder { + /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Get} - * - *
      -     * PullRequest
      -     * 
      + * string destination = 1; */ - public static final class Get extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Get) - GetOrBuilder { + java.lang.String getDestination(); + /** + * string destination = 1; + */ + com.google.protobuf.ByteString + getDestinationBytes(); - // Use Get.newBuilder() to construct. - private Get(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } + /** + * string client_id = 2; + */ + java.lang.String getClientId(); + /** + * string client_id = 2; + */ + com.google.protobuf.ByteString + getClientIdBytes(); - private Get(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } + /** + * int32 fetch_size = 3; + */ + int getFetchSize(); - private static final Get defaultInstance; + /** + *
      +     * 默认-1时代表不控制
      +     * 
      + * + * int64 timeout = 4; + */ + long getTimeout(); - public static Get getDefaultInstance() { - return defaultInstance; - } + /** + *
      +     * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      +     * 
      + * + * int32 unit = 5; + */ + int getUnit(); - public Get getDefaultInstanceForType() { - return defaultInstance; - } + /** + *
      +     * 是否自动ack
      +     * 
      + * + * bool auto_ack = 6; + */ + boolean getAutoAck(); - private final com.google.protobuf.UnknownFieldSet unknownFields; + public com.alibaba.otter.canal.protocol.CanalPacket.Get.TimeoutPresentCase getTimeoutPresentCase(); - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } + public com.alibaba.otter.canal.protocol.CanalPacket.Get.UnitPresentCase getUnitPresentCase(); - private Get(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - destination_ = bs; - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - clientId_ = bs; - break; - } - case 24: { - bitField0_ |= 0x00000004; - fetchSize_ = input.readInt32(); - break; - } - case 32: { - bitField0_ |= 0x00000008; - timeout_ = input.readInt64(); - break; - } - case 40: { - bitField0_ |= 0x00000010; - unit_ = input.readInt32(); - break; - } - case 48: { - bitField0_ |= 0x00000020; - autoAck_ = input.readBool(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); + public com.alibaba.otter.canal.protocol.CanalPacket.Get.AutoAckPresentCase getAutoAckPresentCase(); + } + /** + *
      +   *  PullRequest
      +   * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Get} + */ + public static final class Get extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Get) + GetOrBuilder { + private static final long serialVersionUID = 0L; + // Use Get.newBuilder() to construct. + private Get(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Get() { + destination_ = ""; + clientId_ = ""; + fetchSize_ = 0; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Get( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + + destination_ = s; + break; } - } + case 18: { + java.lang.String s = input.readStringRequireUtf8(); - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Get.class, - com.alibaba.otter.canal.protocol.CanalPacket.Get.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Get parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Get(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int DESTINATION_FIELD_NUMBER = 1; - private java.lang.Object destination_; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; + clientId_ = s; + break; } - } + case 24: { - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; + fetchSize_ = input.readInt32(); + break; } - } - - public static final int CLIENT_ID_FIELD_NUMBER = 2; - private java.lang.Object clientId_; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; + case 32: { + timeoutPresentCase_ = 4; + timeoutPresent_ = input.readInt64(); + break; } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; + case 40: { + unitPresentCase_ = 5; + unitPresent_ = input.readInt32(); + break; } - } - - public static final int FETCH_SIZE_FIELD_NUMBER = 3; - private int fetchSize_; - - /** - * optional int32 fetch_size = 3; - */ - public boolean hasFetchSize() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int32 fetch_size = 3; - */ - public int getFetchSize() { - return fetchSize_; - } - - public static final int TIMEOUT_FIELD_NUMBER = 4; - private long timeout_; - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -         * 默认-1时代表不控制
      -         * 
      - */ - public boolean hasTimeout() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -         * 默认-1时代表不控制
      -         * 
      - */ - public long getTimeout() { - return timeout_; - } - - public static final int UNIT_FIELD_NUMBER = 5; - private int unit_; - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -         * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -         * 
      - */ - public boolean hasUnit() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -         * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -         * 
      - */ - public int getUnit() { - return unit_; - } - - public static final int AUTO_ACK_FIELD_NUMBER = 6; - private boolean autoAck_; - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -         * 是否自动ack
      -         * 
      - */ - public boolean hasAutoAck() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -         * 是否自动ack
      -         * 
      - */ - public boolean getAutoAck() { - return autoAck_; - } - - private void initFields() { - destination_ = ""; - clientId_ = ""; - fetchSize_ = 0; - timeout_ = -1L; - unit_ = 2; - autoAck_ = false; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getDestinationBytes()); + case 48: { + autoAckPresentCase_ = 6; + autoAckPresent_ = input.readBool(); + break; } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getClientIdBytes()); + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeInt32(3, fetchSize_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - output.writeInt64(4, timeout_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - output.writeInt32(5, unit_); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - output.writeBool(6, autoAck_); - } - getUnknownFields().writeTo(output); + } } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; + } - private int memoizedSerializedSize = -1; + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Get.class, com.alibaba.otter.canal.protocol.CanalPacket.Get.Builder.class); + } - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; + private int timeoutPresentCase_ = 0; + private java.lang.Object timeoutPresent_; + public enum TimeoutPresentCase + implements com.google.protobuf.Internal.EnumLite { + TIMEOUT(4), + TIMEOUTPRESENT_NOT_SET(0); + private final int value; + private TimeoutPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static TimeoutPresentCase valueOf(int value) { + return forNumber(value); + } - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(3, fetchSize_); - } - if (((bitField0_ & 0x00000008) == 0x00000008)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(4, timeout_); - } - if (((bitField0_ & 0x00000010) == 0x00000010)) { - size += com.google.protobuf.CodedOutputStream.computeInt32Size(5, unit_); - } - if (((bitField0_ & 0x00000020) == 0x00000020)) { - size += com.google.protobuf.CodedOutputStream.computeBoolSize(6, autoAck_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; + public static TimeoutPresentCase forNumber(int value) { + switch (value) { + case 4: return TIMEOUT; + case 0: return TIMEOUTPRESENT_NOT_SET; + default: return null; } + } + public int getNumber() { + return this.value; + } + }; - private static final long serialVersionUID = 0L; + public TimeoutPresentCase + getTimeoutPresentCase() { + return TimeoutPresentCase.forNumber( + timeoutPresentCase_); + } - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); + private int unitPresentCase_ = 0; + private java.lang.Object unitPresent_; + public enum UnitPresentCase + implements com.google.protobuf.Internal.EnumLite { + UNIT(5), + UNITPRESENT_NOT_SET(0); + private final int value; + private UnitPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static UnitPresentCase valueOf(int value) { + return forNumber(value); + } + + public static UnitPresentCase forNumber(int value) { + switch (value) { + case 5: return UNIT; + case 0: return UNITPRESENT_NOT_SET; + default: return null; } + } + public int getNumber() { + return this.value; + } + }; - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); + public UnitPresentCase + getUnitPresentCase() { + return UnitPresentCase.forNumber( + unitPresentCase_); + } + + private int autoAckPresentCase_ = 0; + private java.lang.Object autoAckPresent_; + public enum AutoAckPresentCase + implements com.google.protobuf.Internal.EnumLite { + AUTO_ACK(6), + AUTOACKPRESENT_NOT_SET(0); + private final int value; + private AutoAckPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static AutoAckPresentCase valueOf(int value) { + return forNumber(value); + } + + public static AutoAckPresentCase forNumber(int value) { + switch (value) { + case 6: return AUTO_ACK; + case 0: return AUTOACKPRESENT_NOT_SET; + default: return null; } + } + public int getNumber() { + return this.value; + } + }; - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } + public AutoAckPresentCase + getAutoAckPresentCase() { + return AutoAckPresentCase.forNumber( + autoAckPresentCase_); + } - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } + public static final int DESTINATION_FIELD_NUMBER = 1; + private volatile java.lang.Object destination_; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } + public static final int CLIENT_ID_FIELD_NUMBER = 2; + private volatile java.lang.Object clientId_; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } + public static final int FETCH_SIZE_FIELD_NUMBER = 3; + private int fetchSize_; + /** + * int32 fetch_size = 3; + */ + public int getFetchSize() { + return fetchSize_; + } - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } + public static final int TIMEOUT_FIELD_NUMBER = 4; + /** + *
      +     * 默认-1时代表不控制
      +     * 
      + * + * int64 timeout = 4; + */ + public long getTimeout() { + if (timeoutPresentCase_ == 4) { + return (java.lang.Long) timeoutPresent_; + } + return -1L; + } - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } + public static final int UNIT_FIELD_NUMBER = 5; + /** + *
      +     * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      +     * 
      + * + * int32 unit = 5; + */ + public int getUnit() { + if (unitPresentCase_ == 5) { + return (java.lang.Integer) unitPresent_; + } + return 2; + } - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } + public static final int AUTO_ACK_FIELD_NUMBER = 6; + /** + *
      +     * 是否自动ack
      +     * 
      + * + * bool auto_ack = 6; + */ + public boolean getAutoAck() { + if (autoAckPresentCase_ == 6) { + return (java.lang.Boolean) autoAckPresent_; + } + return false; + } - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; - public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } + memoizedIsInitialized = 1; + return true; + } - public static Builder newBuilder() { - return Builder.create(); - } + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (!getDestinationBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 2, clientId_); + } + if (fetchSize_ != 0) { + output.writeInt32(3, fetchSize_); + } + if (timeoutPresentCase_ == 4) { + output.writeInt64( + 4, (long)((java.lang.Long) timeoutPresent_)); + } + if (unitPresentCase_ == 5) { + output.writeInt32( + 5, (int)((java.lang.Integer) unitPresent_)); + } + if (autoAckPresentCase_ == 6) { + output.writeBool( + 6, (boolean)((java.lang.Boolean) autoAckPresent_)); + } + unknownFields.writeTo(output); + } - public Builder newBuilderForType() { - return newBuilder(); - } + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Get prototype) { - return newBuilder().mergeFrom(prototype); - } + size = 0; + if (!getDestinationBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(2, clientId_); + } + if (fetchSize_ != 0) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size(3, fetchSize_); + } + if (timeoutPresentCase_ == 4) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size( + 4, (long)((java.lang.Long) timeoutPresent_)); + } + if (unitPresentCase_ == 5) { + size += com.google.protobuf.CodedOutputStream + .computeInt32Size( + 5, (int)((java.lang.Integer) unitPresent_)); + } + if (autoAckPresentCase_ == 6) { + size += com.google.protobuf.CodedOutputStream + .computeBoolSize( + 6, (boolean)((java.lang.Boolean) autoAckPresent_)); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } - public Builder toBuilder() { - return newBuilder(this); - } + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Get)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Get other = (com.alibaba.otter.canal.protocol.CanalPacket.Get) obj; - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } + boolean result = true; + result = result && getDestination() + .equals(other.getDestination()); + result = result && getClientId() + .equals(other.getClientId()); + result = result && (getFetchSize() + == other.getFetchSize()); + result = result && getTimeoutPresentCase().equals( + other.getTimeoutPresentCase()); + if (!result) return false; + switch (timeoutPresentCase_) { + case 4: + result = result && (getTimeout() + == other.getTimeout()); + break; + case 0: + default: + } + result = result && getUnitPresentCase().equals( + other.getUnitPresentCase()); + if (!result) return false; + switch (unitPresentCase_) { + case 5: + result = result && (getUnit() + == other.getUnit()); + break; + case 0: + default: + } + result = result && getAutoAckPresentCase().equals( + other.getAutoAckPresentCase()); + if (!result) return false; + switch (autoAckPresentCase_) { + case 6: + result = result && (getAutoAck() + == other.getAutoAck()); + break; + case 0: + default: + } + result = result && unknownFields.equals(other.unknownFields); + return result; + } - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Get} - * - *
      -         * PullRequest
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + DESTINATION_FIELD_NUMBER; + hash = (53 * hash) + getDestination().hashCode(); + hash = (37 * hash) + CLIENT_ID_FIELD_NUMBER; + hash = (53 * hash) + getClientId().hashCode(); + hash = (37 * hash) + FETCH_SIZE_FIELD_NUMBER; + hash = (53 * hash) + getFetchSize(); + switch (timeoutPresentCase_) { + case 4: + hash = (37 * hash) + TIMEOUT_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getTimeout()); + break; + case 0: + default: + } + switch (unitPresentCase_) { + case 5: + hash = (37 * hash) + UNIT_FIELD_NUMBER; + hash = (53 * hash) + getUnit(); + break; + case 0: + default: + } + switch (autoAckPresentCase_) { + case 6: + hash = (37 * hash) + AUTO_ACK_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashBoolean( + getAutoAck()); + break; + case 0: + default: + } + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Get prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } + /** + *
      +     *  PullRequest
      +     * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Get} + */ + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Get) com.alibaba.otter.canal.protocol.CanalPacket.GetOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Get.class, com.alibaba.otter.canal.protocol.CanalPacket.Get.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Get.class, - com.alibaba.otter.canal.protocol.CanalPacket.Get.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Get.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Get.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - destination_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - clientId_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - fetchSize_ = 0; - bitField0_ = (bitField0_ & ~0x00000004); - timeout_ = -1L; - bitField0_ = (bitField0_ & ~0x00000008); - unit_ = 2; - bitField0_ = (bitField0_ & ~0x00000010); - autoAck_ = false; - bitField0_ = (bitField0_ & ~0x00000020); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Get getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Get.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Get build() { - com.alibaba.otter.canal.protocol.CanalPacket.Get result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Get buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Get result = new com.alibaba.otter.canal.protocol.CanalPacket.Get(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.destination_ = destination_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.clientId_ = clientId_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.fetchSize_ = fetchSize_; - if (((from_bitField0_ & 0x00000008) == 0x00000008)) { - to_bitField0_ |= 0x00000008; - } - result.timeout_ = timeout_; - if (((from_bitField0_ & 0x00000010) == 0x00000010)) { - to_bitField0_ |= 0x00000010; - } - result.unit_ = unit_; - if (((from_bitField0_ & 0x00000020) == 0x00000020)) { - to_bitField0_ |= 0x00000020; - } - result.autoAck_ = autoAck_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Get) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Get) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Get other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Get.getDefaultInstance()) return this; - if (other.hasDestination()) { - bitField0_ |= 0x00000001; - destination_ = other.destination_; - onChanged(); - } - if (other.hasClientId()) { - bitField0_ |= 0x00000002; - clientId_ = other.clientId_; - onChanged(); - } - if (other.hasFetchSize()) { - setFetchSize(other.getFetchSize()); - } - if (other.hasTimeout()) { - setTimeout(other.getTimeout()); - } - if (other.hasUnit()) { - setUnit(other.getUnit()); - } - if (other.hasAutoAck()) { - setAutoAck(other.getAutoAck()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Get parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Get) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object destination_ = ""; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string destination = 1; - */ - public Builder setDestination(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder clearDestination() { - bitField0_ = (bitField0_ & ~0x00000001); - destination_ = getDefaultInstance().getDestination(); - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder setDestinationBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - private java.lang.Object clientId_ = ""; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string client_id = 2; - */ - public Builder setClientId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder clearClientId() { - bitField0_ = (bitField0_ & ~0x00000002); - clientId_ = getDefaultInstance().getClientId(); - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder setClientIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - private int fetchSize_; - - /** - * optional int32 fetch_size = 3; - */ - public boolean hasFetchSize() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int32 fetch_size = 3; - */ - public int getFetchSize() { - return fetchSize_; - } - - /** - * optional int32 fetch_size = 3; - */ - public Builder setFetchSize(int value) { - bitField0_ |= 0x00000004; - fetchSize_ = value; - onChanged(); - return this; - } - - /** - * optional int32 fetch_size = 3; - */ - public Builder clearFetchSize() { - bitField0_ = (bitField0_ & ~0x00000004); - fetchSize_ = 0; - onChanged(); - return this; - } - - private long timeout_ = -1L; - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -             * 默认-1时代表不控制
      -             * 
      - */ - public boolean hasTimeout() { - return ((bitField0_ & 0x00000008) == 0x00000008); - } - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -             * 默认-1时代表不控制
      -             * 
      - */ - public long getTimeout() { - return timeout_; - } - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -             * 默认-1时代表不控制
      -             * 
      - */ - public Builder setTimeout(long value) { - bitField0_ |= 0x00000008; - timeout_ = value; - onChanged(); - return this; - } - - /** - * optional int64 timeout = 4 [default = -1]; - * - *
      -             * 默认-1时代表不控制
      -             * 
      - */ - public Builder clearTimeout() { - bitField0_ = (bitField0_ & ~0x00000008); - timeout_ = -1L; - onChanged(); - return this; - } - - private int unit_ = 2; - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -             * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -             * 
      - */ - public boolean hasUnit() { - return ((bitField0_ & 0x00000010) == 0x00000010); - } - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -             * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -             * 
      - */ - public int getUnit() { - return unit_; - } - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -             * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -             * 
      - */ - public Builder setUnit(int value) { - bitField0_ |= 0x00000010; - unit_ = value; - onChanged(); - return this; - } - - /** - * optional int32 unit = 5 [default = 2]; - * - *
      -             * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      -             * 
      - */ - public Builder clearUnit() { - bitField0_ = (bitField0_ & ~0x00000010); - unit_ = 2; - onChanged(); - return this; - } - - private boolean autoAck_; - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -             * 是否自动ack
      -             * 
      - */ - public boolean hasAutoAck() { - return ((bitField0_ & 0x00000020) == 0x00000020); - } - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -             * 是否自动ack
      -             * 
      - */ - public boolean getAutoAck() { - return autoAck_; - } - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -             * 是否自动ack
      -             * 
      - */ - public Builder setAutoAck(boolean value) { - bitField0_ |= 0x00000020; - autoAck_ = value; - onChanged(); - return this; - } - - /** - * optional bool auto_ack = 6 [default = false]; - * - *
      -             * 是否自动ack
      -             * 
      - */ - public Builder clearAutoAck() { - bitField0_ = (bitField0_ & ~0x00000020); - autoAck_ = false; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Get) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + destination_ = ""; - static { - defaultInstance = new Get(true); - defaultInstance.initFields(); + clientId_ = ""; + + fetchSize_ = 0; + + timeoutPresentCase_ = 0; + timeoutPresent_ = null; + unitPresentCase_ = 0; + unitPresent_ = null; + autoAckPresentCase_ = 0; + autoAckPresent_ = null; + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Get getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Get.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Get build() { + com.alibaba.otter.canal.protocol.CanalPacket.Get result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Get) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Get buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Get result = new com.alibaba.otter.canal.protocol.CanalPacket.Get(this); + result.destination_ = destination_; + result.clientId_ = clientId_; + result.fetchSize_ = fetchSize_; + if (timeoutPresentCase_ == 4) { + result.timeoutPresent_ = timeoutPresent_; + } + if (unitPresentCase_ == 5) { + result.unitPresent_ = unitPresent_; + } + if (autoAckPresentCase_ == 6) { + result.autoAckPresent_ = autoAckPresent_; + } + result.timeoutPresentCase_ = timeoutPresentCase_; + result.unitPresentCase_ = unitPresentCase_; + result.autoAckPresentCase_ = autoAckPresentCase_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Get) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Get)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Get other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Get.getDefaultInstance()) return this; + if (!other.getDestination().isEmpty()) { + destination_ = other.destination_; + onChanged(); + } + if (!other.getClientId().isEmpty()) { + clientId_ = other.clientId_; + onChanged(); + } + if (other.getFetchSize() != 0) { + setFetchSize(other.getFetchSize()); + } + switch (other.getTimeoutPresentCase()) { + case TIMEOUT: { + setTimeout(other.getTimeout()); + break; + } + case TIMEOUTPRESENT_NOT_SET: { + break; + } + } + switch (other.getUnitPresentCase()) { + case UNIT: { + setUnit(other.getUnit()); + break; + } + case UNITPRESENT_NOT_SET: { + break; + } + } + switch (other.getAutoAckPresentCase()) { + case AUTO_ACK: { + setAutoAck(other.getAutoAck()); + break; + } + case AUTOACKPRESENT_NOT_SET: { + break; + } + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Get parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Get) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int timeoutPresentCase_ = 0; + private java.lang.Object timeoutPresent_; + public TimeoutPresentCase + getTimeoutPresentCase() { + return TimeoutPresentCase.forNumber( + timeoutPresentCase_); + } + + public Builder clearTimeoutPresent() { + timeoutPresentCase_ = 0; + timeoutPresent_ = null; + onChanged(); + return this; + } + + private int unitPresentCase_ = 0; + private java.lang.Object unitPresent_; + public UnitPresentCase + getUnitPresentCase() { + return UnitPresentCase.forNumber( + unitPresentCase_); + } + + public Builder clearUnitPresent() { + unitPresentCase_ = 0; + unitPresent_ = null; + onChanged(); + return this; + } + + private int autoAckPresentCase_ = 0; + private java.lang.Object autoAckPresent_; + public AutoAckPresentCase + getAutoAckPresentCase() { + return AutoAckPresentCase.forNumber( + autoAckPresentCase_); + } + + public Builder clearAutoAckPresent() { + autoAckPresentCase_ = 0; + autoAckPresent_ = null; + onChanged(); + return this; + } + + + private java.lang.Object destination_ = ""; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string destination = 1; + */ + public Builder setDestination( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + destination_ = value; + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder clearDestination() { + + destination_ = getDefaultInstance().getDestination(); + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder setDestinationBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + destination_ = value; + onChanged(); + return this; + } + + private java.lang.Object clientId_ = ""; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string client_id = 2; + */ + public Builder setClientId( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + clientId_ = value; + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder clearClientId() { + + clientId_ = getDefaultInstance().getClientId(); + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder setClientIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + clientId_ = value; + onChanged(); + return this; + } + + private int fetchSize_ ; + /** + * int32 fetch_size = 3; + */ + public int getFetchSize() { + return fetchSize_; + } + /** + * int32 fetch_size = 3; + */ + public Builder setFetchSize(int value) { + + fetchSize_ = value; + onChanged(); + return this; + } + /** + * int32 fetch_size = 3; + */ + public Builder clearFetchSize() { + + fetchSize_ = 0; + onChanged(); + return this; + } + + /** + *
      +       * 默认-1时代表不控制
      +       * 
      + * + * int64 timeout = 4; + */ + public long getTimeout() { + if (timeoutPresentCase_ == 4) { + return (java.lang.Long) timeoutPresent_; + } + return 0L; + } + /** + *
      +       * 默认-1时代表不控制
      +       * 
      + * + * int64 timeout = 4; + */ + public Builder setTimeout(long value) { + timeoutPresentCase_ = 4; + timeoutPresent_ = value; + onChanged(); + return this; + } + /** + *
      +       * 默认-1时代表不控制
      +       * 
      + * + * int64 timeout = 4; + */ + public Builder clearTimeout() { + if (timeoutPresentCase_ == 4) { + timeoutPresentCase_ = 0; + timeoutPresent_ = null; + onChanged(); + } + return this; + } + + /** + *
      +       * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      +       * 
      + * + * int32 unit = 5; + */ + public int getUnit() { + if (unitPresentCase_ == 5) { + return (java.lang.Integer) unitPresent_; + } + return 0; + } + /** + *
      +       * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      +       * 
      + * + * int32 unit = 5; + */ + public Builder setUnit(int value) { + unitPresentCase_ = 5; + unitPresent_ = value; + onChanged(); + return this; + } + /** + *
      +       * 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天
      +       * 
      + * + * int32 unit = 5; + */ + public Builder clearUnit() { + if (unitPresentCase_ == 5) { + unitPresentCase_ = 0; + unitPresent_ = null; + onChanged(); + } + return this; + } + + /** + *
      +       * 是否自动ack
      +       * 
      + * + * bool auto_ack = 6; + */ + public boolean getAutoAck() { + if (autoAckPresentCase_ == 6) { + return (java.lang.Boolean) autoAckPresent_; + } + return false; + } + /** + *
      +       * 是否自动ack
      +       * 
      + * + * bool auto_ack = 6; + */ + public Builder setAutoAck(boolean value) { + autoAckPresentCase_ = 6; + autoAckPresent_ = value; + onChanged(); + return this; + } + /** + *
      +       * 是否自动ack
      +       * 
      + * + * bool auto_ack = 6; + */ + public Builder clearAutoAck() { + if (autoAckPresentCase_ == 6) { + autoAckPresentCase_ = 0; + autoAckPresent_ = null; + onChanged(); + } + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Get) } - public interface MessagesOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Messages) - com.google.protobuf.MessageOrBuilder { - - /** - * optional int64 batch_id = 1; - */ - boolean hasBatchId(); - - /** - * optional int64 batch_id = 1; - */ - long getBatchId(); - - /** - * repeated bytes messages = 2; - */ - java.util.List getMessagesList(); - - /** - * repeated bytes messages = 2; - */ - int getMessagesCount(); - - /** - * repeated bytes messages = 2; - */ - com.google.protobuf.ByteString getMessages(int index); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Get) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Get DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Get(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Get getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Get parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Get(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Get getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface MessagesOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Messages) + com.google.protobuf.MessageOrBuilder { + + /** + * int64 batch_id = 1; + */ + long getBatchId(); + + /** + * repeated bytes messages = 2; + */ + java.util.List getMessagesList(); + /** + * repeated bytes messages = 2; + */ + int getMessagesCount(); + /** + * repeated bytes messages = 2; + */ + com.google.protobuf.ByteString getMessages(int index); + } + /** + *
      +   * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Messages} + */ + public static final class Messages extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Messages) + MessagesOrBuilder { + private static final long serialVersionUID = 0L; + // Use Messages.newBuilder() to construct. + private Messages(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Messages() { + batchId_ = 0L; + messages_ = java.util.Collections.emptyList(); + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Messages( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 8: { + + batchId_ = input.readInt64(); + break; + } + case 18: { + if (!((mutable_bitField0_ & 0x00000002) == 0x00000002)) { + messages_ = new java.util.ArrayList(); + mutable_bitField0_ |= 0x00000002; + } + messages_.add(input.readBytes()); + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + if (((mutable_bitField0_ & 0x00000002) == 0x00000002)) { + messages_ = java.util.Collections.unmodifiableList(messages_); + } + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Messages.class, com.alibaba.otter.canal.protocol.CanalPacket.Messages.Builder.class); + } + + private int bitField0_; + public static final int BATCH_ID_FIELD_NUMBER = 1; + private long batchId_; + /** + * int64 batch_id = 1; + */ + public long getBatchId() { + return batchId_; + } + + public static final int MESSAGES_FIELD_NUMBER = 2; + private java.util.List messages_; + /** + * repeated bytes messages = 2; + */ + public java.util.List + getMessagesList() { + return messages_; + } + /** + * repeated bytes messages = 2; + */ + public int getMessagesCount() { + return messages_.size(); + } + /** + * repeated bytes messages = 2; + */ + public com.google.protobuf.ByteString getMessages(int index) { + return messages_.get(index); + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (batchId_ != 0L) { + output.writeInt64(1, batchId_); + } + for (int i = 0; i < messages_.size(); i++) { + output.writeBytes(2, messages_.get(i)); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (batchId_ != 0L) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(1, batchId_); + } + { + int dataSize = 0; + for (int i = 0; i < messages_.size(); i++) { + dataSize += com.google.protobuf.CodedOutputStream + .computeBytesSizeNoTag(messages_.get(i)); + } + size += dataSize; + size += 1 * getMessagesList().size(); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Messages)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Messages other = (com.alibaba.otter.canal.protocol.CanalPacket.Messages) obj; + + boolean result = true; + result = result && (getBatchId() + == other.getBatchId()); + result = result && getMessagesList() + .equals(other.getMessagesList()); + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + BATCH_ID_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getBatchId()); + if (getMessagesCount() > 0) { + hash = (37 * hash) + MESSAGES_FIELD_NUMBER; + hash = (53 * hash) + getMessagesList().hashCode(); + } + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Messages prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Messages} - * *
            * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Messages} */ - public static final class Messages extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Messages) - MessagesOrBuilder { - - // Use Messages.newBuilder() to construct. - private Messages(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Messages(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Messages defaultInstance; - - public static Messages getDefaultInstance() { - return defaultInstance; - } - - public Messages getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Messages(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 8: { - bitField0_ |= 0x00000001; - batchId_ = input.readInt64(); - break; - } - case 18: { - if (!((mutable_bitField0_ & 0x00000002) == 0x00000002)) { - messages_ = new java.util.ArrayList(); - mutable_bitField0_ |= 0x00000002; - } - messages_.add(input.readBytes()); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - if (((mutable_bitField0_ & 0x00000002) == 0x00000002)) { - messages_ = java.util.Collections.unmodifiableList(messages_); - } - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Messages.class, - com.alibaba.otter.canal.protocol.CanalPacket.Messages.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Messages parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Messages(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int BATCH_ID_FIELD_NUMBER = 1; - private long batchId_; - - /** - * optional int64 batch_id = 1; - */ - public boolean hasBatchId() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 batch_id = 1; - */ - public long getBatchId() { - return batchId_; - } - - public static final int MESSAGES_FIELD_NUMBER = 2; - private java.util.List messages_; - - /** - * repeated bytes messages = 2; - */ - public java.util.List getMessagesList() { - return messages_; - } - - /** - * repeated bytes messages = 2; - */ - public int getMessagesCount() { - return messages_.size(); - } - - /** - * repeated bytes messages = 2; - */ - public com.google.protobuf.ByteString getMessages(int index) { - return messages_.get(index); - } - - private void initFields() { - batchId_ = 0L; - messages_ = java.util.Collections.emptyList(); - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeInt64(1, batchId_); - } - for (int i = 0; i < messages_.size(); i++) { - output.writeBytes(2, messages_.get(i)); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(1, batchId_); - } - { - int dataSize = 0; - for (int i = 0; i < messages_.size(); i++) { - dataSize += com.google.protobuf.CodedOutputStream.computeBytesSizeNoTag(messages_.get(i)); - } - size += dataSize; - size += 1 * getMessagesList().size(); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Messages parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Messages prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Messages} - * - *
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Messages) com.alibaba.otter.canal.protocol.CanalPacket.MessagesOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Messages.class, com.alibaba.otter.canal.protocol.CanalPacket.Messages.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Messages.class, - com.alibaba.otter.canal.protocol.CanalPacket.Messages.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Messages.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Messages.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - batchId_ = 0L; - bitField0_ = (bitField0_ & ~0x00000001); - messages_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000002); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Messages getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Messages.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Messages build() { - com.alibaba.otter.canal.protocol.CanalPacket.Messages result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Messages buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Messages result = new com.alibaba.otter.canal.protocol.CanalPacket.Messages(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.batchId_ = batchId_; - if (((bitField0_ & 0x00000002) == 0x00000002)) { - messages_ = java.util.Collections.unmodifiableList(messages_); - bitField0_ = (bitField0_ & ~0x00000002); - } - result.messages_ = messages_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Messages) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Messages) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Messages other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Messages.getDefaultInstance()) return this; - if (other.hasBatchId()) { - setBatchId(other.getBatchId()); - } - if (!other.messages_.isEmpty()) { - if (messages_.isEmpty()) { - messages_ = other.messages_; - bitField0_ = (bitField0_ & ~0x00000002); - } else { - ensureMessagesIsMutable(); - messages_.addAll(other.messages_); - } - onChanged(); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Messages parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Messages) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private long batchId_; - - /** - * optional int64 batch_id = 1; - */ - public boolean hasBatchId() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional int64 batch_id = 1; - */ - public long getBatchId() { - return batchId_; - } - - /** - * optional int64 batch_id = 1; - */ - public Builder setBatchId(long value) { - bitField0_ |= 0x00000001; - batchId_ = value; - onChanged(); - return this; - } - - /** - * optional int64 batch_id = 1; - */ - public Builder clearBatchId() { - bitField0_ = (bitField0_ & ~0x00000001); - batchId_ = 0L; - onChanged(); - return this; - } - - private java.util.List messages_ = java.util.Collections.emptyList(); - - private void ensureMessagesIsMutable() { - if (!((bitField0_ & 0x00000002) == 0x00000002)) { - messages_ = new java.util.ArrayList(messages_); - bitField0_ |= 0x00000002; - } - } - - /** - * repeated bytes messages = 2; - */ - public java.util.List getMessagesList() { - return java.util.Collections.unmodifiableList(messages_); - } - - /** - * repeated bytes messages = 2; - */ - public int getMessagesCount() { - return messages_.size(); - } - - /** - * repeated bytes messages = 2; - */ - public com.google.protobuf.ByteString getMessages(int index) { - return messages_.get(index); - } - - /** - * repeated bytes messages = 2; - */ - public Builder setMessages(int index, com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - ensureMessagesIsMutable(); - messages_.set(index, value); - onChanged(); - return this; - } - - /** - * repeated bytes messages = 2; - */ - public Builder addMessages(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - ensureMessagesIsMutable(); - messages_.add(value); - onChanged(); - return this; - } - - /** - * repeated bytes messages = 2; - */ - public Builder addAllMessages(java.lang.Iterable values) { - ensureMessagesIsMutable(); - com.google.protobuf.AbstractMessageLite.Builder.addAll(values, messages_); - onChanged(); - return this; - } - - /** - * repeated bytes messages = 2; - */ - public Builder clearMessages() { - messages_ = java.util.Collections.emptyList(); - bitField0_ = (bitField0_ & ~0x00000002); - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Messages) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + batchId_ = 0L; - static { - defaultInstance = new Messages(true); - defaultInstance.initFields(); + messages_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000002); + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Messages getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Messages.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Messages build() { + com.alibaba.otter.canal.protocol.CanalPacket.Messages result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Messages) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Messages buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Messages result = new com.alibaba.otter.canal.protocol.CanalPacket.Messages(this); + int from_bitField0_ = bitField0_; + int to_bitField0_ = 0; + result.batchId_ = batchId_; + if (((bitField0_ & 0x00000002) == 0x00000002)) { + messages_ = java.util.Collections.unmodifiableList(messages_); + bitField0_ = (bitField0_ & ~0x00000002); + } + result.messages_ = messages_; + result.bitField0_ = to_bitField0_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Messages) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Messages)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Messages other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Messages.getDefaultInstance()) return this; + if (other.getBatchId() != 0L) { + setBatchId(other.getBatchId()); + } + if (!other.messages_.isEmpty()) { + if (messages_.isEmpty()) { + messages_ = other.messages_; + bitField0_ = (bitField0_ & ~0x00000002); + } else { + ensureMessagesIsMutable(); + messages_.addAll(other.messages_); + } + onChanged(); + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Messages parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Messages) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int bitField0_; + + private long batchId_ ; + /** + * int64 batch_id = 1; + */ + public long getBatchId() { + return batchId_; + } + /** + * int64 batch_id = 1; + */ + public Builder setBatchId(long value) { + + batchId_ = value; + onChanged(); + return this; + } + /** + * int64 batch_id = 1; + */ + public Builder clearBatchId() { + + batchId_ = 0L; + onChanged(); + return this; + } + + private java.util.List messages_ = java.util.Collections.emptyList(); + private void ensureMessagesIsMutable() { + if (!((bitField0_ & 0x00000002) == 0x00000002)) { + messages_ = new java.util.ArrayList(messages_); + bitField0_ |= 0x00000002; + } + } + /** + * repeated bytes messages = 2; + */ + public java.util.List + getMessagesList() { + return java.util.Collections.unmodifiableList(messages_); + } + /** + * repeated bytes messages = 2; + */ + public int getMessagesCount() { + return messages_.size(); + } + /** + * repeated bytes messages = 2; + */ + public com.google.protobuf.ByteString getMessages(int index) { + return messages_.get(index); + } + /** + * repeated bytes messages = 2; + */ + public Builder setMessages( + int index, com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + ensureMessagesIsMutable(); + messages_.set(index, value); + onChanged(); + return this; + } + /** + * repeated bytes messages = 2; + */ + public Builder addMessages(com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + ensureMessagesIsMutable(); + messages_.add(value); + onChanged(); + return this; + } + /** + * repeated bytes messages = 2; + */ + public Builder addAllMessages( + java.lang.Iterable values) { + ensureMessagesIsMutable(); + com.google.protobuf.AbstractMessageLite.Builder.addAll( + values, messages_); + onChanged(); + return this; + } + /** + * repeated bytes messages = 2; + */ + public Builder clearMessages() { + messages_ = java.util.Collections.emptyList(); + bitField0_ = (bitField0_ & ~0x00000002); + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Messages) } - public interface DumpOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Dump) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string journal = 1; - */ - boolean hasJournal(); - - /** - * optional string journal = 1; - */ - java.lang.String getJournal(); - - /** - * optional string journal = 1; - */ - com.google.protobuf.ByteString getJournalBytes(); - - /** - * optional int64 position = 2; - */ - boolean hasPosition(); - - /** - * optional int64 position = 2; - */ - long getPosition(); - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - boolean hasTimestamp(); - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - long getTimestamp(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Messages) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Messages DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Messages(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Messages getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Messages parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Messages(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Messages getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface DumpOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.Dump) + com.google.protobuf.MessageOrBuilder { + + /** + * string journal = 1; + */ + java.lang.String getJournal(); + /** + * string journal = 1; + */ + com.google.protobuf.ByteString + getJournalBytes(); + + /** + * int64 position = 2; + */ + long getPosition(); + + /** + * int64 timestamp = 3; + */ + long getTimestamp(); + + public com.alibaba.otter.canal.protocol.CanalPacket.Dump.TimestampPresentCase getTimestampPresentCase(); + } + /** + *
      +   * TBD when new packets are required
      +   * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Dump} + */ + public static final class Dump extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Dump) + DumpOrBuilder { + private static final long serialVersionUID = 0L; + // Use Dump.newBuilder() to construct. + private Dump(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private Dump() { + journal_ = ""; + position_ = 0L; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private Dump( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + + journal_ = s; + break; + } + case 16: { + + position_ = input.readInt64(); + break; + } + case 24: { + timestampPresentCase_ = 3; + timestampPresent_ = input.readInt64(); + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Dump.class, com.alibaba.otter.canal.protocol.CanalPacket.Dump.Builder.class); + } + + private int timestampPresentCase_ = 0; + private java.lang.Object timestampPresent_; + public enum TimestampPresentCase + implements com.google.protobuf.Internal.EnumLite { + TIMESTAMP(3), + TIMESTAMPPRESENT_NOT_SET(0); + private final int value; + private TimestampPresentCase(int value) { + this.value = value; + } + /** + * @deprecated Use {@link #forNumber(int)} instead. + */ + @java.lang.Deprecated + public static TimestampPresentCase valueOf(int value) { + return forNumber(value); + } + + public static TimestampPresentCase forNumber(int value) { + switch (value) { + case 3: return TIMESTAMP; + case 0: return TIMESTAMPPRESENT_NOT_SET; + default: return null; + } + } + public int getNumber() { + return this.value; + } + }; + + public TimestampPresentCase + getTimestampPresentCase() { + return TimestampPresentCase.forNumber( + timestampPresentCase_); + } + + public static final int JOURNAL_FIELD_NUMBER = 1; + private volatile java.lang.Object journal_; + /** + * string journal = 1; + */ + public java.lang.String getJournal() { + java.lang.Object ref = journal_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + journal_ = s; + return s; + } + } + /** + * string journal = 1; + */ + public com.google.protobuf.ByteString + getJournalBytes() { + java.lang.Object ref = journal_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + journal_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int POSITION_FIELD_NUMBER = 2; + private long position_; + /** + * int64 position = 2; + */ + public long getPosition() { + return position_; + } + + public static final int TIMESTAMP_FIELD_NUMBER = 3; + /** + * int64 timestamp = 3; + */ + public long getTimestamp() { + if (timestampPresentCase_ == 3) { + return (java.lang.Long) timestampPresent_; + } + return 0L; + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (!getJournalBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, journal_); + } + if (position_ != 0L) { + output.writeInt64(2, position_); + } + if (timestampPresentCase_ == 3) { + output.writeInt64( + 3, (long)((java.lang.Long) timestampPresent_)); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (!getJournalBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, journal_); + } + if (position_ != 0L) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(2, position_); + } + if (timestampPresentCase_ == 3) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size( + 3, (long)((java.lang.Long) timestampPresent_)); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.Dump)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.Dump other = (com.alibaba.otter.canal.protocol.CanalPacket.Dump) obj; + + boolean result = true; + result = result && getJournal() + .equals(other.getJournal()); + result = result && (getPosition() + == other.getPosition()); + result = result && getTimestampPresentCase().equals( + other.getTimestampPresentCase()); + if (!result) return false; + switch (timestampPresentCase_) { + case 3: + result = result && (getTimestamp() + == other.getTimestamp()); + break; + case 0: + default: + } + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + JOURNAL_FIELD_NUMBER; + hash = (53 * hash) + getJournal().hashCode(); + hash = (37 * hash) + POSITION_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getPosition()); + switch (timestampPresentCase_) { + case 3: + hash = (37 * hash) + TIMESTAMP_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getTimestamp()); + break; + case 0: + default: + } + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Dump prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Dump} - * *
            * TBD when new packets are required
            * 
      + * + * Protobuf type {@code com.alibaba.otter.canal.protocol.Dump} */ - public static final class Dump extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.Dump) - DumpOrBuilder { - - // Use Dump.newBuilder() to construct. - private Dump(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private Dump(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final Dump defaultInstance; - - public static Dump getDefaultInstance() { - return defaultInstance; - } - - public Dump getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private Dump(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - journal_ = bs; - break; - } - case 16: { - bitField0_ |= 0x00000002; - position_ = input.readInt64(); - break; - } - case 24: { - bitField0_ |= 0x00000004; - timestamp_ = input.readInt64(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Dump.class, - com.alibaba.otter.canal.protocol.CanalPacket.Dump.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public Dump parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new Dump(input, extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int JOURNAL_FIELD_NUMBER = 1; - private java.lang.Object journal_; - - /** - * optional string journal = 1; - */ - public boolean hasJournal() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string journal = 1; - */ - public java.lang.String getJournal() { - java.lang.Object ref = journal_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - journal_ = s; - } - return s; - } - } - - /** - * optional string journal = 1; - */ - public com.google.protobuf.ByteString getJournalBytes() { - java.lang.Object ref = journal_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - journal_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int POSITION_FIELD_NUMBER = 2; - private long position_; - - /** - * optional int64 position = 2; - */ - public boolean hasPosition() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int64 position = 2; - */ - public long getPosition() { - return position_; - } - - public static final int TIMESTAMP_FIELD_NUMBER = 3; - private long timestamp_; - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - public boolean hasTimestamp() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - public long getTimestamp() { - return timestamp_; - } - - private void initFields() { - journal_ = ""; - position_ = 0L; - timestamp_ = 0L; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getJournalBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeInt64(2, position_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeInt64(3, timestamp_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getJournalBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(2, position_); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(3, timestamp_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.Dump parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.Dump prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.Dump} - * - *
      -         * TBD when new packets are required
      -         * 
      - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.Dump) com.alibaba.otter.canal.protocol.CanalPacket.DumpOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.Dump.class, com.alibaba.otter.canal.protocol.CanalPacket.Dump.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.Dump.class, - com.alibaba.otter.canal.protocol.CanalPacket.Dump.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.Dump.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.Dump.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - journal_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - position_ = 0L; - bitField0_ = (bitField0_ & ~0x00000002); - timestamp_ = 0L; - bitField0_ = (bitField0_ & ~0x00000004); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Dump getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.Dump.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Dump build() { - com.alibaba.otter.canal.protocol.CanalPacket.Dump result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.Dump buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.Dump result = new com.alibaba.otter.canal.protocol.CanalPacket.Dump(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.journal_ = journal_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.position_ = position_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.timestamp_ = timestamp_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Dump) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Dump) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Dump other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.Dump.getDefaultInstance()) return this; - if (other.hasJournal()) { - bitField0_ |= 0x00000001; - journal_ = other.journal_; - onChanged(); - } - if (other.hasPosition()) { - setPosition(other.getPosition()); - } - if (other.hasTimestamp()) { - setTimestamp(other.getTimestamp()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.Dump parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Dump) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object journal_ = ""; - - /** - * optional string journal = 1; - */ - public boolean hasJournal() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string journal = 1; - */ - public java.lang.String getJournal() { - java.lang.Object ref = journal_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - journal_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string journal = 1; - */ - public com.google.protobuf.ByteString getJournalBytes() { - java.lang.Object ref = journal_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - journal_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string journal = 1; - */ - public Builder setJournal(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - journal_ = value; - onChanged(); - return this; - } - - /** - * optional string journal = 1; - */ - public Builder clearJournal() { - bitField0_ = (bitField0_ & ~0x00000001); - journal_ = getDefaultInstance().getJournal(); - onChanged(); - return this; - } - - /** - * optional string journal = 1; - */ - public Builder setJournalBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - journal_ = value; - onChanged(); - return this; - } - - private long position_; - - /** - * optional int64 position = 2; - */ - public boolean hasPosition() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional int64 position = 2; - */ - public long getPosition() { - return position_; - } - - /** - * optional int64 position = 2; - */ - public Builder setPosition(long value) { - bitField0_ |= 0x00000002; - position_ = value; - onChanged(); - return this; - } - - /** - * optional int64 position = 2; - */ - public Builder clearPosition() { - bitField0_ = (bitField0_ & ~0x00000002); - position_ = 0L; - onChanged(); - return this; - } - - private long timestamp_; - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - public boolean hasTimestamp() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - public long getTimestamp() { - return timestamp_; - } - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - public Builder setTimestamp(long value) { - bitField0_ |= 0x00000004; - timestamp_ = value; - onChanged(); - return this; - } - - /** - * optional int64 timestamp = 3 [default = 0]; - */ - public Builder clearTimestamp() { - bitField0_ = (bitField0_ & ~0x00000004); - timestamp_ = 0L; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Dump) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + journal_ = ""; - static { - defaultInstance = new Dump(true); - defaultInstance.initFields(); + position_ = 0L; + + timestampPresentCase_ = 0; + timestampPresent_ = null; + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Dump getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.Dump.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Dump build() { + com.alibaba.otter.canal.protocol.CanalPacket.Dump result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Dump) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Dump buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.Dump result = new com.alibaba.otter.canal.protocol.CanalPacket.Dump(this); + result.journal_ = journal_; + result.position_ = position_; + if (timestampPresentCase_ == 3) { + result.timestampPresent_ = timestampPresent_; + } + result.timestampPresentCase_ = timestampPresentCase_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.Dump) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.Dump)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.Dump other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.Dump.getDefaultInstance()) return this; + if (!other.getJournal().isEmpty()) { + journal_ = other.journal_; + onChanged(); + } + if (other.getPosition() != 0L) { + setPosition(other.getPosition()); + } + switch (other.getTimestampPresentCase()) { + case TIMESTAMP: { + setTimestamp(other.getTimestamp()); + break; + } + case TIMESTAMPPRESENT_NOT_SET: { + break; + } + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.Dump parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.Dump) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + private int timestampPresentCase_ = 0; + private java.lang.Object timestampPresent_; + public TimestampPresentCase + getTimestampPresentCase() { + return TimestampPresentCase.forNumber( + timestampPresentCase_); + } + + public Builder clearTimestampPresent() { + timestampPresentCase_ = 0; + timestampPresent_ = null; + onChanged(); + return this; + } + + + private java.lang.Object journal_ = ""; + /** + * string journal = 1; + */ + public java.lang.String getJournal() { + java.lang.Object ref = journal_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + journal_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string journal = 1; + */ + public com.google.protobuf.ByteString + getJournalBytes() { + java.lang.Object ref = journal_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + journal_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string journal = 1; + */ + public Builder setJournal( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + journal_ = value; + onChanged(); + return this; + } + /** + * string journal = 1; + */ + public Builder clearJournal() { + + journal_ = getDefaultInstance().getJournal(); + onChanged(); + return this; + } + /** + * string journal = 1; + */ + public Builder setJournalBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + journal_ = value; + onChanged(); + return this; + } + + private long position_ ; + /** + * int64 position = 2; + */ + public long getPosition() { + return position_; + } + /** + * int64 position = 2; + */ + public Builder setPosition(long value) { + + position_ = value; + onChanged(); + return this; + } + /** + * int64 position = 2; + */ + public Builder clearPosition() { + + position_ = 0L; + onChanged(); + return this; + } + + /** + * int64 timestamp = 3; + */ + public long getTimestamp() { + if (timestampPresentCase_ == 3) { + return (java.lang.Long) timestampPresent_; + } + return 0L; + } + /** + * int64 timestamp = 3; + */ + public Builder setTimestamp(long value) { + timestampPresentCase_ = 3; + timestampPresent_ = value; + onChanged(); + return this; + } + /** + * int64 timestamp = 3; + */ + public Builder clearTimestamp() { + if (timestampPresentCase_ == 3) { + timestampPresentCase_ = 0; + timestampPresent_ = null; + onChanged(); + } + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.Dump) } - public interface ClientRollbackOrBuilder extends - // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.ClientRollback) - com.google.protobuf.MessageOrBuilder { - - /** - * optional string destination = 1; - */ - boolean hasDestination(); - - /** - * optional string destination = 1; - */ - java.lang.String getDestination(); - - /** - * optional string destination = 1; - */ - com.google.protobuf.ByteString getDestinationBytes(); - - /** - * optional string client_id = 2; - */ - boolean hasClientId(); - - /** - * optional string client_id = 2; - */ - java.lang.String getClientId(); - - /** - * optional string client_id = 2; - */ - com.google.protobuf.ByteString getClientIdBytes(); - - /** - * optional int64 batch_id = 3; - */ - boolean hasBatchId(); - - /** - * optional int64 batch_id = 3; - */ - long getBatchId(); + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.Dump) + private static final com.alibaba.otter.canal.protocol.CanalPacket.Dump DEFAULT_INSTANCE; + static { + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.Dump(); } + public static com.alibaba.otter.canal.protocol.CanalPacket.Dump getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public Dump parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new Dump(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.Dump getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + public interface ClientRollbackOrBuilder extends + // @@protoc_insertion_point(interface_extends:com.alibaba.otter.canal.protocol.ClientRollback) + com.google.protobuf.MessageOrBuilder { + + /** + * string destination = 1; + */ + java.lang.String getDestination(); + /** + * string destination = 1; + */ + com.google.protobuf.ByteString + getDestinationBytes(); + + /** + * string client_id = 2; + */ + java.lang.String getClientId(); + /** + * string client_id = 2; + */ + com.google.protobuf.ByteString + getClientIdBytes(); + + /** + * int64 batch_id = 3; + */ + long getBatchId(); + } + /** + * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientRollback} + */ + public static final class ClientRollback extends + com.google.protobuf.GeneratedMessageV3 implements + // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.ClientRollback) + ClientRollbackOrBuilder { + private static final long serialVersionUID = 0L; + // Use ClientRollback.newBuilder() to construct. + private ClientRollback(com.google.protobuf.GeneratedMessageV3.Builder builder) { + super(builder); + } + private ClientRollback() { + destination_ = ""; + clientId_ = ""; + batchId_ = 0L; + } + + @java.lang.Override + public final com.google.protobuf.UnknownFieldSet + getUnknownFields() { + return this.unknownFields; + } + private ClientRollback( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + this(); + if (extensionRegistry == null) { + throw new java.lang.NullPointerException(); + } + int mutable_bitField0_ = 0; + com.google.protobuf.UnknownFieldSet.Builder unknownFields = + com.google.protobuf.UnknownFieldSet.newBuilder(); + try { + boolean done = false; + while (!done) { + int tag = input.readTag(); + switch (tag) { + case 0: + done = true; + break; + case 10: { + java.lang.String s = input.readStringRequireUtf8(); + + destination_ = s; + break; + } + case 18: { + java.lang.String s = input.readStringRequireUtf8(); + + clientId_ = s; + break; + } + case 24: { + + batchId_ = input.readInt64(); + break; + } + default: { + if (!parseUnknownFieldProto3( + input, unknownFields, extensionRegistry, tag)) { + done = true; + } + break; + } + } + } + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + throw e.setUnfinishedMessage(this); + } catch (java.io.IOException e) { + throw new com.google.protobuf.InvalidProtocolBufferException( + e).setUnfinishedMessage(this); + } finally { + this.unknownFields = unknownFields.build(); + makeExtensionsImmutable(); + } + } + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; + } + + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.class, com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.Builder.class); + } + + public static final int DESTINATION_FIELD_NUMBER = 1; + private volatile java.lang.Object destination_; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int CLIENT_ID_FIELD_NUMBER = 2; + private volatile java.lang.Object clientId_; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + return (java.lang.String) ref; + } else { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof java.lang.String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + + public static final int BATCH_ID_FIELD_NUMBER = 3; + private long batchId_; + /** + * int64 batch_id = 3; + */ + public long getBatchId() { + return batchId_; + } + + private byte memoizedIsInitialized = -1; + @java.lang.Override + public final boolean isInitialized() { + byte isInitialized = memoizedIsInitialized; + if (isInitialized == 1) return true; + if (isInitialized == 0) return false; + + memoizedIsInitialized = 1; + return true; + } + + @java.lang.Override + public void writeTo(com.google.protobuf.CodedOutputStream output) + throws java.io.IOException { + if (!getDestinationBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + com.google.protobuf.GeneratedMessageV3.writeString(output, 2, clientId_); + } + if (batchId_ != 0L) { + output.writeInt64(3, batchId_); + } + unknownFields.writeTo(output); + } + + @java.lang.Override + public int getSerializedSize() { + int size = memoizedSize; + if (size != -1) return size; + + size = 0; + if (!getDestinationBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(1, destination_); + } + if (!getClientIdBytes().isEmpty()) { + size += com.google.protobuf.GeneratedMessageV3.computeStringSize(2, clientId_); + } + if (batchId_ != 0L) { + size += com.google.protobuf.CodedOutputStream + .computeInt64Size(3, batchId_); + } + size += unknownFields.getSerializedSize(); + memoizedSize = size; + return size; + } + + @java.lang.Override + public boolean equals(final java.lang.Object obj) { + if (obj == this) { + return true; + } + if (!(obj instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback)) { + return super.equals(obj); + } + com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback other = (com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback) obj; + + boolean result = true; + result = result && getDestination() + .equals(other.getDestination()); + result = result && getClientId() + .equals(other.getClientId()); + result = result && (getBatchId() + == other.getBatchId()); + result = result && unknownFields.equals(other.unknownFields); + return result; + } + + @java.lang.Override + public int hashCode() { + if (memoizedHashCode != 0) { + return memoizedHashCode; + } + int hash = 41; + hash = (19 * hash) + getDescriptor().hashCode(); + hash = (37 * hash) + DESTINATION_FIELD_NUMBER; + hash = (53 * hash) + getDestination().hashCode(); + hash = (37 * hash) + CLIENT_ID_FIELD_NUMBER; + hash = (53 * hash) + getClientId().hashCode(); + hash = (37 * hash) + BATCH_ID_FIELD_NUMBER; + hash = (53 * hash) + com.google.protobuf.Internal.hashLong( + getBatchId()); + hash = (29 * hash) + unknownFields.hashCode(); + memoizedHashCode = hash; + return hash; + } + + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + java.nio.ByteBuffer data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + java.nio.ByteBuffer data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + com.google.protobuf.ByteString data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + com.google.protobuf.ByteString data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(byte[] data) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + byte[] data, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return PARSER.parseFrom(data, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseDelimitedFrom(java.io.InputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseDelimitedFrom( + java.io.InputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseDelimitedWithIOException(PARSER, input, extensionRegistry); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + com.google.protobuf.CodedInputStream input) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input); + } + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + return com.google.protobuf.GeneratedMessageV3 + .parseWithIOException(PARSER, input, extensionRegistry); + } + + @java.lang.Override + public Builder newBuilderForType() { return newBuilder(); } + public static Builder newBuilder() { + return DEFAULT_INSTANCE.toBuilder(); + } + public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback prototype) { + return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype); + } + @java.lang.Override + public Builder toBuilder() { + return this == DEFAULT_INSTANCE + ? new Builder() : new Builder().mergeFrom(this); + } + + @java.lang.Override + protected Builder newBuilderForType( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + Builder builder = new Builder(parent); + return builder; + } /** * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientRollback} */ - public static final class ClientRollback extends com.google.protobuf.GeneratedMessage implements - // @@protoc_insertion_point(message_implements:com.alibaba.otter.canal.protocol.ClientRollback) - ClientRollbackOrBuilder { - - // Use ClientRollback.newBuilder() to construct. - private ClientRollback(com.google.protobuf.GeneratedMessage.Builder builder){ - super(builder); - this.unknownFields = builder.getUnknownFields(); - } - - private ClientRollback(boolean noInit){ - this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); - } - - private static final ClientRollback defaultInstance; - - public static ClientRollback getDefaultInstance() { - return defaultInstance; - } - - public ClientRollback getDefaultInstanceForType() { - return defaultInstance; - } - - private final com.google.protobuf.UnknownFieldSet unknownFields; - - @java.lang.Override - public final com.google.protobuf.UnknownFieldSet getUnknownFields() { - return this.unknownFields; - } - - private ClientRollback(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException{ - initFields(); - int mutable_bitField0_ = 0; - com.google.protobuf.UnknownFieldSet.Builder unknownFields = com.google.protobuf.UnknownFieldSet.newBuilder(); - try { - boolean done = false; - while (!done) { - int tag = input.readTag(); - switch (tag) { - case 0: - done = true; - break; - default: { - if (!parseUnknownField(input, unknownFields, extensionRegistry, tag)) { - done = true; - } - break; - } - case 10: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000001; - destination_ = bs; - break; - } - case 18: { - com.google.protobuf.ByteString bs = input.readBytes(); - bitField0_ |= 0x00000002; - clientId_ = bs; - break; - } - case 24: { - bitField0_ |= 0x00000004; - batchId_ = input.readInt64(); - break; - } - } - } - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - throw e.setUnfinishedMessage(this); - } catch (java.io.IOException e) { - throw new com.google.protobuf.InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(this); - } finally { - this.unknownFields = unknownFields.build(); - makeExtensionsImmutable(); - } - } - - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; - } - - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.class, - com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.Builder.class); - } - - public static com.google.protobuf.Parser PARSER = new com.google.protobuf.AbstractParser() { - - public ClientRollback parsePartialFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return new ClientRollback(input, - extensionRegistry); - } - }; - - @java.lang.Override - public com.google.protobuf.Parser getParserForType() { - return PARSER; - } - - private int bitField0_; - public static final int DESTINATION_FIELD_NUMBER = 1; - private java.lang.Object destination_; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int CLIENT_ID_FIELD_NUMBER = 2; - private java.lang.Object clientId_; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - return (java.lang.String) ref; - } else { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof java.lang.String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - public static final int BATCH_ID_FIELD_NUMBER = 3; - private long batchId_; - - /** - * optional int64 batch_id = 3; - */ - public boolean hasBatchId() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 batch_id = 3; - */ - public long getBatchId() { - return batchId_; - } - - private void initFields() { - destination_ = ""; - clientId_ = ""; - batchId_ = 0L; - } - - private byte memoizedIsInitialized = -1; - - public final boolean isInitialized() { - byte isInitialized = memoizedIsInitialized; - if (isInitialized == 1) return true; - if (isInitialized == 0) return false; - - memoizedIsInitialized = 1; - return true; - } - - public void writeTo(com.google.protobuf.CodedOutputStream output) throws java.io.IOException { - getSerializedSize(); - if (((bitField0_ & 0x00000001) == 0x00000001)) { - output.writeBytes(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - output.writeBytes(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - output.writeInt64(3, batchId_); - } - getUnknownFields().writeTo(output); - } - - private int memoizedSerializedSize = -1; - - public int getSerializedSize() { - int size = memoizedSerializedSize; - if (size != -1) return size; - - size = 0; - if (((bitField0_ & 0x00000001) == 0x00000001)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(1, getDestinationBytes()); - } - if (((bitField0_ & 0x00000002) == 0x00000002)) { - size += com.google.protobuf.CodedOutputStream.computeBytesSize(2, getClientIdBytes()); - } - if (((bitField0_ & 0x00000004) == 0x00000004)) { - size += com.google.protobuf.CodedOutputStream.computeInt64Size(3, batchId_); - } - size += getUnknownFields().getSerializedSize(); - memoizedSerializedSize = size; - return size; - } - - private static final long serialVersionUID = 0L; - - @java.lang.Override - protected java.lang.Object writeReplace() throws java.io.ObjectStreamException { - return super.writeReplace(); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(com.google.protobuf.ByteString data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(com.google.protobuf.ByteString data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(byte[] data) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(byte[] data, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws com.google.protobuf.InvalidProtocolBufferException { - return PARSER.parseFrom(data, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseDelimitedFrom(java.io.InputStream input) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseDelimitedFrom(java.io.InputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseDelimitedFrom(input, extensionRegistry); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(com.google.protobuf.CodedInputStream input) - throws java.io.IOException { - return PARSER.parseFrom(input); - } - - public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parseFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - return PARSER.parseFrom(input, extensionRegistry); - } - - public static Builder newBuilder() { - return Builder.create(); - } - - public Builder newBuilderForType() { - return newBuilder(); - } - - public static Builder newBuilder(com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback prototype) { - return newBuilder().mergeFrom(prototype); - } - - public Builder toBuilder() { - return newBuilder(this); - } - - @java.lang.Override - protected Builder newBuilderForType(com.google.protobuf.GeneratedMessage.BuilderParent parent) { - Builder builder = new Builder(parent); - return builder; - } - - /** - * Protobuf type {@code com.alibaba.otter.canal.protocol.ClientRollback} - */ - public static final class Builder extends com.google.protobuf.GeneratedMessage.Builder implements + public static final class Builder extends + com.google.protobuf.GeneratedMessageV3.Builder implements // @@protoc_insertion_point(builder_implements:com.alibaba.otter.canal.protocol.ClientRollback) com.alibaba.otter.canal.protocol.CanalPacket.ClientRollbackOrBuilder { + public static final com.google.protobuf.Descriptors.Descriptor + getDescriptor() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; + } - public static final com.google.protobuf.Descriptors.Descriptor getDescriptor() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; - } + @java.lang.Override + protected com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internalGetFieldAccessorTable() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable + .ensureFieldAccessorsInitialized( + com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.class, com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.Builder.class); + } - protected com.google.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable.ensureFieldAccessorsInitialized(com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.class, - com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.Builder.class); - } + // Construct using com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.newBuilder() + private Builder() { + maybeForceBuilderInitialization(); + } - // Construct using - // com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.newBuilder() - private Builder(){ - maybeForceBuilderInitialization(); - } - - private Builder(com.google.protobuf.GeneratedMessage.BuilderParent parent){ - super(parent); - maybeForceBuilderInitialization(); - } - - private void maybeForceBuilderInitialization() { - if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) { - } - } - - private static Builder create() { - return new Builder(); - } - - public Builder clear() { - super.clear(); - destination_ = ""; - bitField0_ = (bitField0_ & ~0x00000001); - clientId_ = ""; - bitField0_ = (bitField0_ & ~0x00000002); - batchId_ = 0L; - bitField0_ = (bitField0_ & ~0x00000004); - return this; - } - - public Builder clone() { - return create().mergeFrom(buildPartial()); - } - - public com.google.protobuf.Descriptors.Descriptor getDescriptorForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback getDefaultInstanceForType() { - return com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.getDefaultInstance(); - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback build() { - com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback result = buildPartial(); - if (!result.isInitialized()) { - throw newUninitializedMessageException(result); - } - return result; - } - - public com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback buildPartial() { - com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback result = new com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback(this); - int from_bitField0_ = bitField0_; - int to_bitField0_ = 0; - if (((from_bitField0_ & 0x00000001) == 0x00000001)) { - to_bitField0_ |= 0x00000001; - } - result.destination_ = destination_; - if (((from_bitField0_ & 0x00000002) == 0x00000002)) { - to_bitField0_ |= 0x00000002; - } - result.clientId_ = clientId_; - if (((from_bitField0_ & 0x00000004) == 0x00000004)) { - to_bitField0_ |= 0x00000004; - } - result.batchId_ = batchId_; - result.bitField0_ = to_bitField0_; - onBuilt(); - return result; - } - - public Builder mergeFrom(com.google.protobuf.Message other) { - if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback) { - return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback) other); - } else { - super.mergeFrom(other); - return this; - } - } - - public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback other) { - if (other == com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.getDefaultInstance()) return this; - if (other.hasDestination()) { - bitField0_ |= 0x00000001; - destination_ = other.destination_; - onChanged(); - } - if (other.hasClientId()) { - bitField0_ |= 0x00000002; - clientId_ = other.clientId_; - onChanged(); - } - if (other.hasBatchId()) { - setBatchId(other.getBatchId()); - } - this.mergeUnknownFields(other.getUnknownFields()); - return this; - } - - public final boolean isInitialized() { - return true; - } - - public Builder mergeFrom(com.google.protobuf.CodedInputStream input, - com.google.protobuf.ExtensionRegistryLite extensionRegistry) - throws java.io.IOException { - com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parsedMessage = null; - try { - parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); - } catch (com.google.protobuf.InvalidProtocolBufferException e) { - parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback) e.getUnfinishedMessage(); - throw e; - } finally { - if (parsedMessage != null) { - mergeFrom(parsedMessage); - } - } - return this; - } - - private int bitField0_; - - private java.lang.Object destination_ = ""; - - /** - * optional string destination = 1; - */ - public boolean hasDestination() { - return ((bitField0_ & 0x00000001) == 0x00000001); - } - - /** - * optional string destination = 1; - */ - public java.lang.String getDestination() { - java.lang.Object ref = destination_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - destination_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string destination = 1; - */ - public com.google.protobuf.ByteString getDestinationBytes() { - java.lang.Object ref = destination_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - destination_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string destination = 1; - */ - public Builder setDestination(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder clearDestination() { - bitField0_ = (bitField0_ & ~0x00000001); - destination_ = getDefaultInstance().getDestination(); - onChanged(); - return this; - } - - /** - * optional string destination = 1; - */ - public Builder setDestinationBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000001; - destination_ = value; - onChanged(); - return this; - } - - private java.lang.Object clientId_ = ""; - - /** - * optional string client_id = 2; - */ - public boolean hasClientId() { - return ((bitField0_ & 0x00000002) == 0x00000002); - } - - /** - * optional string client_id = 2; - */ - public java.lang.String getClientId() { - java.lang.Object ref = clientId_; - if (!(ref instanceof java.lang.String)) { - com.google.protobuf.ByteString bs = (com.google.protobuf.ByteString) ref; - java.lang.String s = bs.toStringUtf8(); - if (bs.isValidUtf8()) { - clientId_ = s; - } - return s; - } else { - return (java.lang.String) ref; - } - } - - /** - * optional string client_id = 2; - */ - public com.google.protobuf.ByteString getClientIdBytes() { - java.lang.Object ref = clientId_; - if (ref instanceof String) { - com.google.protobuf.ByteString b = com.google.protobuf.ByteString.copyFromUtf8((java.lang.String) ref); - clientId_ = b; - return b; - } else { - return (com.google.protobuf.ByteString) ref; - } - } - - /** - * optional string client_id = 2; - */ - public Builder setClientId(java.lang.String value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder clearClientId() { - bitField0_ = (bitField0_ & ~0x00000002); - clientId_ = getDefaultInstance().getClientId(); - onChanged(); - return this; - } - - /** - * optional string client_id = 2; - */ - public Builder setClientIdBytes(com.google.protobuf.ByteString value) { - if (value == null) { - throw new NullPointerException(); - } - bitField0_ |= 0x00000002; - clientId_ = value; - onChanged(); - return this; - } - - private long batchId_; - - /** - * optional int64 batch_id = 3; - */ - public boolean hasBatchId() { - return ((bitField0_ & 0x00000004) == 0x00000004); - } - - /** - * optional int64 batch_id = 3; - */ - public long getBatchId() { - return batchId_; - } - - /** - * optional int64 batch_id = 3; - */ - public Builder setBatchId(long value) { - bitField0_ |= 0x00000004; - batchId_ = value; - onChanged(); - return this; - } - - /** - * optional int64 batch_id = 3; - */ - public Builder clearBatchId() { - bitField0_ = (bitField0_ & ~0x00000004); - batchId_ = 0L; - onChanged(); - return this; - } - - // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.ClientRollback) + private Builder( + com.google.protobuf.GeneratedMessageV3.BuilderParent parent) { + super(parent); + maybeForceBuilderInitialization(); + } + private void maybeForceBuilderInitialization() { + if (com.google.protobuf.GeneratedMessageV3 + .alwaysUseFieldBuilders) { } + } + @java.lang.Override + public Builder clear() { + super.clear(); + destination_ = ""; - static { - defaultInstance = new ClientRollback(true); - defaultInstance.initFields(); + clientId_ = ""; + + batchId_ = 0L; + + return this; + } + + @java.lang.Override + public com.google.protobuf.Descriptors.Descriptor + getDescriptorForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback getDefaultInstanceForType() { + return com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.getDefaultInstance(); + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback build() { + com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback result = buildPartial(); + if (!result.isInitialized()) { + throw newUninitializedMessageException(result); } + return result; + } - // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.ClientRollback) + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback buildPartial() { + com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback result = new com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback(this); + result.destination_ = destination_; + result.clientId_ = clientId_; + result.batchId_ = batchId_; + onBuilt(); + return result; + } + + @java.lang.Override + public Builder clone() { + return (Builder) super.clone(); + } + @java.lang.Override + public Builder setField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.setField(field, value); + } + @java.lang.Override + public Builder clearField( + com.google.protobuf.Descriptors.FieldDescriptor field) { + return (Builder) super.clearField(field); + } + @java.lang.Override + public Builder clearOneof( + com.google.protobuf.Descriptors.OneofDescriptor oneof) { + return (Builder) super.clearOneof(oneof); + } + @java.lang.Override + public Builder setRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + int index, java.lang.Object value) { + return (Builder) super.setRepeatedField(field, index, value); + } + @java.lang.Override + public Builder addRepeatedField( + com.google.protobuf.Descriptors.FieldDescriptor field, + java.lang.Object value) { + return (Builder) super.addRepeatedField(field, value); + } + @java.lang.Override + public Builder mergeFrom(com.google.protobuf.Message other) { + if (other instanceof com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback) { + return mergeFrom((com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback)other); + } else { + super.mergeFrom(other); + return this; + } + } + + public Builder mergeFrom(com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback other) { + if (other == com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback.getDefaultInstance()) return this; + if (!other.getDestination().isEmpty()) { + destination_ = other.destination_; + onChanged(); + } + if (!other.getClientId().isEmpty()) { + clientId_ = other.clientId_; + onChanged(); + } + if (other.getBatchId() != 0L) { + setBatchId(other.getBatchId()); + } + this.mergeUnknownFields(other.unknownFields); + onChanged(); + return this; + } + + @java.lang.Override + public final boolean isInitialized() { + return true; + } + + @java.lang.Override + public Builder mergeFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws java.io.IOException { + com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback parsedMessage = null; + try { + parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry); + } catch (com.google.protobuf.InvalidProtocolBufferException e) { + parsedMessage = (com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback) e.getUnfinishedMessage(); + throw e.unwrapIOException(); + } finally { + if (parsedMessage != null) { + mergeFrom(parsedMessage); + } + } + return this; + } + + private java.lang.Object destination_ = ""; + /** + * string destination = 1; + */ + public java.lang.String getDestination() { + java.lang.Object ref = destination_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + destination_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string destination = 1; + */ + public com.google.protobuf.ByteString + getDestinationBytes() { + java.lang.Object ref = destination_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + destination_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string destination = 1; + */ + public Builder setDestination( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + destination_ = value; + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder clearDestination() { + + destination_ = getDefaultInstance().getDestination(); + onChanged(); + return this; + } + /** + * string destination = 1; + */ + public Builder setDestinationBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + destination_ = value; + onChanged(); + return this; + } + + private java.lang.Object clientId_ = ""; + /** + * string client_id = 2; + */ + public java.lang.String getClientId() { + java.lang.Object ref = clientId_; + if (!(ref instanceof java.lang.String)) { + com.google.protobuf.ByteString bs = + (com.google.protobuf.ByteString) ref; + java.lang.String s = bs.toStringUtf8(); + clientId_ = s; + return s; + } else { + return (java.lang.String) ref; + } + } + /** + * string client_id = 2; + */ + public com.google.protobuf.ByteString + getClientIdBytes() { + java.lang.Object ref = clientId_; + if (ref instanceof String) { + com.google.protobuf.ByteString b = + com.google.protobuf.ByteString.copyFromUtf8( + (java.lang.String) ref); + clientId_ = b; + return b; + } else { + return (com.google.protobuf.ByteString) ref; + } + } + /** + * string client_id = 2; + */ + public Builder setClientId( + java.lang.String value) { + if (value == null) { + throw new NullPointerException(); + } + + clientId_ = value; + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder clearClientId() { + + clientId_ = getDefaultInstance().getClientId(); + onChanged(); + return this; + } + /** + * string client_id = 2; + */ + public Builder setClientIdBytes( + com.google.protobuf.ByteString value) { + if (value == null) { + throw new NullPointerException(); + } + checkByteStringIsUtf8(value); + + clientId_ = value; + onChanged(); + return this; + } + + private long batchId_ ; + /** + * int64 batch_id = 3; + */ + public long getBatchId() { + return batchId_; + } + /** + * int64 batch_id = 3; + */ + public Builder setBatchId(long value) { + + batchId_ = value; + onChanged(); + return this; + } + /** + * int64 batch_id = 3; + */ + public Builder clearBatchId() { + + batchId_ = 0L; + onChanged(); + return this; + } + @java.lang.Override + public final Builder setUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.setUnknownFieldsProto3(unknownFields); + } + + @java.lang.Override + public final Builder mergeUnknownFields( + final com.google.protobuf.UnknownFieldSet unknownFields) { + return super.mergeUnknownFields(unknownFields); + } + + + // @@protoc_insertion_point(builder_scope:com.alibaba.otter.canal.protocol.ClientRollback) } - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable; - private static final com.google.protobuf.Descriptors.Descriptor internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; - private static com.google.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable; - - public static com.google.protobuf.Descriptors.FileDescriptor getDescriptor() { - return descriptor; - } - - private static com.google.protobuf.Descriptors.FileDescriptor descriptor; + // @@protoc_insertion_point(class_scope:com.alibaba.otter.canal.protocol.ClientRollback) + private static final com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback DEFAULT_INSTANCE; static { - java.lang.String[] descriptorData = { - "\n\023CanalProtocol.proto\022 com.alibaba.otter" - + ".canal.protocol\"\312\001\n\006Packet\022\030\n\014magic_numb" - + "er\030\001 \001(\005:\00217\022\022\n\007version\030\002 \001(\005:\0011\022:\n\004type" - + "\030\003 \001(\0162,.com.alibaba.otter.canal.protoco" - + "l.PacketType\022H\n\013compression\030\004 \001(\0162-.com." - + "alibaba.otter.canal.protocol.Compression" - + ":\004NONE\022\014\n\004body\030\005 \001(\014\"<\n\tHeartBeat\022\026\n\016sen" - + "d_timestamp\030\001 \001(\003\022\027\n\017start_timestamp\030\002 \001" - + "(\003\"\217\001\n\tHandshake\022$\n\026communication_encodi" - + "ng\030\001 \001(\t:\004utf8\022\r\n\005seeds\030\002 \001(\014\022M\n\026support", - "ed_compressions\030\003 \003(\0162-.com.alibaba.otte" - + "r.canal.protocol.Compression\"\274\001\n\nClientA" - + "uth\022\020\n\010username\030\001 \001(\t\022\020\n\010password\030\002 \001(\014\022" - + "\033\n\020net_read_timeout\030\003 \001(\005:\0010\022\034\n\021net_writ" - + "e_timeout\030\004 \001(\005:\0010\022\023\n\013destination\030\005 \001(\t\022" - + "\021\n\tclient_id\030\006 \001(\t\022\016\n\006filter\030\007 \001(\t\022\027\n\017st" - + "art_timestamp\030\010 \001(\003\"3\n\003Ack\022\025\n\nerror_code" - + "\030\001 \001(\005:\0010\022\025\n\rerror_message\030\002 \001(\t\"E\n\tClie" - + "ntAck\022\023\n\013destination\030\001 \001(\t\022\021\n\tclient_id\030" - + "\002 \001(\t\022\020\n\010batch_id\030\003 \001(\003\"=\n\003Sub\022\023\n\013destin", - "ation\030\001 \001(\t\022\021\n\tclient_id\030\002 \001(\t\022\016\n\006filter" - + "\030\007 \001(\t\"?\n\005Unsub\022\023\n\013destination\030\001 \001(\t\022\021\n\t" - + "client_id\030\002 \001(\t\022\016\n\006filter\030\007 \001(\t\"\200\001\n\003Get\022" - + "\023\n\013destination\030\001 \001(\t\022\021\n\tclient_id\030\002 \001(\t\022" - + "\022\n\nfetch_size\030\003 \001(\005\022\023\n\007timeout\030\004 \001(\003:\002-1" - + "\022\017\n\004unit\030\005 \001(\005:\0012\022\027\n\010auto_ack\030\006 \001(\010:\005fal" - + "se\".\n\010Messages\022\020\n\010batch_id\030\001 \001(\003\022\020\n\010mess" - + "ages\030\002 \003(\014\"?\n\004Dump\022\017\n\007journal\030\001 \001(\t\022\020\n\010p" - + "osition\030\002 \001(\003\022\024\n\ttimestamp\030\003 \001(\003:\0010\"J\n\016C" - + "lientRollback\022\023\n\013destination\030\001 \001(\t\022\021\n\tcl", - "ient_id\030\002 \001(\t\022\020\n\010batch_id\030\003 \001(\003*4\n\013Compr" - + "ession\022\010\n\004NONE\020\001\022\010\n\004ZLIB\020\002\022\010\n\004GZIP\020\003\022\007\n\003" - + "LZF\020\004*\305\001\n\nPacketType\022\r\n\tHANDSHAKE\020\001\022\030\n\024C" - + "LIENTAUTHENTICATION\020\002\022\007\n\003ACK\020\003\022\020\n\014SUBSCR" - + "IPTION\020\004\022\022\n\016UNSUBSCRIPTION\020\005\022\007\n\003GET\020\006\022\014\n" - + "\010MESSAGES\020\007\022\r\n\tCLIENTACK\020\010\022\014\n\010SHUTDOWN\020\t" - + "\022\010\n\004DUMP\020\n\022\r\n\tHEARTBEAT\020\013\022\022\n\016CLIENTROLLB" - + "ACK\020\014B1\n com.alibaba.otter.canal.protoco" + "lB\013CanalPacketH\001" }; - com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner = new com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner() { - - public com.google.protobuf.ExtensionRegistry assignDescriptors(com.google.protobuf.Descriptors.FileDescriptor root) { - descriptor = root; - return null; - } - }; - com.google.protobuf.Descriptors.FileDescriptor.internalBuildGeneratedFileFrom(descriptorData, - new com.google.protobuf.Descriptors.FileDescriptor[] {}, - assigner); - internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor = getDescriptor().getMessageTypes().get(0); - internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor, - new java.lang.String[] { "MagicNumber", "Version", "Type", "Compression", "Body", }); - internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor = getDescriptor().getMessageTypes() - .get(1); - internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor, - new java.lang.String[] { "SendTimestamp", "StartTimestamp", }); - internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor = getDescriptor().getMessageTypes() - .get(2); - internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor, - new java.lang.String[] { "CommunicationEncoding", "Seeds", "SupportedCompressions", }); - internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor = getDescriptor().getMessageTypes() - .get(3); - internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor, - new java.lang.String[] { "Username", "Password", "NetReadTimeout", "NetWriteTimeout", "Destination", - "ClientId", "Filter", "StartTimestamp", }); - internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor = getDescriptor().getMessageTypes().get(4); - internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor, - new java.lang.String[] { "ErrorCode", "ErrorMessage", }); - internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor = getDescriptor().getMessageTypes() - .get(5); - internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor, - new java.lang.String[] { "Destination", "ClientId", "BatchId", }); - internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor = getDescriptor().getMessageTypes().get(6); - internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor, - new java.lang.String[] { "Destination", "ClientId", "Filter", }); - internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor = getDescriptor().getMessageTypes().get(7); - internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor, - new java.lang.String[] { "Destination", "ClientId", "Filter", }); - internal_static_com_alibaba_otter_canal_protocol_Get_descriptor = getDescriptor().getMessageTypes().get(8); - internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Get_descriptor, - new java.lang.String[] { "Destination", "ClientId", "FetchSize", "Timeout", "Unit", "AutoAck", }); - internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor = getDescriptor().getMessageTypes().get(9); - internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor, - new java.lang.String[] { "BatchId", "Messages", }); - internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor = getDescriptor().getMessageTypes().get(10); - internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor, - new java.lang.String[] { "Journal", "Position", "Timestamp", }); - internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor = getDescriptor().getMessageTypes() - .get(11); - internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable = new com.google.protobuf.GeneratedMessage.FieldAccessorTable(internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor, - new java.lang.String[] { "Destination", "ClientId", "BatchId", }); + DEFAULT_INSTANCE = new com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback(); } - // @@protoc_insertion_point(outer_class_scope) + public static com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback getDefaultInstance() { + return DEFAULT_INSTANCE; + } + + private static final com.google.protobuf.Parser + PARSER = new com.google.protobuf.AbstractParser() { + @java.lang.Override + public ClientRollback parsePartialFrom( + com.google.protobuf.CodedInputStream input, + com.google.protobuf.ExtensionRegistryLite extensionRegistry) + throws com.google.protobuf.InvalidProtocolBufferException { + return new ClientRollback(input, extensionRegistry); + } + }; + + public static com.google.protobuf.Parser parser() { + return PARSER; + } + + @java.lang.Override + public com.google.protobuf.Parser getParserForType() { + return PARSER; + } + + @java.lang.Override + public com.alibaba.otter.canal.protocol.CanalPacket.ClientRollback getDefaultInstanceForType() { + return DEFAULT_INSTANCE; + } + + } + + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Get_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable; + private static final com.google.protobuf.Descriptors.Descriptor + internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor; + private static final + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable + internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable; + + public static com.google.protobuf.Descriptors.FileDescriptor + getDescriptor() { + return descriptor; + } + private static com.google.protobuf.Descriptors.FileDescriptor + descriptor; + static { + java.lang.String[] descriptorData = { + "\n\023CanalProtocol.proto\022 com.alibaba.otter" + + ".canal.protocol\"\205\002\n\006Packet\022\026\n\014magic_numb" + + "er\030\001 \001(\005H\000\022\021\n\007version\030\002 \001(\005H\001\022:\n\004type\030\003 " + + "\001(\0162,.com.alibaba.otter.canal.protocol.P" + + "acketType\022D\n\013compression\030\004 \001(\0162-.com.ali" + + "baba.otter.canal.protocol.CompressionH\002\022" + + "\014\n\004body\030\005 \001(\014B\026\n\024magic_number_presentB\021\n" + + "\017version_presentB\025\n\023compression_present\"" + + "<\n\tHeartBeat\022\026\n\016send_timestamp\030\001 \001(\003\022\027\n\017" + + "start_timestamp\030\002 \001(\003\"\255\001\n\tHandshake\022 \n\026c" + + "ommunication_encoding\030\001 \001(\tH\000\022\r\n\005seeds\030\002" + + " \001(\014\022M\n\026supported_compressions\030\003 \001(\0162-.c" + + "om.alibaba.otter.canal.protocol.Compress" + + "ionB \n\036communication_encoding_present\"\363\001" + + "\n\nClientAuth\022\020\n\010username\030\001 \001(\t\022\020\n\010passwo" + + "rd\030\002 \001(\014\022\032\n\020net_read_timeout\030\003 \001(\005H\000\022\033\n\021" + + "net_write_timeout\030\004 \001(\005H\001\022\023\n\013destination" + + "\030\005 \001(\t\022\021\n\tclient_id\030\006 \001(\t\022\016\n\006filter\030\007 \001(" + + "\t\022\027\n\017start_timestamp\030\010 \001(\003B\032\n\030net_read_t" + + "imeout_presentB\033\n\031net_write_timeout_pres" + + "ent\"H\n\003Ack\022\024\n\nerror_code\030\001 \001(\005H\000\022\025\n\rerro" + + "r_message\030\002 \001(\tB\024\n\022error_code_present\"E\n" + + "\tClientAck\022\023\n\013destination\030\001 \001(\t\022\021\n\tclien" + + "t_id\030\002 \001(\t\022\020\n\010batch_id\030\003 \001(\003\"=\n\003Sub\022\023\n\013d" + + "estination\030\001 \001(\t\022\021\n\tclient_id\030\002 \001(\t\022\016\n\006f" + + "ilter\030\007 \001(\t\"?\n\005Unsub\022\023\n\013destination\030\001 \001(" + + "\t\022\021\n\tclient_id\030\002 \001(\t\022\016\n\006filter\030\007 \001(\t\"\257\001\n" + + "\003Get\022\023\n\013destination\030\001 \001(\t\022\021\n\tclient_id\030\002" + + " \001(\t\022\022\n\nfetch_size\030\003 \001(\005\022\021\n\007timeout\030\004 \001(" + + "\003H\000\022\016\n\004unit\030\005 \001(\005H\001\022\022\n\010auto_ack\030\006 \001(\010H\002B" + + "\021\n\017timeout_presentB\016\n\014unit_presentB\022\n\020au" + + "to_ack_present\".\n\010Messages\022\020\n\010batch_id\030\001" + + " \001(\003\022\020\n\010messages\030\002 \003(\014\"S\n\004Dump\022\017\n\007journa" + + "l\030\001 \001(\t\022\020\n\010position\030\002 \001(\003\022\023\n\ttimestamp\030\003" + + " \001(\003H\000B\023\n\021timestamp_present\"J\n\016ClientRol" + + "lback\022\023\n\013destination\030\001 \001(\t\022\021\n\tclient_id\030" + + "\002 \001(\t\022\020\n\010batch_id\030\003 \001(\003*U\n\013Compression\022\037" + + "\n\033COMPRESSIONCOMPATIBLEPROTO2\020\000\022\010\n\004NONE\020" + + "\001\022\010\n\004ZLIB\020\002\022\010\n\004GZIP\020\003\022\007\n\003LZF\020\004*\346\001\n\nPacke" + + "tType\022\037\n\033PACKAGETYPECOMPATIBLEPROTO2\020\000\022\r" + + "\n\tHANDSHAKE\020\001\022\030\n\024CLIENTAUTHENTICATION\020\002\022" + + "\007\n\003ACK\020\003\022\020\n\014SUBSCRIPTION\020\004\022\022\n\016UNSUBSCRIP" + + "TION\020\005\022\007\n\003GET\020\006\022\014\n\010MESSAGES\020\007\022\r\n\tCLIENTA" + + "CK\020\010\022\014\n\010SHUTDOWN\020\t\022\010\n\004DUMP\020\n\022\r\n\tHEARTBEA" + + "T\020\013\022\022\n\016CLIENTROLLBACK\020\014B1\n com.alibaba.o" + + "tter.canal.protocolB\013CanalPacketH\001b\006prot" + + "o3" + }; + com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner = + new com.google.protobuf.Descriptors.FileDescriptor. InternalDescriptorAssigner() { + public com.google.protobuf.ExtensionRegistry assignDescriptors( + com.google.protobuf.Descriptors.FileDescriptor root) { + descriptor = root; + return null; + } + }; + com.google.protobuf.Descriptors.FileDescriptor + .internalBuildGeneratedFileFrom(descriptorData, + new com.google.protobuf.Descriptors.FileDescriptor[] { + }, assigner); + internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor = + getDescriptor().getMessageTypes().get(0); + internal_static_com_alibaba_otter_canal_protocol_Packet_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Packet_descriptor, + new java.lang.String[] { "MagicNumber", "Version", "Type", "Compression", "Body", "MagicNumberPresent", "VersionPresent", "CompressionPresent", }); + internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor = + getDescriptor().getMessageTypes().get(1); + internal_static_com_alibaba_otter_canal_protocol_HeartBeat_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_HeartBeat_descriptor, + new java.lang.String[] { "SendTimestamp", "StartTimestamp", }); + internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor = + getDescriptor().getMessageTypes().get(2); + internal_static_com_alibaba_otter_canal_protocol_Handshake_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Handshake_descriptor, + new java.lang.String[] { "CommunicationEncoding", "Seeds", "SupportedCompressions", "CommunicationEncodingPresent", }); + internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor = + getDescriptor().getMessageTypes().get(3); + internal_static_com_alibaba_otter_canal_protocol_ClientAuth_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_ClientAuth_descriptor, + new java.lang.String[] { "Username", "Password", "NetReadTimeout", "NetWriteTimeout", "Destination", "ClientId", "Filter", "StartTimestamp", "NetReadTimeoutPresent", "NetWriteTimeoutPresent", }); + internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor = + getDescriptor().getMessageTypes().get(4); + internal_static_com_alibaba_otter_canal_protocol_Ack_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Ack_descriptor, + new java.lang.String[] { "ErrorCode", "ErrorMessage", "ErrorCodePresent", }); + internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor = + getDescriptor().getMessageTypes().get(5); + internal_static_com_alibaba_otter_canal_protocol_ClientAck_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_ClientAck_descriptor, + new java.lang.String[] { "Destination", "ClientId", "BatchId", }); + internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor = + getDescriptor().getMessageTypes().get(6); + internal_static_com_alibaba_otter_canal_protocol_Sub_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Sub_descriptor, + new java.lang.String[] { "Destination", "ClientId", "Filter", }); + internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor = + getDescriptor().getMessageTypes().get(7); + internal_static_com_alibaba_otter_canal_protocol_Unsub_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Unsub_descriptor, + new java.lang.String[] { "Destination", "ClientId", "Filter", }); + internal_static_com_alibaba_otter_canal_protocol_Get_descriptor = + getDescriptor().getMessageTypes().get(8); + internal_static_com_alibaba_otter_canal_protocol_Get_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Get_descriptor, + new java.lang.String[] { "Destination", "ClientId", "FetchSize", "Timeout", "Unit", "AutoAck", "TimeoutPresent", "UnitPresent", "AutoAckPresent", }); + internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor = + getDescriptor().getMessageTypes().get(9); + internal_static_com_alibaba_otter_canal_protocol_Messages_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Messages_descriptor, + new java.lang.String[] { "BatchId", "Messages", }); + internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor = + getDescriptor().getMessageTypes().get(10); + internal_static_com_alibaba_otter_canal_protocol_Dump_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_Dump_descriptor, + new java.lang.String[] { "Journal", "Position", "Timestamp", "TimestampPresent", }); + internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor = + getDescriptor().getMessageTypes().get(11); + internal_static_com_alibaba_otter_canal_protocol_ClientRollback_fieldAccessorTable = new + com.google.protobuf.GeneratedMessageV3.FieldAccessorTable( + internal_static_com_alibaba_otter_canal_protocol_ClientRollback_descriptor, + new java.lang.String[] { "Destination", "ClientId", "BatchId", }); + } + + // @@protoc_insertion_point(outer_class_scope) } diff --git a/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalProtocol.proto b/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalProtocol.proto index 80f03439..e4e35b6d 100644 --- a/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalProtocol.proto +++ b/protocol/src/main/java/com/alibaba/otter/canal/protocol/CanalProtocol.proto @@ -1,3 +1,4 @@ +syntax = "proto3"; package com.alibaba.otter.canal.protocol; option java_package = "com.alibaba.otter.canal.protocol"; @@ -5,6 +6,7 @@ option java_outer_classname = "CanalPacket"; option optimize_for = SPEED; enum Compression { + COMPRESSIONCOMPATIBLEPROTO2 = 0; NONE = 1; ZLIB = 2; GZIP = 3; @@ -12,6 +14,8 @@ enum Compression { } enum PacketType { + //compatible + PACKAGETYPECOMPATIBLEPROTO2 = 0; HANDSHAKE = 1; CLIENTAUTHENTICATION = 2; ACK = 3; @@ -29,86 +33,122 @@ enum PacketType { } message Packet { - optional int32 magic_number = 1 [default = 17]; - optional int32 version = 2 [default = 1]; - optional PacketType type = 3; - optional Compression compression = 4 [default = NONE]; - optional bytes body = 5; + //[default = 17]; + oneof magic_number_present { + int32 magic_number = 1; + } + //[default = 1]; + oneof version_present { + int32 version = 2; + }; + PacketType type = 3; + //[default = NONE]; + oneof compression_present { + Compression compression = 4; + } + + bytes body = 5; } message HeartBeat { - optional int64 send_timestamp = 1; - optional int64 start_timestamp = 2; + int64 send_timestamp = 1; + int64 start_timestamp = 2; } message Handshake { - optional string communication_encoding = 1 [default = "utf8"]; - optional bytes seeds = 2; - repeated Compression supported_compressions = 3; + // [default = "utf8"]; + oneof communication_encoding_present { + string communication_encoding = 1; + } + bytes seeds = 2; + Compression supported_compressions = 3; } // client authentication message ClientAuth { - optional string username = 1; - optional bytes password = 2; // hashed password with seeds from Handshake message - optional int32 net_read_timeout = 3 [default = 0]; // in seconds - optional int32 net_write_timeout = 4 [default = 0]; // in seconds - optional string destination = 5; - optional string client_id = 6; - optional string filter = 7; - optional int64 start_timestamp = 8; + string username = 1; + bytes password = 2; // hashed password with seeds from Handshake message + // [default = 0] + oneof net_read_timeout_present { + int32 net_read_timeout = 3; // in seconds + } + // [default = 0]; + oneof net_write_timeout_present { + int32 net_write_timeout = 4; // in seconds + } + string destination = 5; + string client_id = 6; + string filter = 7; + int64 start_timestamp = 8; } message Ack { - optional int32 error_code = 1 [default = 0]; - optional string error_message = 2; // if something like compression is not supported, erorr_message will tell about it. + //[default = 0] + oneof error_code_present { + int32 error_code = 1; + } + string error_message = 2; // if something like compression is not supported, erorr_message will tell about it. } message ClientAck { - optional string destination = 1; - optional string client_id = 2; - optional int64 batch_id = 3; + string destination = 1; + string client_id = 2; + int64 batch_id = 3; } // subscription message Sub { - optional string destination = 1; - optional string client_id = 2; - optional string filter = 7; + string destination = 1; + string client_id = 2; + string filter = 7; } // Unsubscription message Unsub { - optional string destination = 1; - optional string client_id = 2; - optional string filter = 7; + string destination = 1; + string client_id = 2; + string filter = 7; } // PullRequest message Get { - optional string destination = 1; - optional string client_id = 2; - optional int32 fetch_size = 3; - optional int64 timeout = 4 [default = -1]; // 默认-1时代表不控制 - optional int32 unit = 5 [default = 2];// 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天 - optional bool auto_ack = 6 [default = false]; // 是否自动ack + string destination = 1; + string client_id = 2; + int32 fetch_size = 3; + //[default = -1] + oneof timeout_present { + int64 timeout = 4; // 默认-1时代表不控制 + } + //[default = 2] + oneof unit_present { + int32 unit = 5;// 数字类型,0:纳秒,1:毫秒,2:微秒,3:秒,4:分钟,5:小时,6:天 + } + //[default = false] + oneof auto_ack_present { + bool auto_ack = 6; // 是否自动ack + } + } // message Messages { - optional int64 batch_id = 1; + int64 batch_id = 1; repeated bytes messages = 2; } // TBD when new packets are required message Dump{ - optional string journal = 1; - optional int64 position = 2; - optional int64 timestamp = 3 [default = 0]; + string journal = 1; + int64 position = 2; + // [default = 0] + oneof timestamp_present { + int64 timestamp = 3; + } + } message ClientRollback{ - optional string destination = 1; - optional string client_id = 2; - optional int64 batch_id = 3; + string destination = 1; + string client_id = 2; + int64 batch_id = 3; } \ No newline at end of file diff --git a/protocol/src/main/java/com/alibaba/otter/canal/protocol/ClientIdentity.java b/protocol/src/main/java/com/alibaba/otter/canal/protocol/ClientIdentity.java index aaa568e0..bae04a79 100644 --- a/protocol/src/main/java/com/alibaba/otter/canal/protocol/ClientIdentity.java +++ b/protocol/src/main/java/com/alibaba/otter/canal/protocol/ClientIdentity.java @@ -13,9 +13,10 @@ import com.alibaba.otter.canal.common.utils.CanalToStringStyle; */ public class ClientIdentity implements Serializable { - private String destination; - private short clientId; - private String filter; + private static final long serialVersionUID = -8262100681930834834L; + private String destination; + private short clientId; + private String filter; public ClientIdentity(){ diff --git a/protocol/src/main/java/com/alibaba/otter/canal/protocol/EntryProtocol.proto b/protocol/src/main/java/com/alibaba/otter/canal/protocol/EntryProtocol.proto index b6d2ae76..1330bbc7 100644 --- a/protocol/src/main/java/com/alibaba/otter/canal/protocol/EntryProtocol.proto +++ b/protocol/src/main/java/com/alibaba/otter/canal/protocol/EntryProtocol.proto @@ -1,3 +1,4 @@ +syntax = "proto3"; package com.alibaba.otter.canal.protocol; option java_package = "com.alibaba.otter.canal.protocol"; @@ -10,88 +11,101 @@ option optimize_for = SPEED; ****************************************************************/ message Entry { /**协议头部信息**/ - optional Header header = 1; - - /**打散后的事件类型**/ - optional EntryType entryType = 2 [default = ROWDATA]; - + Header header = 1; + ///**打散后的事件类型**/ [default = ROWDATA] + oneof entryType_present{ + EntryType entryType = 2; + } + /**传输的二进制数组**/ - optional bytes storeValue = 3; + bytes storeValue = 3; } /**message Header**/ message Header { - /**协议的版本号**/ - optional int32 version = 1 [default = 1]; - + /**协议的版本号**/ //[default = 1] + oneof version_present { + int32 version = 1; + } + + /**binlog/redolog 文件名**/ - optional string logfileName = 2; - + string logfileName = 2; + /**binlog/redolog 文件的偏移位置**/ - optional int64 logfileOffset = 3; - + int64 logfileOffset = 3; + /**服务端serverId**/ - optional int64 serverId = 4; - + int64 serverId = 4; + /** 变更数据的编码 **/ - optional string serverenCode = 5; - + string serverenCode = 5; + /**变更数据的执行时间 **/ - optional int64 executeTime = 6; - - /** 变更数据的来源**/ - optional Type sourceType = 7 [default = MYSQL]; - + int64 executeTime = 6; + + /** 变更数据的来源**/ //[default = MYSQL] + oneof sourceType_present { + Type sourceType = 7; + } + + /** 变更数据的schemaname**/ - optional string schemaName = 8; - + string schemaName = 8; + /**变更数据的tablename**/ - optional string tableName = 9; - + string tableName = 9; + /**每个event的长度**/ - optional int64 eventLength = 10; - - /**数据变更类型**/ - optional EventType eventType = 11 [default = UPDATE]; - + int64 eventLength = 10; + + /**数据变更类型**/ // [default = UPDATE] + oneof eventType_present { + EventType eventType = 11; + } + + /**预留扩展**/ repeated Pair props = 12; /**当前事务的gitd**/ - optional string gtid = 13; + string gtid = 13; } /**每个字段的数据结构**/ message Column { /**字段下标**/ - optional int32 index = 1; - + int32 index = 1; + /**字段java中类型**/ - optional int32 sqlType = 2; - + int32 sqlType = 2; + /**字段名称(忽略大小写),在mysql中是没有的**/ - optional string name = 3; - + string name = 3; + /**是否是主键**/ - optional bool isKey = 4; - + bool isKey = 4; + /**如果EventType=UPDATE,用于标识这个字段值是否有修改**/ - optional bool updated = 5; - - /** 标识是否为空 **/ - optional bool isNull = 6 [default = false]; - + bool updated = 5; + + /** 标识是否为空 **/ //[default = false] + oneof isNull_present { + bool isNull = 6; + } + + /**预留扩展**/ - repeated Pair props = 7; - + repeated Pair props = 7; + /** 字段值,timestamp,Datetime是一个时间格式的文本 **/ - optional string value = 8; - + string value = 8; + /** 对应数据对象原始长度 **/ - optional int32 length = 9; - + int32 length = 9; + /**字段mysql类型**/ - optional string mysqlType = 10; + string mysqlType = 10; } message RowData { @@ -101,73 +115,81 @@ message RowData { /** 字段信息,增量数据(修改后,新增后) **/ repeated Column afterColumns = 2; - + /**预留扩展**/ - repeated Pair props = 3; + repeated Pair props = 3; } /**message row 每行变更数据的数据结构**/ message RowChange { /**tableId,由数据库产生**/ - optional int64 tableId = 1; - - /**数据变更类型**/ - optional EventType eventType = 2 [default = UPDATE]; - - /** 标识是否是ddl语句 **/ - optional bool isDdl = 10 [default = false]; + int64 tableId = 1; + + + /**数据变更类型**/ //[default = UPDATE] + oneof eventType_present { + EventType eventType = 2; + } + + + /** 标识是否是ddl语句 **/ // [default = false] + oneof isDdl_present { + bool isDdl = 10; + } + /** ddl/query的sql语句 **/ - optional string sql = 11; - + string sql = 11; + /** 一次数据库变更可能存在多行 **/ repeated RowData rowDatas = 12; - + /**预留扩展**/ - repeated Pair props = 13; - + repeated Pair props = 13; + /** ddl/query的schemaName,会存在跨库ddl,需要保留执行ddl的当前schemaName **/ - optional string ddlSchemaName = 14; + string ddlSchemaName = 14; } /**开始事务的一些信息**/ message TransactionBegin{ - + /**已废弃,请使用header里的executeTime**/ - optional int64 executeTime = 1; - + int64 executeTime = 1; + /**已废弃,Begin里不提供事务id**/ - optional string transactionId = 2; - + string transactionId = 2; + /**预留扩展**/ - repeated Pair props = 3; - + repeated Pair props = 3; + /**执行的thread Id**/ - optional int64 threadId = 4; + int64 threadId = 4; } /**结束事务的一些信息**/ message TransactionEnd{ - + /**已废弃,请使用header里的executeTime**/ - optional int64 executeTime = 1; - + int64 executeTime = 1; + /**事务号**/ - optional string transactionId = 2; - + string transactionId = 2; + /**预留扩展**/ - repeated Pair props = 3; + repeated Pair props = 3; } /**预留扩展**/ message Pair{ - optional string key = 1; - optional string value = 2; + string key = 1; + string value = 2; } /**打散后的事件类型,主要用于标识事务的开始,变更数据,结束**/ enum EntryType{ + ENTRYTYPECOMPATIBLEPROTO2 = 0; TRANSACTIONBEGIN = 1; ROWDATA = 2; TRANSACTIONEND = 3; @@ -178,6 +200,7 @@ enum EntryType{ /** 事件类型 **/ enum EventType { + EVENTTYPECOMPATIBLEPROTO2 = 0; INSERT = 1; UPDATE = 2; DELETE = 3; @@ -194,11 +217,14 @@ enum EventType { /** XA **/ XACOMMIT = 13; XAROLLBACK = 14; + /** MASTER HEARTBEAT **/ + MHEARTBEAT = 15; } /**数据库类型**/ enum Type { + TYPECOMPATIBLEPROTO2 = 0; ORACLE = 1; MYSQL = 2; PGSQL = 3; -} \ No newline at end of file +} diff --git a/protocol/src/main/java/com/alibaba/otter/canal/protocol/FlatMessage.java b/protocol/src/main/java/com/alibaba/otter/canal/protocol/FlatMessage.java new file mode 100644 index 00000000..592db497 --- /dev/null +++ b/protocol/src/main/java/com/alibaba/otter/canal/protocol/FlatMessage.java @@ -0,0 +1,345 @@ +package com.alibaba.otter.canal.protocol; + +import java.io.Serializable; +import java.util.ArrayList; +import java.util.HashSet; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import com.google.protobuf.ByteString; + +/** + * @author machengyuan 2018-9-13 下午10:31:14 + * @version 1.0.0 + */ +public class FlatMessage implements Serializable { + + private static final long serialVersionUID = -3386650678735860050L; + + private long id; + private String database; + private String table; + private Boolean isDdl; + private String type; + // binlog executeTime + private Long es; + // dml build timeStamp + private Long ts; + private String sql; + private Map sqlType; + private Map mysqlType; + private List> data; + private List> old; + + public FlatMessage(){ + } + + public FlatMessage(long id){ + this.id = id; + } + + public long getId() { + return id; + } + + public void setId(long id) { + this.id = id; + } + + public String getDatabase() { + return database; + } + + public void setDatabase(String database) { + this.database = database; + } + + public String getTable() { + return table; + } + + public void setTable(String table) { + this.table = table; + } + + public Boolean getIsDdl() { + return isDdl; + } + + public void setIsDdl(Boolean isDdl) { + this.isDdl = isDdl; + } + + public String getType() { + return type; + } + + public void setType(String type) { + this.type = type; + } + + public Long getTs() { + return ts; + } + + public void setTs(Long ts) { + this.ts = ts; + } + + public String getSql() { + return sql; + } + + public void setSql(String sql) { + this.sql = sql; + } + + public Map getSqlType() { + return sqlType; + } + + public void setSqlType(Map sqlType) { + this.sqlType = sqlType; + } + + public Map getMysqlType() { + return mysqlType; + } + + public void setMysqlType(Map mysqlType) { + this.mysqlType = mysqlType; + } + + public List> getData() { + return data; + } + + public void setData(List> data) { + this.data = data; + } + + public List> getOld() { + return old; + } + + public void setOld(List> old) { + this.old = old; + } + + public Long getEs() { + return es; + } + + public void setEs(Long es) { + this.es = es; + } + + /** + * 将Message转换为FlatMessage + * + * @param message 原生message + * @return FlatMessage列表 + */ + public static List messageConverter(Message message) { + try { + if (message == null) { + return null; + } + + List flatMessages = new ArrayList<>(); + List entrys = null; + if (message.isRaw()) { + List rawEntries = message.getRawEntries(); + entrys = new ArrayList(rawEntries.size()); + for (ByteString byteString : rawEntries) { + CanalEntry.Entry entry = CanalEntry.Entry.parseFrom(byteString); + entrys.add(entry); + } + } else { + entrys = message.getEntries(); + } + + for (CanalEntry.Entry entry : entrys) { + if (entry.getEntryType() == CanalEntry.EntryType.TRANSACTIONBEGIN + || entry.getEntryType() == CanalEntry.EntryType.TRANSACTIONEND) { + continue; + } + + CanalEntry.RowChange rowChange; + try { + rowChange = CanalEntry.RowChange.parseFrom(entry.getStoreValue()); + } catch (Exception e) { + throw new RuntimeException( + "ERROR ## parser of eromanga-event has an error , data:" + entry.toString(), + e); + } + + CanalEntry.EventType eventType = rowChange.getEventType(); + + FlatMessage flatMessage = new FlatMessage(message.getId()); + flatMessages.add(flatMessage); + flatMessage.setDatabase(entry.getHeader().getSchemaName()); + flatMessage.setTable(entry.getHeader().getTableName()); + flatMessage.setIsDdl(rowChange.getIsDdl()); + flatMessage.setType(eventType.toString()); + flatMessage.setEs(entry.getHeader().getExecuteTime()); + flatMessage.setTs(System.currentTimeMillis()); + flatMessage.setSql(rowChange.getSql()); + + if (!rowChange.getIsDdl()) { + Map sqlType = new LinkedHashMap<>(); + Map mysqlType = new LinkedHashMap<>(); + List> data = new ArrayList<>(); + List> old = new ArrayList<>(); + + Set updateSet = new HashSet<>(); + for (CanalEntry.RowData rowData : rowChange.getRowDatasList()) { + if (eventType != CanalEntry.EventType.INSERT && eventType != CanalEntry.EventType.UPDATE + && eventType != CanalEntry.EventType.DELETE) { + continue; + } + + Map row = new LinkedHashMap<>(); + List columns; + + if (eventType == CanalEntry.EventType.DELETE) { + columns = rowData.getBeforeColumnsList(); + } else { + columns = rowData.getAfterColumnsList(); + } + + for (CanalEntry.Column column : columns) { + sqlType.put(column.getName(), column.getSqlType()); + mysqlType.put(column.getName(), column.getMysqlType()); + if (column.getIsNull()) { + row.put(column.getName(), null); + } else { + row.put(column.getName(), column.getValue()); + } + // 获取update为true的字段 + if (column.getUpdated()) { + updateSet.add(column.getName()); + } + } + if (!row.isEmpty()) { + data.add(row); + } + + if (eventType == CanalEntry.EventType.UPDATE) { + Map rowOld = new LinkedHashMap<>(); + for (CanalEntry.Column column : rowData.getBeforeColumnsList()) { + if (updateSet.contains(column.getName())) { + if (column.getIsNull()) { + rowOld.put(column.getName(), null); + } else { + rowOld.put(column.getName(), column.getValue()); + } + } + } + // update操作将记录修改前的值 + if (!rowOld.isEmpty()) { + old.add(rowOld); + } + } + } + if (!sqlType.isEmpty()) { + flatMessage.setSqlType(sqlType); + } + if (!mysqlType.isEmpty()) { + flatMessage.setMysqlType(mysqlType); + } + if (!data.isEmpty()) { + flatMessage.setData(data); + } + if (!old.isEmpty()) { + flatMessage.setOld(old); + } + } + } + return flatMessages; + } catch (Exception e) { + throw new RuntimeException(e); + } + } + + /** + * 将FlatMessage按指定的字段值hash拆分 + * + * @param flatMessage flatMessage + * @param partitionsNum 分区数量 + * @param pkHashConfig hash映射 + * @return 拆分后的flatMessage数组 + */ + public static FlatMessage[] messagePartition(FlatMessage flatMessage, Integer partitionsNum, + Map pkHashConfig) { + if (partitionsNum == null) { + partitionsNum = 1; + } + FlatMessage[] partitionMessages = new FlatMessage[partitionsNum]; + String pk = pkHashConfig.get(flatMessage.getDatabase() + "." + flatMessage.getTable()); + if (pk == null || flatMessage.getIsDdl()) { + partitionMessages[0] = flatMessage; + } else { + if (flatMessage.getData() != null) { + int idx = 0; + for (Map row : flatMessage.getData()) { + Map o = flatMessage.getOld().get(idx); + String value; + // 如果old中有pk值说明主键有修改, 以旧的主键值hash为准 + if (o != null && o.containsKey(pk)) { + value = o.get(pk); + } else { + value = row.get(pk); + } + if (value == null) { + value = ""; + } + int hash = value.hashCode(); + int pkHash = Math.abs(hash) % partitionsNum; + // math.abs可能返回负值,这里再取反,把出现负值的数据还是写到固定的分区,仍然可以保证消费顺序 + pkHash = Math.abs(pkHash); + + FlatMessage flatMessageTmp = partitionMessages[pkHash]; + if (flatMessageTmp == null) { + flatMessageTmp = new FlatMessage(flatMessage.getId()); + partitionMessages[pkHash] = flatMessageTmp; + flatMessageTmp.setDatabase(flatMessage.getDatabase()); + flatMessageTmp.setTable(flatMessage.getTable()); + flatMessageTmp.setIsDdl(flatMessage.getIsDdl()); + flatMessageTmp.setType(flatMessage.getType()); + flatMessageTmp.setSql(flatMessage.getSql()); + flatMessageTmp.setSqlType(flatMessage.getSqlType()); + flatMessageTmp.setMysqlType(flatMessage.getMysqlType()); + flatMessageTmp.setEs(flatMessage.getEs()); + flatMessageTmp.setTs(flatMessage.getTs()); + } + List> data = flatMessageTmp.getData(); + if (data == null) { + data = new ArrayList<>(); + flatMessageTmp.setData(data); + } + data.add(row); + if (flatMessage.getOld() != null && !flatMessage.getOld().isEmpty()) { + List> old = flatMessageTmp.getOld(); + if (old == null) { + old = new ArrayList<>(); + flatMessageTmp.setOld(old); + } + old.add(flatMessage.getOld().get(idx)); + } + idx++; + } + } + } + return partitionMessages; + } + + @Override + public String toString() { + return "FlatMessage [id=" + id + ", database=" + database + ", table=" + table + ", isDdl=" + isDdl + ", type=" + + type + ", es=" + es + ", ts=" + ts + ", sql=" + sql + ", sqlType=" + sqlType + ", mysqlType=" + + mysqlType + ", data=" + data + ", old=" + old + "]"; + } +} diff --git a/protocol/src/main/java/com/alibaba/otter/canal/protocol/Message.java b/protocol/src/main/java/com/alibaba/otter/canal/protocol/Message.java index 984766e2..bf79ee45 100644 --- a/protocol/src/main/java/com/alibaba/otter/canal/protocol/Message.java +++ b/protocol/src/main/java/com/alibaba/otter/canal/protocol/Message.java @@ -8,6 +8,7 @@ import org.apache.commons.lang.builder.ToStringBuilder; import com.alibaba.otter.canal.common.utils.CanalToStringStyle; import com.alibaba.otter.canal.protocol.CanalEntry.Entry; +import com.google.protobuf.ByteString; /** * @author zebin.xuzb @ 2012-6-19 @@ -19,10 +20,25 @@ public class Message implements Serializable { private long id; private List entries = new ArrayList(); + // row data for performance, see: + // https://github.com/alibaba/canal/issues/726 + private boolean raw = true; + private List rawEntries = new ArrayList(); public Message(long id, List entries){ this.id = id; this.entries = entries == null ? new ArrayList() : entries; + this.raw = false; + } + + public Message(long id, boolean raw, List entries){ + this.id = id; + if (raw) { + this.rawEntries = entries == null ? new ArrayList() : entries; + } else { + this.entries = entries == null ? new ArrayList() : entries; + } + this.raw = raw; } public Message(long id){ @@ -49,6 +65,26 @@ public class Message implements Serializable { this.entries.add(entry); } + public void setRawEntries(List rawEntries) { + this.rawEntries = rawEntries; + } + + public void addRawEntry(ByteString rawEntry) { + this.rawEntries.add(rawEntry); + } + + public List getRawEntries() { + return rawEntries; + } + + public boolean isRaw() { + return raw; + } + + public void setRaw(boolean raw) { + this.raw = raw; + } + public String toString() { return ToStringBuilder.reflectionToString(this, CanalToStringStyle.DEFAULT_STYLE); } diff --git a/server/pom.xml b/server/pom.xml index 1d243981..709a14e0 100644 --- a/server/pom.xml +++ b/server/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml canal.server @@ -25,6 +25,28 @@ canal.instance.manager ${project.version} + + + org.apache.kafka + kafka_2.11 + 1.1.1 + + + org.slf4j + slf4j-log4j12 + + + + + org.apache.rocketmq + rocketmq-client + + + + org.jboss.netty + netty + 3.2.2.Final + @@ -32,5 +54,9 @@ junit test + + com.aliyun.openservices + aliware-apache-rocketmq-cloud + diff --git a/server/src/main/java/com/alibaba/otter/canal/common/CanalMessageSerializer.java b/server/src/main/java/com/alibaba/otter/canal/common/CanalMessageSerializer.java new file mode 100644 index 00000000..fda5dc65 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/common/CanalMessageSerializer.java @@ -0,0 +1,79 @@ +package com.alibaba.otter.canal.common; + +import java.util.List; + +import org.apache.kafka.common.errors.SerializationException; +import org.springframework.util.CollectionUtils; + +import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.CanalPacket; +import com.alibaba.otter.canal.protocol.CanalPacket.PacketType; +import com.alibaba.otter.canal.protocol.Message; +import com.google.protobuf.ByteString; +import com.google.protobuf.CodedOutputStream; +import com.google.protobuf.WireFormat; + +public class CanalMessageSerializer { + + @SuppressWarnings("deprecation") + public static byte[] serializer(Message data, boolean filterTransactionEntry) { + try { + if (data != null) { + if (data.getId() != -1) { + if (data.isRaw() && !CollectionUtils.isEmpty(data.getRawEntries())) { + // for performance + List rowEntries = data.getRawEntries(); + // message size + int messageSize = 0; + messageSize += CodedOutputStream.computeInt64Size(1, data.getId()); + + int dataSize = 0; + for (int i = 0; i < rowEntries.size(); i++) { + dataSize += CodedOutputStream.computeBytesSizeNoTag(rowEntries.get(i)); + } + messageSize += dataSize; + messageSize += 1 * rowEntries.size(); + // packet size + int size = 0; + size += CodedOutputStream.computeEnumSize(3, PacketType.MESSAGES.getNumber()); + size += CodedOutputStream.computeTagSize(5) + + CodedOutputStream.computeRawVarint32Size(messageSize) + messageSize; + // build data + byte[] body = new byte[size]; + CodedOutputStream output = CodedOutputStream.newInstance(body); + output.writeEnum(3, PacketType.MESSAGES.getNumber()); + + output.writeTag(5, WireFormat.WIRETYPE_LENGTH_DELIMITED); + output.writeRawVarint32(messageSize); + // message + output.writeInt64(1, data.getId()); + for (int i = 0; i < rowEntries.size(); i++) { + output.writeBytes(2, rowEntries.get(i)); + } + output.checkNoSpaceLeft(); + return body; + } else if (!CollectionUtils.isEmpty(data.getEntries())) { + // mq模式只会走到非rowEntry模式 + CanalPacket.Messages.Builder messageBuilder = CanalPacket.Messages.newBuilder(); + for (CanalEntry.Entry entry : data.getEntries()) { + if (filterTransactionEntry + && (entry.getEntryType() == CanalEntry.EntryType.TRANSACTIONBEGIN || entry.getEntryType() == CanalEntry.EntryType.TRANSACTIONEND)) { + continue; + } + + messageBuilder.addMessages(entry.toByteString()); + } + + CanalPacket.Packet.Builder packetBuilder = CanalPacket.Packet.newBuilder(); + packetBuilder.setType(PacketType.MESSAGES); + packetBuilder.setBody(messageBuilder.build().toByteString()); + return packetBuilder.build().toByteArray(); + } + } + } + } catch (Exception e) { + throw new SerializationException("Error when serializing message to byte[] "); + } + return null; + } +} diff --git a/server/src/main/java/com/alibaba/otter/canal/common/MQProperties.java b/server/src/main/java/com/alibaba/otter/canal/common/MQProperties.java new file mode 100644 index 00000000..a337ccc6 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/common/MQProperties.java @@ -0,0 +1,196 @@ +package com.alibaba.otter.canal.common; + +import java.util.Map; + +/** + * kafka 配置项 + * + * @author machengyuan 2018-6-11 下午05:30:49 + * @version 1.0.0 + */ +public class MQProperties { + + private String servers = "127.0.0.1:6667"; + private int retries = 0; + private int batchSize = 16384; + private int lingerMs = 1; + private int maxRequestSize = 1048576; + private long bufferMemory = 33554432L; + private boolean filterTransactionEntry = true; + private String producerGroup = "Canal-Producer"; + private int canalBatchSize = 50; + private Long canalGetTimeout = 100L; + private boolean flatMessage = true; + private String compressionType = "none"; + private String acks = "all"; + private String aliyunAccessKey = ""; + private String aliyunSecretKey = ""; + + public static class CanalDestination { + + private String canalDestination; + private String topic; + private Integer partition; + private Integer partitionsNum; + private Map partitionHash; + + public String getCanalDestination() { + return canalDestination; + } + + public void setCanalDestination(String canalDestination) { + this.canalDestination = canalDestination; + } + + public String getTopic() { + return topic; + } + + public void setTopic(String topic) { + this.topic = topic; + } + + public Integer getPartition() { + return partition; + } + + public void setPartition(Integer partition) { + this.partition = partition; + } + + public Integer getPartitionsNum() { + return partitionsNum; + } + + public void setPartitionsNum(Integer partitionsNum) { + this.partitionsNum = partitionsNum; + } + + public Map getPartitionHash() { + return partitionHash; + } + + public void setPartitionHash(Map partitionHash) { + this.partitionHash = partitionHash; + } + } + + public String getServers() { + return servers; + } + + public void setServers(String servers) { + this.servers = servers; + } + + public int getRetries() { + return retries; + } + + public void setRetries(int retries) { + this.retries = retries; + } + + public int getBatchSize() { + return batchSize; + } + + public void setBatchSize(int batchSize) { + this.batchSize = batchSize; + } + + public int getLingerMs() { + return lingerMs; + } + + public void setLingerMs(int lingerMs) { + this.lingerMs = lingerMs; + } + + public long getBufferMemory() { + return bufferMemory; + } + + public void setBufferMemory(long bufferMemory) { + this.bufferMemory = bufferMemory; + } + + public int getCanalBatchSize() { + return canalBatchSize; + } + + public void setCanalBatchSize(int canalBatchSize) { + this.canalBatchSize = canalBatchSize; + } + + public Long getCanalGetTimeout() { + return canalGetTimeout; + } + + public void setCanalGetTimeout(Long canalGetTimeout) { + this.canalGetTimeout = canalGetTimeout; + } + + public boolean getFlatMessage() { + return flatMessage; + } + + public void setFlatMessage(boolean flatMessage) { + this.flatMessage = flatMessage; + } + + public boolean isFilterTransactionEntry() { + return filterTransactionEntry; + } + + public void setFilterTransactionEntry(boolean filterTransactionEntry) { + this.filterTransactionEntry = filterTransactionEntry; + } + + public String getProducerGroup() { + return producerGroup; + } + + public void setProducerGroup(String producerGroup) { + this.producerGroup = producerGroup; + } + + public String getCompressionType() { + return compressionType; + } + + public void setCompressionType(String compressionType) { + this.compressionType = compressionType; + } + + public String getAcks() { + return acks; + } + + public void setAcks(String acks) { + this.acks = acks; + } + + public String getAliyunAccessKey() { + return aliyunAccessKey; + } + + public void setAliyunAccessKey(String aliyunAccessKey) { + this.aliyunAccessKey = aliyunAccessKey; + } + + public String getAliyunSecretKey() { + return aliyunSecretKey; + } + + public void setAliyunSecretKey(String aliyunSecretKey) { + this.aliyunSecretKey = aliyunSecretKey; + } + public int getMaxRequestSize() { + return maxRequestSize; + } + + public void setMaxRequestSize(int maxRequestSize) { + this.maxRequestSize = maxRequestSize; + } +} diff --git a/server/src/main/java/com/alibaba/otter/canal/kafka/CanalKafkaProducer.java b/server/src/main/java/com/alibaba/otter/canal/kafka/CanalKafkaProducer.java new file mode 100644 index 00000000..230e9607 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/kafka/CanalKafkaProducer.java @@ -0,0 +1,180 @@ +package com.alibaba.otter.canal.kafka; + +import java.util.List; +import java.util.Properties; + +import org.apache.kafka.clients.producer.KafkaProducer; +import org.apache.kafka.clients.producer.Producer; +import org.apache.kafka.clients.producer.ProducerRecord; +import org.apache.kafka.common.serialization.StringSerializer; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.serializer.SerializerFeature; +import com.alibaba.otter.canal.common.MQProperties; +import com.alibaba.otter.canal.protocol.FlatMessage; +import com.alibaba.otter.canal.protocol.Message; +import com.alibaba.otter.canal.spi.CanalMQProducer; + +/** + * kafka producer 主操作类 + * + * @author machengyuan 2018-6-11 下午05:30:49 + * @version 1.0.0 + */ +public class CanalKafkaProducer implements CanalMQProducer { + + private static final Logger logger = LoggerFactory.getLogger(CanalKafkaProducer.class); + + private Producer producer; + + private Producer producer2; // 用于扁平message的数据投递 + + private MQProperties kafkaProperties; + + @Override + public void init(MQProperties kafkaProperties) { + this.kafkaProperties = kafkaProperties; + Properties properties = new Properties(); + properties.put("bootstrap.servers", kafkaProperties.getServers()); + properties.put("acks", kafkaProperties.getAcks()); + properties.put("compression.type", kafkaProperties.getCompressionType()); + properties.put("retries", kafkaProperties.getRetries()); + properties.put("batch.size", kafkaProperties.getBatchSize()); + properties.put("linger.ms", kafkaProperties.getLingerMs()); + properties.put("max.request.size", kafkaProperties.getMaxRequestSize()); + properties.put("buffer.memory", kafkaProperties.getBufferMemory()); + properties.put("key.serializer", StringSerializer.class.getName()); + if (!kafkaProperties.getFlatMessage()) { + properties.put("value.serializer", MessageSerializer.class.getName()); + producer = new KafkaProducer(properties); + } else { + properties.put("value.serializer", StringSerializer.class.getName()); + producer2 = new KafkaProducer(properties); + } + + // producer.initTransactions(); + } + + @Override + public void stop() { + try { + logger.info("## stop the kafka producer"); + if (producer != null) { + producer.close(); + } + if (producer2 != null) { + producer2.close(); + } + } catch (Throwable e) { + logger.warn("##something goes wrong when stopping kafka producer:", e); + } finally { + logger.info("## kafka producer is down."); + } + } + + @Override + public void send(MQProperties.CanalDestination canalDestination, Message message, Callback callback) { + + // producer.beginTransaction(); + if (!kafkaProperties.getFlatMessage()) { + try { + ProducerRecord record; + if (canalDestination.getPartition() != null) { + record = new ProducerRecord(canalDestination.getTopic(), + canalDestination.getPartition(), + null, + message); + } else { + record = new ProducerRecord(canalDestination.getTopic(), 0, null, message); + } + + producer.send(record).get(); + + if (logger.isDebugEnabled()) { + logger.debug("Send message to kafka topic: [{}], packet: {}", + canalDestination.getTopic(), + message.toString()); + } + } catch (Exception e) { + logger.error(e.getMessage(), e); + // producer.abortTransaction(); + callback.rollback(); + return; + } + } else { + // 发送扁平数据json + List flatMessages = FlatMessage.messageConverter(message); + if (flatMessages != null) { + for (FlatMessage flatMessage : flatMessages) { + if (canalDestination.getPartition() != null) { + try { + ProducerRecord record = new ProducerRecord( + canalDestination.getTopic(), + canalDestination.getPartition(), + null, + JSON.toJSONString(flatMessage, SerializerFeature.WriteMapNullValue)); + producer2.send(record).get(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + // producer.abortTransaction(); + callback.rollback(); + return; + } + } else { + if (canalDestination.getPartitionHash() != null + && !canalDestination.getPartitionHash().isEmpty()) { + FlatMessage[] partitionFlatMessage = FlatMessage.messagePartition(flatMessage, + canalDestination.getPartitionsNum(), + canalDestination.getPartitionHash()); + int length = partitionFlatMessage.length; + for (int i = 0; i < length; i++) { + FlatMessage flatMessagePart = partitionFlatMessage[i]; + if (flatMessagePart != null) { + try { + ProducerRecord record = new ProducerRecord( + canalDestination.getTopic(), + i, + null, + JSON.toJSONString(flatMessagePart, SerializerFeature.WriteMapNullValue)); + producer2.send(record).get(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + // producer.abortTransaction(); + callback.rollback(); + return; + } + } + } + } else { + try { + ProducerRecord record = new ProducerRecord( + canalDestination.getTopic(), + 0, + null, + JSON.toJSONString(flatMessage, SerializerFeature.WriteMapNullValue)); + producer2.send(record).get(); + } catch (Exception e) { + logger.error(e.getMessage(), e); + // producer.abortTransaction(); + callback.rollback(); + return; + } + } + } + if (logger.isDebugEnabled()) { + logger.debug("Send flat message to kafka topic: [{}], packet: {}", + canalDestination.getTopic(), + JSON.toJSONString(flatMessage, SerializerFeature.WriteMapNullValue)); + } + } + } + } + + // producer.commitTransaction(); + callback.commit(); + + } + +} diff --git a/server/src/main/java/com/alibaba/otter/canal/kafka/MessageSerializer.java b/server/src/main/java/com/alibaba/otter/canal/kafka/MessageSerializer.java new file mode 100644 index 00000000..39c297d8 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/kafka/MessageSerializer.java @@ -0,0 +1,39 @@ +package com.alibaba.otter.canal.kafka; + +import java.util.Map; + +import org.apache.commons.lang.BooleanUtils; +import org.apache.kafka.common.serialization.Serializer; + +import com.alibaba.otter.canal.common.CanalMessageSerializer; +import com.alibaba.otter.canal.protocol.Message; + +/** + * Kafka Message类的序列化 + * + * @author machengyuan 2018-6-11 下午05:30:49 + * @version 1.0.0 + */ +public class MessageSerializer implements Serializer { + + private boolean filterTransactionEntry = false; + + public MessageSerializer(){ + this.filterTransactionEntry = BooleanUtils.toBoolean(System.getProperty("canal.instance.filter.transaction.entry", + "false")); + } + + @Override + public void configure(Map configs, boolean isKey) { + } + + @Override + public byte[] serialize(String topic, Message data) { + return CanalMessageSerializer.serializer(data, filterTransactionEntry); + } + + @Override + public void close() { + // nothing to do + } +} diff --git a/server/src/main/java/com/alibaba/otter/canal/rocketmq/CanalRocketMQProducer.java b/server/src/main/java/com/alibaba/otter/canal/rocketmq/CanalRocketMQProducer.java new file mode 100644 index 00000000..74e3920b --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/rocketmq/CanalRocketMQProducer.java @@ -0,0 +1,162 @@ +package com.alibaba.otter.canal.rocketmq; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.serializer.SerializerFeature; +import com.alibaba.otter.canal.common.CanalMessageSerializer; +import com.alibaba.otter.canal.common.MQProperties; +import com.alibaba.otter.canal.protocol.FlatMessage; +import com.alibaba.otter.canal.server.exception.CanalServerException; +import com.alibaba.otter.canal.spi.CanalMQProducer; +import com.aliyun.openservices.apache.api.impl.authority.SessionCredentials; +import com.aliyun.openservices.apache.api.impl.rocketmq.ClientRPCHook; +import org.apache.rocketmq.client.exception.MQBrokerException; +import org.apache.rocketmq.client.exception.MQClientException; +import org.apache.rocketmq.client.producer.DefaultMQProducer; +import org.apache.rocketmq.client.producer.MessageQueueSelector; +import org.apache.rocketmq.common.message.Message; +import org.apache.rocketmq.common.message.MessageQueue; +import org.apache.rocketmq.remoting.RPCHook; +import org.apache.rocketmq.remoting.exception.RemotingException; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.List; + +public class CanalRocketMQProducer implements CanalMQProducer { + + private static final Logger logger = LoggerFactory.getLogger(CanalRocketMQProducer.class); + + private DefaultMQProducer defaultMQProducer; + + private MQProperties mqProperties; + + @Override + public void init(MQProperties rocketMQProperties) { + this.mqProperties = rocketMQProperties; + RPCHook rpcHook = null; + if(rocketMQProperties.getAliyunAccessKey().length() > 0 + && rocketMQProperties.getAliyunSecretKey().length() > 0){ + SessionCredentials sessionCredentials = new SessionCredentials(); + sessionCredentials.setAccessKey(rocketMQProperties.getAliyunAccessKey()); + sessionCredentials.setSecretKey(rocketMQProperties.getAliyunSecretKey()); + rpcHook = new ClientRPCHook(sessionCredentials); + } + + defaultMQProducer = new DefaultMQProducer(rocketMQProperties.getProducerGroup(), rpcHook); + defaultMQProducer.setNamesrvAddr(rocketMQProperties.getServers()); + defaultMQProducer.setRetryTimesWhenSendFailed(rocketMQProperties.getRetries()); + defaultMQProducer.setVipChannelEnabled(false); + logger.info("##Start RocketMQ producer##"); + try { + defaultMQProducer.start(); + } catch (MQClientException ex) { + throw new CanalServerException("Start RocketMQ producer error", ex); + } + } + + @Override + public void send(final MQProperties.CanalDestination destination, com.alibaba.otter.canal.protocol.Message data, + Callback callback) { + if (!mqProperties.getFlatMessage()) { + try { + Message message = new Message(destination.getTopic(), CanalMessageSerializer.serializer(data, + mqProperties.isFilterTransactionEntry())); + logger.debug("send message:{} to destination:{}, partition: {}", + message, + destination.getCanalDestination(), + destination.getPartition()); + this.defaultMQProducer.send(message, new MessageQueueSelector() { + + @Override + public MessageQueue select(List mqs, Message msg, Object arg) { + int partition = 0; + if (destination.getPartition() != null) { + partition = destination.getPartition(); + } + return mqs.get(partition); + } + }, null); + } catch (MQClientException | RemotingException | MQBrokerException | InterruptedException e) { + logger.error("Send message error!", e); + callback.rollback(); + return; + } + } else { + List flatMessages = FlatMessage.messageConverter(data); + if (flatMessages != null) { + for (FlatMessage flatMessage : flatMessages) { + if (destination.getPartition() != null) { + try { + logger.info("send flat message: {} to topic: {} fixed partition: {}", + JSON.toJSONString(flatMessage, SerializerFeature.WriteMapNullValue), + destination.getTopic(), + destination.getPartition()); + Message message = new Message(destination.getTopic(), + JSON.toJSONString(flatMessage, SerializerFeature.WriteMapNullValue).getBytes()); + this.defaultMQProducer.send(message, new MessageQueueSelector() { + + @Override + public MessageQueue select(List mqs, Message msg, Object arg) { + return mqs.get(destination.getPartition()); + } + }, null); + } catch (Exception e) { + logger.error("send flat message to fixed partition error", e); + callback.rollback(); + return; + } + } else { + if (destination.getPartitionHash() != null && !destination.getPartitionHash().isEmpty()) { + FlatMessage[] partitionFlatMessage = FlatMessage.messagePartition(flatMessage, + destination.getPartitionsNum(), + destination.getPartitionHash()); + int length = partitionFlatMessage.length; + for (int i = 0; i < length; i++) { + FlatMessage flatMessagePart = partitionFlatMessage[i]; + if (flatMessagePart != null) { + logger.debug("flatMessagePart: {}, partition: {}", + JSON.toJSONString(flatMessagePart, SerializerFeature.WriteMapNullValue), + i); + final int index = i; + try { + Message message = new Message(destination.getTopic(), + JSON.toJSONString(flatMessagePart, SerializerFeature.WriteMapNullValue).getBytes()); + this.defaultMQProducer.send(message, new MessageQueueSelector() { + + @Override + public MessageQueue select(List mqs, Message msg, + Object arg) { + if (index > mqs.size()) { + throw new CanalServerException( + "partition number is error,config num:" + + destination.getPartitionsNum() + + ", mq num: " + mqs.size()); + } + return mqs.get(index); + } + }, null); + } catch (Exception e) { + logger.error("send flat message to hashed partition error", e); + callback.rollback(); + return; + } + } + } + } + } + } + } + } + + callback.commit(); + if (logger.isDebugEnabled()) { + logger.debug("send message to rocket topic: {}", destination.getTopic()); + } + } + + @Override + public void stop() { + logger.info("## Stop RocketMQ producer##"); + this.defaultMQProducer.shutdown(); + } +} diff --git a/server/src/main/java/com/alibaba/otter/canal/server/CanalMQStarter.java b/server/src/main/java/com/alibaba/otter/canal/server/CanalMQStarter.java new file mode 100644 index 00000000..ade0adaf --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/server/CanalMQStarter.java @@ -0,0 +1,204 @@ +package com.alibaba.otter.canal.server; + +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.atomic.AtomicBoolean; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.alibaba.otter.canal.common.MQProperties; +import com.alibaba.otter.canal.instance.core.CanalInstance; +import com.alibaba.otter.canal.instance.core.CanalMQConfig; +import com.alibaba.otter.canal.protocol.ClientIdentity; +import com.alibaba.otter.canal.protocol.Message; +import com.alibaba.otter.canal.server.embedded.CanalServerWithEmbedded; +import com.alibaba.otter.canal.spi.CanalMQProducer; + +public class CanalMQStarter { + + private static final Logger logger = LoggerFactory.getLogger(CanalMQStarter.class); + + private volatile boolean running = false; + + private ExecutorService executorService; + + private CanalMQProducer canalMQProducer; + + private MQProperties properties; + + private CanalServerWithEmbedded canalServer; + + private Map canalMQWorks = new ConcurrentHashMap<>(); + + public CanalMQStarter(CanalMQProducer canalMQProducer){ + this.canalMQProducer = canalMQProducer; + } + + public synchronized void start(MQProperties properties) { + try { + if (running) { + return; + } + this.properties = properties; + canalMQProducer.init(properties); + // set filterTransactionEntry + if (properties.isFilterTransactionEntry()) { + System.setProperty("canal.instance.filter.transaction.entry", "true"); + } + + if (properties.getFlatMessage()) { + // 针对flat message模式,设置为raw避免ByteString->Entry的二次解析 + System.setProperty("canal.instance.memory.rawEntry", "false"); + } + + canalServer = CanalServerWithEmbedded.instance(); + + // 对应每个instance启动一个worker线程 + executorService = Executors.newCachedThreadPool(); + logger.info("## start the MQ workers."); + for (final CanalInstance canalInstance : canalServer.getCanalInstances().values()) { + CanalMQRunnable canalMQRunnable = new CanalMQRunnable(canalInstance); + canalMQWorks.put(canalInstance.getDestination(), canalMQRunnable); + executorService.execute(canalMQRunnable); + } + + running = true; + logger.info("## the MQ workers is running now ......"); + Runtime.getRuntime().addShutdownHook(new Thread() { + + public void run() { + try { + logger.info("## stop the MQ workers"); + running = false; + executorService.shutdown(); + canalMQProducer.stop(); + } catch (Throwable e) { + logger.warn("##something goes wrong when stopping MQ workers:", e); + } finally { + logger.info("## canal MQ is down."); + } + } + + }); + + } catch (Throwable e) { + logger.error("## Something goes wrong when starting up the canal MQ workers:", e); + System.exit(0); + } + } + + public synchronized void startDestination(String destination) { + CanalInstance canalInstance = canalServer.getCanalInstances().get(destination); + if (canalInstance != null) { + stopDestination(destination); + CanalMQRunnable canalMQRunnable = new CanalMQRunnable(canalInstance); + canalMQWorks.put(canalInstance.getDestination(), canalMQRunnable); + executorService.execute(canalMQRunnable); + logger.info("## Start the MQ work of destination:" + destination); + } + } + + public synchronized void stopDestination(String destination) { + CanalMQRunnable canalMQRunable = canalMQWorks.get(destination); + if (canalMQRunable != null) { + canalMQRunable.stop(); + canalMQWorks.remove(destination); + logger.info("## Stop the MQ work of destination:" + destination); + } + } + + private void worker(MQProperties.CanalDestination destination, AtomicBoolean destinationRunning) { + while (!running || !destinationRunning.get()) + ; + logger.info("## start the MQ producer: {}.", destination.getCanalDestination()); + + final ClientIdentity clientIdentity = new ClientIdentity(destination.getCanalDestination(), (short) 1001, ""); + while (running && destinationRunning.get()) { + try { + if (!canalServer.getCanalInstances().containsKey(clientIdentity.getDestination())) { + try { + Thread.sleep(3000); + } catch (InterruptedException e) { + // ignore + } + continue; + } + canalServer.subscribe(clientIdentity); + logger.info("## the MQ producer: {} is running now ......", destination.getCanalDestination()); + + Long getTimeout = properties.getCanalGetTimeout(); + int getBatchSize = properties.getCanalBatchSize(); + while (running && destinationRunning.get()) { + Message message; + if (getTimeout != null && getTimeout > 0) { + message = canalServer + .getWithoutAck(clientIdentity, getBatchSize, getTimeout, TimeUnit.MILLISECONDS); + } else { + message = canalServer.getWithoutAck(clientIdentity, getBatchSize); + } + + final long batchId = message.getId(); + try { + int size = message.isRaw() ? message.getRawEntries().size() : message.getEntries().size(); + if (batchId != -1 && size != 0) { + canalMQProducer.send(destination, message, new CanalMQProducer.Callback() { + + @Override + public void commit() { + canalServer.ack(clientIdentity, batchId); // 提交确认 + } + + @Override + public void rollback() { + canalServer.rollback(clientIdentity, batchId); + } + }); // 发送message到topic + } else { + try { + Thread.sleep(100); + } catch (InterruptedException e) { + // ignore + } + } + + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + } + } catch (Exception e) { + logger.error("process error!", e); + } + } + } + + private class CanalMQRunnable implements Runnable { + + private CanalInstance canalInstance; + + public CanalMQRunnable(CanalInstance canalInstance){ + this.canalInstance = canalInstance; + } + + private AtomicBoolean running = new AtomicBoolean(true); + + @Override + public void run() { + MQProperties.CanalDestination destination = new MQProperties.CanalDestination(); + destination.setCanalDestination(canalInstance.getDestination()); + CanalMQConfig mqConfig = canalInstance.getMqConfig(); + destination.setTopic(mqConfig.getTopic()); + destination.setPartition(mqConfig.getPartition()); + destination.setPartitionsNum(mqConfig.getPartitionsNum()); + destination.setPartitionHash(mqConfig.getPartitionHashProperties()); + worker(destination, running); + } + + public void stop() { + running.set(false); + } + } +} diff --git a/server/src/main/java/com/alibaba/otter/canal/server/CanalServerStarter.java b/server/src/main/java/com/alibaba/otter/canal/server/CanalServerStarter.java new file mode 100644 index 00000000..18f3f7d4 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/server/CanalServerStarter.java @@ -0,0 +1,12 @@ +package com.alibaba.otter.canal.server; + +/** + * 外部服务如Kafka, RocketMQ启动接口 + * + * @author machengyuan 2018-8-23 下午05:20:29 + * @version 1.0.0 + */ +public interface CanalServerStarter { + + void init(); +} diff --git a/server/src/main/java/com/alibaba/otter/canal/server/embedded/CanalServerWithEmbedded.java b/server/src/main/java/com/alibaba/otter/canal/server/embedded/CanalServerWithEmbedded.java index 8bfa8fe6..b07062ee 100644 --- a/server/src/main/java/com/alibaba/otter/canal/server/embedded/CanalServerWithEmbedded.java +++ b/server/src/main/java/com/alibaba/otter/canal/server/embedded/CanalServerWithEmbedded.java @@ -4,6 +4,7 @@ import java.util.ArrayList; import java.util.Collections; import java.util.List; import java.util.Map; +import java.util.ServiceLoader; import java.util.concurrent.TimeUnit; import org.slf4j.Logger; @@ -14,7 +15,7 @@ import org.springframework.util.CollectionUtils; import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; import com.alibaba.otter.canal.instance.core.CanalInstance; import com.alibaba.otter.canal.instance.core.CanalInstanceGenerator; -import com.alibaba.otter.canal.protocol.CanalEntry.Entry; +import com.alibaba.otter.canal.protocol.CanalEntry; import com.alibaba.otter.canal.protocol.ClientIdentity; import com.alibaba.otter.canal.protocol.Message; import com.alibaba.otter.canal.protocol.position.LogPosition; @@ -23,27 +24,34 @@ import com.alibaba.otter.canal.protocol.position.PositionRange; import com.alibaba.otter.canal.server.CanalServer; import com.alibaba.otter.canal.server.CanalService; import com.alibaba.otter.canal.server.exception.CanalServerException; +import com.alibaba.otter.canal.spi.CanalMetricsProvider; +import com.alibaba.otter.canal.spi.CanalMetricsService; +import com.alibaba.otter.canal.spi.NopCanalMetricsService; import com.alibaba.otter.canal.store.CanalEventStore; +import com.alibaba.otter.canal.store.memory.MemoryEventStoreWithBuffer; import com.alibaba.otter.canal.store.model.Event; import com.alibaba.otter.canal.store.model.Events; import com.google.common.base.Function; import com.google.common.collect.Lists; import com.google.common.collect.Maps; import com.google.common.collect.MigrateMap; +import com.google.protobuf.ByteString; /** * 嵌入式版本实现 - * + * * @author jianghang 2012-7-12 下午01:34:00 * @author zebin.xuzb * @version 1.0.0 */ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements CanalServer, CanalService { - private static final Logger logger = LoggerFactory.getLogger(CanalServerWithEmbedded.class); + private static final Logger logger = LoggerFactory.getLogger(CanalServerWithEmbedded.class); private Map canalInstances; // private Map lastRollbackPostions; private CanalInstanceGenerator canalInstanceGenerator; + private int metricsPort; + private CanalMetricsService metrics = NopCanalMetricsService.NOP; private static class SingletonHolder { @@ -61,7 +69,10 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C public void start() { if (!isStart()) { super.start(); - + // 如果存在provider,则启动metrics service + loadCanalMetrics(); + metrics.setServerPort(metricsPort); + metrics.initialize(); canalInstances = MigrateMap.makeComputingMap(new Function() { public CanalInstance apply(String destination) { @@ -92,6 +103,7 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C logger.error(String.format("stop CanalInstance[%s] has an error", entry.getKey()), e); } } + metrics.terminate(); } public void start(final String destination) { @@ -99,6 +111,9 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C if (!canalInstance.isStart()) { try { MDC.put("destination", destination); + if (metrics.isRunning()) { + metrics.register(canalInstance); + } canalInstance.start(); logger.info("start CanalInstances[{}] successfully", destination); } finally { @@ -114,6 +129,9 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C try { MDC.put("destination", destination); canalInstance.stop(); + if (metrics.isRunning()) { + metrics.unregister(canalInstance); + } logger.info("stop CanalInstances[{}] successfully", destination); } finally { MDC.remove("destination"); @@ -176,7 +194,7 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C /** * 获取数据 - * + * *
            * 注意: meta获取和数据的获取需要保证顺序性,优先拿到meta的,一定也会是优先拿到数据,所以需要加同步. (不能出现先拿到meta,拿到第二批数据,这样就会导致数据顺序性出现问题)
            * 
      @@ -188,7 +206,7 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C /** * 获取数据,可以指定超时时间. - * + * *
            * 几种case:
            * a. 如果timeout为null,则采用tryGet方式,即时获取
      @@ -223,16 +241,27 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C
                       logger.debug("get successfully, clientId:{} batchSize:{} but result is null",
                           clientIdentity.getClientId(),
                           batchSize);
      -                return new Message(-1, new ArrayList()); // 返回空包,避免生成batchId,浪费性能
      +                return new Message(-1, true, new ArrayList()); // 返回空包,避免生成batchId,浪费性能
                   } else {
                       // 记录到流式信息
                       Long batchId = canalInstance.getMetaManager().addBatch(clientIdentity, events.getPositionRange());
      -                List entrys = Lists.transform(events.getEvents(), new Function() {
      +                boolean raw = isRaw(canalInstance.getEventStore());
      +                List entrys = null;
      +                if (raw) {
      +                    entrys = Lists.transform(events.getEvents(), new Function() {
       
      -                    public Entry apply(Event input) {
      -                        return input.getEntry();
      -                    }
      -                });
      +                        public ByteString apply(Event input) {
      +                            return input.getRawEntry();
      +                        }
      +                    });
      +                } else {
      +                    entrys = Lists.transform(events.getEvents(), new Function() {
      +
      +                        public CanalEntry.Entry apply(Event input) {
      +                            return input.getEntry();
      +                        }
      +                    });
      +                }
                       if (logger.isInfoEnabled()) {
                           logger.info("get successfully, clientId:{} batchSize:{} real size is {} and result is [batchId:{} , position:{}]",
                               clientIdentity.getClientId(),
      @@ -243,7 +272,7 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C
                       }
                       // 直接提交ack
                       ack(clientIdentity, batchId);
      -                return new Message(batchId, entrys);
      +                return new Message(batchId, raw, entrys);
                   }
               }
           }
      @@ -251,7 +280,7 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C
           /**
            * 不指定 position 获取事件。canal 会记住此 client 最新的 position。 
      * 如果是第一次 fetch,则会从 canal 中保存的最老一条数据开始输出。 - * + * *
            * 注意: meta获取和数据的获取需要保证顺序性,优先拿到meta的,一定也会是优先拿到数据,所以需要加同步. (不能出现先拿到meta,拿到第二批数据,这样就会导致数据顺序性出现问题)
            * 
      @@ -264,14 +293,14 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C /** * 不指定 position 获取事件。canal 会记住此 client 最新的 position。
      * 如果是第一次 fetch,则会从 canal 中保存的最老一条数据开始输出。 - * + * *
            * 几种case:
            * a. 如果timeout为null,则采用tryGet方式,即时获取
            * b. 如果timeout不为null
            *    1. timeout为0,则采用get阻塞方式,获取数据,不设置超时,直到有足够的batchSize数据才返回
            *    2. timeout不为0,则采用get+timeout方式,获取数据,超时还没有batchSize足够的数据,有多少返回多少
      -     *    
      +     * 
            * 注意: meta获取和数据的获取需要保证顺序性,优先拿到meta的,一定也会是优先拿到数据,所以需要加同步. (不能出现先拿到meta,拿到第二批数据,这样就会导致数据顺序性出现问题)
            * 
      */ @@ -299,19 +328,32 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C } if (CollectionUtils.isEmpty(events.getEvents())) { - logger.debug("getWithoutAck successfully, clientId:{} batchSize:{} but result is null", - clientIdentity.getClientId(), - batchSize); - return new Message(-1, new ArrayList()); // 返回空包,避免生成batchId,浪费性能 + // logger.debug("getWithoutAck successfully, clientId:{} + // batchSize:{} but result + // is null", + // clientIdentity.getClientId(), + // batchSize); + return new Message(-1, true, new ArrayList()); // 返回空包,避免生成batchId,浪费性能 } else { // 记录到流式信息 Long batchId = canalInstance.getMetaManager().addBatch(clientIdentity, events.getPositionRange()); - List entrys = Lists.transform(events.getEvents(), new Function() { + boolean raw = isRaw(canalInstance.getEventStore()); + List entrys = null; + if (raw) { + entrys = Lists.transform(events.getEvents(), new Function() { - public Entry apply(Event input) { - return input.getEntry(); - } - }); + public ByteString apply(Event input) { + return input.getRawEntry(); + } + }); + } else { + entrys = Lists.transform(events.getEvents(), new Function() { + + public CanalEntry.Entry apply(Event input) { + return input.getEntry(); + } + }); + } if (logger.isInfoEnabled()) { logger.info("getWithoutAck successfully, clientId:{} batchSize:{} real size is {} and result is [batchId:{} , position:{}]", clientIdentity.getClientId(), @@ -320,7 +362,7 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C batchId, events.getPositionRange()); } - return new Message(batchId, entrys); + return new Message(batchId, raw, entrys); } } @@ -342,7 +384,7 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C /** * 进行 batch id 的确认。确认之后,小于等于此 batchId 的 Message 都会被确认。 - * + * *
            * 注意:进行反馈时必须按照batchId的顺序进行ack(需有客户端保证)
            * 
      @@ -492,10 +534,43 @@ public class CanalServerWithEmbedded extends AbstractCanalLifeCycle implements C } } + private void loadCanalMetrics() { + ServiceLoader providers = ServiceLoader.load(CanalMetricsProvider.class); + List list = new ArrayList(); + for (CanalMetricsProvider provider : providers) { + list.add(provider); + } + if (!list.isEmpty()) { + // 发现provider, 进行初始化 + if (list.size() > 1) { + logger.warn("Found more than one CanalMetricsProvider, use the first one."); + // 报告冲突 + for (CanalMetricsProvider p : list) { + logger.warn("Found CanalMetricsProvider: {}.", p.getClass().getName()); + } + } + // 默认使用第一个 + CanalMetricsProvider provider = list.get(0); + this.metrics = provider.getService(); + } + } + + private boolean isRaw(CanalEventStore eventStore) { + if (eventStore instanceof MemoryEventStoreWithBuffer) { + return ((MemoryEventStoreWithBuffer) eventStore).isRaw(); + } + + return true; + } + // ========= setter ========== public void setCanalInstanceGenerator(CanalInstanceGenerator canalInstanceGenerator) { this.canalInstanceGenerator = canalInstanceGenerator; } + public void setMetricsPort(int metricsPort) { + this.metricsPort = metricsPort; + } + } diff --git a/server/src/main/java/com/alibaba/otter/canal/server/netty/CanalServerWithNettyProfiler.java b/server/src/main/java/com/alibaba/otter/canal/server/netty/CanalServerWithNettyProfiler.java new file mode 100644 index 00000000..cca3fa6b --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/server/netty/CanalServerWithNettyProfiler.java @@ -0,0 +1,39 @@ +package com.alibaba.otter.canal.server.netty; + +import com.alibaba.otter.canal.common.AbstractCanalLifeCycle; +import com.alibaba.otter.canal.server.netty.listener.ChannelFutureAggregator.ClientRequestResult; + +/** + * @author Chuanyi Li + */ +public class CanalServerWithNettyProfiler { + + public static final ClientInstanceProfiler NOP = new DefaultClientInstanceProfiler(); + private ClientInstanceProfiler instanceProfiler; + + private static class SingletonHolder { + private static CanalServerWithNettyProfiler SINGLETON = new CanalServerWithNettyProfiler(); + } + + private CanalServerWithNettyProfiler() { + this.instanceProfiler = NOP; + } + + public static CanalServerWithNettyProfiler profiler() { + return SingletonHolder.SINGLETON; + } + + public void profiling(ClientRequestResult result) { + instanceProfiler.profiling(result); + } + + public void setInstanceProfiler(ClientInstanceProfiler instanceProfiler) { + this.instanceProfiler = instanceProfiler; + } + + private static class DefaultClientInstanceProfiler extends AbstractCanalLifeCycle implements ClientInstanceProfiler { + @Override + public void profiling(ClientRequestResult result) {} + } + +} diff --git a/server/src/main/java/com/alibaba/otter/canal/server/netty/ClientInstanceProfiler.java b/server/src/main/java/com/alibaba/otter/canal/server/netty/ClientInstanceProfiler.java new file mode 100644 index 00000000..2ffbd46e --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/server/netty/ClientInstanceProfiler.java @@ -0,0 +1,13 @@ +package com.alibaba.otter.canal.server.netty; + +import com.alibaba.otter.canal.common.CanalLifeCycle; +import com.alibaba.otter.canal.server.netty.listener.ChannelFutureAggregator.ClientRequestResult; + +/** + * @author Chuanyi Li + */ +public interface ClientInstanceProfiler extends CanalLifeCycle { + + void profiling(ClientRequestResult result); + +} diff --git a/server/src/main/java/com/alibaba/otter/canal/server/netty/NettyUtils.java b/server/src/main/java/com/alibaba/otter/canal/server/netty/NettyUtils.java index 531c817f..43ecbe67 100644 --- a/server/src/main/java/com/alibaba/otter/canal/server/netty/NettyUtils.java +++ b/server/src/main/java/com/alibaba/otter/canal/server/netty/NettyUtils.java @@ -2,8 +2,12 @@ package com.alibaba.otter.canal.server.netty; import java.nio.ByteBuffer; import java.nio.ByteOrder; +import java.util.ArrayList; +import java.util.List; +import org.jboss.netty.buffer.ChannelBuffer; import org.jboss.netty.buffer.ChannelBuffers; +import org.jboss.netty.buffer.CompositeChannelBuffer; import org.jboss.netty.channel.Channel; import org.jboss.netty.channel.ChannelFutureListener; import org.jboss.netty.channel.Channels; @@ -19,9 +23,23 @@ import com.alibaba.otter.canal.protocol.CanalPacket.Packet; public class NettyUtils { private static final Logger logger = LoggerFactory.getLogger(NettyUtils.class); - private static int HEADER_LENGTH = 4; + public static int HEADER_LENGTH = 4; public static Timer hashedWheelTimer = new HashedWheelTimer(); + public static void write(Channel channel, ByteBuffer body, ChannelFutureListener channelFutureListner) { + byte[] header = ByteBuffer.allocate(HEADER_LENGTH).order(ByteOrder.BIG_ENDIAN).putInt(body.limit()).array(); + List components = new ArrayList(2); + components.add(ChannelBuffers.wrappedBuffer(ByteOrder.BIG_ENDIAN, header)); + components.add(ChannelBuffers.wrappedBuffer(body)); + + if (channelFutureListner == null) { + Channels.write(channel, new CompositeChannelBuffer(ByteOrder.BIG_ENDIAN, components)); + } else { + Channels.write(channel, new CompositeChannelBuffer(ByteOrder.BIG_ENDIAN, components)) + .addListener(channelFutureListner); + } + } + public static void write(Channel channel, byte[] body, ChannelFutureListener channelFutureListner) { byte[] header = ByteBuffer.allocate(HEADER_LENGTH).order(ByteOrder.BIG_ENDIAN).putInt(body.length).array(); if (channelFutureListner == null) { @@ -56,4 +74,20 @@ public class NettyUtils { .toByteArray(), channelFutureListener); } + + public static byte[] ackPacket() { + return Packet.newBuilder() + .setType(CanalPacket.PacketType.ACK) + .setBody(Ack.newBuilder().build().toByteString()) + .build() + .toByteArray(); + } + + public static byte[] errorPacket(int errorCode, String errorMessage) { + return Packet.newBuilder() + .setType(CanalPacket.PacketType.ACK) + .setBody(Ack.newBuilder().setErrorCode(errorCode).setErrorMessage(errorMessage).build().toByteString()) + .build() + .toByteArray(); + } } diff --git a/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/ClientAuthenticationHandler.java b/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/ClientAuthenticationHandler.java index 60398ea7..597d692a 100644 --- a/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/ClientAuthenticationHandler.java +++ b/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/ClientAuthenticationHandler.java @@ -73,7 +73,7 @@ public class ClientAuthenticationHandler extends SimpleChannelHandler { MDC.remove("destination"); } } - + // 鉴权一次性,暂不统计 NettyUtils.ack(ctx.getChannel(), new ChannelFutureListener() { public void operationComplete(ChannelFuture future) throws Exception { diff --git a/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/SessionHandler.java b/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/SessionHandler.java index 3eda5a0d..ba0432b8 100644 --- a/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/SessionHandler.java +++ b/server/src/main/java/com/alibaba/otter/canal/server/netty/handler/SessionHandler.java @@ -33,13 +33,11 @@ import com.alibaba.otter.canal.protocol.ClientIdentity; import com.alibaba.otter.canal.protocol.Message; import com.alibaba.otter.canal.server.embedded.CanalServerWithEmbedded; import com.alibaba.otter.canal.server.netty.NettyUtils; +import com.alibaba.otter.canal.server.netty.listener.ChannelFutureAggregator; +import com.google.protobuf.ByteString; +import com.google.protobuf.CodedOutputStream; +import com.google.protobuf.WireFormat; -/** - * 处理具体的客户端请求 - * - * @author jianghang 2012-10-24 下午02:21:13 - * @version 1.0.0 - */ public class SessionHandler extends SimpleChannelHandler { private static final Logger logger = LoggerFactory.getLogger(SessionHandler.class); @@ -52,8 +50,10 @@ public class SessionHandler extends SimpleChannelHandler { this.embeddedServer = embeddedServer; } + @SuppressWarnings({ "deprecation" }) public void messageReceived(ChannelHandlerContext ctx, MessageEvent e) throws Exception { logger.info("message receives in session handler..."); + long start = System.nanoTime(); ChannelBuffer buffer = (ChannelBuffer) e.getMessage(); Packet packet = Packet.parseFrom(buffer.readBytes(buffer.readableBytes()).array()); ClientIdentity clientIdentity = null; @@ -76,13 +76,14 @@ public class SessionHandler extends SimpleChannelHandler { } embeddedServer.subscribe(clientIdentity); - ctx.setAttachment(clientIdentity);// 设置状态数据 - NettyUtils.ack(ctx.getChannel(), null); + // ctx.setAttachment(clientIdentity);// 设置状态数据 + byte[] ackBytes = NettyUtils.ackPacket(); + NettyUtils.write(ctx.getChannel(), ackBytes, new ChannelFutureAggregator(sub.getDestination(), + sub, packet.getType(), ackBytes.length, System.nanoTime() - start)); } else { - NettyUtils.error(401, - MessageFormatter.format("destination or clientId is null", sub.toString()).getMessage(), - ctx.getChannel(), - null); + byte[] errorBytes = NettyUtils.errorPacket(401, MessageFormatter.format("destination or clientId is null", sub.toString()).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes ,new ChannelFutureAggregator(sub.getDestination(), + sub, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 401)); } break; case UNSUBSCRIPTION: @@ -94,12 +95,13 @@ public class SessionHandler extends SimpleChannelHandler { MDC.put("destination", clientIdentity.getDestination()); embeddedServer.unsubscribe(clientIdentity); stopCanalInstanceIfNecessary(clientIdentity);// 尝试关闭 - NettyUtils.ack(ctx.getChannel(), null); + byte[] ackBytes = NettyUtils.ackPacket(); + NettyUtils.write(ctx.getChannel(), ackBytes, new ChannelFutureAggregator(unsub.getDestination(), + unsub, packet.getType(), ackBytes.length, System.nanoTime() - start)); } else { - NettyUtils.error(401, - MessageFormatter.format("destination or clientId is null", unsub.toString()).getMessage(), - ctx.getChannel(), - null); + byte[] errorBytes = NettyUtils.errorPacket(401, MessageFormatter.format("destination or clientId is null", unsub.toString()).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes, new ChannelFutureAggregator(unsub.getDestination(), + unsub, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 401)); } break; case GET: @@ -130,23 +132,80 @@ public class SessionHandler extends SimpleChannelHandler { } // } - Packet.Builder packetBuilder = CanalPacket.Packet.newBuilder(); - packetBuilder.setType(PacketType.MESSAGES); + if (message.getId() != -1 && message.isRaw()) { + List rowEntries = message.getRawEntries(); + // message size + int messageSize = 0; + messageSize += com.google.protobuf.CodedOutputStream.computeInt64Size(1, message.getId()); - Messages.Builder messageBuilder = CanalPacket.Messages.newBuilder(); - messageBuilder.setBatchId(message.getId()); - if (message.getId() != -1 && !CollectionUtils.isEmpty(message.getEntries())) { - for (Entry entry : message.getEntries()) { - messageBuilder.addMessages(entry.toByteString()); + int dataSize = 0; + for (int i = 0; i < rowEntries.size(); i++) { + dataSize += com.google.protobuf.CodedOutputStream.computeBytesSizeNoTag(rowEntries.get(i)); } + messageSize += dataSize; + messageSize += 1 * rowEntries.size(); + // packet size + int size = 0; + size += com.google.protobuf.CodedOutputStream.computeEnumSize(3, + PacketType.MESSAGES.getNumber()); + size += com.google.protobuf.CodedOutputStream.computeTagSize(5) + + com.google.protobuf.CodedOutputStream.computeRawVarint32Size(messageSize) + + messageSize; + // recyle bytes + // ByteBuffer byteBuffer = (ByteBuffer) + // ctx.getAttachment(); + // if (byteBuffer != null && size <= + // byteBuffer.capacity()) { + // byteBuffer.clear(); + // } else { + // byteBuffer = + // ByteBuffer.allocate(size).order(ByteOrder.BIG_ENDIAN); + // ctx.setAttachment(byteBuffer); + // } + // CodedOutputStream output = + // CodedOutputStream.newInstance(byteBuffer); + byte[] body = new byte[size]; + CodedOutputStream output = CodedOutputStream.newInstance(body); + output.writeEnum(3, PacketType.MESSAGES.getNumber()); + + output.writeTag(5, WireFormat.WIRETYPE_LENGTH_DELIMITED); + output.writeRawVarint32(messageSize); + // message + output.writeInt64(1, message.getId()); + for (int i = 0; i < rowEntries.size(); i++) { + output.writeBytes(2, rowEntries.get(i)); + } + output.checkNoSpaceLeft(); + NettyUtils.write(ctx.getChannel(), body, new ChannelFutureAggregator(get.getDestination(), + get, packet.getType(), body.length, System.nanoTime() - start, message.getId() == -1)); + + // output.flush(); + // byteBuffer.flip(); + // NettyUtils.write(ctx.getChannel(), byteBuffer, + // null); + } else { + Packet.Builder packetBuilder = CanalPacket.Packet.newBuilder(); + packetBuilder.setType(PacketType.MESSAGES); + + Messages.Builder messageBuilder = CanalPacket.Messages.newBuilder(); + messageBuilder.setBatchId(message.getId()); + if (message.getId() != -1) { + if (message.isRaw() && !CollectionUtils.isEmpty(message.getRawEntries())) { + messageBuilder.addAllMessages(message.getRawEntries()); + } else if (!CollectionUtils.isEmpty(message.getEntries())) { + for (Entry entry : message.getEntries()) { + messageBuilder.addMessages(entry.toByteString()); + } + } + } + byte[] body = packetBuilder.setBody(messageBuilder.build().toByteString()).build().toByteArray(); + NettyUtils.write(ctx.getChannel(), body, new ChannelFutureAggregator(get.getDestination(), + get, packet.getType(), body.length, System.nanoTime() - start, message.getId() == -1));// 输出数据 } - packetBuilder.setBody(messageBuilder.build().toByteString()); - NettyUtils.write(ctx.getChannel(), packetBuilder.build().toByteArray(), null);// 输出数据 } else { - NettyUtils.error(401, - MessageFormatter.format("destination or clientId is null", get.toString()).getMessage(), - ctx.getChannel(), - null); + byte[] errorBytes = NettyUtils.errorPacket(401, MessageFormatter.format("destination or clientId is null", get.toString()).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes, new ChannelFutureAggregator(get.getDestination(), + get, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 401)); } break; case CLIENTACK: @@ -154,21 +213,20 @@ public class SessionHandler extends SimpleChannelHandler { MDC.put("destination", ack.getDestination()); if (StringUtils.isNotEmpty(ack.getDestination()) && StringUtils.isNotEmpty(ack.getClientId())) { if (ack.getBatchId() == 0L) { - NettyUtils.error(402, - MessageFormatter.format("batchId should assign value", ack.toString()).getMessage(), - ctx.getChannel(), - null); + byte[] errorBytes = NettyUtils.errorPacket(402, MessageFormatter.format("batchId should assign value", ack.toString()).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes, new ChannelFutureAggregator(ack.getDestination(), + ack, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 402)); } else if (ack.getBatchId() == -1L) { // -1代表上一次get没有数据,直接忽略之 // donothing } else { clientIdentity = new ClientIdentity(ack.getDestination(), Short.valueOf(ack.getClientId())); embeddedServer.ack(clientIdentity, ack.getBatchId()); + new ChannelFutureAggregator(ack.getDestination(), ack, packet.getType(), 0, System.nanoTime() - start).operationComplete(null); } } else { - NettyUtils.error(401, - MessageFormatter.format("destination or clientId is null", ack.toString()).getMessage(), - ctx.getChannel(), - null); + byte[] errorBytes = NettyUtils.errorPacket(401, MessageFormatter.format("destination or clientId is null", ack.toString()).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes, new ChannelFutureAggregator(ack.getDestination(), + ack, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 401)); } break; case CLIENTROLLBACK: @@ -183,26 +241,25 @@ public class SessionHandler extends SimpleChannelHandler { } else { embeddedServer.rollback(clientIdentity, rollback.getBatchId()); // 只回滚单个批次 } + new ChannelFutureAggregator(rollback.getDestination(), rollback, packet.getType(), 0, System.nanoTime() - start).operationComplete(null); } else { - NettyUtils.error(401, - MessageFormatter.format("destination or clientId is null", rollback.toString()) - .getMessage(), - ctx.getChannel(), - null); + byte[] errorBytes = NettyUtils.errorPacket(401, MessageFormatter.format("destination or clientId is null", rollback.toString()).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes, new ChannelFutureAggregator(rollback.getDestination(), + rollback, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 401)); } break; default: - NettyUtils.error(400, MessageFormatter.format("packet type={} is NOT supported!", packet.getType()) - .getMessage(), ctx.getChannel(), null); + byte[] errorBytes = NettyUtils.errorPacket(400, MessageFormatter.format("packet type={} is NOT supported!", packet.getType()).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes, new ChannelFutureAggregator(ctx.getChannel().getRemoteAddress().toString(), + null, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 400)); break; } } catch (Throwable exception) { - NettyUtils.error(400, - MessageFormatter.format("something goes wrong with channel:{}, exception={}", + byte[] errorBytes = NettyUtils.errorPacket(400, MessageFormatter.format("something goes wrong with channel:{}, exception={}", ctx.getChannel(), - ExceptionUtils.getStackTrace(exception)).getMessage(), - ctx.getChannel(), - null); + ExceptionUtils.getStackTrace(exception)).getMessage()); + NettyUtils.write(ctx.getChannel(), errorBytes, new ChannelFutureAggregator(ctx.getChannel().getRemoteAddress().toString(), + null, packet.getType(), errorBytes.length, System.nanoTime() - start, (short) 400)); } finally { MDC.remove("destination"); } diff --git a/server/src/main/java/com/alibaba/otter/canal/server/netty/listener/ChannelFutureAggregator.java b/server/src/main/java/com/alibaba/otter/canal/server/netty/listener/ChannelFutureAggregator.java new file mode 100644 index 00000000..e4793640 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/server/netty/listener/ChannelFutureAggregator.java @@ -0,0 +1,180 @@ +package com.alibaba.otter.canal.server.netty.listener; + +import com.alibaba.otter.canal.protocol.CanalPacket; +import com.google.common.base.Preconditions; +import com.google.protobuf.GeneratedMessageV3; +import org.jboss.netty.channel.ChannelFuture; +import org.jboss.netty.channel.ChannelFutureListener; + +import static com.alibaba.otter.canal.server.netty.CanalServerWithNettyProfiler.profiler; +import static com.alibaba.otter.canal.server.netty.NettyUtils.HEADER_LENGTH; + +/** + * @author Chuanyi Li + */ +public class ChannelFutureAggregator implements ChannelFutureListener { + + private ClientRequestResult result; + + public ChannelFutureAggregator(String destination, GeneratedMessageV3 request, CanalPacket.PacketType type, int amount, long latency, boolean empty) { + this(destination, request, type, amount, latency, empty, (short) 0); + } + + public ChannelFutureAggregator(String destination, GeneratedMessageV3 request, CanalPacket.PacketType type, int amount, long latency) { + this(destination, request, type, amount, latency, false, (short) 0); + } + + public ChannelFutureAggregator(String destination, GeneratedMessageV3 request, CanalPacket.PacketType type, int amount, long latency, short errorCode) { + this(destination, request, type, amount, latency, false, errorCode); + } + + private ChannelFutureAggregator(String destination, GeneratedMessageV3 request, CanalPacket.PacketType type, int amount, long latency, boolean empty, short errorCode) { + this.result = new ClientRequestResult.Builder() + .destination(destination) + .type(type) + .request(request) + .amount(amount + HEADER_LENGTH) + .latency(latency) + .errorCode(errorCode) + .empty(empty) + .build(); + } + + @Override + public void operationComplete(ChannelFuture future) { + // profiling after I/O operation + if (future != null && future.getCause() != null) { + result.channelError = future.getCause(); + } + profiler().profiling(result); + } + + /** + * Client request result pojo + */ + public static class ClientRequestResult { + + private String destination; + private CanalPacket.PacketType type; + private GeneratedMessageV3 request; + private int amount; + private long latency; + private short errorCode; + private boolean empty; + private Throwable channelError; + + private ClientRequestResult() {} + + private ClientRequestResult(Builder builder) { + this.destination = Preconditions.checkNotNull(builder.destination); + this.type = Preconditions.checkNotNull(builder.type); + this.request = builder.request; + this.amount = builder.amount; + this.latency = builder.latency; + this.errorCode = builder.errorCode; + this.empty = builder.empty; + this.channelError = builder.channelError; + } + + // auto-generated + public static class Builder { + + private String destination; + private CanalPacket.PacketType type; + private GeneratedMessageV3 request; + private int amount; + private long latency; + private short errorCode; + private boolean empty; + private Throwable channelError; + + Builder destination(String destination) { + this.destination = destination; + return this; + } + + Builder type(CanalPacket.PacketType type) { + this.type = type; + return this; + } + + Builder request(GeneratedMessageV3 request) { + this.request = request; + return this; + } + + Builder amount(int amount) { + this.amount = amount; + return this; + } + + Builder latency(long latency) { + this.latency = latency; + return this; + } + + Builder errorCode(short errorCode) { + this.errorCode = errorCode; + return this; + } + + Builder empty(boolean empty) { + this.empty = empty; + return this; + } + + public Builder channelError(Throwable channelError) { + this.channelError = channelError; + return this; + } + + public Builder fromPrototype(ClientRequestResult prototype) { + destination = prototype.destination; + type = prototype.type; + request = prototype.request; + amount = prototype.amount; + latency = prototype.latency; + errorCode = prototype.errorCode; + empty = prototype.empty; + channelError = prototype.channelError; + return this; + } + + ClientRequestResult build() { + return new ClientRequestResult(this); + } + } + // getters + public String getDestination() { + return destination; + } + + public CanalPacket.PacketType getType() { + return type; + } + + public GeneratedMessageV3 getRequest() { + return request; + } + + public int getAmount() { + return amount; + } + + public long getLatency() { + return latency; + } + + public short getErrorCode() { + return errorCode; + } + + public boolean getEmpty() { + return empty; + } + + public Throwable getChannelError() { + return channelError; + } + } +} diff --git a/server/src/main/java/com/alibaba/otter/canal/spi/CanalMQProducer.java b/server/src/main/java/com/alibaba/otter/canal/spi/CanalMQProducer.java new file mode 100644 index 00000000..9ddbc80d --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/spi/CanalMQProducer.java @@ -0,0 +1,37 @@ +package com.alibaba.otter.canal.spi; + +import java.io.IOException; + +import com.alibaba.otter.canal.common.MQProperties; +import com.alibaba.otter.canal.protocol.Message; + +public interface CanalMQProducer { + + /** + * Init producer. + * + * @param mqProperties MQ config + */ + void init(MQProperties mqProperties); + + /** + * Send canal message to related topic + * + * @param canalDestination canal mq destination + * @param message canal message + * @throws IOException + */ + void send(MQProperties.CanalDestination canalDestination, Message message, Callback callback) throws IOException; + + /** + * Stop MQ producer service + */ + void stop(); + + interface Callback { + + void commit(); + + void rollback(); + } +} diff --git a/server/src/main/java/com/alibaba/otter/canal/spi/CanalMetricsProvider.java b/server/src/main/java/com/alibaba/otter/canal/spi/CanalMetricsProvider.java new file mode 100644 index 00000000..ad0ceddf --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/spi/CanalMetricsProvider.java @@ -0,0 +1,24 @@ +package com.alibaba.otter.canal.spi; + +/** + * Use java service provider mechanism to provide {@link CanalMetricsService}. + *
      + * Example:
      + * {@code
      + *     ServiceLoader providers = ServiceLoader.load(CanalMetricsProvider.class);
      + *     List list = new ArrayList();
      + *     for (CanalMetricsProvider provider : providers) {
      + *         list.add(provider);
      + *     }
      + * }
      + * 
      + * @author Chuanyi Li + */ +public interface CanalMetricsProvider { + + /** + * @return Impl of {@link CanalMetricsService} + */ + CanalMetricsService getService(); + +} diff --git a/server/src/main/java/com/alibaba/otter/canal/spi/CanalMetricsService.java b/server/src/main/java/com/alibaba/otter/canal/spi/CanalMetricsService.java new file mode 100644 index 00000000..a4528800 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/spi/CanalMetricsService.java @@ -0,0 +1,47 @@ +package com.alibaba.otter.canal.spi; + +import com.alibaba.otter.canal.instance.core.CanalInstance; + +/** + * Canal server/instance metrics for export. + * + * Designed to be created by service provider. + * + * @see CanalMetricsProvider + * @author Chuanyi Li + */ +public interface CanalMetricsService { + + /** + * Initialization on canal server startup. + */ + void initialize(); + + /** + * Clean-up at canal server stop phase. + */ + void terminate(); + + /** + * @return {@code true} if the metrics service is running, otherwise {@code false}. + */ + boolean isRunning(); + + /** + * Register instance level metrics for specified instance. + * @param instance {@link CanalInstance} + */ + void register(CanalInstance instance); + + /** + * Unregister instance level metrics for specified instance. + * @param instance {@link CanalInstance} + */ + void unregister(CanalInstance instance); + + /** + * @param port server port for pull + */ + void setServerPort(int port); + +} diff --git a/server/src/main/java/com/alibaba/otter/canal/spi/NopCanalMetricsService.java b/server/src/main/java/com/alibaba/otter/canal/spi/NopCanalMetricsService.java new file mode 100644 index 00000000..45926348 --- /dev/null +++ b/server/src/main/java/com/alibaba/otter/canal/spi/NopCanalMetricsService.java @@ -0,0 +1,43 @@ +package com.alibaba.otter.canal.spi; + +import com.alibaba.otter.canal.instance.core.CanalInstance; + +/** + * @author Chuanyi Li + */ +public class NopCanalMetricsService implements CanalMetricsService { + + public static final NopCanalMetricsService NOP = new NopCanalMetricsService(); + + private NopCanalMetricsService() {} + + @Override + public void initialize() { + + } + + @Override + public void terminate() { + + } + + @Override + public boolean isRunning() { + return false; + } + + @Override + public void register(CanalInstance instance) { + + } + + @Override + public void unregister(CanalInstance instance) { + + } + + @Override + public void setServerPort(int port) { + + } +} diff --git a/server/src/test/java/com/alibaba/otter/canal/server/CanalServerWithEmbedded_FileModeTest.java b/server/src/test/java/com/alibaba/otter/canal/server/CanalServerWithEmbedded_FileModeTest.java new file mode 100644 index 00000000..e986b6ff --- /dev/null +++ b/server/src/test/java/com/alibaba/otter/canal/server/CanalServerWithEmbedded_FileModeTest.java @@ -0,0 +1,53 @@ +package com.alibaba.otter.canal.server; + +import java.net.InetSocketAddress; +import java.util.Arrays; + +import com.alibaba.otter.canal.instance.manager.model.Canal; +import com.alibaba.otter.canal.instance.manager.model.CanalParameter; +import com.alibaba.otter.canal.instance.manager.model.CanalParameter.*; + +public class CanalServerWithEmbedded_FileModeTest extends BaseCanalServerWithEmbededTest { + + protected Canal buildCanal() { + Canal canal = new Canal(); + canal.setId(1L); + canal.setName(DESTINATION); + canal.setDesc("my standalone server test "); + + CanalParameter parameter = new CanalParameter(); + + parameter.setMetaMode(MetaMode.LOCAL_FILE); + parameter.setDataDir("./conf"); + parameter.setMetaFileFlushPeriod(1000); + parameter.setHaMode(HAMode.HEARTBEAT); + parameter.setIndexMode(IndexMode.MEMORY_META_FAILBACK); + + parameter.setStorageMode(StorageMode.MEMORY); + parameter.setMemoryStorageBufferSize(32 * 1024); + + parameter.setSourcingType(SourcingType.MYSQL); + parameter.setDbAddresses(Arrays.asList(new InetSocketAddress(MYSQL_ADDRESS, 3306), + new InetSocketAddress(MYSQL_ADDRESS, 3306))); + parameter.setDbUsername(USERNAME); + parameter.setDbPassword(PASSWORD); + parameter.setPositions(Arrays.asList("{\"journalName\":\"mysql-bin.000001\",\"position\":332L,\"timestamp\":\"1505998863000\"}", + "{\"journalName\":\"mysql-bin.000001\",\"position\":332L,\"timestamp\":\"1505998863000\"}")); + + parameter.setSlaveId(1234L); + + parameter.setDefaultConnectionTimeoutInSeconds(30); + parameter.setConnectionCharset("UTF-8"); + parameter.setConnectionCharsetNumber((byte) 33); + parameter.setReceiveBufferSize(8 * 1024); + parameter.setSendBufferSize(8 * 1024); + + parameter.setDetectingEnable(false); + parameter.setDetectingIntervalInSeconds(10); + parameter.setDetectingRetryTimes(3); + parameter.setDetectingSQL(DETECTING_SQL); + + canal.setCanalParameter(parameter); + return canal; + } +} \ No newline at end of file diff --git a/server/src/test/java/com/alibaba/otter/canal/server/CanalServerWithNettyTest.java b/server/src/test/java/com/alibaba/otter/canal/server/CanalServerWithNettyTest.java index 3b3c0ee0..673918fe 100644 --- a/server/src/test/java/com/alibaba/otter/canal/server/CanalServerWithNettyTest.java +++ b/server/src/test/java/com/alibaba/otter/canal/server/CanalServerWithNettyTest.java @@ -66,6 +66,8 @@ public class CanalServerWithNettyTest { @Test public void testAuth() { + + try { SocketChannel channel = SocketChannel.open(); channel.connect(new InetSocketAddress("127.0.0.1", 1088)); @@ -80,7 +82,7 @@ public class CanalServerWithNettyTest { } // Handshake handshake = Handshake.parseFrom(p.getBody()); - System.out.println(handshake.getSupportedCompressionsList()); + System.out.println(handshake.getSupportedCompressions()); // ClientAuth ca = ClientAuth.newBuilder() .setUsername("") diff --git a/server/src/test/java/com/alibaba/otter/canal/server/ProtocolTest.java b/server/src/test/java/com/alibaba/otter/canal/server/ProtocolTest.java new file mode 100644 index 00000000..110c3d72 --- /dev/null +++ b/server/src/test/java/com/alibaba/otter/canal/server/ProtocolTest.java @@ -0,0 +1,93 @@ +package com.alibaba.otter.canal.server; + +import java.io.IOException; +import java.util.Arrays; +import java.util.List; + +import org.junit.Test; + +import com.alibaba.otter.canal.protocol.CanalEntry.Entry; +import com.alibaba.otter.canal.protocol.CanalEntry.EntryType; +import com.alibaba.otter.canal.protocol.CanalEntry.Header; +import com.alibaba.otter.canal.protocol.CanalPacket.Compression; +import com.alibaba.otter.canal.protocol.CanalPacket.Messages; +import com.alibaba.otter.canal.protocol.CanalPacket.Packet; +import com.alibaba.otter.canal.protocol.CanalPacket.PacketType; +import com.alibaba.otter.canal.protocol.Message; +import com.alibaba.otter.canal.protocol.exception.CanalClientException; +import com.google.protobuf.ByteString; +import com.google.protobuf.CodedOutputStream; +import com.google.protobuf.WireFormat; + +public class ProtocolTest { + + @Test + public void testSimple() throws IOException { + Header.Builder headerBuilder = Header.newBuilder(); + headerBuilder.setLogfileName("mysql-bin.000001"); + headerBuilder.setLogfileOffset(1024); + headerBuilder.setExecuteTime(1024); + Entry.Builder entryBuilder = Entry.newBuilder(); + entryBuilder.setHeader(headerBuilder.build()); + entryBuilder.setEntryType(EntryType.ROWDATA); + Entry entry = entryBuilder.build(); + Message message = new Message(3, true, Arrays.asList(entry.toByteString())); + + byte[] body = buildData(message); + Packet packet = Packet.parseFrom(body); + switch (packet.getType()) { + case MESSAGES: { + if (!packet.getCompression().equals(Compression.NONE)) { + throw new CanalClientException("compression is not supported in this connector"); + } + + Messages messages = Messages.parseFrom(packet.getBody()); + Message result = new Message(messages.getBatchId()); + for (ByteString byteString : messages.getMessagesList()) { + result.addEntry(Entry.parseFrom(byteString)); + } + + System.out.println(result); + break; + } + default: { + throw new CanalClientException("unexpected packet type: " + packet.getType()); + } + } + } + + @SuppressWarnings("deprecation") + private byte[] buildData(Message message) throws IOException { + List rowEntries = message.getRawEntries(); + // message size + int messageSize = 0; + messageSize += com.google.protobuf.CodedOutputStream.computeInt64Size(1, message.getId()); + + int dataSize = 0; + for (int i = 0; i < rowEntries.size(); i++) { + dataSize += com.google.protobuf.CodedOutputStream.computeBytesSizeNoTag(rowEntries.get(i)); + } + messageSize += dataSize; + messageSize += 1 * rowEntries.size(); + // packet size + int size = 0; + size += com.google.protobuf.CodedOutputStream.computeEnumSize(3, PacketType.MESSAGES.getNumber()); + size += com.google.protobuf.CodedOutputStream.computeTagSize(5) + + com.google.protobuf.CodedOutputStream.computeRawVarint32Size(messageSize) + messageSize; + // TODO recyle bytes[] + byte[] body = new byte[size]; + CodedOutputStream output = CodedOutputStream.newInstance(body); + output.writeEnum(3, PacketType.MESSAGES.getNumber()); + + output.writeTag(5, WireFormat.WIRETYPE_LENGTH_DELIMITED); + output.writeRawVarint32(messageSize); + // message + output.writeInt64(1, message.getId()); + for (int i = 0; i < rowEntries.size(); i++) { + output.writeBytes(2, rowEntries.get(i)); + } + output.checkNoSpaceLeft(); + + return body; + } +} diff --git a/sink/pom.xml b/sink/pom.xml index 4ed7e04f..5e706819 100644 --- a/sink/pom.xml +++ b/sink/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter diff --git a/sink/src/main/java/com/alibaba/otter/canal/sink/entry/EntryEventSink.java b/sink/src/main/java/com/alibaba/otter/canal/sink/entry/EntryEventSink.java index bfb4b771..d34450ed 100644 --- a/sink/src/main/java/com/alibaba/otter/canal/sink/entry/EntryEventSink.java +++ b/sink/src/main/java/com/alibaba/otter/canal/sink/entry/EntryEventSink.java @@ -20,6 +20,7 @@ import com.alibaba.otter.canal.sink.CanalEventDownStreamHandler; import com.alibaba.otter.canal.sink.CanalEventSink; import com.alibaba.otter.canal.sink.exception.CanalSinkException; import com.alibaba.otter.canal.store.CanalEventStore; +import com.alibaba.otter.canal.store.memory.MemoryEventStoreWithBuffer; import com.alibaba.otter.canal.store.model.Event; /** @@ -33,12 +34,17 @@ public class EntryEventSink extends AbstractCanalEventSink eventStore; - protected boolean filterTransactionEntry = false; // 是否需要过滤事务头/尾 + protected boolean filterTransactionEntry = false; // 是否需要尽可能过滤事务头/尾 protected boolean filterEmtryTransactionEntry = true; // 是否需要过滤空的事务头/尾 protected long emptyTransactionInterval = 5 * 1000; // 空的事务输出的频率 - protected long emptyTransctionThresold = 8192; // 超过1024个事务头,输出一个 + protected long emptyTransctionThresold = 8192; // 超过8192个事务头,输出一个 + + protected volatile long lastTransactionTimestamp = 0L; + protected AtomicLong lastTransactionCount = new AtomicLong(0L); protected volatile long lastEmptyTransactionTimestamp = 0L; protected AtomicLong lastEmptyTransactionCount = new AtomicLong(0L); + protected AtomicLong eventsSinkBlockingTime = new AtomicLong(0L); + protected boolean raw; public EntryEventSink(){ addHandler(new HeartBeatEntryEventHandler()); @@ -48,6 +54,10 @@ public class EntryEventSink extends AbstractCanalEventSink entrys, InetSocketAddress remoteAddress, String destination) throws CanalSinkException, InterruptedException { - List rowDatas = entrys; - if (filterTransactionEntry) { - rowDatas = new ArrayList(); - for (CanalEntry.Entry entry : entrys) { - if (entry.getEntryType() == EntryType.ROWDATA) { - rowDatas.add(entry); - } - } - } - - return sinkData(rowDatas, remoteAddress); + return sinkData(entrys, remoteAddress); } private boolean sinkData(List entrys, InetSocketAddress remoteAddress) @@ -92,26 +92,35 @@ public class EntryEventSink extends AbstractCanalEventSink events = new ArrayList(); for (CanalEntry.Entry entry : entrys) { - Event event = new Event(new LogIdentity(remoteAddress, -1L), entry); - if (!doFilter(event)) { + if (!doFilter(entry)) { continue; } - events.add(event); + if (filterTransactionEntry + && (entry.getEntryType() == EntryType.TRANSACTIONBEGIN || entry.getEntryType() == EntryType.TRANSACTIONEND)) { + long currentTimestamp = entry.getHeader().getExecuteTime(); + // 基于一定的策略控制,放过空的事务头和尾,便于及时更新数据库位点,表明工作正常 + if (Math.abs(currentTimestamp - lastTransactionTimestamp) > emptyTransactionInterval + || lastTransactionCount.incrementAndGet() > emptyTransctionThresold) { + lastTransactionCount.set(0L); + lastTransactionTimestamp = currentTimestamp; + continue; + } + } + hasRowData |= (entry.getEntryType() == EntryType.ROWDATA); hasHeartBeat |= (entry.getEntryType() == EntryType.HEARTBEAT); + Event event = new Event(new LogIdentity(remoteAddress, -1L), entry, raw); + events.add(event); } - if (hasRowData) { - // 存在row记录 - return doSink(events); - } else if (hasHeartBeat) { - // 存在heartbeat记录,直接跳给后续处理 + if (hasRowData || hasHeartBeat) { + // 存在row记录 或者 存在heartbeat记录,直接跳给后续处理 return doSink(events); } else { // 需要过滤的数据 if (filterEmtryTransactionEntry && !CollectionUtils.isEmpty(events)) { - long currentTimestamp = events.get(0).getEntry().getHeader().getExecuteTime(); + long currentTimestamp = events.get(0).getExecuteTime(); // 基于一定的策略控制,放过空的事务头和尾,便于及时更新数据库位点,表明工作正常 if (Math.abs(currentTimestamp - lastEmptyTransactionTimestamp) > emptyTransactionInterval || lastEmptyTransactionCount.incrementAndGet() > emptyTransctionThresold) { @@ -126,15 +135,15 @@ public class EntryEventSink extends AbstractCanalEventSink> handler : getHandlers()) { events = handler.before(events); } - + long blockingStart = 0L; int fullTimes = 0; do { if (eventStore.tryPut(events)) { + if (fullTimes > 0) { + eventsSinkBlockingTime.addAndGet(System.nanoTime() - blockingStart); + } for (CanalEventDownStreamHandler> handler : getHandlers()) { events = handler.after(events); } return true; } else { + if (fullTimes == 0) { + blockingStart = System.nanoTime(); + } applyWait(++fullTimes); + if (fullTimes % 100 == 0) { + long nextStart = System.nanoTime(); + eventsSinkBlockingTime.addAndGet(nextStart - blockingStart); + blockingStart = nextStart; + } } for (CanalEventDownStreamHandler> handler : getHandlers()) { @@ -202,4 +222,8 @@ public class EntryEventSink extends AbstractCanalEventSink before(List events) { boolean existHeartBeat = false; for (Event event : events) { - if (event.getEntry().getEntryType() == EntryType.HEARTBEAT) { + if (event.getEntryType() == EntryType.HEARTBEAT) { existHeartBeat = true; } } @@ -29,7 +29,7 @@ public class HeartBeatEntryEventHandler extends AbstractCanalEventDownStreamHand // 目前heartbeat和其他事件是分离的,保险一点还是做一下检查处理 List result = new ArrayList(); for (Event event : events) { - if (event.getEntry().getEntryType() != EntryType.HEARTBEAT) { + if (event.getEntryType() != EntryType.HEARTBEAT) { result.add(event); } } diff --git a/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineBarrier.java b/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineBarrier.java index be9edfa0..24f457b7 100644 --- a/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineBarrier.java +++ b/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineBarrier.java @@ -139,7 +139,7 @@ public class TimelineBarrier implements GroupBarrier { } private Long getTimestamp(Event event) { - return event.getEntry().getHeader().getExecuteTime(); + return event.getExecuteTime(); } } diff --git a/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineTransactionBarrier.java b/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineTransactionBarrier.java index 774818f2..59bf8fd7 100644 --- a/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineTransactionBarrier.java +++ b/sink/src/main/java/com/alibaba/otter/canal/sink/entry/group/TimelineTransactionBarrier.java @@ -113,11 +113,11 @@ public class TimelineTransactionBarrier extends TimelineBarrier { } private boolean isTransactionBegin(Event event) { - return event.getEntry().getEntryType() == EntryType.TRANSACTIONBEGIN; + return event.getEntryType() == EntryType.TRANSACTIONBEGIN; } private boolean isTransactionEnd(Event event) { - return event.getEntry().getEntryType() == EntryType.TRANSACTIONEND; + return event.getEntryType() == EntryType.TRANSACTIONEND; } } diff --git a/sink/src/test/java/com/alibaba/otter/canal/sink/stub/DummyEventStore.java b/sink/src/test/java/com/alibaba/otter/canal/sink/stub/DummyEventStore.java index 8a52bb05..7f786ef2 100644 --- a/sink/src/test/java/com/alibaba/otter/canal/sink/stub/DummyEventStore.java +++ b/sink/src/test/java/com/alibaba/otter/canal/sink/stub/DummyEventStore.java @@ -60,33 +60,33 @@ public class DummyEventStore implements CanalEventStore { } public void put(Event data) throws InterruptedException, CanalStoreException { - System.out.println("time:" + data.getEntry().getHeader().getExecuteTime()); + System.out.println("time:" + data.getExecuteTime()); } public boolean put(Event data, long timeout, TimeUnit unit) throws InterruptedException, CanalStoreException { - System.out.println("time:" + data.getEntry().getHeader().getExecuteTime()); + System.out.println("time:" + data.getExecuteTime()); return true; } public boolean tryPut(Event data) throws CanalStoreException { - System.out.println("time:" + data.getEntry().getHeader().getExecuteTime()); + System.out.println("time:" + data.getExecuteTime()); return true; } public void put(List datas) throws InterruptedException, CanalStoreException { Event data = datas.get(0); - System.out.println("time:" + data.getEntry().getHeader().getExecuteTime()); + System.out.println("time:" + data.getExecuteTime()); } public boolean put(List datas, long timeout, TimeUnit unit) throws InterruptedException, CanalStoreException { Event data = datas.get(0); - System.out.println("time:" + data.getEntry().getHeader().getExecuteTime()); + System.out.println("time:" + data.getExecuteTime()); return true; } public boolean tryPut(List datas) throws CanalStoreException { Event data = datas.get(0); - System.out.println("time:" + data.getEntry().getHeader().getExecuteTime()); + System.out.println("time:" + data.getExecuteTime()); return true; } diff --git a/store/pom.xml b/store/pom.xml index 318c2f9d..4ff3d1e1 100644 --- a/store/pom.xml +++ b/store/pom.xml @@ -3,7 +3,7 @@ com.alibaba.otter canal - 1.0.26-SNAPSHOT + 1.1.3-SNAPSHOT ../pom.xml com.alibaba.otter diff --git a/store/src/main/java/com/alibaba/otter/canal/store/helper/CanalEventUtils.java b/store/src/main/java/com/alibaba/otter/canal/store/helper/CanalEventUtils.java index ac858446..4fdbfcba 100644 --- a/store/src/main/java/com/alibaba/otter/canal/store/helper/CanalEventUtils.java +++ b/store/src/main/java/com/alibaba/otter/canal/store/helper/CanalEventUtils.java @@ -2,7 +2,6 @@ package com.alibaba.otter.canal.store.helper; import org.apache.commons.lang.StringUtils; -import com.alibaba.otter.canal.protocol.CanalEntry; import com.alibaba.otter.canal.protocol.position.EntryPosition; import com.alibaba.otter.canal.protocol.position.LogPosition; import com.alibaba.otter.canal.store.model.Event; @@ -48,14 +47,13 @@ public class CanalEventUtils { */ public static LogPosition createPosition(Event event) { EntryPosition position = new EntryPosition(); - position.setJournalName(event.getEntry().getHeader().getLogfileName()); - position.setPosition(event.getEntry().getHeader().getLogfileOffset()); - position.setTimestamp(event.getEntry().getHeader().getExecuteTime()); + position.setJournalName(event.getJournalName()); + position.setPosition(event.getPosition()); + position.setTimestamp(event.getExecuteTime()); // add serverId at 2016-06-28 - position.setServerId(event.getEntry().getHeader().getServerId()); - + position.setServerId(event.getServerId()); // add gtid - position.setGtid(event.getEntry().getHeader().getGtid()); + position.setGtid(event.getGtid()); LogPosition logPosition = new LogPosition(); logPosition.setPostion(position); @@ -68,9 +66,9 @@ public class CanalEventUtils { */ public static LogPosition createPosition(Event event, boolean included) { EntryPosition position = new EntryPosition(); - position.setJournalName(event.getEntry().getHeader().getLogfileName()); - position.setPosition(event.getEntry().getHeader().getLogfileOffset()); - position.setTimestamp(event.getEntry().getHeader().getExecuteTime()); + position.setJournalName(event.getJournalName()); + position.setPosition(event.getPosition()); + position.setTimestamp(event.getExecuteTime()); position.setIncluded(included); LogPosition logPosition = new LogPosition(); @@ -84,13 +82,14 @@ public class CanalEventUtils { */ public static boolean checkPosition(Event event, LogPosition logPosition) { EntryPosition position = logPosition.getPostion(); - CanalEntry.Entry entry = event.getEntry(); - boolean result = position.getTimestamp().equals(entry.getHeader().getExecuteTime()); + boolean result = position.getTimestamp().equals(event.getExecuteTime()); boolean exactely = (StringUtils.isBlank(position.getJournalName()) && position.getPosition() == null); if (!exactely) {// 精确匹配 - result &= StringUtils.equals(entry.getHeader().getLogfileName(), position.getJournalName()); - result &= position.getPosition().equals(entry.getHeader().getLogfileOffset()); + result &= position.getPosition().equals(event.getPosition()); + if (result) {// short path + result &= StringUtils.equals(event.getJournalName(), position.getJournalName()); + } } return result; diff --git a/store/src/main/java/com/alibaba/otter/canal/store/memory/MemoryEventStoreWithBuffer.java b/store/src/main/java/com/alibaba/otter/canal/store/memory/MemoryEventStoreWithBuffer.java index 99995a8f..7f5eeb47 100644 --- a/store/src/main/java/com/alibaba/otter/canal/store/memory/MemoryEventStoreWithBuffer.java +++ b/store/src/main/java/com/alibaba/otter/canal/store/memory/MemoryEventStoreWithBuffer.java @@ -7,6 +7,8 @@ import java.util.concurrent.atomic.AtomicLong; import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.ReentrantLock; +import org.apache.commons.lang.StringUtils; + import com.alibaba.otter.canal.protocol.CanalEntry; import com.alibaba.otter.canal.protocol.CanalEntry.EventType; import com.alibaba.otter.canal.protocol.position.LogPosition; @@ -35,29 +37,40 @@ import com.alibaba.otter.canal.store.model.Events; */ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge implements CanalEventStore, CanalStoreScavenge { - private static final long INIT_SQEUENCE = -1; + private static final long INIT_SEQUENCE = -1; private int bufferSize = 16 * 1024; - private int bufferMemUnit = 1024; // memsize的单位,默认为1kb大小 + private int bufferMemUnit = 1024; // memsize的单位,默认为1kb大小 private int indexMask; private Event[] entries; // 记录下put/get/ack操作的三个下标 - private AtomicLong putSequence = new AtomicLong(INIT_SQEUENCE); // 代表当前put操作最后一次写操作发生的位置 - private AtomicLong getSequence = new AtomicLong(INIT_SQEUENCE); // 代表当前get操作读取的最后一条的位置 - private AtomicLong ackSequence = new AtomicLong(INIT_SQEUENCE); // 代表当前ack操作的最后一条的位置 + private AtomicLong putSequence = new AtomicLong(INIT_SEQUENCE); // 代表当前put操作最后一次写操作发生的位置 + private AtomicLong getSequence = new AtomicLong(INIT_SEQUENCE); // 代表当前get操作读取的最后一条的位置 + private AtomicLong ackSequence = new AtomicLong(INIT_SEQUENCE); // 代表当前ack操作的最后一条的位置 // 记录下put/get/ack操作的三个memsize大小 private AtomicLong putMemSize = new AtomicLong(0); private AtomicLong getMemSize = new AtomicLong(0); private AtomicLong ackMemSize = new AtomicLong(0); + // 记录下put/get/ack操作的三个execTime + private AtomicLong putExecTime = new AtomicLong(System.currentTimeMillis()); + private AtomicLong getExecTime = new AtomicLong(System.currentTimeMillis()); + private AtomicLong ackExecTime = new AtomicLong(System.currentTimeMillis()); + + // 记录下put/get/ack操作的三个table rows + private AtomicLong putTableRows = new AtomicLong(0); + private AtomicLong getTableRows = new AtomicLong(0); + private AtomicLong ackTableRows = new AtomicLong(0); + // 阻塞put/get操作控制信号 private ReentrantLock lock = new ReentrantLock(); private Condition notFull = lock.newCondition(); private Condition notEmpty = lock.newCondition(); - private BatchMode batchMode = BatchMode.ITEMSIZE; // 默认为内存大小模式 + private BatchMode batchMode = BatchMode.ITEMSIZE; // 默认为内存大小模式 private boolean ddlIsolation = false; + private boolean raw = true; // 针对entry是否开启raw模式 public MemoryEventStoreWithBuffer(){ @@ -192,7 +205,7 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple putMemSize.getAndAdd(size); } - + profiling(data, OP.PUT); // tell other threads that store is not empty notEmpty.signal(); } @@ -278,7 +291,7 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple // 提取数据并返回 for (; next <= end; next++) { Event event = entries[getIndex(next)]; - if (ddlIsolation && isDdl(event.getEntry().getHeader().getEventType())) { + if (ddlIsolation && isDdl(event.getEventType())) { // 如果是ddl隔离,直接返回 if (entrys.size() == 0) { entrys.add(event);// 如果没有DML事件,加入当前的DDL事件 @@ -297,7 +310,7 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple for (; memsize <= maxMemSize && next <= maxAbleSequence; next++) { // 永远保证可以取出第一条的记录,避免死锁 Event event = entries[getIndex(next)]; - if (ddlIsolation && isDdl(event.getEntry().getHeader().getEventType())) { + if (ddlIsolation && isDdl(event.getEventType())) { // 如果是ddl隔离,直接返回 if (entrys.size() == 0) { entrys.add(event);// 如果没有DML事件,加入当前的DDL事件 @@ -325,9 +338,9 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple for (int i = entrys.size() - 1; i >= 0; i--) { Event event = entrys.get(i); - if (CanalEntry.EntryType.TRANSACTIONBEGIN == event.getEntry().getEntryType() - || CanalEntry.EntryType.TRANSACTIONEND == event.getEntry().getEntryType() - || isDdl(event.getEntry().getHeader().getEventType())) { + // GTID模式,ack的位点必须是事务结尾,因为下一次订阅的时候mysql会发送这个gtid之后的next,如果在事务头就记录了会丢这最后一个事务 + if ((CanalEntry.EntryType.TRANSACTIONBEGIN == event.getEntryType() && StringUtils.isEmpty(event.getGtid())) + || CanalEntry.EntryType.TRANSACTIONEND == event.getEntryType() || isDdl(event.getEventType())) { // 将事务头/尾设置可被为ack的点 range.setAck(CanalEventUtils.createPosition(event)); break; @@ -337,6 +350,7 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple if (getSequence.compareAndSet(current, end)) { getMemSize.addAndGet(memsize); notFull.signal(); + profiling(result.getEvents(), OP.GET); return result; } else { return new Events(); @@ -348,17 +362,17 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple lock.lock(); try { long firstSeqeuence = ackSequence.get(); - if (firstSeqeuence == INIT_SQEUENCE && firstSeqeuence < putSequence.get()) { + if (firstSeqeuence == INIT_SEQUENCE && firstSeqeuence < putSequence.get()) { // 没有ack过数据 Event event = entries[getIndex(firstSeqeuence + 1)]; // 最后一次ack为-1,需要移动到下一条,included // = false return CanalEventUtils.createPosition(event, false); - } else if (firstSeqeuence > INIT_SQEUENCE && firstSeqeuence < putSequence.get()) { + } else if (firstSeqeuence > INIT_SEQUENCE && firstSeqeuence < putSequence.get()) { // ack未追上put操作 Event event = entries[getIndex(firstSeqeuence + 1)]; // 最后一次ack的位置数据 // + 1 return CanalEventUtils.createPosition(event, true); - } else if (firstSeqeuence > INIT_SQEUENCE && firstSeqeuence == putSequence.get()) { + } else if (firstSeqeuence > INIT_SEQUENCE && firstSeqeuence == putSequence.get()) { // 已经追上,store中没有数据 Event event = entries[getIndex(firstSeqeuence)]; // 最后一次ack的位置数据,和last为同一条,included // = false @@ -377,10 +391,10 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple lock.lock(); try { long latestSequence = putSequence.get(); - if (latestSequence > INIT_SQEUENCE && latestSequence != ackSequence.get()) { + if (latestSequence > INIT_SEQUENCE && latestSequence != ackSequence.get()) { Event event = entries[(int) putSequence.get() & indexMask]; // 最后一次写入的数据,最后一条未消费的数据 return CanalEventUtils.createPosition(event, true); - } else if (latestSequence > INIT_SQEUENCE && latestSequence == ackSequence.get()) { + } else if (latestSequence > INIT_SEQUENCE && latestSequence == ackSequence.get()) { // ack已经追上了put操作 Event event = entries[(int) putSequence.get() & indexMask]; // 最后一次写入的数据,included // = @@ -408,8 +422,15 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple boolean hasMatch = false; long memsize = 0; + // ack没有list,但有已存在的foreach,还是节省一下list的开销 + long localExecTime = 0L; + int deltaRows = 0; for (long next = sequence + 1; next <= maxSequence; next++) { Event event = entries[getIndex(next)]; + if (localExecTime == 0 && event.getExecuteTime() > 0) { + localExecTime = event.getExecuteTime(); + } + deltaRows += event.getRowsCount(); memsize += calculateSize(event); boolean match = CanalEventUtils.checkPosition(event, (LogPosition) position); if (match) {// 找到对应的position,更新ack seq @@ -425,11 +446,14 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple if (ackSequence.compareAndSet(sequence, next)) {// 避免并发ack notFull.signal(); + ackTableRows.addAndGet(deltaRows); + if (localExecTime > 0) { + ackExecTime.lazySet(localExecTime); + } return; } } } - if (!hasMatch) {// 找不到对应需要ack的position throw new CanalStoreException("no match ack position" + position.toString()); } @@ -453,9 +477,9 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple final ReentrantLock lock = this.lock; lock.lock(); try { - putSequence.set(INIT_SQEUENCE); - getSequence.set(INIT_SQEUENCE); - ackSequence.set(INIT_SQEUENCE); + putSequence.set(INIT_SEQUENCE); + getSequence.set(INIT_SEQUENCE); + ackSequence.set(INIT_SEQUENCE); putMemSize.set(0); getMemSize.set(0); @@ -532,7 +556,7 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple private long calculateSize(Event event) { // 直接返回binlog中的事件大小 - return event.getEntry().getHeader().getEventLength(); + return event.getRawLength(); } private int getIndex(long sequcnce) { @@ -545,7 +569,49 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple || type == EventType.DINDEX; } + private void profiling(List events, OP op) { + long localExecTime = 0L; + int deltaRows = 0; + if (events != null && !events.isEmpty()) { + for (Event e : events) { + if (localExecTime == 0 && e.getExecuteTime() > 0) { + localExecTime = e.getExecuteTime(); + } + deltaRows += e.getRowsCount(); + } + } + switch (op) { + case PUT: + putTableRows.addAndGet(deltaRows); + if (localExecTime > 0) { + putExecTime.lazySet(localExecTime); + } + break; + case GET: + getTableRows.addAndGet(deltaRows); + if (localExecTime > 0) { + getExecTime.lazySet(localExecTime); + } + break; + case ACK: + ackTableRows.addAndGet(deltaRows); + if (localExecTime > 0) { + ackExecTime.lazySet(localExecTime); + } + break; + default: + break; + } + } + + private enum OP { + PUT, GET, ACK + } + // ================ setter / getter ================== + public int getBufferSize() { + return this.bufferSize; + } public void setBufferSize(int bufferSize) { this.bufferSize = bufferSize; @@ -563,4 +629,57 @@ public class MemoryEventStoreWithBuffer extends AbstractCanalStoreScavenge imple this.ddlIsolation = ddlIsolation; } + public boolean isRaw() { + return raw; + } + + public void setRaw(boolean raw) { + this.raw = raw; + } + + public AtomicLong getPutSequence() { + return putSequence; + } + + public AtomicLong getAckSequence() { + return ackSequence; + } + + public AtomicLong getPutMemSize() { + return putMemSize; + } + + public AtomicLong getAckMemSize() { + return ackMemSize; + } + + public BatchMode getBatchMode() { + return batchMode; + } + + public AtomicLong getPutExecTime() { + return putExecTime; + } + + public AtomicLong getGetExecTime() { + return getExecTime; + } + + public AtomicLong getAckExecTime() { + return ackExecTime; + } + + public AtomicLong getPutTableRows() { + return putTableRows; + } + + public AtomicLong getGetTableRows() { + return getTableRows; + } + + public AtomicLong getAckTableRows() { + return ackTableRows; + } + + } diff --git a/store/src/main/java/com/alibaba/otter/canal/store/model/Event.java b/store/src/main/java/com/alibaba/otter/canal/store/model/Event.java index c31d37f3..db1618e1 100644 --- a/store/src/main/java/com/alibaba/otter/canal/store/model/Event.java +++ b/store/src/main/java/com/alibaba/otter/canal/store/model/Event.java @@ -1,12 +1,16 @@ package com.alibaba.otter.canal.store.model; import java.io.Serializable; +import java.util.List; import org.apache.commons.lang.builder.ToStringBuilder; import com.alibaba.otter.canal.common.utils.CanalToStringStyle; import com.alibaba.otter.canal.protocol.CanalEntry; +import com.alibaba.otter.canal.protocol.CanalEntry.EntryType; +import com.alibaba.otter.canal.protocol.CanalEntry.EventType; import com.alibaba.otter.canal.protocol.position.LogIdentity; +import com.google.protobuf.ByteString; /** * store存储数据对象 @@ -18,14 +22,58 @@ public class Event implements Serializable { private static final long serialVersionUID = 1333330351758762739L; private LogIdentity logIdentity; // 记录数据产生的来源 + private ByteString rawEntry; + + private long executeTime; + private EntryType entryType; + private String journalName; + private long position; + private long serverId; + private EventType eventType; + private String gtid; + private long rawLength; + private int rowsCount; + + // ==== https://github.com/alibaba/canal/issues/1019 private CanalEntry.Entry entry; public Event(){ } public Event(LogIdentity logIdentity, CanalEntry.Entry entry){ + this(logIdentity, entry, true); + } + + public Event(LogIdentity logIdentity, CanalEntry.Entry entry, boolean raw){ this.logIdentity = logIdentity; - this.entry = entry; + this.entryType = entry.getEntryType(); + this.executeTime = entry.getHeader().getExecuteTime(); + this.journalName = entry.getHeader().getLogfileName(); + this.position = entry.getHeader().getLogfileOffset(); + this.serverId = entry.getHeader().getServerId(); + this.gtid = entry.getHeader().getGtid(); + this.eventType = entry.getHeader().getEventType(); + if (entryType == EntryType.ROWDATA) { + List props = entry.getHeader().getPropsList(); + if (props != null) { + for (CanalEntry.Pair p : props) { + if ("rowsCount".equals(p.getKey())) { + rowsCount = Integer.parseInt(p.getValue()); + break; + } + } + } + } + + if (raw) { + // build raw + this.rawEntry = entry.toByteString(); + this.rawLength = rawEntry.size(); + } else { + this.entry = entry; + // 按照6倍的event length预估 + this.rawLength = entry.getHeader().getEventLength() * 6; + } } public LogIdentity getLogIdentity() { @@ -36,6 +84,86 @@ public class Event implements Serializable { this.logIdentity = logIdentity; } + public ByteString getRawEntry() { + return rawEntry; + } + + public void setRawEntry(ByteString rawEntry) { + this.rawEntry = rawEntry; + } + + public long getExecuteTime() { + return executeTime; + } + + public void setExecuteTime(long executeTime) { + this.executeTime = executeTime; + } + + public EntryType getEntryType() { + return entryType; + } + + public void setEntryType(EntryType entryType) { + this.entryType = entryType; + } + + public String getJournalName() { + return journalName; + } + + public void setJournalName(String journalName) { + this.journalName = journalName; + } + + public long getPosition() { + return position; + } + + public void setPosition(long position) { + this.position = position; + } + + public long getServerId() { + return serverId; + } + + public void setServerId(long serverId) { + this.serverId = serverId; + } + + public String getGtid() { + return gtid; + } + + public void setGtid(String gtid) { + this.gtid = gtid; + } + + public long getRawLength() { + return rawLength; + } + + public void setRawLength(long rawLength) { + this.rawLength = rawLength; + } + + public EventType getEventType() { + return eventType; + } + + public void setEventType(EventType eventType) { + this.eventType = eventType; + } + + public int getRowsCount() { + return rowsCount; + } + + public void setRowsCount(int rowsCount) { + this.rowsCount = rowsCount; + } + public CanalEntry.Entry getEntry() { return entry; } @@ -47,4 +175,5 @@ public class Event implements Serializable { public String toString() { return ToStringBuilder.reflectionToString(this, CanalToStringStyle.DEFAULT_STYLE); } + } diff --git a/store/src/test/java/com/alibaba/otter/cancel/store/memory/buffer/MemoryEventStoreMultiThreadTest.java b/store/src/test/java/com/alibaba/otter/cancel/store/memory/buffer/MemoryEventStoreMultiThreadTest.java index 4209e4f1..9aa216f6 100644 --- a/store/src/test/java/com/alibaba/otter/cancel/store/memory/buffer/MemoryEventStoreMultiThreadTest.java +++ b/store/src/test/java/com/alibaba/otter/cancel/store/memory/buffer/MemoryEventStoreMultiThreadTest.java @@ -161,13 +161,12 @@ public class MemoryEventStoreMultiThreadTest extends MemoryEventStoreBase { first = entrys.getPositionRange().getEnd(); for (Event event : entrys.getEvents()) { - this.result.add(event.getEntry().getHeader().getLogfileOffset()); + this.result.add(event.getPosition()); } emptyCount = 0; - System.out.println("offest : " - + entrys.getEvents().get(0).getEntry().getHeader().getLogfileOffset() - + " , count :" + entrys.getEvents().size()); + System.out.println("offest : " + entrys.getEvents().get(0).getPosition() + " , count :" + + entrys.getEvents().size()); ackCount++; if (ackCount == 1) { eventStore.cleanUntil(entrys.getPositionRange().getEnd());