如何:在 WSFederationHttpBinding 上禁用安全会话

某些服务可能需要联合凭据,但不支持安全会话。 在这种情况下,必须禁用安全会话功能。 与 WSHttpBinding 不同,WSFederationHttpBinding 类不支持在与服务通信时禁用安全会话。 相反,你必须创建一个自定义绑定,以便用引导来替换安全会话设置。

本主题演示如何修改 WSFederationHttpBinding 中包含的绑定元素以创建自定义绑定。 结果与 WSFederationHttpBinding 基本相同,只是它不使用安全会话。

创建不使用安全会话的自定义联合绑定

  1. 创建 WSFederationHttpBinding 类的一个实例,方法可以是在代码中以强制方式创建,也可以是从配置文件中加载。

  2. WSFederationHttpBinding 克隆到一个 CustomBinding 中。

  3. SecurityBindingElement 中查找 CustomBinding

  4. SecureConversationSecurityTokenParameters 中查找 SecurityBindingElement

  5. SecurityBindingElement 中的引导安全绑定元素替换原始 SecureConversationSecurityTokenParameters

示例

下面的示例创建一个不使用安全会话的自定义联合绑定。

using System;
using System.Collections.Generic;
using System.ServiceModel;
using System.ServiceModel.Channels;
using System.ServiceModel.Security.Tokens;

namespace Samples
{
    public sealed class CustomBindingCreator
    {
        // This method creates a CustomBinding based on a WSFederationHttpBinding which does not use secure conversation.
        public static CustomBinding CreateFederationBindingWithoutSecureSession(WSFederationHttpBinding inputBinding)
        {
            // This CustomBinding starts out identical to the specified WSFederationHttpBinding.
            CustomBinding outputBinding = new CustomBinding(inputBinding.CreateBindingElements());
            // Find the SecurityBindingElement for message security.
            SecurityBindingElement security = outputBinding.Elements.Find<SecurityBindingElement>();
            // If the security mode is message, then the secure session settings are the protection token parameters.
            SecureConversationSecurityTokenParameters secureConversation;
            if (WSFederationHttpSecurityMode.Message == inputBinding.Security.Mode)
            {
                SymmetricSecurityBindingElement symmetricSecurity = security as SymmetricSecurityBindingElement;
                secureConversation = symmetricSecurity.ProtectionTokenParameters as SecureConversationSecurityTokenParameters;
            }
            // If the security mode is message, then the secure session settings are the endorsing token parameters.
            else if (WSFederationHttpSecurityMode.TransportWithMessageCredential == inputBinding.Security.Mode)
            {
                TransportSecurityBindingElement transportSecurity = security as TransportSecurityBindingElement;
                secureConversation = transportSecurity.EndpointSupportingTokenParameters.Endorsing[0] as SecureConversationSecurityTokenParameters;
            }
            else
            {
                throw new NotSupportedException(String.Format("Unhandled security mode {0}.", inputBinding.Security.Mode));
            }
            // Replace the secure session SecurityBindingElement with the bootstrap SecurityBindingElement.
            int securityIndex = outputBinding.Elements.IndexOf(security);
            outputBinding.Elements[securityIndex] = secureConversation.BootstrapSecurityBindingElement;
            // Return modified binding.
            return outputBinding;
        }
        // It is a good practice to create a private constructor for a class that only
        // defines static methods.
        private CustomBindingCreator() { }
        static void Main()
        {
            // Code not shown.
        }
    }
Imports System.Collections.Generic
Imports System.ServiceModel
Imports System.ServiceModel.Channels
Imports System.ServiceModel.Security.Tokens
Imports System.Security.Permissions





Public NotInheritable Class CustomBindingCreator

    ' This method creates a CustomBinding based on a WSFederationHttpBinding which does not use secure conversation.
    Public Shared Function CreateFederationBindingWithoutSecureSession(ByVal inputBinding As WSFederationHttpBinding) As CustomBinding
        ' This CustomBinding starts out identical to the specified WSFederationHttpBinding.
        Dim outputBinding As New CustomBinding(inputBinding.CreateBindingElements())
        ' Find the SecurityBindingElement for message security.
        Dim security As SecurityBindingElement = outputBinding.Elements.Find(Of SecurityBindingElement)()
        ' If the security mode is message, then the secure session settings are the protection token parameters.
        Dim secureConversation As SecureConversationSecurityTokenParameters
        If WSFederationHttpSecurityMode.Message = inputBinding.Security.Mode Then
            Dim symmetricSecurity As SymmetricSecurityBindingElement = CType(security, SymmetricSecurityBindingElement)
            secureConversation = CType(symmetricSecurity.ProtectionTokenParameters, SecureConversationSecurityTokenParameters)
            ' If the security mode is message, then the secure session settings are the endorsing token parameters.
        ElseIf WSFederationHttpSecurityMode.TransportWithMessageCredential = inputBinding.Security.Mode Then
            Dim transportSecurity As TransportSecurityBindingElement = CType(security, TransportSecurityBindingElement)
            secureConversation = CType(transportSecurity.EndpointSupportingTokenParameters.Endorsing(0), SecureConversationSecurityTokenParameters)
        Else
            Throw New NotSupportedException(String.Format("Unhandled security mode {0}.", inputBinding.Security.Mode))
        End If
        ' Replace the secure session SecurityBindingElement with the bootstrap SecurityBindingElement.
        Dim securityIndex As Integer = outputBinding.Elements.IndexOf(security)
        outputBinding.Elements(securityIndex) = secureConversation.BootstrapSecurityBindingElement
        ' Return modified binding.
        Return outputBinding

    End Function

    ' It is a good practice to create a private constructor for a class that only 
    ' defines static methods.
    Private Sub New()

    End Sub

    Shared Sub Main()

    End Sub
End Class

编译代码

  • 若要编译代码示例,请创建一个引用 System.ServiceModel.dll 程序集的项目。

另请参阅