DataX 官网地址 https://maxwells-daemon.io/
DataX GitHub源码地址 https://github.com/alibaba/DataX
DataX 是Alibaba集团下阿里云 DataWorks数据集成的开源版本,用作异构数据源离线同步工具或平台;其实现了如 MySQL、Oracle、OceanBase、SqlServer、Postgre、HDFS、Hive、HBase、ClickHouse 等各种异构数据源之间稳定高效的数据同步功能。本文全部内容只对最新框架3.0系列说明,最新版本为datax_v202210
为了解决异构数据源同步问题,DataX将复杂的网状的同步链路变成了星型数据链路,DataX作为中间传输载体负责连接各种数据源。当需要接入一个新的数据源的时候,只需要将此数据源对接到DataX,便能跟已有的数据源做到无缝数据同步;基于插件式扩展能力上可以说DataX框架具备支持任意数据源类型的数据同步工作的能力。
Apache Sqoop™是一种用于在Apache Hadoop和结构化数据存储(如关系数据库)之间高效传输批量数据的工具,最新的稳定版本是1.4.7,而其Sqoop2的最新版本是1.99.7,但是1.99.7与1.4.7不兼容,而且特性不完整,因此Sqoop2不用于生产部署。Sqoop1.4.7在2017年后就没有再更新,不是说Sqoop不好,是官方已没有需要修复的问题,稳定,据说项目PMC也都解散了。如果业务只需要对关系数据库同步的HDFS(还包括hive、hbase),使用sqoop也是可以的。Sqoop也可以实现增量数据同步,比如通过查询的sql中增加时间过滤字段,也可以结合自身job记住带有单调递增的编号字段实现增量同步。
虽然说DataX是单机版压力大,但可以通过手工调度系统布置多个节点分开配置来实现类似多台分布式处理,提高处理能力。
DataX框架设计也比较简单,与其他数据采集框架如Flume相似,采用Framework + plugin架构构建;将数据源读取和写入抽象成为Reader/Writer插件,纳入到整个同步框架中。
DataX目前已经有了比较全面的插件体系,主流的RDBMS数据库、NOSQL、大数据、时序数据库等都已经接入;DataX Framework提供了简单的接口与插件交互,提供简单的插件接入机制,只需要任意加上一种插件,就能无缝对接其他数据源,具体数据源使用说明根据需要点击读或写查看使用详细介绍。下面支持类型就在DataX GitHub主页READERME上。
DataX 支持单机多线程模式完成同步作业运行,这里以一个DataX作业生命周期的时序图,从整体架构设计非常简要说明DataX各个模块相互关系。
核心模块介绍:
DataX调度流程拿一个举例,比如用户提交了一个DataX作业并配置了20个并发,目的是将一个100张分表的mysql数据同步到odps里面。 DataX的调度决策思路是:
# 下载最新版本datax_v202210的datax
wget https://datax-opensource.oss-cn-hangzhou.aliyuncs.com/202210/datax.tar.gz
# 解压文件
tar -xvf datax.tar.gz
# 进入根目录
cd datax/
# 自检脚本
python ./bin/datax.py ./job/job.json
创建json格式作业的配置文件,可以通过查看配置模板示例
python bin/datax.py -r streamreader -w streamwriter
在job目录下创建stream2stream.json,vim stream2stream.json
{
"job": {
"content": [
{
"reader": {
"name": "streamreader",
"parameter": {
"sliceRecordCount": 10,
"column": [
{
"type": "long",
"value": "10"
},
{
"type": "string",
"value": "hello,welcome to DataX"
}
]
}
},
"writer": {
"name": "streamwriter",
"parameter": {
"encoding": "UTF-8",
"print": true
}
}
}
],
"setting": {
"speed": {
"channel": 5
}
}
}
}
# 执行job
python bin/datax.py job/stream2stream.json
可以通过GitHub找到支持数据通道并通过查阅读、写相关文档,非常详细,不仅包含实现原理、功能说明、约束限制,还对每一种数据通道提供了性能测试报告,可见DataX是把性能做到了极致。参数的说明
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gtc3fCRv-1671803026649)(image-20221223135319256.png)]
需要同步数据表为test数据库的student表
在job目录下创建mysql2hdfs.json,vim job/mysql2hdfs.json
{
"job": {
"content": [
{
"reader": {
"name": "mysqlreader",
"parameter": {
"column": [
"id",
"name",
"age"
],
"connection": [
{
"jdbcUrl": ["jdbc:mysql://hadoop3:3308/test"],
"table": ["student"]
}
],
"password": "123456",
"username": "root"
}
},
"writer": {
"name": "hdfswriter",
"parameter": {
"column": [
{
"name": "id",
"type": "INT"
},
{
"name": "name",
"type": "STRING"
},
{
"name": "age",
"type": "INT"
}
],
"defaultFS": "hdfs://hadoop1:9000",
"fieldDelimiter": "\t",
"fileName": "student.txt",
"fileType": "text",
"path": "/",
"writeMode": "append"
}
}
}
],
"setting": {
"speed": {
"channel": "1"
}
}
}
}
# 执行job
python bin/datax.py job/mysql2hdfs.json
从控制台的日志打印可以看到这个job写入hdfs时先写入临时文件,全部成功则修改文件名和路径;如果个别失败则整个job失败,删除临时路径。查看hdfs上可以看到文件已经写入成功,并且固定加了一串后缀
点击文件查看内容和间隔符也是正确的
如果是HA模式可以hadoopConfig里配置
"hadoopConfig":{
"dfs.nameservices": "testDfs",
"dfs.ha.namenodes.testDfs": "namenode1,namenode2",
"dfs.namenode.rpc-address.aliDfs.namenode1": "",
"dfs.namenode.rpc-address.aliDfs.namenode2": "",
"dfs.client.failover.proxy.provider.testDfs": "org.apache.hadoop.hdfs.server.namenode.ha.ConfiguredFailoverProxyProvider"
}
创建一张同样表结构的student1表,在job目录下创建hdfs2mysql.json,vim job/hdfs2mysql.json
{
"job": {
"content": [
{
"reader": {
"name": "hdfsreader",
"parameter": {
"column": ["*"],
"defaultFS": "hdfs://hadoop1:9000",
"encoding": "UTF-8",
"fieldDelimiter": "\t",
"fileType": "text",
"path": "/student.txt__6eeb1730_21bd_40e9_a360_16de5396b140"
}
},
"writer": {
"name": "mysqlwriter",
"parameter": {
"column": [
"id",
"name",
"age"
],
"connection": [
{
"jdbcUrl": "jdbc:mysql://hadoop3:3308/test?useUnicode=true&characterEncoding=gbk",
"table": ["student1"]
}
],
"password": "123456",
"username": "root",
"writeMode": "insert"
}
}
}
],
"setting": {
"speed": {
"channel": "1"
}
}
}
}
# 由于我的mysql是8,因此需要将plugin/writer/mysqlwriter/libs的mysql-connector-java-5.1.47.jar替换为高版本,这里就直接使用mysql-connector-java-8.0.29.jar
rm plugin/writer/mysqlwriter/libs/mysql-connector-java-5.1.47.jar
cp mysql-connector-java-8.0.29.jar plugin/writer/mysqlwriter/libs/
# 执行job
python bin/datax.py job/hdfs2mysql.json
查看student1表已经有4条包含指定3个字段的数据