Chapter 7. Understanding WCF Security

WHAT'S IN THIS CHAPTER?

  • Understanding the service security principles

  • Getting started with WCF security

Security is a critical piece of any programming technology or framework for implementing service-oriented applications.

As you will see throughout this chapter, WCF has been built from the ground up for providing the necessary security infrastructure at the message and service level. In that sense, WCF provides a versatile extensibility model for security that allows developers to customize a large variety of runtime capabilities. The flexibility of incorporating extensions in the security subsystems has made it possible for WCF to support many of the existing security schemas and scenarios used to secure services. Many of the features that WCF provides in this area are covered, as well as some common deployment scenarios you might need while developing service-oriented applications with this technology. You also explore many of the core concepts involved in web service security. By having a previous understanding of these concepts, your learning curve for understanding and taking advantage of the available security features in WCF is more direct.

THE EVOLUTION OF SECURITY IN WEB SERVICES

Security has always been a strong requirement for web services in the enterprise. There is no doubt that security and interoperability are two key contributors in the adoption and success of web services for developing distributed applications in the enterprise.

When the first generation of web services was released in the late nineties, SOAP did not provide a secure message from tampering, nor was there a way to encrypt the messages to provide confidentiality. All the security details were delegated to the transport layer, which was Http at that time. In that way, many of the existing Http/Https security capabilities were leveraged for authenticating clients and securing messages. For example, sending SOAP messages through Https would guarantee confidentiality.

However, relying on the transport layer for proving these security capabilities tied the initial web service implementations to the transport layer, resulting in a big impediment in making SOAP totally independent of the platform.

As the enterprise started demanding more features for the web services, a new generation was born under the umbrella of what was called the WS-* specifications.

WS-*, also known as web services specifications, represents a set of protocols and specifications created in combination with big leaders in the industry such as Microsoft, IBM, VeriSign, and SUN among others. It leverages the existing messaging web services capabilities using extensions to the initial SOAP specification.

Back to security, one of most relevant specifications released as part of the WS-* specifications was WS-Security.

Initially released on April 19, 2004, this specification included a new model for securing web services at message level, extending the existing SOAP specification with security capabilities for client authentication and message protection.

A time after the first WS-* specifications were announced, Microsoft released the first version of web services enhancements (WSE), a lightweight framework specially designed for extending the web service stack in the .NET platform with custom implementations of the WS-* protocols. This framework evolved gradually, adding three major versions as more features were required. It was discontinued in 2006 with the announcement of WCF. The last version, WSE 3.0, included implementations of well-known protocols such as WS-Security, WS-Addressing, WS-SecureConversation, MTOM, and WS-ReliableMessaging. If you compare WSE and WCF, it is clear that WSE was the opportunity for Microsoft to get involved in the WS-* world, and all the experience and lessons learned were used to design and develop many of the available features in WCF and Windows Identity Foundation (WIF).

Today, as the business evolves, aspects such as user authentication and authorization are slowly moving toward federated identity management solutions. Federated identity management makes the vision of treating the user identity as a service possible, where authentication and authorization functions are web services available to any application in the enterprise. This also represents a big step toward moving away from the user identity silos that were created in the past to more decentralized authentication and authorization schemas. Microsoft is pushing hard in this direction, and recently announced the Geneva platform as part of the strategy to implement identity management solutions in the .NET platform.

MAIN PRINCIPLES IN WEB SERVICE SECURITY

When you read literature about security for web services, you typically find a consistent set of fundamental principles that apply in any distributed messaging system. You use some of these principles throughout this chapter, so it is a good idea to refresh them before getting specific WCF details.

Authentication

Client authentication is the process of uniquely identifying the party that acts as a source of messages to your applications or services. For the purpose of this chapter, "message sender" or "service client" is used for this party.

Note

The message sender is not necessarily an end user; it can also be an application or a service.

The authentication process generally addresses two questions: "Who are you?" and "How do you prove that?"

For the first question, the sender must provide some evidence to prove its identity, which can take the form of intangible credentials such as a pair of usernames and passwords, a Kerberos ticket, a token with cryptographic information, or something more tangible such as an X509 certificate. On the other hand, the service must have a mechanism in place to verify that the presented evidence is legitimate, and whether it can trust or not in that evidence according to the results of the verification. The sender is successfully authenticated only when the verification drops good results.

