ENTERPRISE

BizTalk 2006 : Dealing with Compressed Files (part 2) - Receiving Zipped Files

11/12/2012 2:36:21 AM

Sending Multiple Zipped Files

In order to accommodate the scenario where a single ZIP file will contain multiple ZIP entries, you need to make some modifications to the preceding example. Specifically, you need to pass in multiple documents and have them all included within the outbound ZIP file. For this, you can write a BizTalk Assembler component. The Assembler component will take an array of messages, loop through them, and compress each of them into the final message output. To actually send the messages to the assembler, you can use the ExecuteSendPipeline from an orchestration feature that is included with BizTalk 2006. What you need to do is build an orchestration that will have a subscription for all messages required to be included within the ZIP file. The orchestration listens for these messages, and when it receives them, it adds them to an ArrayList object. At some point, the orchestration will need to call the send pipeline and pass it in the ArrayList it has built. From here, the send pipeline will call the Assembler component, which will add each of the messages it has received within the ArrayList to the outbound message. An example of this pattern is included in the SDK with BizTalk under the \Program Files\Microsoft BizTalk Server 2006\ SDK\Samples\Pipelines\Aggregator\ directory.

Receiving Zipped Files

The reverse scenario to sending ZIP files is receiving them. When receiving ZIP files, you will need to create a Decoding component, which can extract the files inside and submit them to the pipeline for further processing. This example only addresses the simple example of a ZIP file containing one XML file inside. The following example could be expanded upon to handle ZIP files with multiple files inside and files of binary types.

Imports Microsoft.VisualBasic
Imports System
Imports System.ComponentModel
Imports System.Collections
Imports System.Diagnostics
Imports System.Drawing
Imports System.IO
Imports System.Reflection

Imports Microsoft.BizTalk.Component.Interop
Imports Microsoft.Utility.PipelinePropertyAttribute
Imports ICSharpCode.SharpZipLib.Zip
Namespace Microsoft.Utility.PipelineZip

       <ComponentCategory(CategoryTypes.CATID_PipelineComponent),_
ComponentCategory(CategoryTypes.CATID_Decoder),_
System.Runtime.InteropServices.Guid("67C8CFB9-D89A-4415-A112-76187FC294D1")> _
       Public Class ZipDecodeComponent
              Inherits BaseCustomTypeDescriptor
              Implements IBaseComponent,_
Microsoft.BizTalk.Component.Interop.IComponent,_
Microsoft.BizTalk.Component.Interop.IPersistPropertyBag, IComponentUI

         ' Component information
          #Region "IBaseComponent"
          <Browsable(False)> _
          Public ReadOnly Property Name() As String
                 Get
                       Return "ZIP decoder"
                 End Get
          End Property
          <Browsable(False)> _
          Public ReadOnly Property Version() As String
                 Get
                        Return "1.0"
                 End Get
          End Property
          <Browsable(False)>
          Public ReadOnly Property Description() As String
                 Get
                        Return "Zip Decode Pipeline Component"
                 End Get
          End Property
          <Browsable(False)>
          Public ReadOnly Property Icon() As System.IntPtr
                 Get
                        Return (CType(resourceManager.GetObject("IconBitmap"),_
Bitmap)).GetHicon()
                 End Get
         End Property
         #End Region

         Private resourceManager As System.Resources.ResourceManager = New_
System.Resources.ResourceManager_
("Microsoft.Utility.PipelineGnuPG.ZipDecodeComponent",_
System.Reflection.Assembly.GetExecutingAssembly())

					  

' Property: Password
          Private _password As String

          Public Property Password() As String
                 Get
                        Return _password
                 End Get
                 Set
                        _password = Value
                 End Set
         End Property

         Private Function Decode(ByVal inStream As Stream) As Stream
                Dim inFile As String = Path.GetTempFileName()
                Dim outFile As String = Path.ChangeExtension(inFile, "txt")

                Try
                        Dim zipStream As ZipInputStream = New_
ZipInputStream(inStream)

                        ' get password, if supplied
                        If (Not _password Is Nothing) AndAlso (_password <> "")_
