Поделиться через


Программная обработка событий

Область применения: среда выполнения интеграции SSIS SQL Server в Фабрика данных Azure

В среде выполнения служб SSIS имеется коллекция событий, возникающих до, во время и после проверки и выполнения пакета. Эти события можно зафиксировать двумя способами. Первый метод включает реализацию интерфейса IDTSEvents в классе и указание класса в качестве параметра для методов Execute и Validate пакета. Второй метод включает создание объектов DtsEventHandler, которые могут содержать другие объекты служб SSIS, например задачи и циклы, выполняемые при возникновении события в IDTSEvents. В данном разделе описаны эти два метода и приведены примеры кода, иллюстрирующие их использование.

Получение обратных вызовов IDTSEvents

Разработчики, создающие и программно выполняющие пакеты, могут получать уведомления о событиях во время проверки и выполнения с помощью интерфейса IDTSEvents. Для этого создается класс, в котором реализован интерфейс IDTSEvents, и этот класс указывается в качестве параметра для методов Validate и Execute пакета. Методы класса затем вызываются подсистемой выполнения при возникновении события.

Класс DefaultEvents — это класс, в котором уже реализован интерфейс IDTSEvents. Поэтому другой альтернативой прямой реализации IDTSEvents является создание производного от DefaultEvents класса и переопределение событий, требующих отклика. Затем этот класс указывается в качестве параметра для методов Validate и Execute класса Package для получения обратных вызовов событий.

В следующем образце кода показан класс, производный от DefaultEvents, переопределяющий метод OnPreExecute. Затем этот класс указывается в качестве параметра для методов Validate и Execute пакета.

using System;  
using Microsoft.SqlServer.Dts.Runtime;  
  
namespace Microsoft.SqlServer.Dts.Samples  
{  
  class Program  
  {  
    static void Main(string[] args)  
    {  
      Package p = new Package();  
      MyEventsClass eventsClass = new MyEventsClass();  
  
      p.Validate(null, null, eventsClass, null);  
      p.Execute(null, null, eventsClass, null, null);  
  
      Console.Read();  
    }  
  }  
  class MyEventsClass : DefaultEvents  
  {  
    public override void OnPreExecute(Executable exec, ref bool fireAgain)  
    {  
      // TODO: Add custom code to handle the event.  
      Console.WriteLine("The PreExecute event of the " +  
        exec.ToString() + " has been raised.");  
    }  
  }  
}  
Imports Microsoft.SqlServer.Dts.Runtime  
  
Module Module1  
  
  Sub Main()  
  
    Dim p As Package = New Package()  
    Dim eventsClass As MyEventsClass = New MyEventsClass()  
  
    p.Validate(Nothing, Nothing, eventsClass, Nothing)  
    p.Execute(Nothing, Nothing, eventsClass, Nothing, Nothing)  
  
    Console.Read()  
  
  End Sub  
  
End Module  
  
Class MyEventsClass  
  Inherits DefaultEvents  
  
  Public Overrides Sub OnPreExecute(ByVal exec As Executable, ByRef fireAgain As Boolean)  
  
    ' TODO: Add custom code to handle the event.  
    Console.WriteLine("The PreExecute event of the " & _  
      exec.ToString() & " has been raised.")  
  
  End Sub  
  
End Class  

Создание объектов DtsEventHandler

Подсистема выполнения обеспечивает гибкую и мощную систему обработки событий и уведомления о них с помощью объекта DtsEventHandler. Эти объекты позволяют создавать с помощью обработчика событий целые рабочие процессы, выполняющиеся только при возникновении события, которому принадлежит обработчик событий. Объект DtsEventHandler является контейнером, выполняющимся только при возникновении соответствующего события в родительском объекте. Эта архитектура позволяет создавать изолированные рабочие процессы, выполняющиеся в ответ на возникновение событий в контейнере. Поскольку объекты DtsEventHandler являются синхронными, выполнение не возобновляется до тех пор, пока не будут возвращены обработчики событий, связанные с событием.

В следующем примере кода показано, как создать объект DtsEventHandler. Код добавляет FileSystemTask к коллекции Executables пакета, а затем создает объект DtsEventHandler для события OnError задачи. Задача FileSystemTask добавляется к обработчику событий, который выполняется при возникновении события OnError для первой задачи FileSystemTask. В этом примере предполагается, что для тестирования существует файл с именем «C:\Windows\Temp\DemoFile.txt». При первом запуске образца файл успешно копируется и обработчик событий не вызывается. При втором запуске образца первой задаче FileSystemTask не удается скопировать файл (так как для OverwriteDestinationFile задано значение false), вызывается обработчик события, вторая задача FileSystemTask удаляет исходный файл, а пакет сообщает о сбое, так как возникла ошибка.

Пример

using System;  
using System.IO;  
using Microsoft.SqlServer.Dts.Runtime;  
using Microsoft.SqlServer.Dts.Tasks.FileSystemTask;  
  