Client authentication is not the only scenario for authentication. There are some cases where the sender also needs to verify the service identity. This type of authentication is commonly known as Service authentication, and represents a proven practice to prevent phishing attacks.

Phishing in this context represents a common security threat where someone, the attacker, makes available a fake service with the same signature as the original one to capture sensitive or private data about the user.

Mutual authentication is when both the client and the service authenticate each other before any operation is made.

Let's say that a store offering products online provides a service for third-party applications. They can buy products directly without referring users to the website. That service receives sensitive user information such as credit cards and bank account numbers. As a third-party integrator, you should authenticate the server before trusting sensitive information about the user. And as a developer working on the service, you should authenticate the user to associate the purchase information with his profile. As you can see, this is a typical scenario for requiring mutual authentication.

Authorization

Authorization is the process that determines what system resources and operations can be accessed by the authenticated user. It generally addresses the things you are allowed to do.

Authorization decisions are mostly based on evidence presented in the identity of the authenticated user such as user claims, or some other evidence provided by the consumer application.

Continuing the example discussed in authentication, the website might decide to grant different permissions to the users consuming the service based on a specific key or attribute provided by the third-party application.

Message Integrity

Message integrity guarantees that the data in the message is protected from deliberate or accidental modifications. In other words, it ensures that the service receiving the data has not been tampered with or modified in transit.

Integrity for data in transit is generally based on cryptographic techniques such as digital signatures, hashing, and message authentication codes. Integrity is extremely useful to prevent Man-In-The-Middle attacks, where someone intentionally starts sniffing the packets in the network or modifies some of them before the message reaches the service.

Message Confidentiality

Message confidentiality is the process of making sure that the data in the messages remains private and confidential, and that it cannot be read by unauthorized parties. As with message integrity, confidentiality is also based on cryptographic techniques such as data encryption. Different algorithms can be used to encrypt the data, but the most secure are the ones that are based on asymmetric keys such as RSA.

Man-In-The-Middle or Eavesdropping attacks can also be avoided thanks to data encryption.

TRANSPORT SECURITY AND MESSAGE SECURITY

As we already discussed in the section "The Evolution of Security in Web Services," two security models have been traditionally used to secure the communication between client applications as well as web services, transport security, and message security.

Both security models provide some of the aspects or security principles that were mentioned in the last section, in different ways. Security in this context is very important, and it is mainly concerned with providing authentication and guaranteeing the integrity and confidentiality of the service messages as they move across the network.

Knowing the differences between the models will help you choose one model over another according to many of the requirements you have for implementing the right security schema for your services.

Transport Security

Transport security is about leveraging the security capabilities that the different transports provide to secure an end-to-end communication between the message sender or client application and the final service. Because the original SOAP specification lacked any kind of security schema, transport security was best complement for securing communications.

In transport security, all the available authentication mechanisms are tied to the transport implementation. Therefore, this represents a big impediment for creating new kinds of credentials or extending existing ones.

The same thing happens for handling message protection; each transport provides a limited number of built-in options. The most common option for protecting the messages is based on a combination of TLS (Transport Layer Security) and SSL (Security Socket Layer), which are used to encrypt and sign the content sent over the wire. A common limitation of SSL/TLS is that they only provide point-to-point security between two endpoints, the client and the server. If a message needs to be sent through different intermediaries, they have to forward the message over a new SSL connection. In addition, after the messages leave the transport, they are no longer secure.

A big advantage of transport security over message security is that the involved parties do not need to understand WS-Security at all, which sometimes represents a big impediment to achieve protocol interoperability between different platforms or web services stacks. This impediment is inherent to two main factors:

  • The complexity of the WS-Security specification.

  • The differences in the final implementations on behalf of the web services vendors.

Message Security

When using message security, all the security metadata such as digital signatures, encrypted elements, user credentials, and cryptographic keys are self-contained within the SOAP message. This security model is based on the WS-Security specification, which mainly describes how to sign or encrypt parts of the SOAP envelope using different algorithms or even different keys.

