Paolo Salvatori's Blog

Adventures in the magic world of Windows Azure

BizTalk Server and Protocol Transition

BizTalk Server and Protocol Transition

Rate This
  • Comments 10

Scenario

Consider the following scenario:

You have to implement a BizTalk Server application that has to interact with one or more downstream systems. Request messages are submitted by a front-end application which authenticates callers using the Windows Integrated Security. These messages are received by one or more SOAP or WCF Receive Locations which use the Windows Integrated Security to authenticate the original caller. The orchestration and/or the Send Ports (WCF, SOAP, SQL) responsible to process incoming requests need to impersonate the user account credentials of the original caller whilst invoking one or more downstream systems (e.g. Web Service, SQL Server database).


Enterprise Single Sign-On (SSO) that is part of BizTalk Server since the 2004 release provides services to enable credential mappings and single sign-on to end users for enterprise application integration (EAI) solutions. The SSO system maps Microsoft Windows accounts to back-end credentials. SSO simplifies the management of user IDs and passwords, both for users and administrators. It enables users to access back-end systems and applications by logging on only once to the Windows network. If the BizTalk Server application is able to properly authenticate the original caller, her/his credentials can be mapped to a username/password couple that can be used to access a downstream system (SAP, mainframe, etc.) on her/his behalf. What about if the target system in question is a web service which makes use of the Windows Integrated Security in order to authenticate and authorize incoming requests or SQL Server database configured to use the Windows Integrated Security? In this case, you should create a SSO Affiliate Application for each target system and map each domain account to its username/password credentials. The major drawback of this approach is that you should use the Password Change Notification Service to receive password changes directly from domain controllers and keep password in sync with the Active Directory. But there’s another issue with this approach: the SSO support for WCF and SOAP Send Ports include the Digest and Basic Authentication but not the Windows Integrated Security (see Single Sign-On Support for the WCF Adapters for more information on this topic). As a consequence, even if you manage to successfully impersonate the original caller, the Send Handler of the WCF and SOAP Adapters won’t be able to use these credentials when invoking the downstream service.

The solution to this problem is to use the Kerberos protocol extensions provided by Windows Server 2003 and in particular the Kerberos Protocol Transition and Constrained Delegation. The objective of this article is not to provide full coverage of this topic. For more information on this subject, see the following articles:

The following section provides an introduction to the Protocol Transition and Constraint Delegation.

Protocol Transition and Constraint Delegation

The Protocol Transition and Constraint Delegation can be used in managed code to initialize a valid WindowsIdentity object to impersonate any domain account just using its user principal name in order to accomplish one of the following tasks:

  • Authorization checks.
  • Impersonation.
  • Access remote resources.

The first two operations can be implemented independently of each other, but the third operation requires that you use Protocol Transition when you are not using Kerberos authentication. In other words, constrained delegation has two configurations; one that requires Kerberos authentication and another that works with any authentication protocol. When you use the configuration that supports any authentication protocol, you must first implement protocol transition with impersonation before you implement constrained delegation.

The next section provides details on the extensions themselves. After you have an understanding of these extensions, see the “Implementation” section to learn how to implement the operations described earlier.

New Kerberos Extensions

As previously mentioned, Windows Server 2003 provides two new Service-for-User (S4U) Kerberos extensions that support protocol transition and constrained delegation. Protocol transition and constrained delegation can be used independently of each other, but they are often used together to implement the scenario described in the introduction.

Protocol Transition

The S4U2Self Kerberos extension can be used to initialize a WindowsIdentity object with the user principal name of a valid Windows account in Active Directory. The password associated with the user principal name is not required. This feature allows you to transition from any authentication protocol into the Kerberos authentication protocol. This operation is accomplished by using the ticket-granting ticket (TGT) of a service account to request a service ticket for itself. The service account in this case is the one associated with the Web service that performs the protocol transition. The service ticket that is returned from the ticket-granting service (TGS) contains identity and principal information for the user whose ID was sent with the request.

The new WindowsIdentity that is initialized with this service ticket can then be used to perform role-based authorization checks. In addition, when used with constrained delegation, this new identity can be used to access downstream resources. There are limitations to what this new identity is allowed to do that are based on the privileges of the service account. These limitations are discussed in the “Implementation” section later in this technical supplement.

Constrained Delegation

