|
ETL工具设计之一 - 最终幻想ETL工具的使用者是谁?
一直以来,我都有一个想法,开发一个易于部署、使用的ETL工具,弱化ETL工程师的责任,转换规则、映射关系由数据仓库设计人员自己来实现,目前已经有了比较清晰的方案,无论是前台界面还是后台结构,都初见雏形。但需要较多的人力、物力,个人是无法完成的。同时也很想证实一下,方案是不是合理,毕竟我经历了一个在ETL上遇到很大困难的BI项目和其他几个小项目,参与过数据仓库建设,维护过一个很难使用的ETL工具,参加了一个极度延时的ETL工具开发项目,经历了这么多的磨难,对ETL工具开发这块至少是积累了不少的行业经验,同时也从客户那里直接获得了不少的需求,对于功能的取舍相对理性。
在ETL中,有两种图,一种是“控制流程图”,另外一个是“数据流程图”。
但“数据流程图”比较少见,一般在元数据中见的比较多。这种图,关注的是数据之间的依赖关系。比如一张A表,其数据的来源是哪里,又派生出来多少数据集,派生的依据是什么。由于此图清晰的描述了数据之间的关系,在数据仓库应用中有着至关重要的作用。我刚到中国移动省级项目组时,要为一级经营分析准备数据,但当时,对业务的理解非常弱,面对纷乱复杂的数据流,根本不知道从哪里下手,每次都要问一经的负责人。现在看来,如果在ETL中提供了数据流的描述,效率要高很多。后来,新到的项目总监安排了一个人专门绘制这样图,项目组获益非常大。
个人认为做为数据仓库驱动器的ETL工具,应该能够清晰的展现数据流图。目前绝大多数ETL工具的调度图都是按照抽取、转换、装载和清洗4大步骤展现,如此并没有大的错误,但没有真正理解ETL工具存在的最终目的。这些步骤只是手段,但最终目的是为了建设、维护数据仓库。因此,在ETL中至少应该看到如下的数据流图。
在ETL工具中,对数据流进行描述是不是很困难?我看未必!目前,数据流向无非4种:表→表,表→文件,文件→表,文件→文件,应该很容易定义才对。元数据其实就是干这个工作的!如果能借鉴元数据,应该不难实现。个人认为难点在于与ETL本身的调度联系起来,对调度策略会有一些特殊的要求。一个大的数据流动才定为一个job,比如从接口到表,虽然经过了转换、清洗、装载,但这个步骤都只为一个目的服务:将数据从接口装入到表,因此可以定为一个job,而不是象常见的ETL工具,定为3个job,否则就割裂了之间的联系,不便于描述数据流向。我曾看过另外一个公司的中国移动经营分析项目资料,从接口层到dw层,足有500多个任务,并以此做为宣传点。乍一看,觉得很专业,但做久了之后,觉得很不可思议,简直就是自讨苦吃,不仅割裂了数据之间的联系,也增加了维护难度,每修改一个接口都必须同时修改3处地方,苦不堪言。我以前使用的一个ETL工具也是采用类似的方法,吃尽了苦头。
ETL工具设计之二-狐妖之惑
开发ETL工具时,都会设计出4个步骤,extract(抽取)、transfer(转换)、clean(清洗)和load(装载)。但最重要的步骤是哪个?
我想,目前90%以上的ETL工具开发人员都会认为是转换。一年前的我也是这么认为,但当我在项目组呆了一段时间,亲自参与了数据仓库建设,再也不这样想了。按重要程度递减排序,分别是load(装载)、clean(清洗)、transfer(转换)、extract(抽取)。当时在这个中国移动省级经营分析项目,用到的转换一般都是substr和trim,很少再用到其他的特殊转换。实际上,在数据仓库中,尽量避免使用复杂的转换,要不然,转的面目全非了,谁都头痛,最常见的不过是维表转换,但这个可以使用数据库的存储过程来实现,简单而且有效。
ETL工具设计之三–文件格式
一张表,怎么表示才不会导致数据错误?
常见的有两种方式:
字符分割法:用特殊字符做分割,比较常见的是“ | ”符号,简单有效,但缺陷也是极其明显,一旦在数据中有分割符,将导致数据错误!
定长分割法:数据库中,字段的长度是固定的,只要设计得当,总能正确无误的描述所有的数据,但这个方法有一个很大的缺陷,很难表示blob字段。
如果是开发ETL工具,用上面的方法明显是行不通的,我使过的一个ETL工具,也没有解决这个问题,但我后来辞职研究了一段时间的系统内核,研究了文件格式,发现AT&T实验室早就解决了数据展现的问题,因此,我模拟COFF文件格式,初步设计了一个新的文件格式,用来展现表状数据,以解决数据描述的问题,在文件中,各节之间使用0x0来做分割。
这样做,可能会带来数据量的问题,需要传送的数据成倍的增加。以一个字段为8字节计算,在32位机器上,字节数会增加2倍多一点。我以前所接触的数据,每天可达到
上面的设计,还不是很完善,如果需要在多平台下运行,必须指定结构的长度。大部分情况下,ETL程序会在不同的主机上同时运行,但这些主机型号不一定完全相同,对类型的解释就有可能不同,比如在32位和64位下, 对int类型的解释就有可能不一样。
ETL工具设计之四-万流归海
网络编程其实是很大的一块,很需要设计功力,虽然我以前没有写过一行网络代码,但还是想尝试一下,在各位大大面前献丑了!勿怪!
首先,我觉得网络数据传送机制和CPU中断处理机制极其相似:
我把网络模块设计成如下结构:
操作系统传输层: 此层实现socket所有的功能。
传输控制层:ETL运行时,由于各模块处理速度不同,有可能产生数据拥塞。比如,转换的速度一般来讲都是要远大于装载速度,转换结束后,如果不加限制的传给装载模块,在装载部分就会产生数据积压,因此需要一种机制抑止此种情况的发生。
我目前想到的是采用应答机制,发送端有数据需要发送时,就向接受端发送一个有数据的信号。接受端接到信号后,就将这个发送端的状态置为有数据状态。以后接受端认为自己可以接受新的数据了,就向发送端发送一个可以发送数据的消息,发送端接到这个消息后,然后发送数据。同样,对于消息的处理,也采用同样的机制。其实这种控制机制是借鉴了linux的中断处理机制,与之很类似。
数据拼装/切割层: 在底层socket,每次用send函数发送的数据包,一般不会超过2k大小,在ETL中,一般需要处理上G的数据,很多时候,单条记录都会超过2k,这时,就需要一个层次来拼装/切割上层应用程序的数据。比如最上层数据处理模块要求一次性的发送
不过,在这层,会有一个隐患。在程序中,有一个原则,尽量不要动态的 分配/释放内存,我以前在编写内核调试器的时候,做到了这一点,内存只申请一次,以后循环使用。但使用上面的设计,达不到这个要求,必须动态分配内存,因为有一个条件限制:接受端是无法预测发送端会发送多少数据!比如,BLOB字段,你就不知道他有多大,我曾见过一张表,它有一个BLOB字段,里面存放了日志文件,很多都超过了
解析层: 接受到数据后,需要判断是命令还是纯数据,并由此分发到不同的模块
实际上,网络编程还有一个问题,如果接受端的内存过小,会出现数据截断。例如:
A: 发送端
B: 接受端 A向B发送两条记录,每条记录各100字节,共200字节,B端的操作系统会将这200字节缓存起来。此时,运行在B上应用程序,用recv(sockfd,pBuf, 150, flags);函数接受数据,这个时候,只读出了150个字节,产生数据截断,第二条记录将出现问题。对于这个问题,最简单的解决办法是双方约定最大发送的字节数, 比如,在上面的例子中,如果A,B已经约定最大可以发送150字节,则A需要发送两次,每发送100字节,即一条记录。
ETL工具设计之五-初见雏形
对于整个ETL程序框架,你会怎么设计?
我的设计如下:
这里将任务执行器和任务驱动器分开,本来,也可以设计成整体,但我总觉得分开为好,一个模块只做一件事情,便于控制和处理。 上面这副图没有什么新意,估计绝大多数ETL工具都会设计成这样,呵呵,献丑了!
然后呢,谈谈各部分的特点
但是,如果不是象我在另外一篇文章《在合适的地方使用合适的技术》中说的那样BT,还是有一些规律可寻的。常见的文件效验无非是个数、字节数两类。做一个统一的界面还是可以对付的。
转换模块(transfer): 我对转换的定义比较广泛,将清洗(clean)部分也看作是转换的一部分,觉得简单。对于这部分,没有什么特别的要求,有substr和trim功能就心满意足了。其他更高、更复杂的转换函数,等有人力物力的时候再开发吧。当然NULL值过滤功能是少不了的。
装载模块(load): 这个部分最影响ETL性能,速度一般只有转换的1/5。而且这一部分,必须自己写装载程序,不能依赖数据本身的工具。有一个ETL工具在ORACLE环境下运行时,就是调用的SQLLDR装载,一旦启动就没有办法控制,直到SQLLDR退出,真郁闷。这部分的速度达到30万条/分钟就可以了,即使每天4千万的数据量,2个小时多一点就可以搞定。
统计模块(statistic): 一般的ETL工具没有直接提出来这个功能,我自己加上的。有一段时间,客户突然对数据质量重视起来,天天向我要统计数据,比如源记录多少啊,转换丢失了多少,装载丢失了多少,库中有多少,后来又进行了KPI效验。这个模块可以最直接的反应出数据质量问题,将记录数一比照,问题一目了然。
最后呢,让我来策一策怎么将这些模块拼装起来。无论是抽取,转换,还是清洗,都有一个特点,其功能都是不定的,而且可以拆分。我想将这些功能都独立开来,每个功能一个动态链接库,并且按统一的规则输出函数,比如每次动态链接库都必须有数据出口、数据入口、初始化和停止函数。运行时,根据配置动态的加载。这么做,有一个最大的好处,可以减少网络传送量,按逻辑设计,每个功能都应该非常独立,都是通过socket连接起来,有多少个功能就要传送多少次,有点过分!
以下是个人观点,也是自己经验的总结,在很多地方都不适用,权当参考。
在转换中, 不应该提供排序之类的多记录关联操作,至少是在初始版本中不提供。从我第一天接触ETL开始,就持有这个观点。觉得这样的功能放在ETL工具中有点不可理解。数据在数据库存放时,数据库会做优化,犯不着ETL工具操心,而且数据库的算法一般很先进,比ETL工具高了不止一点点,同时,数据库服务器比ETL服务器一般都要高一个档次。另外一个原因,开发这样的功能,需要优秀的算法工程师,非常人所能为,耗时耗力,从整个ETL工具开发项目的来讲,觉得不值。但如果志向远大,一定要与datastage之类的专业软件比肩,转换部分应该向内存数据库靠拢,可以实现在工具中做汇总。这样,你的对手就不只是datastage之类专业的ETL工具了,还增加了oracle,db2这些数据库厂商。
个人认为,开发复杂的转换模块,还不如开发功能强大的质量控制模块有意义,对项目的支持也更大。BI项目进行到后期,数据质量问题应该会成为一个焦点。以前参与过的几个项目,也出了不少的报表、分析数据,我一直怀疑客户从来没有看过,说实在的,我自己都对这些数据持怀疑态度,数据质量不过关哪!客户一直以来都比较相信生产系统,更喜欢看他们出的报表、分析数据。要客户相信你,就必须向他证明:数据是真实有效的。对质量控制模块的要求相当高,需要尽心尽力的去做。
20050217
客户使用生产系统的报表或者查询,肯定是暂时的。由于企业的发展和和信息量的增加,数据仓库不仅仅是为了做数据挖掘或者出复杂报表、OLAP用,而是为所有数据查询和分析应用所使用。客户之所以用生产系统查询、出报表,而且还花钱做数据仓库,是因为客户上面领导意识到要搞,即使失败也要搞。现在只是过渡阶段,如果生产系统已经无法承受客户不断的查询和出报表的时候,他们自然只有依赖数据仓库系统。 etl工具设计之十一-需要自己编写etl工具吗?
我的前面几篇文章贴出来之后,陆续收到了一些反馈,发现一个奇怪的现象,很多公司都有自己开发ETL工具的计划。其实呢,ETL工具开发很难,没有很深的行业经验和技术积累,根本想都不要想,失败几率实在太高。我所知道的一个ETL工具项目,即使前面已经有了不少的积累,只是进行版本升级,累计用了30人月,都还没有达到项目要求。从头开发,难度可想而知。
就我自己设计的这个ETL工具,估计得要6人年才能完成一个初始版本。我设想的人员配置如下表
如此昂贵的开发成本,估计一般的小公司是无法接受。除非公司实力强劲,能够支付得起,或者公司有多个BI项目都需要ETL工具,工具开发已经迫在眉睫,否则,都不要贸然立项。 如果实在是不想购买专业的ETL工具,可以尝试使用一下免费的开源ETL工具, 应该能满足部分要求,而且,也可以进行二次开发,省时省力。
后记:这几篇文章只是我一年多工作经验的总结, 完完全全基于自己的领悟,里面所涉及到的内容,基本上都是自己平时理解、感悟,适用范围很有限。本来,还有几篇文章, 分别关于前台界面、 调度设计、数据质量控制、元数据、消息控制机制和后台数据结构设计,但总觉得力有所不逮,都只写了一半,也就不贴出来了,以免误导。
Inovate511
20050217
现在数据仓库项目分为很多种,可以从金额分,也可以用数据量+业务复杂程度分,还可以按行业分。所以是否需要ETL工具,并没有绝对的答案,要看实际项目的具体情况。 刘庆
20050220
Innovate的这段分析针对BI项目团队构成、数据集市的误解、数据仓库功能组件的误解,主题应该是告诫我们不要以为数据仓库就那么点玩意儿。
但有些意犹未尽,这些问题没有深入,如他自己所说,是抛砖引玉罢。
确实,很多刚接触数据仓库项目的人有一些共同的思路旅程,没有做过项目的时候,听到所谓星型模式、数据挖掘的术语,感到高深莫测。而介入以后,又发现其实没什么技术含量可言,星型模式也是一种带冗余的关系模型,数据挖掘,根本就不需要你有多了解其算法是怎么回事。这未免让一些人感到失望,想过瘾却过不上,想写代码,可都是用一些工具来拖拖拽拽,配置配置,要不就写一些简单的shell。
数据仓库项目并不是基于一种成熟的技术或是成熟的方法论。什么样是成熟的,我以为,成熟的技术应该是可以将项目大卸八块,将它们分给若干不同的团队完成,最后还可以合在一起。也就是能够将项目外包出去,显然,数据仓库项目在目前是很难做到这点的。现在还没有办法说,客户提出需求,就可以让设计者根据需求作架构、详细设计,实施人员也没有一个详细设计让他知道,该怎样实施。
常的事情是一位工程师从需求开始,到最后的实现、测试,还可能同时兼任项目管理的职责。而客户需求描述不清,变更频繁,工程师陷入重复的无用功劳动,也是各个项目组存在的。这都是不成熟的表现。
如果要走向成熟,就要将每个部分的接口定义清楚。可现实情况是做不到,不光是BI项目,传统的IT项目,例如一个计费系统、一个OA也很难定义。缺乏形式化的需求描述语言,缺乏能够将业务表述明确的人。同样,在设计层面也是如此,缺乏严格的设计表示方法,总归还不能做到向建筑行业那样,在图纸上明确标示出建筑的形状、规格。但有人在努力地寻找这些缺少的东西,例如UML就是这样一种表达语言。
BI项目中,需求、设计比传统项目更加难以表达,因为流程还算是可以理解的,而决策这种东西,似乎还停留在决策者的大脑中,如何将他们表达出来还得爬一层楼。不能将这应用层面的需求表达清楚,就更加难以将其依赖的数据管理需求表达清楚。
请问,你要建数据仓库,怎样才算完成目标?
对这个问题又很多种回答,有说,能够实现某某报表、实现某某cube就ok了。有说,能够让客户满意就是成功。还有说,能够满足客户日益增长的查询、分析需求(够虚的)。
他们作为目标,用什么去衡量?第一种说辞还算有客观标准,用报表和cube来衡量,但通常客户又不会如此罢休,还是有不断的报表需求产生,因此这只能算是口头的目标。而后两者说辞,能够达到,确实算成功,不过多数情况,但这是一种期望,也没有指明客观衡量标准。因此达到这种目标通常可以采取一些"艺术"的方法,例如在酒桌或是澡堂解决。 说了这么多,要使BI项目走向成熟,就为其各个模块的接口、职责制定可以客观衡量的标准。当然,这是漫长的事。
20060220
根据刘庆补充的东西,我也再多说一些自己的体会。 刘庆
20060221
国外项目已经成熟到可以外包了吗?
对这点我还是心存怀疑的,当然,我没有参与过国外的项目,没有结果他们的外包。如果有这样的情况,真的是非常想了解一下。
主要想了解外包的接口是如何划分,如何表述客户的需求?如何用设计表述这些需求?如何为客户的实际数据环境实施ETL?当客户的分析需求变化以后会是什么样的流程?这对于国内BI项目的管理也是非常有帮助的。
国外的理论是不错的,相信很多设计师在做第一个数据仓库项目的时候,确实是按照这些理论来的。但问题是这些理论的掌握并非就是学习了就可以的,还得在实践中去摸,否则知其然而不知其所以然。比如kimball提出的代理键,觉得不错,于是在设计中完全使用代理键,却造成不必要的转换工作。那么kimball的理论有没有详细说明那些情况下该使用代理键,哪些情况下不需要用呢?我想他遇到的情况和中国的情况未必相同,他面临的案例,可能以多种、异构的、诸多不一致的数据源,因此而考虑了代理键。但在国内的一些项目中,其数据源还是比较单纯的,或者在编码的统一性方面做的不错,不管不顾地还是使用代理键来代替原来的业务主键,吃力不讨好。
我们当然也可以说kimball的维度矩阵、confirm dimension好的不得了,但他究竟解决什么设计上的问题?这些问题在我们实际项目环境中是否严重存在?还得好好探讨一下。我想很多人对这套理论其实了解不够深入,也请innovate给我们分析分析。
Inovate511
20060221
数据仓库项目,无论是最初的项目开发还是项目升级,都可以把一些具体开发任务模块化,分发出去,降低运维成本。具体办法大概是:
测试方面,乙方写好测试文档交给甲方审核,然后测试,并记录结果,由甲方确定。由于每个项目实际情况不同,流程可以更具体,也可以粗略点,这是效率和质量的平衡关系。 外包甲方确定需求,并把每个需求模块化,写好需求文档,交给外包乙方。如需求 0001 号,实现把 A 库的 a,b,c,d 表按照 xxx 规则转换到 xx 事实表,使用开发工具、环境都要说明。
责编:向师富
微信扫一扫实时了解行业动态
微信扫一扫分享本文给好友
著作权声明:kaiyun体育官方人口 文章著作权分属kaiyun体育官方人口 、网友和合作伙伴,部分非原创文章作者信息可能有所缺失,如需补充或修改请与我们联系,工作人员会在1个工作日内配合处理。
|
热门博文
|
|