As an XML implementation, WS-Security represents a very flexible solution for supporting different kinds of credentials or creating new ones. The credentials and keys are represented in this specification as security tokens, a generic XML construct that encapsulates specific information about them. In addition, different security tokens have already derived from existing security technologies such as Kerberos, X509 certificates, and usernames and passwords, and are made available in satellite specifications named token profiles.

A main difference with transport security is that the messages can be forwarded to other services or intermediary systems without breaking the security — security is always present, no matter whether the messages leave the transport or not. See Figure 7-1.

Message security

Figure 7.1. Message security

Let's discuss how WS-Security works with an example. The message sender modifies part of the message by substituting the message body with encrypted data, and signing other headers. The description of all the transformations that took place is included as part of a special SOAP header called "security." When the service or message receiver gets the message, it can analyze this special security header to discover that the body was encrypted, some headers were signed, and which cryptographic keys and algorithms were used to perform those operations. If it owns the keys, it can decrypt the body and verify that the signatures are valid:

<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope"
xmlsn:a="http://www.w3.org/2005/08/addressing"
xmlsn:u="http://docs.oasis-open.org/wss/2004/01/
oasis-200401-wss-wssecurity-utility-1.0.xsd">
  <s:Header>
    <a:Action s:mustUnderstand="1" u:Id="_2">
       http://tempuri.org/IHelloWorld/Hello
    </a:Action>
    <a:MessageID u:Id="_3">
      urn:uuid:4dabcfb1-6939-402d-919b-8e8486206e1f
    </a:MessageID>
    <o:Security s:mustUnderstand="1" xmlns:o="http://docs.oasis-open.org/
      wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
      <u:Timestamp u:Id="uuid-ea4659dc-85e5-4054-9b0c-c674f0128e7f-11">
        <u:Created>2009-07-27T20:03:36.830Z</u:Created>
        <u:Expires>2009-07-27T20:08:36.830Z</u:Expires>
      </u:Timestamp>
      <!-- Removed for simplicity -->
    </o:Security>
  </s:Header>
  <s:Body u:Id="_0">
    <e:EncryptedData Id="_1" Type="http://www.w3.org/2001/04/xmlenc#Content"
      xmlns:e="http://www.w3.org/2001/04/xmlenc#">
      <e:EncryptionMethod Algorithm="http://www.w3.org/2001/04/xmlenc#aes256-cbc">
      </e:EncryptionMethod>
      <KeyInfo xmlns="http://www.w3.org/2000/09/xmldsig#">
        <o:SecurityTokenReference xmlns:o="http://docs.oasis-open.org/wss/2004/01/
          oasis-200401-wss-wssecurity-secext-1.0.xsd">
          <o:Reference ValueType="http://schemas.xmlsoap.org/ws/2005/02/sc/dk"
            URI="#uuid-ea4659dc-85e5-4054-9b0c-c674f0128e7f-10"></o:Reference>
        </o:SecurityTokenReference>
      </KeyInfo>
      <e:CipherData>
        <e:CipherValue>.....</e:CipherValue>
      </e:CipherData>
    </e:EncryptedData>
  </s:Body>
</s:Envelope>

The previous example illustrates how WS-Security is applied to a SOAP message. As you can see, the body has been replaced by an encrypted section that contains references to other security tokens contained within the security headers. Those are the references that the message receiver must resolve to get access to the cryptographic keys.

WCF SECURITY OVERVIEW

At this point you have seen enough of the theory behind security in web services. Now you get your hands dirty with the implementation details of WCF. In the following sections, you see how to use many of the available security settings in WCF, and some common deployment scenarios where the security principles already discussed can be put into practice.

For message protection, WCF supports the two traditional security models, transport security and message security, or a hybrid model of the two (transport security and message credentials). In addition, a great variety of authentication and authorization schemas are supported out of the box to meet the requirements of the most common scenarios. If those schemas do not satisfy your needs, you can easily customize them, as extensibility is one of the strong points of WCF in this area.

Configuring Security in WCF

The binding and behaviors in WCF represent the main entry point for the configuration subsystem and the policies that affect the services at runtime. This rich and configurable environment enables you to create security policies and enforce them at runtime in your services. Choosing the right security schema and policies for your services should only be a matter of determining the initial requirements in terms of message protection, authentication, and authorization.