The S4U2Proxy Kerberos extension provides an implementation of constrained delegation that allows you to use a Kerberos service ticket — instead of a TGT — to request another service ticket. Delegation is considered to be constrained because the identity (service account) that is used to request the service ticket must be configured to access a specific service. Constrained delegation works with or without protocol transition. The primary restriction is that the service account used to request a Kerberos service ticket must be configured to access the requested service. In addition, the service account must be able to impersonate the client prior to calling the service. For example, when you use Windows integrated authentication with impersonation, the default Web server’s computer account can be configured for constrained delegation without making any changes to the Internet Information Services (IIS) process account. A restriction of protocol transition is that the Web server’s computer account cannot be used for constrained delegation without modifying the IIS process account or better the service account used by the Application Pool. The reason for this is that the default IIS process account (which is the NT AUTHORITY\NETWORK SERVICE account on Windows 2003 Server) does not have necessary privileges to implement impersonation using the WindowsIdentity object that was created during protocol transition. Instead of modifying the default IIS process account, you can also use a different service account for the Application Pool.

Protocol Transition

.NET Framework applications can implement protocol transition by creating an instance of the WindowsIdentity object with a User Principal Name (UPN), which is similar to an e-mail address. For example, if the user ID is john and the corresponding Active Directory domain is contoso.com, the UPN is john@contoso.com.

It is also possible to use protocol transition to initialize a WindowsIdentity object using a common Active Directory account for trusted subsystem implementations. This type of approach is normally used when you want to improve scalability with resources that use object or connection pooling based on the credentials that were used to access them. For example, connection pooling with SQL Server will work only if a common identity is used. As a result, the following two primary scenarios are associated with protocol transition in Windows:

  • Transitioning from a different authentication protocol, such as X.509 client certificates, into the Kerberos protocol.
  • Transitioning from custom authentication by using a common identity for trusted subsystem implementations.

For more information on these topics you can review Protocol Transition with Constrained Delegation Technical Supplement.

Protocol Transition and BizTalk Server

In the following section I’ll introduce the 3 scenarios implemented to demonstrate how exploiting the Protocol Transition technique in a BizTalk Server project.

Scenario 1 – Messaging Only Scenario with a SOAP Receive Location

The picture below depicts the architecture design and message flow of the first scenario.

ProtocolTransition_Scenario1

Fig.1: Architecture Design of the first Scenario

1. A WinForm client application submits a Request to a Request-Response Soap Receive using the following code.

Private void btnSoap_Click(object sender, EventArgs e)
{
    SoapReceiveLocation.HelloWorldService client = null;
    try
    {
    client = new SoapReceiveLocation.HelloWorldService();
    client.Credentials = CredentialCache.DefaultCredentials;
    SoapReceiveLocation.RequestMessage request = new 
            SoapReceiveLocation.RequestMessage();
    request.Message = txtRequest.Text;
    SoapReceiveLocation.ResponseMessage response = 
            client.SayHello(request);
    if (response != null &&
        !string.IsNullOrEmpty(response.Greeting))
    {
        WriteToLog(response.Greeting);
    }
    }
    catch (Exception ex)
    {
    MessageBox.Show(ex.Message, 
            ExceptionCaption, 
            MessageBoxButtons.OK, 
            MessageBoxIcon.Error);
    }
}

Fig.2: Client code to invoke the Soap Receive Location

As you can see in the code above, the client invokes the Soap Receive Location through an instance of a Soap proxy class which inherits from SoapHttpClientProtocol and uses the Integrated Windows authentication with the credentials of the current user. The Soap Receive Location is hosted by a custom authentication trusted isolated host called BizTalkServerTrustedIsolatedHost (see Fig.3). BizTalk Server trusts authentication trusted hosts to place the sender security ID (SSID) on messages that the trusted host is queuing that map to users other than to the host. For more information about authentication trusted hosts, see Authenticating the Sender of a Message on MSDN.

SoapReceiveLocation1

Fig.3: The Soap Receive Location is hosted by an authentication trusted host.

The virtual directory hosting the Soap Receive Location on IIS is configured to use the Integrated Windows authentication (see Fig.4).

Authentication_Methods

Fig.4: Integrated Windows authentication configured on the RL virtual directory.

In addition, the Soap Receive Location was configured to use the Enterprise Single Sign-On (see Fig.5).

Soap_Transport_Properties

