保存/记录SSIS中变量的值以供下次执行

时间:2019-02-25 13:20:33

标签: xml for-loop foreach ssis etl

我当前正在将数据从数据库导出到XML文件中。这很好。根据数据量,一个XML文件仅包含一个或数百个数据集。每天都会触发此过程。现在,数据集应具有“ FileNo”之类的属性,该属性应在开始时为零,然后始终增加一。现在我已经看到SSIS中有foreach容器和for容器。不幸的是,我担心使用这样的容器会使所有数据集每天都具有相同的“ FileNo”,因此并不能正确地提出它们。此外,我不知道在SSIS中是否可以将变量“ FileNo”的最后一个值缓存在某个地方,以便第二天可以使用下一个较高的“ FileNo”值,而不是从零开始。 ..

您是否知道如何计算此类变量并将其存储在某个地方,以便在第二天再次调用它?所以最后应该看起来像这样:

谢谢您的帮助。

2 个答案:

答案 0 :(得分:0)

C#脚本任务可用于检索最后的DateTime.Now值。完成此操作后,可以更新SSIS变量以保存该变量,您可以通过将其记录到表或其他方法中来存储它。另一种选择是直接在脚本任务中存储在表中。以下概述了这两个选项。在脚本中,FileNo属性也存储为时间戳。以下示例介绍了使用LINQLastOrDefault方法从XML元素和属性中获取最后一个Last的方法。如果找不到任何元素,则此方法返回默认值,而using System.Data; using System.Data.SqlClient; using System.Linq; using System.Xml.Linq; string xmlFile = Dts.Variables["User::XMLFilePath"].Value.ToString(); //load xml document XDocument xmlDoc = XDocument.Load(xmlFile); //get last FileNo value string lastFileNoElement = xmlDoc.Elements("Root").Elements("Element1"). Elements("Element2").Elements("FileNo").LastOrDefault().Value.ToString(); string lastFileNoAttribute = xmlDoc.Elements("Root").Elements("Element1") .Elements("Element2").Attributes("FileNo").LastOrDefault().Value.ToString(); //update ssis variable (element) Dts.Variables["User::FileNoElement"].Value = lastFileNoElement; //update ssis variable (attribute) Dts.Variables["User::FileNoAttribute"].Value = lastFileNoAttribute; //create connection string connStr = @"Data Source=YourServer;Initial Catalog=Database;Integrated Security=true"; string cmd = "INSERT INTO Schema.LoggingTable (FileNoAttribute, FileNoElement, ExecutionTime) values(@atName, @eleName, @execTime)"; using (SqlConnection conn = new SqlConnection(connStr)) { SqlCommand sql = new SqlCommand(cmd, conn); //attribute parameter SqlParameter aParam = new SqlParameter("@atName", SqlDbType.VarChar); aParam.Size = 50; aParam.Direction = ParameterDirection.Input; aParam.Value = lastFileNoAttribute; //element parameter SqlParameter eParam = new SqlParameter("@eleName", SqlDbType.VarChar); eParam.Size = 50; eParam.Direction = ParameterDirection.Input; eParam.Value = lastFileNoElement; //timestamp SqlParameter dateParam = new SqlParameter("@execTime", SqlDbType.DateTime); dateParam.Direction = ParameterDirection.Input; dateParam.Value = DateTime.Now; sql.Parameters.Add(aParam); sql.Parameters.Add(eParam); sql.Parameters.Add(dateParam); conn.Open(); //insert data sql.ExecuteNonQuery(); } 方法将在这种情况下引发错误。当然,使用的XML路径只是一个示例,需要将其更改为您的路径。

func collectionView(_ collectionView: NSCollectionView, itemForRepresentedObjectAt indexPath: IndexPath) -> NSCollectionViewItem {
    let item = collectionView.makeItem(withIdentifier: NSUserInterfaceItemIdentifier(rawValue: "LabelItem"), for: indexPath)
    item.textField?.stringValue = "PPPP"
    item.imageView?.image = NSImage(named: "firstimage")

    let button = NSButton()
    button.frame = NSMakeRect(100, 10, 50, 30)
    button.action = #selector(test)
    item.view.addSubview(button)
    return item
}

@objc func test(sender: NSButton) {
    print("CLICKED")
    let cell: NSCollectionViewItem? = (sender.view.superview as? NSCollectionViewItem)        
}

答案 1 :(得分:0)

我将尝试将您的问题分为两部分:

  1. 在每个循环中递增变量FileNo
  2. 存储最新文件值

在每个循环中递增变量FileNo

要增加每个循环的值,最简单的方法是在foreach循环容器内使用一个Expression Task,其表达式类似:

@[User::FileNo] = @[User::FileNo] + 1

有关更多信息,您可以参考以下答案:

存储最新文件值

不幸的是,没有选择将此值存储在SSIS包中,但是您可以将其存储在数据库或文本文件中,并在包执行开始时进行检索,并在末尾更新该值。

如果您决定将值存储在数据库中,则需要使用 Execute SQL Task 。如果决定使用平面文件,则必须使用脚本任务编写脚本以在开头检索值并将其存储在末尾。

我将提供一些有助于实现此过程的链接:

从数据库中读取值

使用c#

从平面文件读取和存储值