The bindings, in addition to specifying the communication protocol and encoding for the services, will also allow you to configure the message protection settings and the authentication schema. On the other hand, the behaviors allow you to specify other kinds of security settings such as client and service credentials, credential validators, authorization policies, and managers, to name a few.

The binding selection also influences the available configuration options for the service security policy. For instance, the BasicHttp binding only supports legacy web service protocols, and therefore only transport security can be configured with this binding.

All the configuration settings in the bindings and behaviors can be set either as programming against the configuration object model or through a .NET configuration section.

To avoid bad practices when configuring security, the WCF team restricts the number of security settings that can be used in the configuration section. Username and password credentials represent a good example of this. It would not be a good idea to hardcode some passwords in a configuration file, and for that reason, they are only available in the configuration object model.

To simplify the configuration process even more, all the bindings come with a pre-defined configuration schema that satisfies the most common scenarios. In that way, as long as you do not tweak specific settings, WCF tries to use the default security schema.

Table 7-1 summarizes the default security schema for the most common bindings.

Table 7.1. Default Security Settings

BINDING

SETTINGS

WsHttpBinding

Message Security with Windows Authentication (NTLM or Kerberos)

BasicHttpBinding

No Security

WsFederationHttpBinding

Message Security with Federated Authentication (Issue Tokens)

NetTcpBinding

Transport Security with Windows Authentication (NTLM or Kerberos)

NetNamedPipeBinding

Transport Security with Windows Authentication (NTLM or Kerberos)

NetMsmqBinding

Transport Security with Windows Authentication (NTLM or Kerberos)

Consider the following service configuration that supports WsHttpBinding:

<wsHttpBinding>
  <binding name="UsernameBinding">
    <security mode="Message">
      <message clientCredentialType="UserName"/>
    </security>
  </binding>
</wsHttpBinding>

In this example, the service has been configured with message security and the username security token profile. The rest of the security settings for the binding take the default values.

Now we dive into more details about the different security configuration aspects in WCF.

Security Mode

The security mode setting determines two fundamental security aspects for any service: the security model for message protection and the supported client authentication schema.

Each security mode has its own mechanism for passing the authentication credentials to the service, and therefore some authentication options might not be available according to the selected security model.

For example, federated authentication is supported only with message authentication. If you need to support that security schema, message security is the only option you have.

This setting is available in the configuration model through the Mode property in the security element.

The following examples show how to configure the security mode for a WsHttpBinding using the WCF configuration section, and the equivalent version using the code model:

<wsHttpBinding>
  <binding name="helloWorld">
    <security mode="TransportWithMessageCredential"></security>
</binding>
</wsHttpBinding>

WSHttpBinding binding = new WSHttpBinding();
binding.Security.Mode = SecurityMode.TransportWithMessageCredential;

The possible options for this setting are listed in Table 7-2.

Table 7.2. Security Modes

MODE

DESCRIPTION

None

The service is available for anyone, and the messages are not protected as they go through the transport. When this mode is used, the service is vulnerable to any kind of attack.

Transport

Uses the transport security model for authenticating clients and protecting the messages. This mode provides the advantages and disadvantages discussed in transport security.

Message

Uses the message security model for authenticating clients and protecting the messages. This mode provides the advantages and disadvantages discussed in message security.

Both

Uses the transport security and message security models at the same time for authenticating the service consumers and protecting the messages. This mode is only supported by the MSMQ bindings and requires the same credentials at both levels.

TransportWithMessageCredentials

The message protection is provided by transport, and the credentials for authenticating the service consumers travel as part of the message. This mode provides the flexibility of using any of the credentials or token types supported in message authentication while the service authentication and message protection is performed at transport level.

TransportCredentialOnly

Uses transport security for authenticating clients. The service is not authenticated, and the messages, including the client credentials, go as plain text through the transport. This security mode can be useful for scenarios where the kind of information transmitted between the client and the service is not sensitive, although the credentials also get exposed to anyone.

Protection Level

By default, WCF encrypts and signs all the messages on wire to provide data confidentiality and integrity. In some circumstances, if the message you are sending through the transport does not contain any sensitive information, you might want to turn off encryption and sign the message to preserve the integrity of the data — without concern about confidentially. For those scenarios, WCF provides the flexibility of changing the default protection level when Message Security mode is used.