Fig.5: The SSO was enabled on the Soap Receive Location.

In this way, when the Soap Receive Location is invoked by the client application, the Soap Adapter assigns the client credentials (DOMAIN\USER) to the BTS.WindowsUser message context property. Note that this property is accessible within an orchestration via the Microsoft.BizTalk.XLANGs.BTXEngine.OriginatorSID property.

2. The Message Agent submits the incoming request message to the MessageBox (BizTalkMsgBoxDb).

3. The inbound request is consumed by a Solicit Response WCF-Custom Send Port. This latter uses a Filter Expression to receive all the documents published by the Receive Port hosting the Soap Receive Location.

4. The inbound message is mapped to the request format by the downstream HelloWorldService web service. This latter is hosted by IIS and exposes a single WsHttpBinding endpoint.

5. The WCF-Custom Send Port invokes the underlying HelloWorldService WCF service that in the scenario is hosted by a separate Application Pool (w3wp.exe) on the same IIS instance. The WCF-Custom Send Port uses a CustomBinding which contains the following binding elements (see Fig.9):

  • ProtocolTransitionBindingElement.
  • TextMessageEncodingBindingElement,
  • HttpsTransportBindingElement.

This ProtocolTransitionBindingElement binding element is a custom binding which injects a custom channel in the channel stack used by the WCF Send Handler to send out the request message. The binding element exposes multiple properties which allow controlling the channel behavior at run time. For example, the binding element can be configured to read the client credentials from a given message context property setting the value of the WindowsUserPosition to Context. In this case, the name and namespace of the source context property must be specified respectively with the ContextPropertyName and ContextPropertyNamespace properties exposed by the custom binding element. By default, the context property used to read the client account is the http://schemas.microsoft.com/BizTalk/2003/system-properties#WindowsUser promoted in this scenario by the Soap Adapter on the inbound Receive Location, but it could be read from a custom message context property. Instead, if the client account must be read from the Xml request message using an XPath Expression specified in the WindowsUserXPath property of the binding element, the value of the WindowsUserPosition property must be set to Message. At run time, the custom channel called InspectingRequestChannel reads the client account name from the context property or from the message and impersonates the original caller before passing the call to the innerChannel. When reading the client account name from the message context, the custom channel exploits a feature provided by the WCF Send Handler: when creating the System.ServiceModel.Channels.Message from the inbound IBaseMessage, this latter writes all the message context properties in the Properties of the newly WCF message. So to to read the name of the client user is sufficient to use the following lines of code within the custom channel.

private const string ContextPropertyKeyFormat = "{0}#{1}";
...
string contextPropertyKey = string.Format(ContextPropertyKeyFormat, 
                                          contextPropertyNamespace, 
                                          contextPropertyName);
if (message.Properties.ContainsKey(contextPropertyKey))
{
    windowsUser = message.Properties[contextPropertyKey] as string;
}

Fig.6: Code snippet from the helper class invoked by the custom channel.

A helper component invoked by the custom channel transforms the original account name (DOMAIN\USER) into the equivalent User Principal Name (USER@DOMAIN). Finally the custom channel impersonates the client user using the following code:

public Message Request(Message message, TimeSpan timeout)
{
    string upn = null;
    ...
    try
    {
        ...
        upn = InspectingHelper.GetUserPrincipalName(...);
        if (!string.IsNullOrEmpty(upn))
        {
            WindowsIdentity identity = new WindowsIdentity(upn);
            impersonationContext = identity.Impersonate();
        }
        reply = this.InnerChannel.Request(request);
    }
    catch (Exception ex)
    {
        Debug.WriteLineIf(traceEnabled, string.Format(MessageFormat, ex.Message));
        throw ex;
    }
    finally
    {
        if (impersonationContext != null)
        {
            impersonationContext.Undo();
            Debug.WriteLineIf(traceEnabled, string.Format(UndoneFormat, upn ?? Unknown));
        }
    }
    return reply;
}

Fig.7: Request method of the InspectingRequestChannel custom channel class.

The custom binding element, along with other components (binding element extension, channel, channelfactory etc.) used to extend the default behavior of the WCF Send Port, is contained in a custom assembly. In order to let BizTalk to use the custom binding element inside a WCF-Custom Send Port, it’s necessary to register the corresponding binding element extension inside the machine.config configuration file with the following section.

