HDFS:解决HDFS跨版本兼容问题

[size=medium]
HDFS提供用户客户端服务,在协助用户操作集群数据的同时,内部也包含大量的控制逻辑。这样我们就可以把HDFS客户端理解为两部分:一部分提供客户调用,另外一部分属于HDFS内部,作为集群的入口,与NameNode与DataNode通信,并且不同的HDFS版本有不同的通信接口。下面是一张HDFS的客户端模型,可以让大家对它的客户端有清晰的认识。[/size]
[img]http://dl.iteye.com/upload/attachment/557696/a5f2cf63-7fbb-3b69-be55-0696c0a3cf6c.jpg[/img]
[size=medium]
这里我们把整个HDFS变透明,只知道客户端与它的交互是通过RPC(与DataNode的数据传输是通过二进制流,一些相应的方法调用也是通过RPC,简化起见,我们说客户端与整个HDFS的交互都是RPC)。RPC的请求是需要验证版本号的,因为不同版本的server或client可能有接口差异、实现逻辑区别,就连某些存储结构的布局都可能不甚相同。所以在RPC交互中一定得保证客户端与服务端(NameNode/DataNode)有相同的版本号。

正常情况下,每个HDFS的release会被指定RPC版本号,它属于HDFS的一部分,对用户不可见。如果每个集群都有相同的HDFS RPC版本,自然不用担心。但事实上,我们可能拥有不同版本的HDFS集群,且集群间的数据传输也不可避免。如果强行使用某个版本的HDFS集群访问其它版本的服务端,就会碰到VersionMismatch异常信息,表明客户端与服务端版本不一致,无法进行数据交互。

HDFS的开发人员也意识到这种问题的存在,他们推出了[url=http://hadoop.apache.org/hdfs/docs/r0.21.0/hdfsproxy.html]HDFS proxy[/url]方案。这种方案利用了Servlet容器(Tomcat/Jetty等)来管理不同RPC版本的HDFS客户端,因为处于容器的管理之下,不同版本的客户端自然被不同的classloader管理着,利用HTTP/HPPTS forward功能完成用户请求的转发。随之而来的问题是,当前HDFS只响应HTTPS请求(HDFS的HSFTP协议),且不能灵活的操纵数据。可能最让我头痛的是一大堆与HTTPS权限相关的配置及jar文件部署,相当地折腾。

Cloudera也在此HDFS proxy基础上作了一些改进,换名为[url=http://www.cloudera.com/blog/2011/07/hoop-hadoop-hdfs-over-http/]Hoop[/url],但实现细节与HDFS proxy无二般区别。

在此两种方案的基础上可以考虑下,HDFS为了解决多版本兼容问题而引入Servlet容器,就是想利用容器的多classloader机制,分别管理不同版本的客户端,然后将请求forward到正确的客户端。明白这个初衷后,我们实现了自己的多classloader方案,完全摈弃Servlet的引入及令人头痛的各种配置。它的基本结构如下图[/size]
[img]http://dl.iteye.com/upload/attachment/557691/8aa8cb92-84c0-3447-b4db-9257f5e0261a.jpg[/img]
[size=medium]
平时我们对HDFS的操作就是这些基本的如open, create, append, status等,完全可以将这些基本操作抽象成特定的接口,就是图中黄色标识的HDFS Abstract Interface,不管是哪个版本,都得实现这个特定接口的每个操作。与这个接口相关的业务逻辑处理都可以归结为一层,这层由system classloader加载,与HDFS无任何关系,用户只是看到这个接口,然后调用相应的逻辑。这层的控制逻辑主要是这样:把哪些数据从哪个集群迁移到哪个集群,并且处理各种异常情况。

每个版本的HDFS由不同的classloader加载并管理,同时也包含着HDFS Abstract Interface的不同实现,每个选定版本都创建独立的FileSystem,并调用与之处于同一classloader的HDFS客户端,这些客户端的配置(core-site.xml)指向相同版本的HDFS集群。可以说,像图中的v1-impl,v2-impl都是一层真实版本的代理,让真正的调用者(由system classloader管理)不用顾忌版本之间的区别。

依这种实现方式的话,我们需要做的事情是:1. 为每个版本的HDFS jar添加配置文件core-site.xml,指向相应版本的HDFS集群;2. 实现system classloader管理的这层的业务逻辑,制订统一接口;3. 对于各个HDFS版本,创建自己的接口实现类。这样就用简洁的方式替代了Servlet容器的引入及配置,可以用独立进程或嵌入其它组件的方式运行此系统。

当然它解决的不限于跨版本问题,跨集群,跨DC也同样适用。在此之上可以开发独立控制组件来完善相应的功能。[/size]
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值