The protection level can be configured either at service level in the contract definition or at operation level for a more granular control. When the protection level is defined at both levels, the protection level in operation overrides the existing definition on the service level.

Message contracts also support a way to override the protection level for the operation. The [ProtectionLevel] attribute can be specified in the message contract itself or any specific message header or body.

The supported values for the ProtectionLevel setting are None, Sign, and EncryptAndSign.

None disables the message protection. Sign only provides message integrity against any possible change in the original message, and the last one, EncryptAndSign, provides message confidentiality and integrity.

The protection level is only configurable through attributes in the service definition, and it is not available in the binding configuration settings. The following examples illustrate how this setting can change different levels (an operation or a message contract) in the service definition:

[MessageContract(ProtectionLevel = ProtectionLevel.None)]
public class HelloWorldRequestMessage
{
  [MessageHeader]
  public string SampleHeader { get; set; }

  [MessageBodyMember()]
  public string Message { get; set; }
}

[MessageContract]
public class HelloWorldResponseMessage
{
  public string ResponseMessage { get; set; }
}

[ServiceContract(ProtectionLevel = ProtectionLevel.EncryptAndSign)]
public interface IHelloWorld
{
  [OperationContract(ProtectionLevel = ProtectionLevel.Sign)]
  HelloWorldResponseMessage Hello(HelloWorldRequestMessage request);
}

The final result, shown in the previous example, is that the request message will not be protected, and the response message will use the protection level defined for the operation, which is sign only.

Algorithm Suite

The algorithmSuite setting is something specific to message security and determines the set of algorithms that will be used for message integrity and confidentiality. For practical purposes, you should understand that this setting basically affects the way in which WCF generates the final keys for digitally signing and encrypting the messages. The algorithm suite typically represents a pair of algorithms, an asymmetric algorithm for deriving a symmetric key, and a symmetric algorithm for encrypting and signing the messages.

Performing cryptographic operations such as digitally signing or encrypting information with asymmetric keys is very expensive in terms of computer resources such as CPU or memory. For that reason, WCF first generates and derives a symmetric key by using the asymmetric algorithm, and then uses that symmetric key to effectively perform the cryptographic operations.

Note

The default value for this setting is Basic256, which represents a combination of RSA-OAEP as the asymmetric algorithm and AES256 as the symmetric one.

The client and the service must agree on the selected algorithm suite to interoperate well. This is a very important aspect because some platforms or web services stacks only support specific algorithm suites. As long as interoperability is not a concern for you, you should consider leaving the default value for this setting:

<netTcpBinding>
  <binding name="helloWorld">
    <security mode="Message">
      <message algorithmSuite="Basic256"/>
    </security>
  </binding>
</netTcpBinding>

The previous configuration segment shows how that setting can be changed in a NetTcpBinding configured with message security.

Client Credential Type

The client credential type is a very important setting that determines the authentication schema used by your service. It represents the type of credentials expected for authenticating the client or consumer application.

Something that you should know first is that the supported options for this setting will vary according to the selected security mode and transport. Although the available options for message security in the most common bindings are pretty much the same — None, Windows, Username, Certificate, and IssueToken — the options for transport security are limited by the supported authentication schemas in the transport layer itself.

Tables 7-3 and 7-4 illustrate the available options for message security and transport security with a brief description about each one.

Table 7.3. Message Security

CREDENTIAL TYPE

DESCRIPTION

None

The clients are not authenticated by the service. It is equivalent to anonymous authentication.

Windows

The clients are authenticated by the service with traditional Windows authentication through Kerberos or NTLM.

Username

The clients are authenticated by the service with a pair of usernames and passwords.

Certificate

The clients are authenticated by the service using information provided in a X509 certificate.

IssueToken

The clients are authenticated by the service with a token issued by a third party. This is common for federated authentication scenarios.

Table 7.4. Transport Security

CREDENTIAL TYPE

DESCRIPTION

None

Equivalent to None in message security.

Windows

Equivalent to Windows in message security.

Certificate

Equivalent to Certificate in message security.

Basic

The clients are authenticated with Http Basic Authentication. This option is specific to Http.