<system.serviceModel>
    <extensions>
        <bindingElementExtensions>
            <add name="protocolTransition" type="Microsoft.BizTalk.Rangers.ProtocolTransition.WCFCustomChannel.InspectingBindingExtensionElement,
             Microsoft.BizTalk.Rangers.ProtocolTransition.WCFCustomChannel, Version=1.0.0.0, Culture=neutral, PublicKeyToken=874a60d7e5a4dd9b" />
        </bindingElementExtensions>
    </extensions>
</system.serviceModel>

Fig.8: How to configure Binding Element Extension in the machine.config.

To configure the WCF-Custom Send Port to use protocolTransition binding element, the custom binding element extension class needs to be configured in the machine.config. This functionality is implemented by the InspectingBindingExtensionElement class which returns the InspectingBindingElement class to indirectly handle the message modification. InspectingBindingElement is the only class that must be public. The factory, listener, and channels can all be internal implementations of the public run-time interfaces. The protocolTransition custom binding element is associated with a BizTalk Server Send Port under the properties of the adapter in the WCF-Custom Transport Properties dialog box (see Fig.9). On the Binding tab, you can select a binding provided by the .NET Framework 3.0, in our scenario the CustomBinding. Then in the Binding panel it’s possible to select any message encoding and transport element along with other custom or standard binding elements. In our case we selected the InspectingBindingElement (protocolTransition), TextMessageEncodingBindingElement and HttpsTransportBindingElement. The assembly Microsoft.BizTalk.Rangers.ProtocolTransition.WCFCustomChannel containing the custom binding element and channel needs to be installed into the GAC.

WCF-Custom_Transport_Properties

Fig.9: Binding configuration of the WCF-Custom Send Port.

6. The HelloWorldService WCF service returns a response message.

7. The incoming response message is mapped to the format expected by the client application.

8. The transformed response message is published to the MessageBox.

9. The response message is retrieved by the Request-Response Soap Custom Receive Location which originally received the request call.

10. The response message is returned to the client WinForm application.

 

Scenario 2 – Messaging Only Scenario with a WCF-Custom Receive Location

The picture below depicts the architecture design and message flow of the second scenario.

ProtocolTransition_Scenario2

Fig.10: Architecture Design of the second Scenario

In this sample the Soap Receive Location was replaced by a WCF-Custom Receive Location.

1. A WinForm client application submits a Request to a Request-Response Soap Receive using the following code.

private void btnBizTalk_Click(object sender, EventArgs e)
{
    WCFReceiveLocation.HelloWorldServiceClient client = null;

    try
    {
        client = new WCFReceiveLocation.HelloWorldServiceClient();
        client.ClientCredentials.Windows.AllowedImpersonationLevel = TokenImpersonationLevel.Impersonation;
        WCFReceiveLocation.RequestMessage request = new WCFReceiveLocation.RequestMessage();
        request.Message = txtRequest.Text;
        WCFReceiveLocation.ResponseMessage response = client.SayHello(request);
        if (response != null && !string.IsNullOrEmpty(response.Greeting))
        {
            WriteToLog(response.Greeting);
        }
    }
    catch (FaultException ex)
    {
        MessageBox.Show(ex.Message, 
                        ExceptionCaption, 
                        MessageBoxButtons.OK,
                        MessageBoxIcon.Error);
    }
    catch (Exception ex)
    {
        MessageBox.Show(ex.Message,
                        ExceptionCaption,
                        MessageBoxButtons.OK,
                        MessageBoxIcon.Error);
    }
    finally
    {
        if (client != null)
        {
            try
            {
                client.Close();
            }
            catch (Exception)
           {
           }
        }
    }
}

Fig.11: Client code to invoke the Soap Receive Location

As you can see in the code above, the client invokes the Soap Receive Location through an instance of a WCF proxy class and uses the Integrated Windows authentication with the credentials of the current user. The WCF-Custom Receive Location is hosted by an authentication trusted in-process host called BizTalkServerTrustedHost (see Fig.12).

WCF-Custom_ReceiveLocation

Fig.12: WCF-Custom Receive Location Host configuration.

This WCF-Custom Receive Location uses the NetTcpBinding and is configured to use the Transport level security (see Fig.13).

WCF-Custom_Binding

Fig.13: WCF-Custom Receive Location Binding configuration.

