本节说明可用于修改或扩展 Windows Communication Foundation (WCF) 安全组件的功能的各个扩展点。若要了解这些扩展点,必须了解总体 WCF 安全体系结构。本主题从组件及其关系方面说明 WCF 安全体系结构以及本节后面说明的扩展点如何适应总体体系结构模型。
WCF 安全组件的范围
WCF 安全性跨越 WCF 体系结构中的多个组件。WCF 中安全性的主要目的是,为建立在 WCF 框架基础之上的应用程序提供完整性、保密性、身份验证、授权和审核。WCF 体系结构将这些功能拆分为以下部分:
- 传输安全 - 负责提供消息保密性、数据完整性和通信方的身份验证。
- 授权 - 负责为授权决策提供框架。
- 审核 - 负责将安全相关事件记录到审核日志中。
本文档说明的安全模式和范围
传输安全可使用以下安全模式之一来执行:
- 传输。在客户端和服务之间传输消息时使用的传输将提供所有三种通信安全功能。
- 消息。仅在 SOAP 消息级别提供传输安全,这意味着直接在 XML 级别将安全应用于 SOAP 消息。
- 使用消息凭据的传输。在传输层和消息层上都执行传输安全。传输层提供通信保密性、数据完整性和服务身份验证。消息层提供客户端身份验证。
本文档的其余部分着重介绍“消息”安全模式,但某些信息同样适用于“使用消息凭据的传输”模式。具体而言,本文档适用于客户端身份验证的部分也适用于“使用消息凭据的传输”模式,因为“使用消息凭据的传输”模式使用消息层执行客户端身份验证的方式与“消息”模式相同。
有关“身份验证”和“审核”组件的讨论同样适用于所有三种安全模式。因此,本文档中说明的与这些组件相关的所有信息适用于所有支持的安全模式。
消息安全模式概念
WS-Security 模式
“消息”安全模式的基础是 WS-Security 规范。WS-Security 规范定义一个框架,该框架允许对 SOAP 消息应用安全。该规范指定了一种结合数字签名和加密使用安全令牌来保护 SOAP 消息并对其进行身份验证的消息安全模式。有关该规范的信息,请参见 Web 服务安全 (WS-Security)(可能为英文网页)。
术语
安全令牌断言声明并可用于断言身份验证秘密或密钥和安全标识之间的绑定。
声明是由实体所做的有关实体(例如名称、标识、组、密钥或特权)的声明。作出声明的实体称为“声明颁发者”;对其作出声明的有关实体称为“声明主题”。
声明颁发者可以通过使用其密钥对安全令牌进行签名或加密来保证或认可安全令牌中的声明。这会在安全令牌中启用声明的身份验证。
消息签名用于验证消息来源和完整性。消息签名还可供消息创作者用于证明他们知道密钥(通常来自第三方,用于确认安全令牌中的声明),因此会将消息创作者的标识(以及由安全令牌表示的任何其他声明)绑定到所创建的消息。
安全令牌
WS-Security 定义了多种类型的安全令牌,并提供了一个可扩展模型,允许单独定义其他的安全令牌类型。每个令牌类型定义均包含令牌的 XML 序列化。这允许直接向消息添加令牌表示形式。
下面是 WS-Security 中定义的一些安全令牌类型:
- 用户名令牌。
- X.509 证书令牌。
- Kerberos 令牌。
- SAML 令牌。
已定义四种令牌使用方式,附加到给定消息的令牌只能属于其中的一个类别:
- SignedSupporting
- SignedEndorsing
- SignedEncrypted
- EncryptedEndorsing
在 .NET Framework 3.0 中,客户端消息只能包含任何给定类型的一个令牌,但是可以包含不同类型的令牌。
在 .NET Framework 3.5 中,客户端消息可以包含给定类型的多个令牌,也可以包含不同类型的令牌。
通过此功能可以实现多个方案,如下所述:
- 增量声明发送。对服务执行的所有操作可能都要求一组声明存在,但是某些操作可能需要其他声明。客户端不对每项操作使用单独颁发的令牌,而是获取一个具有初始声明集的已颁发令牌,并使用另一个已颁发的令牌(该令牌具有要调用的操作所需的其余声明)。
- 多因素身份验证。在客户端必须先收集多个颁发者颁发的令牌或具有不同声明集的令牌,然后才能执行操作时执行。WCF 将颁发的令牌视为一个令牌类型,因此,在这种情况下会要求消息中能够包含两个已颁发的支持令牌。
请注意,不能以这种方式配置服务:一个服务只能包含一个支持令牌。
有关更多信息,请参见 如何:使用相同类型的多个安全令牌。
WS-Security 实现
由于 WS-Security 为消息安全奠定了基础,因此 WS-Security 的 WCF 实现是整个“消息”安全模式的基础。若要扩展“消息”安全模式功能,必须了解 WS-Security 实现的工作方式。
WCF 中的 WS-Security 实现处理以下操作:
- 安全令牌与 SOAP 消息之间的序列化。
- 安全令牌的身份验证。
- 消息签名的应用和验证。
- SOAP 消息的加密和解密。
WCF 扩展点允许自定义前两项。可以更改现有安全令牌的序列化或 WCF 安全对这些令牌进行身份验证的方式。也可能向 WCF 安全引入全新的安全令牌类型,包括序列化和身份验证功能。
本节的以下主题演示如何使用 WS-Security 实现扩展点来自定义安全令牌功能。
授权
安全令牌会在传入消息中进行反序列化并进行身份验证。身份验证过程会产生一组授权策略对象。每个对象均表示安全令牌数据的一部分。在授权阶段将使用这些数据。
授权策略创建给定的安全令牌表示的一组声明。然后,会将此声明集提供给 ServiceAuthorizationManager 和 AuthorizationContext 属性内的逻辑以便作出授权决策。
标识
除了声明外,WCF 还会创建 IIdentity 接口的实现,用于表示现有基础结构(使用 .NET Framework 安全模型创建)的调用方。此 IIdentity 实例表示调用方的 Windows 标识(如果该安全令牌映射到 Windows 帐户)或包含调用方名称的主标识。这些标识还可以使用 ServiceSecurityContext 进行访问。(有关更多信息,请参见 如何:检查安全上下文。)通过使用以下方法之一,可以自定义在 WCF 中创建标识的方式:
- 实现 SecurityTokenAuthenticator 类的自定义扩展。
- 通过扩展 MembershipProvider 类,或通过创建自定义 IAuthorizationPolicy 实现并将其插入到 ServiceAuthorizationManager 中,与 ASP.NET 集成。
- 创建自定义 IAuthorizationPolicy。
仅当使用用户名/密码身份验证对调用方进行身份验证时,自定义成员资格提供程序才能工作。MembershipProvider 验证 用户名/密码对。如果为有效对,WCF 将在 MembershipProvider 验证后创建表示已进行身份验证的调用方的主标识。
为便于与现有的 .NET Framework 安全基础结构集成,默认情况下,WCF 将 CurrentPrincipal 属性设置为一个表示调用方的 IPrincipal 实例。IPrincipal 实例是基于所生成的 IIdentity 中包含的信息创建的。
通过与 ASP.NET RoleProvider 集成,可以进一步扩充 IIdentity。RoleProvider 会添加调用方所属的角色集。授权逻辑将使用此信息做出访问决策。
有关 标识的更多信息,请参见服务标识和身份验证。
发送安全消息
下图显示使用“消息”安全模式时如何在客户端保证消息的安全。该图显示了涉及的组件和它们之间的关系:
- 应用程序代码运行并生成消息。
- 在令牌配置阶段,附加客户端凭据(如 X.509 证书)。在联合身份验证方案中,将联系令牌颁发者以提供凭据。
- 使用这些凭据创建安全令牌。
- 在令牌身份验证阶段验证令牌。
- 最后,序列化并发送安全令牌。
接收安全消息
下图显示在从网络提取安全消息并在接收端验证这些安全消息时发生的过程:
- 在令牌身份验证阶段对安全令牌进行反序列化和处理。如果需要,可以在此时使用 ASP.NET 成员资格提供程序提供用户名和密码。
- 进行身份验证后,提取授权策略。
- 在授权策略评估阶段,评估授权策略并可将声明添加到评估上下文中。此时也使用外部授权策略。这一步以及下一步是通过 ServiceAuthorizationManager 的方法完成的。
- 在服务授权阶段,基于由授权策略添加的声明赋予正确的授权。这一步是通过 ServiceAuthorizationManager 的方法完成的。
- 授权之后,如果调用方允许且服务方法需要进行调用方模拟,或对服务授权行为设置了 ImpersonateCallerForAllOperations 属性,则会进行调用方模拟。有关更多信息,请参见 WCF 的委派和模拟。
- 此时,WCF 将使用凭据生成 PrincipalPermission。如果需要,可以在此时使用 ASP.NET 角色提供程序。
- 应用程序代码运行。
安全扩展点概述
下图显示由 WCF 安全组件提供的扩展点。该图分为四个不同类别,具体取决于消息处理过程中到达扩展点的时间。这些类别可映射到消息安全处理阶段,如前两节所述。该图还显示可以将现有基础结构技术与 WCF 安全相集成。