我正在一个数据仓库项目中工作,有很多源创建平面文件作为源,我们正在使用SSIS将它们加载到我们的临时表中,我们目前正在使用平面文件源组件。
然而,过了一段时间,我们需要在其中一个文件中添加一个额外的列,并从文件规范更改的日期开始添加该额外的列。这种练习经常发生,随着时间的推移积累了很多版本。
根据我可以在这里和互联网的其他部分找到的答案,处理这种情况的商定方法似乎是在这个版本的新的单独数据流中设置一个新的平面文件源,以保持重新运行用于旧文件的ETL过程。 此处概述了方法,例如:SSIS pkg with flat-file connection with fewer columns will fail
在我们的特定设置中,附加列总是附加列(从不删除旧列),并且出于逻辑原因,如果我们在其单独的数据流中保持旧文件的可重新运行性,则新列不能是强制性的。
我认为创建重复数据流的方法一遍又一遍地处理同一组列的方法对于像我们这样的数据仓库项目来说是一个很好的答案,我会优先考虑采用最后一个文件版本的源组件并且能够将列标记为“非mandadory”,并在缺少时提供空值。
是否有人知道SSIS Flat File组件在处理旧文件版本时更灵活,或者有更好的解决方案来解决这个问题? 我假设这样的组件需要在命名列的基础上接近文件而不是现有的从左到右的方法?
欢迎任何想法或建议!
答案 0 :(得分:0)
以下将在处理时失去效率(通过单独的数据流),但会为您提供在单个数据流中处理多种文件类型的灵活性。
您可以通过仅指定行分隔符来安排平面文件连接以返回行而不是单个列。将其连接到平面文件源组件,该组件将每行输出一列。我们现在有一行代表您知道的众多文件类型之一 - 下一步是确定您拥有的文件类型。
使用脚本组件使用平面文件类型的输出。传入一个列并传递所有可能列的超集。我们丢失了通常从文件源中发现的元数据,因此您需要在脚本组件输出类型中构建列名/类型/大小。
在脚本组件中,传递该行并将其分解为其组件列。您必须执行模式匹配(可能使用RegularExpression.Regex.Match)来识别新列何时开始。希望文件格式正确,这将有助于您 - 谨防文本列中的引号和逗号。
现在,您可以通过确定所拥有的列数并默认缺少的列来访问文件类型。设置行的输出列以传递组成部分。您可能需要附加一个新列来记录输出的文件类型。
当您为脚本中的所有文件类型提供服务时,该过程的其余部分应该能够使用单个数据流加载您的表。
我不建议你轻轻地执行上述操作。当您必须对所有列/类型等进行编码时,SSIS的好处会有所减少,但是它会为您提供单个数据流来处理每个文件版本,并且可以在传递新列时进行扩展。