In addition, the WCF-Custom Receive Location was configured to use the Enterprise Single Sign-On (see Fig.14).

WCF-Custom_Other

Fig.14: The SSO was enabled on the Soap Receive Location.

In this way, when the WCF-Custom Receive Location is invoked by the client application, the WCF-Custom Adapter assigns the client credentials (DOMAIN\USER) to the BTS.WindowsUser message context property. Note that this property is accessible within an orchestration via the Microsoft.BizTalk.XLANGs.BTXEngine.OriginatorSID property. The original WCF Adapter contained in BizTalk Server 2006 R2 has a bug that is the Receive Handler doesn’t assign the client credentials to the BTS.WindowsUser context property. The product group made patch was done to fix this problem, but this package is not publicly available. By the way, even without the fix, it’s possible to read and promote the client user account. To accomplish this task, you need to create a custom endpoint behavior which injects a message inspector in the execution chain of the WCF Receive Location. The endpoint behavior can be configured on the WCF-Custom Receive Location on the Behavior tab. The message inspector needs to implement the methods defined by the IDispatchMessageInspector interface. In particular, the AfterReceiveRequest method is executed after the WCF Receive Adapter has received a request message. This function can be used to read the client Windows identity name from the current service security context and to write this information in a custom header identified by a name and namespace that can be configured in the endpoint configuration.

public object AfterReceiveRequest(ref Message request, 
                                  IClientChannel channel,
                                  InstanceContext instanceContext)
{
    ...
    string windowsUserName = ServiceSecurityContext.Current.WindowsIdentity.Name;
    request.Headers.Add(MessageHeader.CreateHeader(contextPropertyName,
                                                   contextPropertyNamespace,
                                                   windowsUserName));
    ...
    return null;
}

Fig.15: The custom interceptor used to read the client user account.

If you define a message context property in a custom PropertySchema with the same name and namespace as the header created by the message inspector component at the previous step, the WCF Adapter will transform the custom header in a written context property with the same name and namespace when transforming the inbound WCF message (System.ServiceModel.Channels.Message) in an IBaseMessage instance. Unofrtunately, the value of the header will be contained in a <name xmlns=”…”></name> Xml snippet, so it’s necessary to create a custom pipeline component and a custom receive pipeline in order to extract the information from the custom context property and sets its value without the Xml start and end tags. The solution developed for to this article contains the code for the endpoint behavior, custom pipeline component and receive pipeline that you eventually need to set on the WCF-Custom Receive Location.

2. The Message Agent submits the incoming request message to the MessageBox (BizTalkMsgBoxDb).

3. The inbound request is consumed by a Solicit Response WCF-Custom Send Port. This latter uses a Filter Expression to receive all the documents published by the Receive Port hosting the Soap Receive Location.

4. The inbound message is mapped to the request format by the downstream HelloWorldService web service. This latter is hosted by IIS and exposes a single WsHttpBinding endpoint.

5. The WCF-Custom Send Port invokes the underlying HelloWorldService WCF service that in the scenario is hosted by a separate Application Pool (w3wp.exe) on the same IIS instance. For more details about this step, see the point number 5 of scenario 1.

6. The HelloWorldService WCF service returns a response message.

7. The incoming response message is mapped to the format expected by the client application.

8. The transformed response message is published to the MessageBox.

9. The response message is retrieved by the Request-Response Soap Custom Receive Location which originally received the request call.

10. The response message is returned to the client WinForm application.

Scenario 3 – Orchestration with an Inline Send Port

The picture below depicts the architecture design and message flow of the third scenario.

ProtocolTransition_Scenario3

Fig.16: Architecture Design of the third Scenario.

This scenario uses a technique commonly known as Inline Send Ports pattern: orchestrations do not use any logical ports bound to physical ports to invoke underlying services (e.g. WCF, Soap, Http services) or access data repositories (e.g. SQL Server, Oracle, Mainframe) but in their place they use custom .NET components (e.g. an instance of a SOAP or WCF proxy class to invoke a downstream web service or a ADO.NET component to invoke a SQL or an Oracle database) invoked inside an Expression Shape. Note that not using adapters and physical ports, the application will not benefit from their functional capabilities such as batching, retries, correlation sets initialization, declarative configuration and secondary transports. The advantage of this technique is that for each Solicit Response call made by the orchestration, it allows to eliminate 4 roundtrips to the MessageBox:

  • Orchestration Logical Port --> Request --> MessageBox
  • MessageBox --> Request --> Physical Send Port
  • Physical Send Port --> Response --> MessageBox
  • MessageBox --> Response --> Orchestration Logical Port