Digest

The clients are authenticated with Http Digest Authentication. This option is specific to Http.

NTLM

The clients are authenticated with Http Windows Integrated Authentication. This option is specific to Http transport.

There are some exceptions to the previous table for the NetMsqmBinding and the NetNamedPipeBinding.

The first binding replaces the clientCredentialType setting with an equivalent one, msmqAuthenticationMode, which supports WindowsDomain for Windows authentication and Certificate for authentication based on certificates.

The NetNamedPipeBinding only supports transport security with Windows authentication.

This setting is available in the configuration model through two elements, Message and Transport. WCF picks one of these at runtime according to the configured security mode:

<wsHttpBinding>
  <binding name="helloWorld">
    <security mode="Transport">
      <transport clientCredentialType="Windows"/>
      <message clientCredentialType="Windows"/>
    </security>
  </binding>
</wsHttpBinding>

In this example, WCF uses the client credential type definition in the transport element because the security mode has been set to Transport. The message element can still exist in the configuration, but it is ignored by WCF.

Configuring this setting by code can be done in the same way seen with the configuration section:

WSHttpBinding binding = new WSHttpBinding();
binding.Security.Mode = SecurityMode.Transport;
binding.Security.Transport.ClientCredentialType = HttpClientCredentialType.Windows;
binding.Security.Message.ClientCredentialType = MessageCredentialType.Windows;

Service Credentials Authentication and Negotiation

Services in WCF must provide credentials to clients to support mutual authentication and message protection. In other words, the client uses the service credentials for authenticating it before sending a message, and also provides message protection aspects such as data confidentiality and integrity.

In most cases the credentials are automatically negotiated between the client and the service. The SSL handshake in transport security is a good example of this. This handshake allows the server to authenticate itself to the client by proving an X509 public key, and then allows the client and the server to cooperate in the creation of symmetric keys used for message protection during the secure session that follows.

For some message security authentication schemas, WCF gives the flexibility to change this behavior with a specific setting negotiateServiceCredentials. By default, WCF automatically negotiates the credentials at message level using protocols such as TLSNego when the client credentials are set to None, Username, or Certificate, or SPNego only when they are set to Windows. This mechanism to negotiate the credentials is something specific to WCF, so you should disable it to interoperate well with other service stacks or platforms. That can be accomplished as shown next:

<wsHttpBinding>
  <binding name="helloWorld">
    <security mode="Message">
      <message clientCredentialType="Certificate"
               negotiateServiceCredential="false" />
    </security>
  </binding>
</wsHttpBinding>

When this setting is disabled, in case of certificate credentials, the service certificate must be provided to all the clients prior to establishing a communication with the service, and the clients should refer to the service certificate in their configuration:

<clientCredentials>
  <serviceCertificate>
    <defaultCertificate findValue="WCFService"
       storeLocation="LocalMachine" storeName="My"
       x509FindType="FindBySubjectName"/>
  </serviceCertificate>
</clientCredentials>

The service authentication is performed by WCF at the moment of establishing the communication by comparing the provided credentials with the configured identity element in the service endpoint. If that element is not configured, WCF will try to assume default values prior to making the comparison. For example, in case you are using certificate credentials, WCF will check whether the subject name in the certificate matches the Internet name of the server.

In most cases, you have to define the service endpoint identity explicitly. That can be done by adding an identity element to the endpoint configuration:

<endpoint name="sampleProxy"
    address="http://localhost:8000/helloWorld/"
    bindingConfiguration="sampleBinding"
    behaviorConfiguration="sampleBehavior"
    binding="wsHttpBinding"
    contract="WCFBook.Samples.IHelloWorld">
    <identity>
      <dns value="WCFService"/>
    </identity>
</endpoint>

The equivalent version using the object model would be the following:

ServiceEndpoint ep = myServiceHost.AddServiceEndpoint(
typeof(WCFBook.Samples.IHelloWorld),
new WSHttpBinding(),
String.Empty);

EndpointAddress myEndpointAdd = new EndpointAddress(
new Uri("http://localhost:8000/helloWorld"),
EndpointIdentity.CreateDnsIdentity("WCFService"));

ep.Address = myEndpointAdd;

