Hadoop数据迁移(集群内迁移,集群间迁移),主要通过拷贝数据来完成。对于小量数据,可以使用"hadoop fs -cp"来完成;对于大量数据,可以借助Distcp 来完成。
Distcp介绍
Distcp是Hadoop自带的分布式拷贝工具。它基于MapReduce实现,将需要拷贝的源数据尽量平均地split到多个map中,每个map将负责的split拷贝到目的集群上,最终利用了MapReduce的优势加速了拷贝(相对于"hadoop fs -cp"的单线程拷贝)。
用法
首先需登录目标服务器或者客户端
$
ssh hadoop
-0249
$
cd
$HADOOP_HOME
~HADOOP_HOME $ bin
/hadoop
distcp hdfs:
//hadoop-0001
:29000
/distcptest/abc
/distcptest/
如有资源池调度器
~HADOOP_HOME $ bin
/hadoop
distcp -Dmapred.queue.name=test hdfs:
//hadoop-0249
:29000
/test/input/test2
.log.lzo
/test/input/test2
.log.lzo
|
上面命令利用distcp将hadoop-0001集群上的/distcptest/abc目录拷贝到了hadoop-0249集群的/distcptest目录下。
选项
-p [rbugp] | 保持文件的备份数(r)/块大小(b)/用户(b)/组(g)/权限(p) |
-i | 忽略拷贝错误(否则会终止拷贝,长时间的distcp一般加上此选项,个别错误可用-update选项修复) |
-log | 指定distcp的日志目录(不指定的话,在目的目录下生成,一般使用默认即可) |
-m <num_maps> | distcp的map数量(如果想控制并发度) |
-overwrite | 覆盖拷贝(谨慎使用!拷贝语义发生变化,见注意事项) |
-update | 更新拷贝(谨慎使用!拷贝语义发生变化,见注意事项)。默认情况下比较两个文件大小是否一样,如果一样,并且有CRC checksum,则再比较CRC |
-f | 指定包含需要拷贝的文件列表的文件 |
-delete | 删除目的目录多余的文件(源端没有的) |
注意事项
拷贝语义
distcp的拷贝语义,跟Unix下的cp很像。下面以几个例子说明。
- /src/aa 拷贝至 /dest/aa
如果/dest/aa存在,则/src/aa拷贝成/dest/aa/aa
如果/dest/aa不存在,则/src/aa拷贝成/dest/aa - /src/aa, /src/bb 拷贝至 /dest/aa
无论/dest/aa存在或不存在,始终拷贝成/dest/aa/aa, /dest/aa/bb - /src/aa 更新/覆盖拷贝(-update/-overwrite) 至 /dest/aa
无论/dest/aa存在不存在,始终拷贝成/dest/aa - /src/aa, /src/bb 更新/覆盖拷贝至 /dest/aa
同上,但是,如果/src/aa和/src/bb下有同名的文件,那么就会引起冲突,报错。
关闭Speculative Execution
如果mapred.speculative.execution为true,而且被设置成final,那么distcp行为将不可预测。所以,至少不要将mapred.speculative.execution设置成final.
版本差异
对于RPC不兼容的Hadoop版本,不能直接使用hdfs://协议进行distcp。而是必须在目的集群上,使用hftp://来进行拷贝。譬如源集群的Hadoop版本为0.19.x,而目的集群的Hadoop版本为0.20.2-cdh3u4,那么使用distcp时,可以:
# 登录目的集群
~HADOOP_HOME $ bin
/hadoop
distcp hftp:
//src-namenode
:29005
/aa
/aa
# 注:29005为dfs.http.address的端口
|