In the third scenario the request message is received by the same Soap Receive Location used by the first scenario, but in this case the incoming document is consumed and processed by an orchestration. This latter directly invokes the downstream HelloWorldService WCF service using an instance of a WCF proxy.

1. A WinForm client application submits a Request to a Request-Response Soap Receive using the following code. See point 1 of the first scenario for more information on the code used by the client application and the Soap Receive Location configuration.

2. The Message Agent submits the incoming request message to the MessageBox (BizTalkMsgBoxDb).

3. The inbound request is consumed by new instance of the CallHelloWorld orchestration.

Orchestration

Fig.17: The structure of the orchestration used by the third scenario.

4. The orchestration instance invokes the SayHello static method exposed by the OrchestrationHelper class inside the WCF Call Expression Shape.

stream = Microsoft.BizTalk.Rangers.ProtocolTransition.Helpers.OrchestrationHelper.SayHello(
                                                        RequestMessage(Microsoft.BizTalk.XLANGs.BTXEngine.OriginatorSID), 
                                                        RequestMessage.BodyPart.Message);

Fig.18: Helper component call inside the CallHelloWorld orchestration.

5. The SayHello method invoked by the orchestration impersonates the user account specified in the originatorSID parameter and then invokes the HelloWorld WCF service using the following code.

private const string UserPrincipalNameFormat = "{0}@{1}";    
...
public static Stream SayHello(string originatorSID, string message) { WindowsImpersonationContext impersionationContext = null; try { if (!string.IsNullOrEmpty(originatorSID)) { string[] parts = originatorSID.Split(new char[] {Path.DirectorySeparatorChar}); if (parts != null && parts.Length > 1) { string upn = string.Format(UserPrincipalNameFormat, parts[1], domainFQDN); WindowsIdentity identity = new WindowsIdentity(upn); impersionationContext = identity.Impersonate(); } } RequestMessage request = new RequestMessage(); request.Message = message; HelloWorldClient client = new HelloWorldClient(); ResponseMessage response = client.SayHello(request); string greeting; if (response != null && !string.IsNullOrEmpty(response.Greeting)) { greeting = response.Greeting; } else { greeting = NoGreeting; } return WriteStream(greeting); } catch (FaultException<GreetingFault> ex) { return WriteStream(ex.Detail.Message); } catch (Exception ex) { return WriteStream(ex.Message); } finally { if (impersionationContext != null) { impersionationContext.Undo(); } } }

Fig.19: The code of the SayHello method called by the CallHelloWorld orchestration.

The client endpoint used by the HelloWorldClient WCF proxy class is defined in the BizTalk Server configuration file (BTSNTSvc.exe.config) as follows:

<system.serviceModel>
    <bindings>
        <wsHttpBinding>
            <binding name="HelloWorldBinding" 
                     closeTimeout="00:01:00"
                     openTimeout="00:01:00"
                     receiveTimeout="00:10:00"
                     sendTimeout="00:01:00"
                     bypassProxyOnLocal="false"
                     transactionFlow="false"
                     hostNameComparisonMode="StrongWildcard"
                     maxBufferPoolSize="524288"
                     maxReceivedMessageSize="65536"
                     messageEncoding="Text"
                     textEncoding="utf-8"
                     useDefaultWebProxy="true"
                     allowCookies="false">
            <readerQuotas maxDepth="32" 
                          maxStringContentLength="8192"
                          maxArrayLength="16384"
                          maxBytesPerRead="4096" 
                          maxNameTableCharCount="16384" />
            <reliableSession ordered="true"
                             inactivityTimeout="00:10:00"
                             enabled="false" />
            <security mode="Transport">
            <transport clientCredentialType="Windows" 
                       proxyCredentialType="None"
                       realm="" />
            <message clientCredentialType="Windows"
                     negotiateServiceCredential="true"
                     establishSecurityContext="true" />
            </security>
            </binding>
        </wsHttpBinding>
    </bindings>
    <client>
        <endpoint address="https://domokun/HelloWorldService/HelloWorldService.svc"
                  binding="wsHttpBinding"
                  bindingConfiguration="HelloWorldBinding"
                  contract="IHelloWorld"
                  name="HelloWorldBinding">
        </endpoint>
    </client>