namespace Microsoft.SqlServer.Dts.Samples  
{  
  class Program  
  {  
    static void Main(string[] args)  
    {  
      string f = "DemoFile.txt";  
      Executable e;  
      TaskHost th;  
      FileSystemTask fst;  
  
      Package p = new Package();  
  
      p.Variables.Add("sourceFile", true, String.Empty,  
        @"C:\Windows\Temp\" + f);  
      p.Variables.Add("destinationFile", true, String.Empty,  
        Path.Combine(Directory.GetCurrentDirectory(), f));  
  
      // Create a first File System task and add it to the package.  
      // This task tries to copy a file from one folder to another.  
      e = p.Executables.Add("STOCK:FileSystemTask");  
      th = e as TaskHost;  
      th.Name = "FileSystemTask1";  
      fst = th.InnerObject as FileSystemTask;  
  
      fst.Operation = DTSFileSystemOperation.CopyFile;  
      fst.OverwriteDestinationFile = false;  
      fst.Source = "sourceFile";  
      fst.IsSourcePathVariable = true;  
      fst.Destination = "destinationFile";  
      fst.IsDestinationPathVariable = true;  
  
      // Add an event handler for the FileSystemTask's OnError event.  
      DtsEventHandler ehOnError = (DtsEventHandler)th.EventHandlers.Add("OnError");  
  
      // Create a second File System task and add it to the event handler.  
      // This task deletes the source file if the event handler is called.  
      e = ehOnError.Executables.Add("STOCK:FileSystemTask");  
      th = e as TaskHost;  
      th.Name = "FileSystemTask2";  
      fst = th.InnerObject as FileSystemTask;  
  
      fst.Operation = DTSFileSystemOperation.DeleteFile;  
      fst.Source = "sourceFile";  
      fst.IsSourcePathVariable = true;  
  
      DTSExecResult vr = p.Validate(null, null, null, null);  
      Console.WriteLine("ValidationResult = " + vr.ToString());  
      if (vr == DTSExecResult.Success)  
      {  
        DTSExecResult er = p.Execute(null, null, null, null, null);  
        Console.WriteLine("ExecutionResult = " + er.ToString());  
        if (er == DTSExecResult.Failure)  
          if (!File.Exists(@"C:\Windows\Temp\" + f))  
            Console.WriteLine("Source file has been deleted by the event handler.");  
      }  
      Console.Read();  
    }  
  }  
}  
Imports System.IO  
Imports Microsoft.SqlServer.Dts.Runtime  
Imports Microsoft.SqlServer.Dts.Tasks.FileSystemTask  
  
Module Module1  
  
  Sub Main()  
  
    Dim f As String = "DemoFile.txt"  
    Dim e As Executable  
    Dim th As TaskHost  
    Dim fst As FileSystemTask  
  
    Dim p As Package = New Package()  
  
    p.Variables.Add("sourceFile", True, String.Empty, _  
      "C:\Windows\Temp\" & f)  
    p.Variables.Add("destinationFile", True, String.Empty, _  
      Path.Combine(Directory.GetCurrentDirectory(), f))  
  
    ' Create a first File System task and add it to the package.  
    ' This task tries to copy a file from one folder to another.  
    e = p.Executables.Add("STOCK:FileSystemTask")  
    th = CType(e, TaskHost)  
    th.Name = "FileSystemTask1"  
    fst = CType(th.InnerObject, FileSystemTask)  
  
    fst.Operation = DTSFileSystemOperation.CopyFile  
    fst.OverwriteDestinationFile = False  
    fst.Source = "sourceFile"  
    fst.IsSourcePathVariable = True  
    fst.Destination = "destinationFile"  
    fst.IsDestinationPathVariable = True  
  
    ' Add an event handler for the FileSystemTask's OnError event.  
    Dim ehOnError As DtsEventHandler = CType(th.EventHandlers.Add("OnError"), DtsEventHandler)  
  
    ' Create a second File System task and add it to the event handler.  
    ' This task deletes the source file if the event handler is called.  
    e = ehOnError.Executables.Add("STOCK:FileSystemTask")  
    th = CType(e, TaskHost)  
    th.Name = "FileSystemTask1"  
    fst = CType(th.InnerObject, FileSystemTask)  
  
    fst.Operation = DTSFileSystemOperation.DeleteFile  
    fst.Source = "sourceFile"  
    fst.IsSourcePathVariable = True  
  
    Dim vr As DTSExecResult = p.Validate(Nothing, Nothing, Nothing, Nothing)  
    Console.WriteLine("ValidationResult = " + vr.ToString())  
    If vr = DTSExecResult.Success Then  
      Dim er As DTSExecResult = p.Execute(Nothing, Nothing, Nothing, Nothing, Nothing)  
      Console.WriteLine("ExecutionResult = " + er.ToString())  
      If er = DTSExecResult.Failure Then  
        If Not File.Exists("C:\Windows\Temp\" + f) Then  
          Console.WriteLine("Source file has been deleted by the event handler.")  
        End If  
      End If  
    End If  
    Console.Read()  
  
  End Sub  
  
End Module  

См. также

Обработчики событий в службах Integration Services (SSIS)
Добавление обработчика событий к пакету