Then
                                zipStream.Password = _password
                        End If

                       ' this algorithm demands that the ZIP archive contain
                       ' exactly one file
                       Dim entry As ZipEntry = zipStream.GetNextEntry()
                       If entry Is Nothing Then
       Throw New ApplicationException("Input ZIP archive does not contain any _
       files - expecting exactly one file")
                       End If
                       If entry.IsDirectory Then
                              Throw New ApplicationException("Input ZIP _
   contains a directory - expecting exactly one file")
                               End If

                               ' copy the compressed stream into the output stream
                               outStream = New MemoryStream()
                               Dim buffer As Byte() = New Byte(4095){}
                               Dim count As Integer = 0
                               count = zipStream.Read(buffer, 0, buffer.Length
                               Do While count <> 0
                                     outStream.Write(buffer, 0, count)
                                      count = zipStream.Read(buffer, 0, buffer.Length
                               Loop

					  

' make sure that was the one and only file
                              entry = zipStream.GetNextEntry()
                              If Not entry Is Nothing Then
            Throw New ApplicationException("Input ZIP archive contains multiple files_
            and/or directories - expecting exactly one file")
                               End If

                               zipStream.Close()
#If DEBUG Then
                               outStream.Seek(0, SeekOrigin.Begin)

PipelinePropertyAttribute.FileStreamReadWrite.DumpStreamToFile(outStream,_
outFile)
#End If
                            outStream.Seek(0, SeekOrigin.Begin)
                      Catch ex As Exception
                            System.Diagnostics.Debug.WriteLine(ex)
                            Throw ex
                     Finally
                            If File.Exists(inFile) Then
                                   File.Delete(inFile)
                            End If

                            If File.Exists(outFile) Then
                                   File.Delete(outFile)
                            End If
                     End Try

                     Return outStream
              End Function

             #Region "IPersistPropertyBag Members"

             Public Sub InitNew()
             End Sub

             Public Sub GetClassID(<System.Runtime.InteropServices.Out()> ByRef_
classID As Guid)

                    classID = New Guid ("19800584-283D-44da-B1EE-0968387DA088")
             End Sub

					  

Public Sub Load(ByVal propertyBag As IPropertyBag, ByVal errorLog As_
Integer)
                    Dim text As String
                    text = CStr(PropertyBagReadWrite.ReadPropertyBag(propertyBag,_
"Password"))
                    If Not text Is Nothing Then
                    _password = text
                    End If
             End Sub

             Public Sub Save(ByVal propertyBag As IPropertyBag, _
             ByVal clearDirty As Boolean, ByVal saveAllProperties As Boolean)
                    Dim val As Object
                    val = CObj(_password)
                    PropertyBagReadWrite.WritePropertyBag(propertyBag, "Password",_
val)
            End Sub

            #End Region

           #Region "IComponent Members"

            Public Function Execute(ByVal pContext As IPipelineContext, _
ByVal pInMsg As Microsoft.BizTalk.Message.Interop.IBaseMessage) As_
 Microsoft.BizTalk.Message.Interop.IBaseMessage
                     Try
                           If Not pInMsg Is Nothing Then
                                  Dim originalStream As _
Stream = pInMsg.BodyPart.GetOriginalDataStream()
                                   pInMsg.BodyPart.Data = Decode(originalStream)
                                   pContext.ResourceTracker.AddResource_
(pInMsg.BodyPart.Data)
                             End If
                     Catch ex As Exception
                           System.Diagnostics.Debug.WriteLine("Exception caught in_
ZipDecodeComponent::Execute: " & ex.Message)
       Throw New ApplicationException("ZipDecodeComponent was_
       unable to decompress input stream. This may occur if there is more than_
       one file in the ZIP archive. See inner exception for more information.", ex)
                    End Try
                    Return pInMsg
             End Function

             #End Region

             #Region "IComponentUI Members"

					  

'<summary>
             'The Validate method is called by the BizTalk Editor_
             'during the build of a BizTalk project.
             '</summary>
             '<param name="obj">An Object containing the configuration
             'properties.</param>
             '<returns>The IEnumerator enables the caller to _enumerate through a
             'collection of strings containing error messages. These error_
             'messages appear as compiler error messages. To report successful
             'property validation, the method should return an empty
             'enumerator.</returns>
             Public Function Validate(ByVal projectSystem As Object) As_
IEnumerator
                                      ' example implementation:
                                      ' ArrayList errorList = new ArrayList();
                                      ' errorList.Add("This is a compiler error");
                                      ' return errorList.GetEnumerator();
                                      Return Nothing
                          End Function

                          #End Region

              End Class
End Namespace				  
Other  
 
Most View
Steinberg Cubase 7 – The Fantastic Success (Part 1)
Nook HD - A High-Definition Tablet With The Heart Of A Reader (Part 3)
Keep Selective Colour In Mono Conversions (Part 2)
Top Tablet Apps – December 2012 (Part 1)
Sharepoint 2010 : Making Search Work - Analyzing and Designing Search (part 2) - Creating a Design Document
Top Ten Raspberry Pi Projects (Part 2)
A New Leaf (Part 1)
New Products For May (Part 2)
Sony Vaio FIT 15 - Sony's Mainstream Notebooks Get A Makeover (Part 1)
Windows Server 2008 and Windows Vista : Group Policy Management Console Delegation - Linking GPOs
Top 10
Sharepoint 2013 : Farm Management - Disable a Timer Job,Start a Timer Job, Set the Schedule for a Timer Job
Sharepoint 2013 : Farm Management - Display Available Timer Jobs on the Farm, Get a Specific Timer Job, Enable a Timer Job
Sharepoint 2013 : Farm Management - Review Workflow Configuration Settings,Modify Workflow Configuration Settings
Sharepoint 2013 : Farm Management - Review SharePoint Designer Settings, Configure SharePoint Designer Settings
Sharepoint 2013 : Farm Management - Remove a Managed Path, Merge Log Files, End the Current Log File
SQL Server 2012 : Policy Based Management - Evaluating Policies
SQL Server 2012 : Defining Policies (part 3) - Creating Policies
SQL Server 2012 : Defining Policies (part 2) - Conditions
SQL Server 2012 : Defining Policies (part 1) - Management Facets
Microsoft Exchange Server 2010 : Configuring Anti-Spam and Message Filtering Options (part 4) - Preventing Internal Servers from Being Filtered