</system.serviceModel>

Fig.20: The system.serviceModel configuration in the BTSNTSvc.exe.config file.

6. The HelloWorldService WCF service returns a response message to the helper component.

7. The orchestration creates a response message.

8. The response message is published to the MessageBox.

9. The response message is retrieved by the Request-Response Soap Custom Receive Location which originally received the request call.

10. The response message is returned to the client WinForm application.

Summary

This article described how using the Protocol Transition technique in a BizTalk Server project to impersonate the original caller authenticated with the Windows Integrated security at the transport level. At the same time the samples shown demonstrate the WCF extensibility points provided by the WCF Adapters and the use of the Inline Send Pattern. You can download the code here.

Update

In April 2010 I extended the code to support impersonation of a domain account statically defined in the WCF Send Port. You can read the article and download the new version of the code here.

  • Today I found an excellent post about BizTalk Protocol transition by Paolo Salvatori . It's absolutely clear and helpful.

  • Paolo,

    Brilliant article and clears up some implementation scenarios which have been missing/undocumented for ages.

    Regards

    Mike

  • I was recently doing a POC where we were doing one of the scenarios described above.  We were getting an error while impersonating the user to call an external web service.  I was getting problems such as an error about trying to access a forbidden resource.

    After exchanging emails with Paolo and a bit of digging around I worked out what wasnt setup correctly.  The missing setup was as follows:

    If you want to access a local resource on the server once you have impersonated then your service account which is running the process needs to have the "act as part of operating system" priveledge

    If you want to access a remote resource eg call a web service and delegate the credential after impersonating in this way your service account running the process needs to have the "act as part of operating system" priveledge and also be configured for delegation to any authentication protocol using the appropriate SPN for the service you are going to call

    Hope this helps

    Mike

  • Paolo,

    Excellent post, it clearly defines the problem and explains the concepts. The configuration steps are well defined.

    A must to read blog for implementing impersonation with BizTalk

    rgds,

    Kunal

  • Hi Paolo, thanks for providing the article to this rarely documented topic. I also tried to implement a POC using your 1st scenario, but I run into an "Either a required impersonation level was not provided, or the provided impersonation level is invalid." error. Do you have any ideas what's the fact I could have missed?

  • Hi mate, unfortunately I didn't experience that issue so I couldn't give you any suggestions apart from testing Protocol Transition outside of BizTalk to make sure that is properly configured. Sorry about that. :-(

  • Hi Paolo,

    Thanks for this excellent article. I tried to implement a scenario using SQL server as target system. but i run into " A network-related or instance-specific error occurred while establishing a connection to SQL Server. The server was not found or was not accessible" error.

    SQL Server is up and running. It works perfectly if i donot use Protocol transition. Any ideas on what i am missing?

  • Hi Paolo,

    Thanks for keep updating this post. Is it possible to impersonate the original caller authenticated with the Windows Integrated security at the message level? I f yes, it is much appreciate if you can advise the necessary changes.

  • Hi Paolo,

    Instead of using "HTTPS", is it okay to use "HTTP" for the whole implementation? The reason for this is due to Figure 9, I.e. one of the binding element is "HttpsTransport".

    Should the solution will be implemented by HTTP, may I have your advice on the necessary changes on the CustomBinding component.

    Rgds,

    Margaux

  • Hi Paolo,

    Based on your sources, I have revised scenario using HTTP and message security. However, for Scenario 2, the WinForm receives "The message could not be processedd. This is most likely because the action 'microsoft.biztalk.rangers.protocoltransition.helloworld/.../SayHello& is incorrect or because the message contains an invalid or expired security context token or because there is a mismatch between bindings. The security context token would be invalid if the service aborted the channel due to inactivity. To prevent the service from aborting idle sessions prematurely increase the Receive timeout on the service endpoint's binding.".

    After changing the custom binding of "Solicit Response WCF-Custom Send Port" to wsHttpBinding (with message security)", the WinForm can receive the exact response message from BizTalk server.

    Do you have any ideas what's the fact I could have missed for using HTTP and custom binding (with message security)?

    Rgds,

    Margaux

Page 1 of 1 (10 items)
Leave a Comment
  • Please add 8 and 6 and type the answer here:
  • Post
Search Blogs