从SSIS中的CSV导入yyyyMMdd日期

时间:2017-04-18 18:15:52

标签: sql-server csv ssis etl derived-column

我使用 yyyymmdd 格式有12列。在数据流任务中,我有一个平面文件源,一个派生列任务和一个 OLE DB目标 。我将以下表达式应用于派生列任务中的这些字段:

(DT_DBDATE)(SUBSTRING((DT_STR,10,1252)([Date_Column]),1,4) + "-"
+ SUBSTRING((DT_STR,10,1252)([Date_Column]),5,2) + "-"
+ SUBSTRING((DT_STR,10,1252)([Date_Column]),7,2))

它一直让我转换字段然后再将其子字符串,但我在连接管理器中将字段设置为 DT_STR 。目标字段在SQL Server中采用 DATE 格式。 SSIS始终显示“由于潜在的数据丢失而无法转换”错误。我已经检查了CSV中的原始数据,但没有看到任何看起来不合适的日期。一切都符合格式。

我还尝试按建议here使用数据转换任务,但最终得到了同样的错误。有什么建议?我在这里看到的答案都指向使用 Derived Column 任务,但我提到的其他几个问题我遇到了同样的问题。

编辑:这是一个数据样本。所有错误中特别提到的字段是CRTFCTN_DT。数据集中有470个字段,但这确实显示了前两个日期字段。

Sample

解决方案:在 Connection Manager 中,我将 yyyymmdd 字段更改为DT_STR(10)(日期为8个字符,2为添加的破折号),并重建我的数据流任务。这解决了这个问题。如果您不重建任务,派生列任务将无法获取新数据类型。重新创建任务后,我也不再需要在应用子字符串之前将日期转换为字符串。

2 个答案:

答案 0 :(得分:2)

在Connection Manager中将列[Date_Column]设置为DT_STR。你指定的长度是多少?默认情况下,它是50.在派生列中,您将其长度用作10,这是错误消息“由于可能丢失数据而无法转换”。

答案 1 :(得分:1)

尝试转换为(DT_DATE)而不是DT_DBDATE

(DT_DATE)((SUBSTRING((DT_STR,50,1252)([Date_Column]),1,4) + "-"
+ SUBSTRING((DT_STR,50,1252)([Date_Column]),5,2) + "-"
+ SUBSTRING((DT_STR,50,1252)([Date_Column]),7,2)))

您可以执行此解决方法

假设日期列名称为inColumn

在DataflowTask中,添加脚本组件,将inColumn标记为输入列,使用dataType DT_DBTIMESTAMP

添加新的输出列outColumn

将脚本语言更改为vb.net

enter image description here

将您的日期列标记为输入

enter image description here

为每个日期列创建一个输出列

enter image description here

在脚本内部,在Input0_ProcessInputRow子使用DateTime.ParseExact功能如下:

在此示例中,日期列为MailReceivingDate

Public Class ScriptMain
    Inherits UserComponent


    Public Overrides Sub Input0_ProcessInputRow(ByVal Row As Input0Buffer)

        If Not Row.MailReceivingDate_IsNull AndAlso
              Not String.IsNullOrEmpty(Row.MailReceivingDate.Trim) Then

            Row.outColumn = DateTime.ParseExact(Row.MailReceivingDate.Trim, "yyyyMMdd", New System.Globalization.CultureInfo("en-GB"))

        Else

            Row.outColumn_IsNull = True

        End If

    End Sub

End Class