In the previous example, the service should provide a certificate with a subject name equal to WCFService to be successfully authenticated by WCF.

WCF supports five types of identities for a service. Their uses depend on the scenario you want to implement and the security requirements that the services demand. All the possible values for the identity types are discussed in Table 7-5.

Table 7.5. Identity Types

IDENTITY TYPE

DESCRIPTION

Domain Name System (DNS)

This type of identity is valid for X509 certificates or Windows accounts. The value specified in this element must match the Windows account name or the certificate subject name. In case of certificates, as long as the subject name does not change, the identity check is still valid.

Certificate

This type specifies an X509 certificate encoded as Base64. As you need to encode the entire certificate, which includes unique information such as the certificate thumbprint, this identity type represents a more precise alternative to the DNS identity.

A downside is that you need to hardcode the complete certificate representation in the WCF configuration.

Certificate Reference

Pretty similar to the previous option. The main difference is that this identity type enables you to specify a certificate name and the location in the certificate store rather than hard coding the credential representation. It requires a previous deployment of the certificate in the Windows certificate store.

RSA

This identity type specifies a certificate RSA key. This option enables you to specifically restrict authentication to a single certificate based on a certificate key. As the certificate option, the key representation must be specified in Base64 encoding.

User Principal Name (UPN)

This identity type is specific to Windows authentication and specifies the UPN that the service is running under. This option is used by default when the service process is not running under of one the system accounts. In other words, it ensures that the service is running under a specific Windows account, which can be either the current logged-on user or any user account.

Service Principal Name (SPN)

This identity type is also specific to Windows authentication and specifies the SPN associated with the account that is running the service process. This option is used by default when the service process is running under the system accounts LocalService, LocalSystem, or NetworkService.

WCF can automatically negotiate the value for this identity when the service is configured with Windows authentication and the negotiateServiceCredential for message security is set to true.

Secure Sessions

Secure sessions represent the last aspect that we discuss here before jumping into more concrete examples in the next chapter.

Secure sessions or secure conversations provide a way to improve the service response time when a client application needs to interchange more than one message with the service.

When this feature is enabled, the credential negotiation and authentication happen once during the first message interchange between the client and the service. Otherwise, these two steps are performed for every service call.

You should not confuse this type of session with typical Http-based sessions. WCF secure sessions are initiated by the clients and are there to support some kind of shared context between the client and the service.

This feature represents a specific implementation of the WS-SecureConversation and WS-Trust specifications in WCF, and therefore demands the use of message security.

In the way secure conversation works under the hood, the client first sends a special message RequestSecurityToken (with SOAP action http://schemas.xmlsoap.org/ws/2005/02/trust/RST/Issue) to the service for a session token. This message is part of the WS-Trust specification and contains a reference to the client credentials that will be used to create the session token:

<s:Envelope xmlns:s="..." xmlns:a="...">
  <s:Header>
    <a:Action s:mustUnderstand="1">
      http://schemas.xmlsoap.org/ws/2005/02/trust/RST/Issue
    </a:Action>
    <a:MessageID>urn:uuid:d55bd2a7-bae8-4751-a010-07e95fd82ee2</a:MessageID>
    <a:ReplyTo>
      <a:Address>http://www.w3.org/2005/08/addressing/anonymous</a:Address>
    </a:ReplyTo>
    <a:To s:mustUnderstand="1">http://localhost/HelloWorld</a:To>
  </s:Header>
  <s:Body>
    <t:RequestSecurityToken Context="uuid-f422503c-7974-42ab-9b8a-c330727290e9-1"
                          xmlns:t="http://schemas.xmlsoap.org/ws/2005/02/trust">
     <t:TokenType>http://schemas.xmlsoap.org/ws/2005/02/sc/sct</t:TokenType>
     <t:RequestType>
       http://schemas.xmlsoap.org/ws/2005/02/trust/Issue
     </t:RequestType>
     <t:KeySize>256</t:KeySize>
     <t:BinaryExchange
       ValueType="http://schemas.xmlsoap.org/ws/2005/02/trust/spnego"
       EncodingType="http://docs.oasis-open.org/wss/2004/01/
         oasis-200401-wss-soap-message-security-1.0#Base64Binary">
     </t:BinaryExchange>
    </t:RequestSecurityToken>
  </s:Body>
</s:Envelope>

After the service receives the message and authenticates the client credentials, it creates a new session token called Secure Context Token (SCT) which references the client credentials and a symmetric key to perform cryptographic operations such as encrypt or sign messages (message confidentiality and integrity).

The service sends the session token back to the client using a RequestSecurityTokenResponse message (with SOAP action http://schemas.xmlsoap.org/ws/2005/02/trust/RSTR/Issue), and keeps track of the original credentials using different strategies such as encrypted Http cookies or in-memory caches:

<s:Envelope xmlns:s="..." xmlns:a="...">
  <s:Header>
    <a:Action s:mustUnderstand="1">
      http://schemas.xmlsoap.org/ws/2005/02/trust/RSTR/Issue
    </a:action>
    <a:RelatesTo>urn:uuid:d55bd2a7-bae8-4751-a010-07e95fd82ee2</a:RelatesTo>
  </s:Header>
  <s:Body>
  <t:RequestSecurityTokenResponse
     Context="uuid-f422503c-7974-42ab-9b8a-c330727290e9-1"
     xmlns:t="http://schemas.xmlsoap.org/ws/2005/02/trust"
     xmlns:u="http://docs.oasis-open.org/wss/2004/01/
       oasis-200401-wss-wssecurity-utility-1.0.xsd">
     <t:BinaryExchange
       ValueType="http://schemas.xmlsoap.org/ws/2005/02/trust/spnego"
       EncodingType="http://docs.oasis-open.org/wss/2004/01/
         oasis-200401-wss-soap-message-security-1.0#Base64Binary">
      </t:BinaryExchange>
    </t:RequestSecurityTokenResponse>
  </s:Body>
</s:Envelope>

In that way, the client can later protect messages with the symmetric key included in the session token or use the session token itself as a client credential.

The most important benefits of using a SCT to protect communication between the client and service are as follows:

  1. The service response time is three or four times faster than the same execution with other credentials as the client is authenticated only the first time and the symmetric session key is used to protect communication.

  2. It is valid for a short time but it can be automatically renewed as it is used. As a consequence, the client application does not need to keep the original credentials. This is an important aspect when the original credentials contain sensitive information such as a username or password.

From the perspective of the client application, secure conversation is something completely transparent that WCF keeps at channel level. For that reason, the session token is reused as long as the client application uses the same instance of the client channel.

When the client channel is closed in a normal fashion, a message is sent to the service to shut down the session and release all the associated resources. If the channel closes abruptly, the session will eventually be shut down on the service side after a fixed period of inactivity.

This feature is enabled by default for all the bindings that support message security (WS-Security). The custom binding also offers the possibility of enabling Secure Conversation by setting the value SecureConversation to the authenticationMode attribute. In addition, you can configure a binding that will be initially used to negotiate the session token by means of the element secureConversationBootstrap.

The following configuration shows how secure conversation can be enabled for a wsHttpBinding, and the equivalent version with a custom binding:

<bindings>
  <wsHttpBinding>
    <binding name="ServiceBinding">
      <security mode="Message">
        <message clientCredentialType="Certificate"
           establishSecurityContext="true"/>
      </security>
    </binding>
  </wsHttpBinding>

  <customBinding>
    <binding name="ServiceBinding">

      <security authenticationMode="SecureConversation"
            requireSecurityContextCancellation ="false">
        <secureConversationBootstrap authenticationMode="MutualCertificate">
        </secureConversationBootstrap>
      </security>
      <httpTransport/>
    </binding>
  </customBinding>
</bindings>

The attribute requireSecurityContextCancellation in the previous configuration specifies whether the client application must send a shutdown message to the service after closing the client channel. When this attribute is set to false, WCF uses an encrypted cookie to keep the state of the session token instead of keeping it in memory on the service side. As the cookies travel in every message to the service, they are ideal for web farm scenarios where intermediary servers or load balancers are used, and there is no guarantee that all the messages are handled by the same server.

You cannot reuse the client channel for sending more than one message to the same service because the benefits of using secure conversation get lost. The extra overhead associated with the initial handshake will affect your service performance, and you should consider disabling this feature when that happens.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.225.149.238