Thursday, January 30, 2014

WCF Tutorial Part-V

Module 8

Implementing WCF Security

Security is an essential consideration for any distributed application. The application relies on the capabilities of the underlying infrastructure and the access provided by the framework; therefore, it is important for you to understand both of these aspects. The security policy associated with your application defines the types of credentials you can use and the level of message integrity and privacy your application requires. This policy governs which bindings are suitable for use with the Windows® Communication Foundation (WCF) client applications and services that form part of your application.
·         Lesson 1:
·         Overview of Security in WCF
·        
·         WCF provides a rich set of security features from which you can choose. To make this selection, you must understand what each of these features provides for your application.

Security Objectives in WCF

The specification for a system typically expresses the security requirements for that system in terms of the authentication, authorization, integrity, and confidentiality of messages and the data that they contain. The following table lists examples of the types of questions that you must consider before you implement a security policy for a system.
Concept
Requirement Questions
Authentication
How do users of the system identify themselves to the system?
·         Do they enter a user name and password or do they have some form of smart card?
·         Is there some form of biometric identity system or have they installed a certificate in their browser?
·         Will they have one identity that spans the whole system or different identities for different parts of the system?
Must you identify users or is it sufficient for them to remain anonymous?
Authorization
What sensitive information does the system hold?
Who is allowed to access that information?
Are there resources to which access should be limited?
How do you associate users with access to specific information or resources?
Integrity
Must the system protect data from alteration in transit?
Is detection sufficient or must the system prevent it?
Privacy
What sensitive data does the system pass across the network?
To what degree must the system protect that data?
Are all parts of the network equally untrusted or is privacy required for only some messages and not others?

Additional Reading

For more information about how to build security into your application design, see "Microsoft patterns & practices Security Guidance for Applications Index" on the MSDN Web site.


Authentication Mechanisms

There are four sources of authentication information that a client can present to a service:
Source
Description
User name and password
This is the simplest authentication mechanism that involves passing a user name and password pair to the service in one form or another. The service will then be responsible to ensure that these match and are associated with a valid user identity.
Windows security token
If the user has authenticated with a Windows domain, he or she can present his or her Windows security token to the service as a means of authentication.
Issued token
In a broader context (for example, an organization) you may use a security token service such as Kerberos that issues an authentication token that can be presented to the service as a means of authentication.
Certificate
For Internet, extranet, and very large organizations, you can use certificates issued by a third-party certification authority as a way to authenticate users to services.
The transport-level credential types (Basic, Digest, NTLM, Windows, Certificate) and message-level credential types (UserName, Windows, IssuedToken, Certificate) offered by WCF all use one of these mechanisms. You can differentiate between the types of credentials in various ways. Some mechanisms rely on what a user knows (such as user name and password), whereas others rely on something given to the user.
When you decide what sort of authentication mechanism to use, you must consider how much control you have over the computers and networks that make up your system. You must also compare the technical and administrative awkwardness of some of these mechanisms against the risk of a security breach. The attributes of the credentials used by the different authentication mechanisms form part of the decision-making process. There is a scale of distance between the principal and the issuing authority (the Windows operating system is the closest and the certification authority is the furthest away). This makes it more difficult to quickly replace credentials such as certificates issued by third parties if they are compromised. There is also a scale of lifespan that goes a different way (such as certificate, user name and password, Windows token, or issued token). If an access token is compromised, there is a far smaller window of opportunity for someone to take advantage of this (because it times out fairly quickly) than if a certificate is stolen.
Authentication works both ways. The client may want to authenticate the service and the service may want to authenticate the client.

Additional Reading

For more information about the authentication mechanisms available in Windows, see "Explained: Windows Authentication in ASP.NET 2.0" on the MSDN Web site.


Authorization Mechanisms

The Microsoft® .NET Framework 2.0 provides access to three authorization mechanisms. You can:
·         Assign a user to a Windows role and then use that role as the basis on which to grant or deny access to the resource.
·         Achieve a similar effect with Microsoft ASP.NET roles if your application is Web-based.
·         Create a custom authorization mechanism and hook that into your application.
All of these mechanisms are still available for you to use in WCF applications and the .NET Framework 3.5.
WCF also includes a new authorization mechanism named claims-based authorization. This authorization mechanism addresses some of the issues that you will encounter if you use the previous techniques and also provides a uniform authorization framework that is independent of the transport.

Additional Reading

For more information about authentication in WCF, see "Access Control Mechanisms" on the MSDN Web site.


Claims-Based Security in WCF

The security model in Windows Communication Foundation (WCF) provides a new, claims-based approach to authorization. This enables you to represent almost any security token as a set of claims. These claims range from simple user names and passwords to X509 certificates. By using claims-based authorization, you can normalize the claims across all the different transport mechanisms that are used to access your application, which makes access control more consistent and maintainable.
As an example, consider an application that receives messages over two different endpoints that use different types of credentials. The first endpoint may use certificates to authenticate the client and the second endpoint uses Windows authentication. In each case, you can assume that the authentication information contains:
·         One or more credentials that help the receiver decide if it wants to allow the user to access a particular operation or resource. For a certificate, this can be a common name such as "CN=Fred", and for Windows authentication, it can be the Windows security identifier (SID) of the caller.
·         An issuer that asserts that this particular set of credentials is genuine. For a certificate, this would be the certification authority that signed the certificate. For Windows authentication, it would be the domain security system (as identified by its SID).
One way to approach this would be to access the individual credential types exposed by WCF (WindowsIdentity and X509Identity) and programmatically examine them. However, this would require you to write specific code for each authentication mechanism. Under the claims-based identity model, WCF will map both of these sets of credentials to a ClaimSet. The ClaimSet is associated with an issuer and contains individual claims that represent aspects of the credentials passed. For a certificate, the claims would be aspects of identity such as the common name in the certificate or the type of encryption used. For a Windows identity, the claims would be the SIDs of the caller and the groups to which they belong. The service can then use the claims presented by the client to decide on access to resources.
At this point, you are not much further forward in some ways because the two claim sets in the example represent different types of identity. However, you now have a common framework under which one type of credential (claim) can be mapped to another or where both types of credential can be mapped to a different type of claim on which access control can be based.
There are different predefined types of claim such as e-mail address, Uniform Resource Identifier (URI), and so on. Claims also have a right associated with them. Currently, the two preprovided rights are Identity (which represents an identity) and PossessProperty (elements of data or permissions that the given identity possesses).
This example has focused on claims to assess identity and basic access permissions. However, you can also use claims to represent access rights to a particular resource regardless of the caller's identity. In this case, if the ClaimSet contained a claim that states that the caller possessed the property read for subject WCFFile.doc and was vouched for by an issuer trusted by the service, the service would agree to give the call access to that file.

Additional Reading

For more information about how claims work in WCF, see "Security Briefs: Exploring Claims-Based Identity" on the MSDN Web site.
For more information about how to use claims to create a custom authentication model, see the Microsoft MSDN® Webcast: Windows Communication Foundation Top to Bottom (Part 11 of 15): Federated Security (Level 200) .


Integrity and Confidentiality

WCF provides developers with the ability to specify the integrity and confidentiality required when passing messages. Maintaining the integrity of a message means that if anyone alters the message contents after it has left the sender, the receiver will be able to detect that such a change has taken place. Maintaining the confidentiality of a message means that nobody will have been able to read and understand the message contents since it left the sender.
You can specify your integrity and confidentiality requirements at the transport level and at the message level. It is important to differentiate between transport-level security and message-level security:
·         Transport-level security uses a transport protocol such as Hyper Text Transfer Protocol Secure (HTTPS) to achieve transfer security at the level of the network protocol. Transport-level security is widely adopted and available on many platforms. However, transport-level security only secures messages from point-to-point.
·         Message-level security uses WS-Security to achieve transfer security at the application level. The message carries this security information inside the Simple Object Access Protocol (SOAP) envelope together with the application data; this means that it is independent of the transport protocol. Because the message carries the security information, it ensures end-to-end security.
Under both transport-level security and message-level security, the enforcement of integrity and confidentiality relies on the use of digital certificates to provide validated public keys that can be used for encryption and digital signatures.

Additional Reading

For more information about integrity and confidentiality in terms of distributed systems and transfer security, see "Distributed Application Security" on the MSDN Web site.

Delivering Message-Level Integrity

WCF provides message-level integrity as follows:
1.    The sender calculates a checksum for the message content and then uses the sender's private key to encrypt the checksum.
2.    This encrypted checksum is then bundled with the message content and the sender’s certificate to create the overall message.
3.    The sender then sends the message to the recipient (potentially over multiple hops).
4.    The recipient extracts the sender’s public key from the certificate.
5.    The recipient uses this public key to decrypt the checksum sent with the message.
6.    The recipient recalculates the checksum for the message content.
7.    If the two checksums match, the message content has not been altered since the sender calculated the original checksum.

Additional Reading

For more information about the mechanics of message-level data integrity, see "Exchange Data More Securely with XML Signatures and Encryption" on the MSDN Web site.


Delivering Message-Level Confidentiality

WCF provides message-level confidentiality as follows:
1.    The sender obtains the receiver’s certificate and extracts the receiver’s public key.
2.    The sender uses the receiver’s public key to encrypt the message content.
3.    The sender forms the encrypted content into a message and sends it to the receiver (potentially over several hops).
4.    The receiver then uses its private key to decrypt the message contents. The receiver can decrypt the message with the receiver’s private key. If the message has been tampered with, it will not decrypt correctly.

Additional Reading

For more information about the mechanics of message-level data integrity, see "Exchange Data More Securely with XML Signatures and Encryption" on the MSDN Web site. 


Delivering Transport-Level Confidentiality

You can summarize the way that WCF provides transport-level confidentiality through a protocol such as HTTPS as follows:
1.    The sender and receiver use the public and private keys in their certificate(s) to exchange symmetric session keys that they use to encrypt messages. Session key encryption is faster than the public and private keys in certificates.
2.    The sender encapsulates the message content in a Simple Object Access Protocol (SOAP) message.
3.    Nobody can view or tamper with the message because the channel encrypts everything sent across it. This mechanism provides only point-to-point protection.

Additional Reading

For more information about HTTPS, see "RFC 2660".


Applying Security in WCF

Security is a very important issue for many organizations. Most organizations have a security policy that relates to their use of IT and defines aspects of security such as:
·         Who can access the different systems in an organization. For example, only people who work in the accounts department can access the financial system.
·         Who is permitted to access particular sets of organizational data. For example, a policy may state that only senior managers and people who work in the Human Resources department should have access to staff personnel records.
·         The level of protection that certain data must have in transit. For example, patient records must be encrypted when they are sent over the Internet.
Such a security policy is likely to form part of the context for your application. Therefore, specific security requirements will map to elements of system architecture and design.
There are different mechanisms in WCF that help you to enforce your security requirements. The primary tool is the binding that you select and the security options that you set on that binding. You then use behaviors to enforce aspects of authentication and authorization. You will see how this works throughout the rest of this module.

Additional Reading

For more information about how to apply security in WCF, see "Securing Services and Clients" on the MSDN Web site.


Federated Security

The primary objective of federated security is to prevent a user from having to maintain different sets of credentials for different systems and resources. Duplication of credentials is an overhead and leads to insecure practices such as writing down passwords. Typically, each group of systems on a local network has some common security framework such as a Windows domain. Federation involves setting up a trust relationship between two realms (a collection of systems under a common security framework is also know as a realm) so that users from one realm can access resources in another without having to reauthenticate.
The following table lists elements that are fundamental concepts in federated security.
Element
Description
Domain/Realm
A single unit of security administration or trust. A typical domain may include a single organization.
Federation
A set of domains or realms that have established a trust relationship. The level of trust may vary, but it typically includes authentication and authorization.
Security Token Service (STS)
A service that issues security tokens allows access to protected resources.
A user in one realm can authenticate himself or herself with the STS for his or her realm. The user can then present a token from his or her own STS to the STS of the realm on which the target resource exists. This other STS can refer to information about the trust relationship between the two realms when you decide whether to issue a token that allows the user to access the target resource.
WCF provides turnkey support for federated security through the wsFederationHttpBinding element.

Additional Reading

For more information about federated security, see "Federation" on the MSDN Web site.

Lesson 2:
Applying Overall Security Requirements to a Binding
The bindings provided by WCF have a powerful set of security features to help you enforce an appropriate level of security in your application.

Security Modes for Bindings

The following table describes the different types of security mode available with WCF.
Mode
Description
None
WCF does not provide any form of security at the transport layer or at the message layer.
Transport
WCF uses a secure transport such as HTTPS for integrity, confidentiality, and mutual authentication.
Message
WCF uses SOAP-message security (WS-Security) for integrity, confidentiality, and mutual authentication.
TransportWithMessageCredential
WCF uses transport security for integrity, confidentiality, and server authentication. Uses SOAP message security for client authentication. This is also known as mixed mode.
Both
WCF performs protection and authentication at both levels.
TransportCredentialOnly
WCF does not provide integrity or confidentiality. Uses the transport to provide client credentials.

Additional Reading

For more information about how to apply binding security modes, see "Programming WCF Security" on the MSDN Web site.
For more information about the security capabilities of specific bindings, you must refer to their individual pages in the WCF documentation. For example, see "<security> of <basicHttpBinding>" on the MSDN Web site.

Applying Default Security Settings

Each predefined WCF binding has a default security mode. The following table shows the default security mode values for commonly used bindings.
Binding
Default security mode
basicHttpBinding
None
wsHttpBinding
Message
netTcpBinding
Transport
netNamedPipeBinding
Transport

Additional Reading

For more information about security modes on bindings, see the security elements of the individual bindings under "<bindings>" on the MSDN Web site.


Transport-Level Security Mode

The specific protocol used to deliver transport-level security depends on the binding that you choose. For example, if you select basicHttpBinding and choose transport-level security, the binding will use HTTPS. However, if you use netTcpBinding, setting the security mode to Transport will cause WCF to use Transport Layer Security (TLS) over TCP or the Simple and Protected GSS-API Negotiation (SPNEGO). In some cases, you may have to make configuration changes to the system on which the client or service runs such as installing a Secure Sockets Layer (SSL) certificate.
The following code example shows two ways in which you can set the security mode for a binding.
[Visual Basic]
Dim binding As New BasicHttpBinding(SecurityMode.Transport)

' Alternatively, set the mode property.
binding.Security.Mode = BasicHttpSecurityMode.Transport

[Visual C#]
BasicHttpBinding binding =
                         new BasicHttpBinding(SecurityMode.Transport);

// Alternatively, set the mode property.
binding.Security.Mode = BasicHttpSecurityMode.Transport;
After you select transport-level security, there are properties that you can specify that are specific to the transport that you use. For example, if you use the native TCP transport that underlies netTcpBinding, you can set a protection level to indicate that messages should be signed, both encrypted and signed, or neither. You can also set the client credential type to Windows, Kerberos, or none.
You can find the set of values to which you can programmatically set the security mode in the SecurityMode enumeration.

Additional Reading

For more information about transport-level security, see "Transport Security Overview" on the MSDN Web site.
For more information about how to set security modes on bindings in code, see the Security property and the constructors of the individual bindings in the WCF documentation.


Applying Security Mode Through Configuration

Each ServiceModel binding element in the application configuration file has a security child element through which you can set the desired security mode. To apply a different security mode from the default, you must provide a binding configuration with the appropriate mode set and reference this from your service endpoint.
The following example shows how you can enforce transport-level security through a binding configuration.
<bindings>
  <basicHttpBinding>
    <binding name="myBasicHttpBindingConfig">
      <security mode="Transport"/>
    </binding>
  </basicHttpBinding>
</bindings>

Additional Reading

For more information about security modes on bindings in configuration files, see the security elements of the individual bindings under "<bindings>" on the MSDN Web site.

Message-Level Security Mode

When you select message-level protection, WCF uses the WS-Security protocols to protect the message contents inside the SOAP message. By default, WCF signs and encrypts message contents when you select the Message security mode.
You must assess the advantages and disadvantages of choosing message-level security or transport-level security when you design your application. For example, message-level security requires more resources and is usually slower than transport-level security, but it does secure the message end-to-end.
There are a variety of algorithms that you can use to encrypt messages and create digital signatures. Each one has its own set of properties that you can use to specify the level of security. You can use the algorithmSuite property to set the message encryption and key-wrap algorithms. The properties of the SecurityAlgorithmSuite class expose the possible algorithms. These algorithms map to those specified in the WS-SecurityPolicy specification. The default algorithm is Basic256.
The following example shows how to set message-level security by using a configuration file.
<basicHttpBinding>
  <binding name=“bankInteropBinding">
    <security mode="Message">
      <message clientCredentialType="Certificate"
                     algorithmSuite="Basic256Rsa15" />
    </security>
  </binding>
</basicHttpBinding>
The following is the equivalent code.
[Visual Basic]
Dim binding As New BasicHttpBinding(SecurityMode.Message)

' or alternatively
binding.Security.Mode = BasicHttpSecurityMode.Message

' and then
binding.Security.Message.AlgorithmSuite = _
    SecurityAlgorithmSuite.Basic256Rsa15
binding.Security.Message.ClientCredentialType = _
    BasicHttpMessageCredentialType.Certificate

[Visual C#]
BasicHttpBinding binding =
    new BasicHttpBinding(SecurityMode.Message);

// or alternatively
binding.Security.Mode = BasicHttpSecurityMode.Message;

// and then
binding.Security.Message.AlgorithmSuite =
    SecurityAlgorithmSuite.Basic256Rsa15;
binding.Security.Message.ClientCredentialType =
    BasicHttpMessageCredentialType.Certificate;

Additional Reading

For more information about message-level security, see "Message Security in WCF" on the MSDN Web site.
For more information about the different algorithms, see "[Algorithm Suite] Property".

Selecting Security Modes for Bindings

Not all bindings provide all security modes. The main reason that a binding may not provide all security modes is because the binding does not support some fundamental characteristic that the security mode requires. The following table lists which bindings support which modes.
Binding
Transport Security
Message Security
BasicHttp
HTTPS
WS-Security
WSHttp
HTTPS
WS-Security
WSDualHttp
Not supported
WS-Security
NetTcp
Transport Layer Security (TLS)
WS-Security
NetNamedPipe
Transport Layer Security (TLS)
Not supported
MsmqIntegration
MSMQ Transport Security
Not supported
NetMsmq
MSMQ Transport Security
WS-Security
WSFederationHttp
HTTPS
WS-Security
If you specify an invalid mode for a binding, an exception is thrown at run time.

Requiring a Protection Level

You can specify the protection level required by messages sent to operations. The following table lists the values of protection level you can request.
Setting
Description
None
No protection
Sign
Digitally signs the given part of the message to ensure its integrity.
EncryptAndSign
Encrypts the part of the message before digitally signing it.
The following code shows an example of setting a protection level for all operations on a service contract.
[Visual Basic]
<ServiceContract([Namespace] := "http://myuri.org/Simple", _
    ProtectionLevel := ProtectionLevel.None)> _
Public Interface IBank
    ...
End Interface

[Visual C#]
[ServiceContract(Namespace="http://myuri.org/Simple",
    ProtectionLevel=ProtectionLevel.None)]
public interface IBank
{
   ...
}
The message protection level builds on the capabilities of the security mode to request that WCF signs or encrypts part or all of a message. You can request a particular message protection level at various points. For example, you can specify a ServiceContract or OperationContract attribute that requires messages sent to a particular service or operation to be protected to the specified degree. If the security capabilities of the binding do not support that level of protection, an error occurs.
There are some restrictions on what you can specify. For example, if the security mode is set to Transport, all parts of the message must have the same protection level.
The protection level affects only application data in the message. WS-Addressing headers are infrastructure data; therefore, the protection level setting does not affect them.

Additional Reading

For more information about the protection level, see "Understanding Protection Level" on the MSDN Web site.

Web Service Security

WS-SecurityPolicy defines an XML-based language for expressing a security policy. WS-SecurityPolicy is an implementation of the WS-Policy specification. The WS-MetadataExchange specification enables the exchange of policy information as part of a metadata exchange between a service and a tool such as svcutil.exe. This means that the tool can download the security requirements for the service and incorporate these requirements in the client-side artifacts that it generates such as the client proxy.

Additional Reading

For more information about WS-SecurityPolicy, see "Web Services Security Policy Language (WS-SecurityPolicy)".
For more information about WS-MetadataExchange, see "Web Services Metadata Exchange (WS-MetadataExchange)".

Protecting Connections to Older Web Services

Older Web services such as those created by using ASP.NET 2.0 or 1.1 do not support WS-SecurityPolicy and the set of Web service protocols that enable more recent services to enforce rich and complex security requirements. The developers of such older Web services may have implemented them with no security requirements if they were intended for internal use and do not expose sensitive data or functionality. This type of service can be accessed by using a basicHttpBinding on the WCF client and setting the security mode to None.

Additional Reading

For more information about interoperability with older Web services, see "Interoperability with ASP.NET Web Services" on the MSDN Web site.


Internet Security for Older Web Services

People and organizations had been building and deploying Web services for many years before the advent of the WS-* protocols. Many of these services have been deployed in scenarios that require security, so they have usually been protected by using HTTPS, potentially with client certificates. If you build WCF components that must communicate with a protected, older Web service, you can use a basicHttpBinding binding with the security mode set to Transport. You can then decide what type of client credentials you require to achieve an adequate level of authentication.
This type of transport-only security should also work with older Web Services that require the client to connect to an HTTPS URL.

Additional Reading

For more information about Web Service transport security, see "<transport>" on the MSDN Web site.

Lesson 3:
Specifying Required Client and Service Credentials
WCF enables clients and services to request credentials from each other to ensure that each side can identify the party that they exchange messages with.

Transport-Level Client Credential Types

A transport-based binding configuration can specify one of six client credential types. The following table describes these types.
Value
Description
None
Security is disabled.
Basic
Uses basic authentication. The caller passes the user name and password in clear text as part of the authentication.
Digest
Uses digest authentication. The side that demands authentication provides a one-time value, and the caller creates a hash of the user name, the password, the specific one-time value, the Hypertext Transfer Protocol (HTTP) method, and the requested URI. The side that demands the authentication recreates this hash and compares the two values to determine whether to authenticate the client.
Ntlm
Uses NTLM as a fallback within a Windows domain if Kerberos is not available.
Windows
Uses integrated Windows authentication. This can use Kerberos or NTLM.
Certificate
Uses X.509 certificates to authenticate the caller.
Each binding supports some or all of the credential types. You should refer to the documentation for the specific binding to learn which credential types it supports.
The following code example shows an example of how to set the client credential type for transport-mode security.
[Visual Basic]
binding.Security.Mode = BasicHttpSecurityMode.Transport
binding.Security.Transport.ClientCredentialType = _
    HttpClientCredentialType.Ntlm

[Visual C#]
binding.Security.Mode = BasicHttpSecurityMode.Transport;
binding.Security.Transport.ClientCredentialType =
    HttpClientCredentialType.Ntlm;

Additional Reading

For more information about basic and digest authentication, see "RFC 2617".
For more information about the benefits of different credential types, see "Selecting a Credential Type" on the MSDN Web site.


Message-Level Client Credential Types

A message-based binding configuration can specify one of five client credential types. The following table describes these types.
Setting
Description
None
Specifies that the client does not have to present any credential. This translates to an anonymous client.
Windows
The client must present a Windows token for authentication.
Username
The client must present a user name/password combination for authentication.
Certificate
The client must provide an X.509 certificate to be authenticated.
Issued Token
The client must present a custom token type configured to a security policy. The default token type is SAML. The token is issued by a Secure Token Service (STS).
Each binding supports some or all of the credential types. You should refer to the documentation for the specific binding to learn which credential types it supports.
The following code shows an example of how to set the client credential type for message mode security.
[Visual Basic]
binding.Security.Mode = BasicHttpSecurityMode.Message
binding.Security.Message.ClientCredentialType = _
    BasicHttpMessageCredentialType.Certificate

[Visual C#]
binding.Security.Mode = BasicHttpSecurityMode.Message;
binding.Security.Message.ClientCredentialType =
    BasicHttpMessageCredentialType.Certificate;

Additional Reading

For more information about the benefits of different credential types, see "Selecting a Credential Type" on the MSDN Web site.
For more information about issued tokens, see "Federation and Issued Tokens" on the MSDN Web site.


Requiring Credentials

You can request that a message provides the credentials of the sender programmatically or through the binding configuration. The binding-specific enumerations you use in code are limited to the set of credentials supported by that particular binding.
The credentials can be required by the service (the client must provide them in its request messages) or by the client (the service must provide them in its response messages).
The following code example shows how you can define the credential type to use for a message exchange in code.
[Visual Basic]
Dim binding As New BasicHttpBinding(SecurityMode.Transport)

binding.Security.Mode = BasicHttpSecurityMode.None

binding.Security.Transport.ClientCredentialType = _
    HttpClientCredentialType.Windows

[Visual C#]
BasicHttpBinding binding =
    new BasicHttpBinding(SecurityMode.Transport);

binding.Security.Mode = BasicHttpSecurityMode.None;

binding.Security.Transport.ClientCredentialType =
    HttpClientCredentialType.Windows;
The equivalent configuration settings would be the following.
<bindings>
  <basicHttpBinding>
    <binding name="myBasicHttpBindingConfig">
      <security mode="Transport">
        <transport clientCredentialType="Windows"/>
      </security>
    </binding>
  </basicHttpBinding>
</bindings>

Additional Reading

For more information about how to set the required credential type, see "How To: Specify the Client Credential Type" on the MSDN Web site.


Supplying Credentials

The credentials required for communications between a client and a service are exchanged when the communications are first established. If a client requires a service to provide its credentials before accepting response messages, it is often impractical to provide credentials in code on the server side (if you cannot establish the identity of a service before communicating with it, you cannot receive response messages). You should always provide service-side credentials through a behavior.
There is a balance to strike between protecting the credentials so that they do not appear in a configuration file and hard-coding credential-handling code.

Additional Reading

For more information about how to specify client credentials, see "How To: Specify Client Credential Values" on the MSDN Web site.


Supplying Credentials Programmatically

When you generate a proxy through svcutil.exe or by adding a service reference in Microsoft Visual Studio® 2008 development system, it contains properties that match the service security policy defined in the WS-SecurityPolicy metadata for the service. You can then set the appropriate values for these properties to provide the credentials that identify the user that is running the client.
The following code shows an example of code that specifies a user name and password to use for authentication.
[Visual Basic]
' Proxy
proxy.ClientCredentials.UserName.UserName = "Fred"
proxy.ClientCredentials.UserName.Password = "My_Pa$$wd"

' Channel factory
Dim factory As New ChannelFactory(Of IBankService)()
factory.Credentials.UserName.UserName = "Fred"
factory.Credentials.UserName.Password = "My_Pa$$wd"

[Visual C#]
// Proxy
proxy.ClientCredentials.UserName.UserName = "Fred";
proxy.ClientCredentials.UserName.Password = "My_Pa$$wd";

// Channel factory
ChannelFactory<IBankService> factory =
    new ChannelFactory<IBankService>();
factory.Credentials.UserName.UserName = "Fred";
factory.Credentials.UserName.Password = "My_Pa$$wd";

Additional Reading

For more information about how to specify client credentials, see "How To: Specify Client Credential Values" on the MSDN Web site.


Supplying Credentials by Using Behaviors

You can use the clientCredential child element of the behavior element in the configuration file to create a custom behavior that specifies the value of a credential. You can then reference this custom behavior from one or more endpoint bindings. WCF will then use this credential value when a client requires that credential type. You can specify credential information for different types of security so that you can share the behavior across multiple bindings that use different authentication mechanisms.
The following example shows a binding configuration that contains credentials.
<endpointBehaviors>
  <behavior name=“bankServiceCredentialBehavior ">
    <clientCredentials>
      <serviceCertificate>
        <defaultCertificate
           findValue="SubjectKey"
           storeLocation="LocalMachine"
           storeName="TrustedPublisher"
           x509FindType="FindBySubjectName"/>
    </clientCredentials>
  </behavior>
</endpointBehaviors>

Additional Reading

For more information about how to specify client credentials, see "How To: Specify Client Credential Values" on the MSDN Web site.

Windows CardSpace and WCF Credentials

By using Windows CardSpace, users can choose from a portfolio of identities that belong to them and use them in contexts where they are accepted, independent of the identity systems where the identities originate and are used. The card simply contains the identity information and is not preauthenticated in any way.
Some cards are issued by third parties who provide authentication and authorization associated with the credentials held on the card.

Additional Reading

For more information about Windows CardSpace and WCF, see "Using CardSpace in Windows Communication Foundation" on the MSDN Web site.


Demonstration: Setting Security Modes and Credentials


Lesson 4:
Working with Security Information
Service operations may have to access security information as part of their operation on behalf of the client or to check the credential or authorization level of a caller. This requires programmatic access to security information inside the service.

Accessing Security Information in a Service

The ServiceSecurityContext class represents the security context of the remote party that a client or service communicates with. On the client side, it represents the identity of the service with which the client interacts. On the service side, it represents the identity of the client that invoked the operation.
The following code shows how a service can access the Windows identity of the calling client.
[Visual Basic]
If ServiceSecurityContext.Current Is Nothing Then
    Console.WriteLine("Called without a security context")
Else
    Console.WriteLine("Windows identity is {1}", _
        ServiceSecurityContext.Current.WindowsIdentity.Name)
End If

[Visual C#]
if (ServiceSecurityContext.Current == null)
{
    Console.WriteLine("Called without a security context");
}
else
{
    Console.WriteLine("Windows identity is {1}",
        ServiceSecurityContext.Current.WindowsIdentity.Name);
}

Additional Reading

For more information about how to programmatically access the security context, see "How To: Examine the Security Context" on the MSDN Web site.


Accessing Identity Information

The PrimaryIdentity class is a simple representation of the remote party.
The WindowsIdentity class provides more information than is provided by IIdentity; for example, it provides group and Windows security ID information. If the remote party cannot be associated with a Windows account, the IsAnonymous property is set to true.

Additional Reading

For more information about the WindowsIdentity class, see "WindowsIdentity class" on the MSDN Web site.


Enforcing Authorization Requirements

If you use role-based authorization (either Windows or ASP.NET), you must check if the principal identity provided by the remote party is in a role authorized to access a particular resource. You use the serviceAuthorization service behavior to change the role provider.
The following code shows how to use role-based authorization on the current principal associated with the caller.
[Visual Basic]
If Thread.CurrentPrincipal.IsInRole("BUILTIN\Administrators") Then
    ' Access protected resources
End If

[Visual C#]
if (Thread.CurrentPrincipal.IsInRole(@"BUILTIN\Administrators"))
{
    // Access protected resources
}

Additional Reading

For more information about how to use the ASP.NET role provider, see "How To: Use the ASP.NET Role Provider with a Service" on the MSDN Web site.


Accessing Claims Programmatically

As noted earlier in the module, WCF introduces another option for service authorization in the claims-based model.
A claim is the expression of a right with respect to a particular value. Examples of rights include Read, Write, and Execute. Examples of values include a database, a file, a mailbox, and a property. Claims also have a claim type. The combination of claim type and right provides the mechanism for specifying capabilities with respect to the value. For example, a claim of type File with right Read over the value WCF.doc indicates that the entity with which this claim is associated has read access to the file WCF.doc.
The Claim type represents an individual claim. A ClaimSet is a collection that holds multiple Claims. You can retrieve the claims associated with the remote party through the AuthorizationContext and the ServiceSecurityContext classes. You can then search this ClaimSet for claims of a particular type and ensure that they have the value you expect. Typically, the code shown on the slide would be part of a custom authorization manager.
The following code shows an example of how claims may be used by a custom authorization manager.
[Visual Basic]
Dim authContext As AuthorizationContext = _
    operationContext.ServiceSecurityContext.AuthorizationContext

For Each cs As ClaimSet In authContext.ClaimSets
    If cs.Issuer = ClaimSet.System Then
        For Each c As Claim In _
        cs.FindClaims("http://example.org/claims/allowedoperation", _
        Rights.PossessProperty)
            If actionUri = c.Resource.ToString() Then
                Return True
            End If
        Next
    End If
    Return False
Next

[Visual C#]
AuthorizationContext authContext =
      operationContext.ServiceSecurityContext.AuthorizationContext;

foreach(ClaimSet cs in authContext.ClaimSets)
{
  if (cs.Issuer == ClaimSet.System)
  {
    foreach (Claim c in
        cs.FindClaims("http://example.org/claims/allowedoperation",
            Rights.PossessProperty))
    {
      if (actionUri == c.Resource.ToString())
      return true;
    }
  }

  return false;                
}

Additional Reading

For more information about how to handle authentication with claims, see "Managing Claims and Authorization with the Identity Model" on the MSDN Web site.
For more information about the claims-based model, see "Security Briefs: Exploring Claims-Based Identity" on the MSDN Web site.


Impersonation

Impersonation allows the service to perform activities such as connecting to a database or opening files by using the identity of the client. Impersonation has obvious security issues, so you should use it with care; however, it does make auditing a lot easier.
The following table lists the values of the ImpersonationOption that you can use on the OperationBehavior.
Description
Allowed
Impersonation is performed if credentials are available and ImpersonateCallerForAllOperations is equal to true.
NotAllowed
Impersonation is not performed. If ImpersonateCallerForAllOperations is equal to true, a validation exception occurs at service startup time.
Required
Impersonation is required
The following code shows an example of an operation behavior that allows impersonation.
[Visual Basic]
<OperationBehavior(ImpersonationOption.Allowed)> _
Public Sub Deposit(ByVal account As String, ByVal amount As Decimal)
    ...
End Sub

[Visual C#]
[OperationBehavior(ImpersonationOption.Allowed)]
public void Deposit(string account, decimal amount)
{
    ...
}

Additional Reading

For more information about impersonation in WCF, see "Delegation and Impersonation with WCF" on the MSDN Web site.
For more information about how to implement impersonation in WCF, see "How To: Impersonate a Client on a Service" on the MSDN Web site.

Demonstration: Accessing Security Information


Lab: Protecting a Service

Scenario

The Contoso, Ltd Clinic Management System allows users to access sensitive patient data; the system then passes that data across the clinic network. You must ensure that only authorized users can access the patient data and that this data is encrypted at all times when it is in transit.

Exercise 1: Applying Security for Internal Network Communication


In this exercise, you will start to protect the connections made by the ClinicAdminClient application. This requires you to apply message-level security to a message exchange to sign and encrypt message contents. You will then ensure that only authorized users can access patient data.
The main tasks for this exercise are as follows:
1.    Start the 6461A-LON-DEV-08 virtual machine and log on as Student.
2.    Apply message-level encryption to a service.
3.    Apply message-level encryption to a client.
4.    Use message logging to see the effects of message-level encryption on the message contents.
5.    Display caller credentials in the service.
6.    Provide Windows credentials from the client to the service.

Task 1: Start the 6461A-LON-DEV-08 virtual machine and log on as Student

1.    Open the Virtual Server Remote Control Client, and then double-click 6461A -LON-DEV-08.
2.    Log on to 6461A -LON-DEV-08 as Student by using the password Pa$$w0rd.

Task 2: Apply message-level encryption to a service

1.    Open Microsoft Visual Studio® 2008 development system as ADMINISTRATOR.
2.    Open the starter solution ConnectedWCF.sln:
    • If you are using Microsoft Visual Basic® development system, browser to the E:\Labfiles\Starter\VB\InternalNetwork\ConnectedWCF folder, and then double-click ConnectedWCF.sln.
    • If you are using Microsoft Visual C#® development tool, browse to the E:\Labfiles\Starter\CS\InternalNetwork\ConnectedWCF folder, and then double-click ConnectedWCF.sln.
3.    In the ContosoServicesSelfHostExtConfig project, use the WCF Configuration Editor window to add a new netTcpBinding binding configuration named NetTcpSecureMessageBindingConfig with the following settings:
    • Message-level security
    • Basic128 algorithm
    • Windows client credential type
4.    Set the appointment service TCP endpoint (APService_TCP) to use this binding configuration.

Task 3: Apply message-level encryption to a client

1.    In the ClinicAdminClient project, use the WCF Configuration Editor to edit the existing appointment service TCP endpoint binding configuration (APService_TCP) to specify the same security settings that you applied to the service endpoint in Task 2.
2.    Rebuild the solution, and then verify that there are no errors.

Task 4: Use message logging to see the effects of message-level encryption on the message contents

1.    In Visual Studio 2008, run the WCF service and client.
2.    On the Clinic Administration Client form, list the available appointment slots, and then stop debugging.
3.    From the Microsoft Windows SDK, open the Microsoft Service Trace Viewer.
4.    Open the E:\LabFiles\logs\messages.svclog file.
5.    On the Message tab, click the most recent message with an action of http://contoso.com/ClinicManagementSystem/2007/10/AppointmentServiceContract/ListAvailableAppointmentTimesResponse.
Note: You will see each message and response listed twice. This is because WCF has logged each message at both the message level and the transport level.
6.    In the lower-right pane, click the Message tab, and then examine the SOAP message that was passed from the transport level to the message level. This message is encrypted. Scroll down to find the SOAP body. You can see an <e:CipherValue> element that contains the encrypted version of the list of available appointment slots.
7.    In the left pane, click the previous message with an action of http://contoso.com/ClinicManagementSystem/2007/10/AppointmentServiceContract/ListAvailableAppointmentTimesResponse. In the lower-right pane, scroll down again to the SOAP message body. You can see that this is an unencrypted list of available appointment times. This is the SOAP message that was passed from the service to the message level and so has not yet been encrypted.
8.    Close the Service Trace Viewer.

Task 5: Display caller credentials in the service

1.       In the AppointmentService project, edit the AppointmentServiceImplementation class, and then locate the TODO 1 comment. Add a new static (Shared) method named ShowSecurityInformation that takes a string parameter. You will write code in the next step to call this method passing in the name of the method calling ShowSecurityInformation as its parameter. In this method, add code to write a message to the console to show the identity under which the operation runs. The identity information should include the thread principal, the primary identity, and the Windows identity of the operation.
2.       In the ListAvailableAppointmentTimes method, locate the TODO 2 comment, and then add a statement to call the ShowSecurityInformation method, passing "ListAvailableAppointmentTimes" as the parameter.
3.    Run the WCF service and client.
4.    On the Clinic Administration Client form, list the available appointment slots, and then locate the ContosoServicesSelfHostExtConfig console window. Check that the security information displayed shows LON-DEV\Student for the thread principal, the primary identity, and the Windows identity of the request.

Task 6: Provide Windows credentials from the client to the service

1.    In the ClinicAdminClient project, edit the ClinicAdminForm class, in the findSlots_Click method, locate the TODO 3 comment. Change the type of the proxy variable to AppointmentServiceContractClient. This type provides access to the proxy security information through the proxy variable.
2.    Locate the TODO 4 comment, and then add code to explicitly set the credentials used when you call the service. Use an intentionally fake user name (such as "Fred"), password (such as "Secret"), and domain (such as "TestDomain").
3.    Run the WCF service and client.
4.    Click Find Slots, and then examine the SecurityNegotiationException exception that occurs because of the invalid credentials.
5.       Stop debugging, and then change the values for the Windows credentials. Specify a user name of LocalAdmin, a password of Pa$$w0rd, and a domain of LON-DEV.
6.    Run the ClinicAdminClient, and then list the available appointment slots. Locate the ContosoServicesSelfHostExtConfig console window. Check that the security information displayed shows LON-DEV\LocalAdmin for the thread principal, the primary identity, and the Windows identity of the request.
7.    Close Visual Studio 2008.
Results: After completing this exercise, you should have seen how to secure message contents by using message-level security and how to pass Windows credentials from a client to a service.

Exercise 1: Answer Key (detailed steps)


Exercise 2: Applying Security for Internet Communication

Scenario

The Clinic Management System enables remote family practitioner administrators to make appointments for patients. You must ensure that only authorized users can make such appointments and that the system encrypts the data when it is in transit across the Internet.
In this exercise, you will secure the connections made by the family practitioner client application to the appointment service. This requires you to apply transport-level security to a message exchange that encrypts the entire communication, including message headers. You will then ensure that only authorized users can access patient data.
The main tasks for this exercise are as follows:
1.    Create and install an SSL certificate on Internet Information Services (IIS).
2.    Create an IIS-based Web site to host your service.
3.    Add the service functionality to your IIS-based Web site.
4.    Call the SSL-protected service.

Task 1: Create and install an SSL certificate on IIS

1.    Open a Microsoft Visual Studio 2008 Command Prompt window as ADMINISTRATOR.
2.    In the Command Prompt window, type the following command.
makecert -sr LocalMachine -ss My -n CN=LON-DEV -sky exchange -sk HTTPS-Key
This command creates a certificate that you can use to test HTTPS communications on your computer.
Note: This is a test certificate only. You should never deploy certificates generated by using the makecert command in a production environment.
3.    On the Start menu, click Control Panel, click System and Maintenance, click Administrative Tools, and then double-click Internet Information Services (IIS) Manager.
4.    In Internet Information Services (IIS) Manager, in the left pane, expand the LON-DEV node, expand Web Sites, right-click Default Web Site, and then click Edit Bindings.
5.    In the Web Site Bindings dialog box, click Add. In the Add Web Site Binding dialog box, set Type to https, set the SSL certificate to LON-DEV, and then click OK.
6.    In the Web Site Bindings dialog box, click Close.

Task 2: Create an IIS-based Web site to host your service

1.    Open Microsoft Visual Studio 2008 as ADMINISTRATOR.
2.    Open the starter solution ConnectedWCF.sln:
o    If you are using Visual Basic, browse to the E:\Labfiles\Starter\VB\Internet\ConnectedWCF folder and then double-click ConnectedWCF.sln.
o    If you are using Visual C#, browse to the E:\Labfiles\Starter\CS\Internet\ConnectedWCF folder, and then double-click ConnectedWCF.sln.
3.    Add a new Web site to the ConnectedWCF solution with the following settings:
o    Use the WCF Service template.
o    Set the Location to HTTP.
o    If you are using Visual Basic, set the Language to Visual Basic.
o    If you are using Visual C#, set the Language to Visual C#.
4.    Click Browse, and in the Choose Location dialog box, in the left pane, click Local IIS. In the right pane, click Default Web Site, and then in the upper-right corner of the dialog box, click Create New Virtual Directory.
5.    In the New Virtual Directory dialog box, enter ContosoInternetGateway as the Alias name, and then next to the Folder box, click Browse.
6.    In the Browse For Folder dialog box, browse to one of the following:
o    If you are using Visual Basic, browse to the E:\Labfiles\Starter\VB\Internet\ConnectedWCF folder.
o    If you are using Visual C#, browse to the E:\Labfiles\Starter\CS\Internet\ConnectedWCF folder.
7.    In the toolbar, use the New Folder function to create a new folder named ContosoInternetGateway.
8.    In the Browse For Folder dialog box, click Select Folder.
9.    In the New Virtual Directory dialog box, click OK.
10. In the Choose Location dialog box, click the ContosoInternetGateway folder. At the bottom of the dialog box, select the Use Secure Sockets Layer check box, and then click Open.
11. In the Add New Web Site dialog box, verify that the address for the new Web site is https://localhost/ContosoInternetGateway, and then click OK.
12. In the Internet Information Services (IIS) Manager, in the left pane, expand the LON-DEV node, expand Web Sites, expand Default Web Site, and then click the ContosoInternetGateway node. In the main pane, click Features View.
13. In the main panel, in the IIS section, double-click SSL Settings.
14. In the SSL Settings pane, select Require SSL, but leave all the other properties at their default values.
15. In the right pane, click Apply.
16. In the Internet Information Services (IIS) Manager navigation bar, click Back, and then in the main panel, double-click Authentication.
17. In the Authentication pane, click Basic Authentication.
18. In the right pane, click Enable.
19. Close Internet Information Services (IIS) Manager.

Task 3: Add the service functionality to your IIS-based Web site

1.    Switch to Microsoft Visual Studio 2008.
2.    In the https://localhost/ContosoInternetGateway/ project, remove the files under the App_Code folder, and then add a reference to the AppointmentService project.
3.    Rename Service.svc as AppointmentService.svc. Edit the file to remove the CodeBehind attribute, and then set the service to com.contoso.AppointmentService.AppointmentServiceImplementation.
4.    Open the web.config file by using the WCF Configuration Editor, and then rename the existing Service to com.contoso.AppointmentService.AppointmentServiceImplementation.
5.    Configure the first (Empty Name) endpoint in the list of service endpoints with the following settings:
o    Binding: basicHttpBinding
o    Contract: com.contoso.AppointmentService.AppointmentServiceContract
o    Name: APService_HTTPS
o    Leave the Address property empty. IIS handles this for you.
6.    Configure the second (Empty Name) endpoint with the following settings:
o    Binding: mexHttpsBinding
o    Name: Metadata_HTTPS
7.    Add a new basicHttpBinding binding configuration named BasicHttpSecureTransportBindingConfig that has the following settings:
o    Transport-level security
o    No transport client credential type
8.    Configure the appointment service HTTP endpoint to use this binding configuration.
9.    Change the existing serviceMetadata behavior to set the HttpsGetEnabled property to true and the HttpGetEnabled property to false.
10. Rebuild the solution and ensure that it builds successfully.
11. Start Windows Internet Explorer® and go to the URL https://localhost/ContosoInternetGateway /AppointmentService.svc. Internet Explorer will display the message "There is a problem with this Website's security certificate." Click Continue to this Website. You should then see the service test page for the AppointmentServiceImplementation.
12. Close Internet Explorer.
Note: The Web site security problem is a result of the test certificate. Certificates generated by using the makecert commend do not have a valid certification authority and cannot be verified. If you ever see this warning when you connect to a production Web site, it is recommended that you do not click Continue to this Website.

Task 4: Call the SSL-protected service

1.    In the FPAdminClient project, edit the FPAdminForm class, in the GetAppointmentServiceProxy method locate the //TODO 5 comment, and then make the following changes:
o    Change the URL of the endpoint address to https://localhost/ContosoInternetGateway/AppointmentService.svc
o    Alter the BasicHttpBinding to pass the value BasicHttpSecurityMode.Transport into the constructor.
2.    In the FPAdminClient project, in the WCF Configuration Editor window change the existing appointment service HTTP endpoint binding configuration (APService_HTTP) so that is has the same security settings that you applied to the service endpoint in Task 3.
3.    Run the WCF service and client.
4.    Click Find Slots. This should result in an exception with the message "Could not establish a trust relationship for the SSL/TLS secure channel with authority 'localhost'." This exception occurs because the client binding cannot validate the certificate presented to it by the service (it has the same problem that Internet Explorer has because the certificate does not have a valid certification authority). To overcome this, you must handle the validation yourself.
5.    Stop the application, return to Visual Studio 2008, and then edit the PermissiveCertificatePolicy class. This class contains code that enables you to specify that the client should automatically trust a certificate with a specified value in its subject. Locate the RemoteCertValidate and Enact methods, and then confirm that RemoteCertValidate returns true (valid) if the certificate refers to the name passed into the Enact method.
6.    Add a statement to the FPAdminForm class that calls the Enact method on PermissiveCertificatePolicy, passing the name used in the certificate: "CN=LON-DEV".
[Visual Basic]
'TODO 5
PermissiveCertificatePolicy.Enact("CN=LON-DEV")

[Visual C#]
//TODO 5
PermissiveCertificatePolicy.Enact("CN=LON-DEV");
7.    Run the WCF service and client.
8.    Click Find Slots. This time the operation should be successful and display the list of possible appointments.
Note: The PermissiveCertificatePolicy class is provided to enable you to test your applications against the test certificate. You should never use this technique to bypass the validation mechanism of certificates in a production application.
Results: After completing this exercise, you have should seen how to secure message contents across the Internet by using transport-level security.

Exercise 2: Answer Key (detailed steps)


Module 9

Implementing Transactions

Service-oriented applications are inherently distributed. If your solution requires transactions, they may span more than one service, in which case you must design the relevant operations exposed by each service to support distributed transactions. The services that take part in transactions must propagate the transaction information to the resources affected by these transactions. Finally, you must decide where transactions start and stop. You can start your transactions explicitly in code or implicitly at service boundaries?
·         Lesson 1:
·         Overview of Transactions in a Service-Oriented Application
·        
·         Windows® Communication Foundation (WCF) provides settings that you can use to initiate transactions and propagate them between services and operations. To use these settings successfully, it is important to understand how distributed transactions work and what facilities must be in place to enable them.

Transaction Properties

Transactions should ensure the integrity of the data used by your services, and they must provide a consistent view of that data to the outside world. The transactional capabilities of Windows Communication Foundation (WCF) help your services maintain the ACID properties of any transactions that they participate in. These properties are:
·         Atomic. Either all the operations that participate in a transaction must complete successfully; if any of them fail, all the work performed by any completed operations must be undone.
·         Consistent. The transaction is not allowed to lose data or information. The state of the system at the end of the transaction must be consistent with the state at the start of the transaction and the operations performed by the transaction. For example, in a system that performs balance transfers between bank accounts, a transaction that deposits money in one account must perform an equivalent withdrawal from another account. This ensures that the amount of money in the system is the same at the end of the transaction as it was at the start.
·         Isolated. While a system performs a transaction, it can be in an inconsistent state, but it must not expose this inconsistent state to the outside world. For example, when you transfer money between bank accounts, a system can withdraw money from the source account first and then deposit the money into the target account. After performing the withdrawal, but before performing the deposit, the system is in an inconsistent state. However, other transactions should not normally be able to see the data in this state.
·         Durable. When a transaction completes, it should be made permanent. Transactions cannot be lost. In the event of a subsequent failure, you must be able to return to recover the system to the state that it was in when the transaction finished.

Additional Reading

For more information about the essential elements of transactions, see "Transaction Processing Fundamentals" on the MSDN Web site.
For more information about the ACID properties of transactions, see "ACID Properties" on the MSDN Web site. 


Coordinating Transactions

In a typical transaction, your code will cause changes to several transactional resources such as relational databases. You use a transaction when you want to be sure that either all the changes you cause are persisted or that they all roll back.
The principles of transactions are as follows. As application code executes, it changes the state of transactional resources such as databases or message queues. At the end of a particular execution sequence, the application either makes all of the changes permanent (the changes are committed) or undoes all of the changes (the changes are aborted or rolled back). To do this, you require:
·         Transaction-aware resource managers, which manage access to each transactional resource. Typical transactional resource managers include relational databases such as Microsoft® SQL Server® and transactional messaging systems such as Microsoft Message Queuing (also known as MSMQ).
·         A transaction context that identifies the current transaction (if there is one) and is carried in every call to a transactional resource.
·         A transaction coordinator that enables the resource managers to act in unison.
The resource manager identifies the transaction context and contacts the transaction coordinator to enlist in that particular transaction. The resource manager keeps track of what has changed as part of that transaction and guarantees the correct level of isolation from other transactions.
The transaction coordinator oversees the transaction and keeps track of which resource managers have enlisted. When the transaction reaches the end of its scope (completes), the transaction coordinator performs a two-phase commit (2PC) with the resource managers. At this time:
·         Each resource manager votes to commit or abort the transaction.
·         If one resource manager votes to abort, the transaction will abort.
·         If all resource managers vote to commit, the transaction will commit.
Whatever the decision, the transaction coordinator then instructs all the resource managers to either commit or abort—there is no middle ground.
By using the Microsoft .NET Framework, you can work with transactions that are local or distributed. In a local transaction, your code makes changes to one or more locally configured transactional resources. Although the resource itself, for example a database, may be hosted on another computer, the transaction counts as local because you deal with the resource directly through a connection. In other cases, you may call services across a network that work with their own set of transactional resources. If you call several such services, you must make sure that they take part in one single transaction. In this case, you must use a distributed transaction so that it extends to all transactional resource managers to which remote code makes changes. The principles of transactions are the same whether they are local or distributed.
Resource managers keep hold of locks on resources to ensure the correct levels of isolation, so you should design this type of transaction to be relatively short-lived (seconds at most). For longer-lived transactions, you would have to use a compensating transaction. You can find more information about compensating transactions in the "Distributed Transactions" section later in this module.

Additional Reading

For more information about transaction propagation, see "Transaction Processing Fundamentals" on the MSDN Web site.
For more information about the two-phase commit sequence, see "Two-Phase Commit" on the MSDN Web site.


Transaction Context

For a resource manager to know whether the current request to access its associated transaction resource forms part of a transaction, it must be able to inspect part of the execution context of the current thread. If the current thread is part of an ongoing transaction, part of that execution context will be the transaction context that contains an identifier that the resource manager can use to enlist with the transaction coordinator.
After it enlists as part of the current transaction, the resource manager keeps track of changes made to the resource (data added, updated, or removed) so that it can apply them if the transaction coordinator issues a commit instruction or roll them back if the transaction coordinator issues an abort instruction.
When an application handles resource managers in a single process address space, it is sufficient to store the transaction context in the current thread and interact with a local transaction coordinator. When execution becomes distributed and you leave the current address space, additional measures are required to ensure the coordination of the transaction.

Additional Reading

For more information about transaction context under the Windows operating system, see "Transaction Management in Windows" on the MSDN Web site.
For more information about how WCF handles transaction context, see "WCF Transaction Propagation" on the MSDN Web site.

Distributed Transactions

Distributing transactions across process address spaces brings its own set of problems such as:
·         How does the transaction context cross the process boundary?
·         Can the transaction context have the same representation in the other process?
·         What happens if an error occurs in the other process?
·         What happens if a problem occurs when marshaling back and forth between processes?
The same issues apply to transactions that are distributed across systems and propagated over networks—only more so. You must also consider communication delays and errors. Extending timeouts to allow for networking delays leads to resources being locked for longer periods of time. Longer lock periods increases the potential for what threading specialists call "liveness" problems in your application.
Because these are difficult problems to solve, you may be tempted to look for an alternative solution. One alternative is to have the users of the resources undo their own changes (usually referred to as compensating transactions). At a high level, it makes sense considering the loosely coupled nature of service-oriented systems, but this approach has its own set of tricky problems to solve. Consequently, the W3C standards body have opted for the coordinated approach and developed the WS-AtomicTransaction standard, which defines how transactional information should flow in a service-oriented environment.

Additional Reading

For more information about transaction propagation under Windows in general, see "Transaction Management in Windows" on the MSDN Web site.
For more information about transaction propagation under WCF, see "WCF Transaction Propagation" on the MSDN Web site.
For more information about compensating transactions, see "Compensating Transactions"

Coordinating Distributed Transactions

Microsoft introduced the Distributed Transaction Coordinator (DTC) as part of Microsoft Transaction Server (MTS) and then COM+ inherited it. As its name suggests, its original purpose was to coordinate transactions running on different computers. Each computer taking part in a distributed transaction coordinated by DTC must run its own instance of the DTC. Each DTC instance communicates with resource managers running on that computer for enlisting and performing a two-phase commit. The DTC on the computer on which the transaction originates is sometimes referred to as the transaction root. It takes on the role of an overarching transaction coordinator. The transaction root works with the resource managers on that computer (if any) and the DTC instances on the other computers to coordinate a distributed two-phase commit.
The DTC was originally designed to work with durable resource managers such as those for databases and message queues. However, it has been extended to work with volatile resource managers. This means that as a developer, you do not have to worry about the scope of a transaction because it is automatically promoted as required when it crosses the relevant boundary.

Additional Reading

For more information about the DTC, see "Distributed Transaction Coordinator in COM+ Documentation" on the MSDN Web site.


Web Services and Transactions

The WS-Coordination (WS-COOR) specification defines a structure for the context that can be carried by a distributed operation so that the operation can take part in a coordinated exchange of instructions and information between two or more services. It also defines the framework that governs the exchange of such information in general terms that supports both tightly coupled transactions and loosely coupled workflow-style long-running transactions.
Building on WS-COOR, the WS-AtomicTransaction specification defines the extensions that are required to support the type of tightly coupled transactions discussed so far in this course. It provides solutions for the sort of problems that occur specifically in “activities having a short duration and executed within limited trust domains.” The industry body OASIS has ratified both the WS-Coordination and WS-AtomicTransaction specifications.
Microsoft Distributed Transaction Coordinator (DTC) implements its own native transaction protocol named OLE Transactions. This is the default protocol for any transactional interaction that uses DTC. Recently, DTC has been adapted to support the WS-COOR and WS-AT Web service protocols so that WCF developers can use these open protocols and enable interoperability with non-Microsoft Web services and clients.

Additional Reading

For more information about WS-AtomicTransaction, see "Web Services Atomic Transaction (WS-AtomicTransaction) specification".
For more information about WS-Coordination, see "Web Services Coordination (WS-Coordination) specification".
For more information about the DTC's native transaction protocol, see the "OLE Transactions Standard" on the MSDN Web site.
For more information about enabling WS-AT on a computer running Windows, see "WS-Atomic Transaction Configuration Utility" on the MSDN Web site.

Lesson 2:
Creating Transactional Service Operations
WCF enables you to specify the transactional characteristics of a service and control the way that clients use that service

Selecting a Transaction-Aware Binding

Only certain protocols are capable of supporting an atomic transaction; consequently, only the following predefined WCF bindings support transactions:
·         NetTcpBinding
·         NetNamedPipeBinding
·         WSHttpBinding
·         WSDualHttpBinding
·         WSFederationHttpBinding
If you use any of the other predefined WCF bindings for a transactional service, a run-time exception is thrown.
To ensure that the transaction context propagates between the client and the service, both sides must set the transactionFlow property of the binding that they use to true. By default, this engages the OLE Transaction protocol to propagate transactions. If you want to use Web service transactions, you must also specify the Web service transaction protocol, as shown here.
<bindings>
  <wsHttpBinding>
    <binding name = "BankExtranet" transactionFlow = "true"
         transactionProtocol="WSAtomicTransactionOctober2004"/>
  </wsHttpBinding>
</bindings>

Additional Reading

For more information about how WCF deals with transactions and bindings, see "Windows Communication Foundation Transactions Overview" on the MSDN Web site.
For more information about the use of the transactional attributes of bindings, see "Enabling Transaction Flow" on the MSDN Web site.


Setting Transactional Requirements of an Operation

By default, WCF does not make incoming transactions accessible to the service code; if a call from a client application tries to propagate transaction context in this situation, a run-time exception is thrown. The service contract designer can modify the level of transactional support for every operation in the service contract by setting the TransactionFlow attribute to one of the following values:
·         Allowed. This value indicates that if a client application provides a transaction context, the WCF runtime will pass this context information to the operation, enabling it to participate.
·         Mandatory. This value indicates that a client application must provide a transaction context when it invokes the operation; otherwise, the WCF runtime will throw an exception.
·         NotAllowed. This value indicates that any transaction context created by a client application will be ignored by the WCF runtime.
When the WCF runtime propagates a transaction to an operation, you can use the methods in the System.Transaction namespace in the .NET Framework library to control the transaction.

Additional Reading

For more information about transaction flow, see "WCF Transaction Propagation" on the MSDN Web site. 
For more information about the transaction flow attribute, see "TransactionFlowAttribute Class" on the MSDN Web site.
For more information about general .NET transaction programming, see "System.Transactions Namespace" on the MSDN Web site.


Defining Isolation and Timeout for an Operation

It is often very important in a transactional application to control how the ongoing operation of one transaction affects another transaction by setting the isolation level. You can set this through the TransactionIsolationLevel property of the service behavior. The following table shows the values that you can set for the TransactionIsloationLevel and their meanings.
Value
Description
Serializable
The resource manager must give the impression that no other transactions are working on the data. If another transaction must change data that a serializable transaction has read or written, that transaction must block until the serializable transaction completes.
This is the default value.
RepeatableRead
A transaction with this setting must always read the same value after it reads some data. However, other transactions can update the data in parallel with the first transaction.
ReadCommitted
The transaction will read data that has been committed at the point it queries the data.
ReadUncommitted
As yet uncommitted changes to data made by another transaction will be visible during the transaction.
Snapshot
This is a special form of ReadCommitted. Before a transaction modifies data, it verifies whether another transaction has changed the data after it was initially read. If the data has been updated, an error is raised. This allows a transaction to get to the previously committed value of the data.
Chaos
The pending changes from more highly isolated transactions cannot be overwritten.
Unspecified
A different isolation level than the one specified is being used, but the level cannot be determined. An exception is thrown if this value is set.
The service behavior also enables the service implementer to specify the timeout applied to the transaction. This is the length of time after which the WCF runtime automatically rolls back the transaction if it has not finished.

Additional Reading

For more information about the values and effects of these properties, see "ServiceModel Transaction Attributes" on the MSDN Web site.


Controlling Transactions on Service Operations

The TransactionScopeRequired property of the OperationBehaviorAttribute has a slightly misleading name. If you set it to true, the operation will always execute in a transaction as long as the binding that you use supports transactions. However, if it is set to false, the method will not execute in the scope of a transaction. The following table explains the behavior of the TransactionScopeRequired property when used with and without a binding that supports transactions.
Property Value
Transaction-Aware Binding
Client Flows Transaction
Result
False
No
No
Operation executes without a transaction
True
No
No
Operation creates and executes in a new transaction
True or False
No
Yes
A Simple Object Access Protocol (SOAP) fault is returned for the transaction header
False
Yes
Yes
Operation executes without a transaction
True
Yes
Yes
Operation executes under the flowed transaction

Additional Reading

For more information about the effects of the TransactionScopeRequired property, see "OperationBehaviorAttribute.TransactionScopeRequired Property" on the MSDN Web site. 


Demonstration: Automatic Transaction Initiation


Lesson 3:
Enabling the Flow of Transactions from Client to Service
Some transactions start at service boundaries and some start explicitly in the calling code. To propagate transactions, you must configure the client application and the service. When you use transactions under WCF, you must consider how transactions affect other service behaviors viewed from the client application such as exception handling and instance management.

Configuring a Client to Propagate Transactions

You must configure both the client application and the server bindings so that transaction context flows from the client to the service. The transactionFlow property of the binding used by the client application endpoint in the configuration file must be set to true, and the type of transaction specified in the binding must match the type specified on the service side. Alternatively, you can write code in the client application to perform this configuration.

Additional Reading

For more information about how WCF deals with transactions and bindings, see "Windows Communication Foundation Transactions Overview" on the MSDN Web site.
For more information about the use of the transactional attributes of bindings, see "Enabling Transaction Flow" on the MSDN Web site.

Starting a Transaction on the Client

Sometimes it is sufficient to start transactions at service boundaries. At other times, you must create client applications (which may take the form of Windows-based applications or other services) that take control of their own transactions. In this case, you use the standard .NET transaction classes to start, manage, and commit or abort your transactions. There is nothing specific to WCF that you must do in code to make your transactions work in a distributed environment. The .NET Framework and the WCF infrastructure handle all this for you.
It is usually better to keep transactional interaction on the server-side because the client computer may be widely distributed or may not be able to run the DTC or an equivalent transaction controller. In this case, the service methods that make up the transaction are batched together as part of an operation on another service specifically designed to manage such groups of operations. Such a service operation is usually referred to as a façade after the Façade design pattern.

Additional Reading

For more information abut how to start and manage transactions, including the TransactionScope class, see "Features Provided by System.Transactions" on the MSDN Web site.
For more information about how to use the Façade pattern to batch together methods, see the Façade design pattern in Design Patterns: Elements of Reusable Object-Oriented Software by Erich Gamma, Richard Helm, Ralph Johnson, and John M. Vissides (published by Addison-Wesley Professional).
For more information about using the Transaction Script design pattern, see Patterns of Enterprise Application Architecture by Martin Fowler (published by Addison-Wesley Professional).

Handling Client Transaction Exceptions

Under normal conditions, the success or failure of a transaction depends on the votes of the resource managers and code involved in the transaction. However, if an exception occurs in an implicit transaction scope DTC assumes that the transaction has failed and then rolls back the work done. For a WCF application, this means that any WCF-related exception such as a communication timeout causes an exception to be thrown and the transaction to roll back.
There are transaction-specific exceptions that WCF generates under various circumstances such as when:
·         No transaction is provided when the service contract mandates one.
·         A transaction is provided when the service contract does not permit one.
·         The client and service transaction types are mismatched.
·         The client and service isolation levels are mismatched.
·         The client or service does not have transactionFlow enabled.

Additional Reading

For more information about the behavior of implicit transactions when exceptions occur, see "TransactionScope Class" on the MSDN Web site.

Transactional Behavior of Instances and Sessions

Any form of long-running transaction (30 seconds or longer in duration) causes you to consider questions about how to roll back any changes it has made if it fails later in its execution. You may encounter such issues if your application uses a long-running service instance such as one that uses the PerSession or Single instance management modes, particularly if the instance stores data in memory or in a non-transactional persistent store such as the file system.
The accumulated wisdom of many developers of transactional systems is that wherever possible, you should save transactional data to a transactional store. This means that the resource managers take responsibility for isolation, rollback, and commit changes instead of the service code. All shared data must be persisted at the end of any method call and retrieved as required at the start of the next one. This means that the PerCall instance mode is usually best because it avoids the possibility of holding any data between operation calls that may affect the result of the transaction.

Additional Reading

For more information about transactions, instances and sessions, see "ServiceModel Transaction Attributes" on the MSDN Web site.

Demonstration: Transaction Flow from Client to Service


Lab: Implementing Transactions for a Service

Scenario

You are a developer for the Contoso, Ltd Clinic Management System. The requirement for making an appointment states that the creation of the appointment and the issuing of the appointment letter must be performed together.

Exercise 1: Controlling the Flow of a Transaction from Client to Service


In this exercise, you will flow a transaction from client to service to ensure that appointments are not marked as taken unless subsequent processing succeeds.
The main tasks for this exercise are as follows:
1.    Start the 6461A-LON-DEV-09 virtual machine and log on as Student.
2.    Add transactional requirements to the AppointmentServiceContract.
3.    Configure the service to flow transactions.
4.    Configure the client to flow transactions.
5.    Start a transaction from the client.
6.    Ensure that failure in the client transaction rolls back the changes to the Appointment service.

Task 1: Start the 6461A-LON-DEV-09 virtual machine and log on as Student

1.    Open the Virtual Server Remote Control Client, and then double-click 6461A-LON-DEV-09.
2.    Log on to 6461A-LON-DEV-09 as Student by using the password Pa$$w0rd.

Task 2: Add transactional requirements to the appointment service contract

1.    Open Microsoft Visual Studio® 2008 development system as ADMINISTRATOR.
2.    Open the ConnectedWCF solution:
    • If you are using Microsoft Visual Basic® development system, browse to the E:\Labfiles\Starter\VB\TransactionFlow\ConnectedWCF\ folder, and then double-click ConnectedWCF.sln.
    • If you are using Microsoft Visual C#® development tool, browse to the E:\Labfiles\Starter\CS\TransactionFlow\ConnectedWCF\ folder, and then double-click ConnectedWCF.sln.
3.    In the AppointmentService project, in the AppointmentServiceContract source file, and set the CreateAppointment operation attribute to TransactionFlow to force client applications to call this method in a transaction scope.

Task 3: Configure the service to flow transactions

1.    Edit the AppointmentServiceImplementation source file and set the OperationBehavior of the CreateAppointment method so that the method code will form part of any transaction flowed from the client.
2.    Add a reference to the System.Transactions.dll assembly to the project, and then import the System.Transactions namespace into the AppointmentServiceImplementation source file.
3.    In the AppointmentServiceImplementation class, add a method named ShowTransactionalStatus. This method should take a string parameter named methodName. Add code to test whether Transaction.Current is null, and then write a suitable message to the console to show that the method was called with or without a transaction.
4.    Modify the CreateAppointment method to determine if the method is running in the scope of a transaction by calling the ShowTransactionalStatus method.
5.    In the ContosoServicesSelfHostExtConfig project, edit the app.config file to define a binding configuration named WsHttpTransactionalBindingConfig for the wsHttpBinding binding that sets the transactionFlow property to enable transactions to flow into a service that uses this binding. Add a similar binding configuration named NetTcpTransactionalBindingConfig to the netTcpBinding.
6.    Find the service definition for the appointment service, and then apply the transactional wsHttpBinding binding configurations to the wsHttpBinding endpoint. Apply the transactional netTcpBinding binding configuration to the netTcpBinding endpoint.
7.    Build the Appointment service and the Contoso service host applications.

Task 4: Configure the client to flow transactions

Note: The purpose of this task is to update an existing service reference. Doing this requires a running instance of the Contoso services host.
1.    Start the Contoso services outside of Microsoft Visual Studio 2008. To do this:
    • If you are using Visual Basic, open Windows Explorer, browse to the E:\Labfiles\Starter\VB\TransactionFlow\ConnectedWCF\ContosoServicesSelfHostExtConfig\bin\debug folder, and then run ContosoServicesSelfHostExtConfig.exe as ADMINISTRATOR.
    • If you are using Visual C#, open Windows Explorer, browse to the E:\Labfiles\Starter\CS\TransactionFlow\ConnectedWCF\ContosoServicesSelfHostExtConfig\bin\debug folder, and then run ContosoServicesSelfHostExtConfig.exe as ADMINISTRATOR.
2.    In the ClinicAdminClient project, update the service reference for the Appointment service to incorporate the transactional information that you added to the service into the client-side proxy.
3.    After the service reference updates, in the ContosoServicesSelfHostExtConfig console window, press ENTER.
4.    In the WCF Service Configuration Editor, edit the app.config file for the ClinicAdminClient project. Find the NetTcp and WsHttp bindings for the Appointment Service client endpoints, and then set the TransactionFlow property of each endpoint to True.

Task 5: Start a transaction from the client

1.    In the ClinicAdminClient project, add a reference to the System.Transactions assembly.
2.    Open the ClinicAdminForm file, and then locate the MakeAppointmentWithClientTransaction method. Examine the code in this method and identify the lines that create proxies for the Appointment Service and Patient Letters Service, and then use these proxies to create an appointment and send a letter.
3.    Wrap this section of code in a TransactionScope. Remember to call Complete at the end of the scope.
4.    Rebuild the ConnectedWCF solution.

Task 6: Ensure that failure in the client transaction rolls back the changes to the Appointment service

1.    Run the ClinicAdminClient project and ensure that you can make an appointment for today with one of the doctors listed for patient ID NH991199Z. After you make the appointment, display the currently available slots to ensure that the slot you selected is no longer available.
2.    Open the ClinicAdminForm, and then locate the MakeAppointmentWithClientTransaction method. Just before the call to the SendLetter method of the Patient Letter Service proxy, add a statement that tests the local Boolean variable causeAnIntentionalError and, if it is true, throws an ApplicationException.
3.    Rebuild the ConnectedWCF solution, and then try to make another appointment for the same patient. This time an error message appears. Display the currently available slots to ensure that the slot you selected is still available. This proves that the effects of the CreateAppointment operation have been rolled back because of the client-side exception that aborts the transaction.
Results: After completing this exercise, you should have seen how to flow a transaction from a client application to a service and ensure that when the transaction is aborted, the changes made by the service are rolled back.

Exercise 1: Answer Key (detailed steps)


Exercise 2: Forcing a Transaction to Start When a Service Operation Is Called

Scenario

To avoid the requirement for transactions on the client, you have decided to refactor the small piece of transactional workflow code that you created earlier so that all the transactions are created by the server.
In this exercise, you will move the workflow code that creates the appointment and send the patient letter from the client to the Clinic Management Service.
The main tasks for this exercise are as follows:
1.    Add references to the Clinic Management Service so that it can act as a client for the Appointment Service and Patient Letter Service.
2.    Enable transaction flow on the Appointment service client endpoints.
3.    Implement the appointment and letter workflow in the Clinic Management Service.
4.    Replace the client invocations with a call to the Clinic Management Service.
5.    Ensure that failure in the Clinic Management Service transaction rolls back the changes to the Appointment service.

Task 1: Add references to the Clinic Management Service so that it can act as a client for the Appointment Service and Patient Letter Service

1.    Switch to Microsoft Visual Studio 2008.
2.    Open the ConnectedWCF solution:
    • If you are using Visual Basic, browse to the E:\Labfiles\Starter\VB\AutomaticTransactions\ConnectedWCF\ folder, and then double-click ConnectedWCF.sln.
    • If you are using Visual C#, browse to the E:\Labfiles\Starter\CS\AutomaticTransactions\ConnectedWCF\ folder, and then double-click ConnectedWCF.sln.
3.    Rebuild the 'Connected WCF' solution.
4.    Start the Contoso services outside of Visual Studio 2008. To do this, perform one of the following steps:
    • If you are using Visual Basic, in Windows Explorer, browse to the E:\Labfiles\Starter\VB\AutomaticTransactions\ConnectedWCF\ContosoServicesSelfHostExtConfig\bin\debug folder, and then run ContosoServicesSelfHostExtConfig.exe as ADMINISTRATOR.
    • If you are using Visual C#, in Windows Explorer, browse to the E:\Labfiles\Starter\CS\AutomaticTransactions\ConnectedWCF\ContosoServicesSelfHostExtConfig\bin\debug folder, and then run ContosoServicesSelfHostExtConfig.exe as ADMINISTRATOR.
5.       Add the following service references to the ClinicManagementService project:
6.    After the service references are added, in the ContosoServicesSelfHostExtConfig console window, press ENTER.
7.    Removed the configuration file from the ClinicManagementService project.
8.    Import the following namespaces into the ClinicManagementServiceImplementation file:
    • com.contoso.ClinicManagementService.AppointmentServiceReference
    • com.contoso.ClinicManagementService.PatientLetterServiceReference

Task 2: Enable transaction flow on the appointment service client endpoint

In the ContosoServicesSelfHostExtConfig project, in the WCF Service Configuration Editor window, open the app.config file. Find the NetTcpBinding_AppointmentServiceContract and WSHttpBinding_AppointmentServiceContract binding configurations for the Appointment Service client endpoints, and then verify that the TransactionFlow property of both binding configurations is set to True.

Task 3: Implement the appointment and letter workflow in the Clinic Management Service

1.    Switch to Visual Studio 2008.
2.    In the ClinicManagementService project, edit the ClinicManagementServiceContract source file, and then add an operation named CreateAppointmentWorkflow that takes four parameters: a string patient id, a string doctor id, a DateTime time slot, and a Boolean that indicates whether to throw an exception inside the method.
3.    Add the CreateAppointmentWorkflow method to the ClinicManagementServiceImplementation source file. In the ClinicAdminForm form, copy the MakeAppointmentWithClientTransaction method that creates proxies for the Appointment Service and Patient Letters Service, and then use these proxies to create an appointment and send a letter. Change the name of the method to CreateAppointmentWorkflow, and make it public. Add the Boolean parameter to match the operation contract and remove the local variable causeAnIntentionalError. Remove the code that creates the TransactionScope object, and then delete the statement that calls the Complete method. Add a statement that calls the ClinicManagementServiceHelper.ShowTransactionalStatus message, passing the name of the CreateAppointmentWorkflow method as the parameter after the declaration of the appointmentId local variable
4.    In the CreateAppointmentWorkflow method, change the code that creates the AppointmentServiceContract proxy object to create a new instance of the AppointmentServiceContractClient class, and then spicy APService_TCP as the binding configuration.
5.    Add an OperationBehavior attribute to the CreateAppointmentWorkflow method, and then specify that the WCF runtime should create a transaction scope when it calls this method.
6.    Rebuild the 'Connected WCF' solution and ensure that the solution builds successfully.

Task 4: Replace the client invocations with a call to the Clinic Management Service

1.    Start the Contoso services outside of Visual Studio 2008. To do this, perform one of the following steps:
    • If you are using Visual Basic, in Windows Explorer, browse to the E:\Labfiles\Starter\VB\ConnectedWCF\ContosoServicesSelfHostExtConfig\bin\debug folder, and then run ContosoServicesSelfHostExtConfig.exe as ADMINISTRATOR.
    • If you are using Visual C#, in Windows Explorer, go to the E:\Labfiles\Starter\CS\ConnectedWCF\ContosoServicesSelfHostExtConfig\bin\debug folder, and then run ContosoServicesSelfHostExtConfig.exe as ADMINISTRATOR.
2.    Update the service reference in the ClinicAdminClient project for the Appointment service to incorporate the transactional information that you added to the service into the client-side proxy.
3.    After the service reference updates, in the ContosoServicesSelfHostExtConfig console window, press ENTER.
4.    Open the ClinicAdminForm, and then locate the CreateAppointment_Click method. Replace the statement that calls the MakeAppointmentWithClientTransaction method with a statement that calls the MakeAppointmentWithServerTransaction method, passing the same parameters.
5.    Add the MakeAppointmentWithServerTransaction method to the ClinicAdminForm class. This method should perform the following tasks:
    • Create a local Boolean variable named causeAnIntentionalError and initialize it to false.
    • Create a new instance of the ClinicManagementServiceContract proxy class.
    • Call the CreateAppointmentWorkflow method on the proxy object, passing the arguments passed in to the MakeAppointmentWithServerTransaction method as parameters, together with the causeAnIntentionalError variable.
    • Return the value of the CreateAppointmentWorkflow method as the return value of the MakeAppointmentWithServerTransaction method.

Task 5: Ensure that failure in the Clinic Management Service transaction rolls back the changes to the Appointment service

1.    Run the ClinicAdminClient project, and then verify that you can make an appointment for today with one of the doctors listed for patient ID NH991199Z. After you make the appointment, display the currently available slots to ensure that the slot you selected is no longer available.
2.    Open the ClinicAdminForm and locate the CreateAppointment_Click method Change the value of the causeAnIntentionalError variable to true. This causes the service to throw an exception before the patient letter is sent.
3.    Rebuild and run the ClinicAdminClient project. Try to make another appointment for the same patient. This time an error message appears. Display the currently available slots to verify that the slot you selected is still available. This proves that the effects of the CreateAppointment operation have been rolled back because of the service-side exception that aborts the transaction.
Results: After this exercise, you should have removed the transaction code from the client and used WCF to automatically start a transaction on the service.

Exercise 2: Answer Key (detailed steps)


Resources

This section contains a categorized view of the resources that supplement the content contained in this course.

Microsoft Learning

This section describes various Microsoft Learning programs and offerings.
·         Microsoft Skills Assessments
Describes the skills assessment options available through Microsoft.
·         Microsoft Learning
Describes the training options available through Microsoft — face-to-face or self-paced.
Details how to become a Microsoft Certified Professional, Microsoft Certified Database Administrators, and more.
·         Microsoft Learning Support
o    To provide comments or feedback about the course, send e-mail to support@mscourseware.com.
o    To ask about the Microsoft Certification Program (MCP), send e-mail to mcphelp@microsoft.com

TechNet and MSDN content

This section includes content from Microsoft TechNet and MSDN that provides in-depth discussion on technical topics related to this course.

TechNet content

MSDN content

Product/technology content


Knowledgebase

This section contains content from and links to Microsoft Knowledge Base in-depth discussions on technical topics.

Communities

This section describes the various Microsoft communities that may be of use to web developers.

Review and Takeaway Questions and Answers

This section includes questions and answers that are found in the Review and Takeaways topics at the end of each module.
Module 1
Review Questions
1.    Why is WCF a unified programming model, and why would you use it over other technologies such as ASP.NET ASMX Web services?
WCF is a unified programming model because it offers this functionality of existing Microsoft distributed communication, component, and Web service technologies. You can use WCF over previous technologies because Microsoft built WCF to include these technologies, so that developers would no longer have to learn many different technologies to develop a distributed system.
2.    What role does metadata play in WCF, and how and when does Visual Studio 2008 use it?
Metadata describes your WCF service and the operations that it exposes. When you use the Add Service Reference function in Visual Studio 2008, Visual Studio will use the metadata to generate a proxy for your WCF service.
3.    How would you expose a method in a WCF contract?
To expose a method in a WCF contract, you must add the OperationContract attribute to the method.
4.    How can you generate a proxy object from your WCF service?
You can use the Add Service Reference function in Visual Studio 2008 and the Svcutil.exe command-line tool.
Best Practices Related to WCF
Supplement or modify the following best practices for your own work situations:
·         Design your WCF service with SOA in mind.
·         Keep your WCF contract and implementation separated from your host application.
·         Change the namespace of your service contract to something more meaningful than the default http://tempuri.org.
Tools
Tool
Use for
Where to find it
Microsoft Service Configuration Editor
Modify configuration files
In Visual Studio 2008 and the Windows SDK
Svcutil.exe
Manually create proxy objects from a service
Windows SDK
Module 2
Review Questions
1.    Why do you think it is important to keep the service separate from host specifics?
Keeping your service separate from the projects that you use to host the service enables you to modify the current host, or create another host, without directly affecting the service.
2.    Why would you create your own self-host application?
You would create your own self-host application if you did not have access to a Web server such as IIS. Also, creating your own self-host application enables you to implement only the functionality that your want in a host such as managing service events. Self-host applications also enable you to use any protocol.
3.    What would be the consequences if you had to change an endpoint address in your client if you used programmatic configuration?
You would have to make the programmatic change and then recompile the assembly.
4.    Why would you host your WCF service in WAS instead of IIS?
You would host your WCF service in WAS instead of IIS if you want to use a non-HTTP protocol such as TCP.
5.    How could you deploy your WCF service to a remote server?
You could use the Publish Web function in Visual Studio 2008 and create a custom MSI.
Best Practices Related to WCF
Supplement or modify the following best practices for your own work situations:
·         Keep your service contract and implementation separated from host-specific projects.
·         Use external configuration files.
Tools
Tool
Use
Where to find it
Appcmd.exe
Bind desired Web site (usually default) to a non-HTTP port to support non–HTTP–based activation
Installed with IIS 7 at c:\Windows\system32\inetsrv\
Module 3
Review Questions
1.    Why do you think WCF enables you to expose multiple endpoints for a single WCF service?
o    WCF enables your WCF service to support clients that use different bindings simultaneously, for example, an intranet client over TCP and an Internet client over HTTP.
o    WCF enables you to add a new endpoint without the requirement to modify any existing endpoints. This enables you to support clients that may use the existing endpoint.
2.    Why would you want to define a service behavior element in your WCF configuration for your service?
o    You may want to change the way that the WCF runtime runs your WCF service.
o    You may want to specify additional service behavior such as enabling debugging and publishing metadata.
3.    If you want to enable interoperation between your WCF solution and an older Web service, what should you do?
Ensure that both the client and service conform to WS-I Basic Profile 1.1.
Best Practices Related to WCF Endpoints
Supplement or modify the following best practices for your own work situations:
·         Add a new endpoint instead of modifying an existing endpoint to ensure that legacy clients can still use your service.
·         Expose a metadata endpoint to enable clients to discover your WCF service only when necessary because malicious users can use the information in the WSDL to attack your service.
Module 4
Review Questions
1.    What is the difference between message logging and activity tracing?
Your answer should include:
·         Message logging enables you to capture the messages sent between your WCF service and client applications.
·         Tracing provides an alternative to the debugger and enables you to monitor the behavior of your WCF application and diagnose any exceptions.
2.    What property would you set to ensure your messages are automatically flushed to your trace listener?
·         Set the autoflush property to true.
3.    WCF enables you to analyze the correlations between trace activities. What property controls the correlation functionality?
·         Set the propagateActivity property to true. By default, the correlation functionality is enabled when you add a trace listener.
Best Practices Related to WCF Message Logging and Activity Tracing
Supplement or modify the following best practices for your own work situations:
·         Consider the type of information that you log in your log files such as sensitive user data that may be protected by legislation.
·         Keep log files secure from unauthorized access.
Tools
Tool
Use for
Where to find it
SvcTraceViewer.exe
View svclog log files
C:\Program Files\Microsoft SDKs\Windows\v6.0A\bin
Module 5

Review Questions

1.    What are the essential elements of a service contract?
Your answer should include:
o    The operations
o    The parameters and return types of the operations
o    The complex data types used as parameters or return values.
o    The errors that a client should expect in normal operation
2.    In what format are operation requests and responses encoded?
They are encoded as SOAP messages.
3.    Name the three types of message exchange pattern supported by WCF.
o    Request/response
o    One-way
o    Duplex
4.    List some best practices for contract versioning.
Your answer might include:
·         Add but do not remove operations or data members
·         Do not change data types
·         Do not change namespaces
5.    How do you specific that an operation in an operation contract is a one-way operation?
Set the IsOneWay property of the OperationContract attribute to true.
6.    Why does method overloading present a problem for services?
The default SOAP action is based on the method name, so identical method names will result in identical SOAP actions unless you specify a different action for each operation.
7.    What role does the callback contract play in a duplex contract?
The callback contract is implemented by the client. The service can call methods on the callback contract when it must communicate with the client.
8.    How does the service obtain a reference to the callback contract?
The service calls the GetCallbackChannel method of the current OperationContext.
9.    What types does the WCF serializer support by default?
Your answer should include:
·         Primitive types
·         XML-based types
·         Collections
·         Enumerations
·         Some simple composite types
Real-World Issues and Scenarios
1.    A development team is trying to improve the perceived performance of an e-commerce site. They change the operation that delivers the order to the back-end service to a one-way operation. This speeds up the Web user interface at the expense of knowing whether the order has been placed successfully. If there is a problem with orders, customers must now be informed by e-mail after they have completed their transaction.
2.    A service maintenance team must update the service contract in a way that involves removing some operations. They decide to retain the original contract to support existing clients and to create a new version of the contract for updated clients.
3.    There is no built-in mechanism to detect if a one-way message has failed. If you must do this, you must implement your own way of getting this information back to the caller (maybe another channel).
4.    You cannot define two operations with the same name in the same service contact.
Best Practices Related to Contract Definition
Supplement or modify the following best practices for your own work situations:
·         Implement IExtensibleDataObject for data contract types.
·         Follow the guidelines for forward compatibility of contracts.
·         Use one-way operations to improve throughput and client response times.
Module 6
Review Questions
1.    Why do .NET Framework exceptions not fit well in service-oriented applications?
Your answer should include:
  • They are automatically propagated up the call chain, so they will make contact with the service interface and be propagated back to the client if unchecked.
  • They contain local error information, much of which should not be sent to the client.
  • Their information is encoded in a language-specific or platform-specific structure which does not sit well with cross-platform services.
  • An exception ultimately terminates its host if uncaught, which is a bad characteristic for a shared service.
2.    How do you represent an error in a service contract?
Define a FaultContract.
3.    In what form does error information propagate from the service to the caller?
It is represented in a SOAP fault.
4.    Who must know about any errors caused by a service, and what information do they require?
There are different groups of stakeholders who must know about errors: end users, client-side support teams, and service-side support teams. They require increasing levels of detail to help to diagnose the underlying problem.
5.    What are the benefits of typed fault?
If you define a typed fault:
  • It can contain application-specific information that can be used by the caller to better handle and report the error.
  • It can be converted to a typed exception in the caller, which makes it easier to handle because its processing can be split out from other errors
6.    Which configuration property can you enable in development and test environments to propagate detailed error information about unexpected exceptions to clients?
The property is includeExceptionDetailInFaults.
7.    Other than faults generated by services, what other sorts of errors will a caller have to deal with?
There are different communication errors embodied in the subclasses of CommunicationException.
Common Issues Related to WCF Error Handling
Identify the causes for the following common issues related to WCF error handling and fill in the troubleshooting tips. For answers, refer to relevant lessons in the module.
Issue
Troubleshooting tip
An unexpected error occurs and faults the channel which causes problems for the caller.
Handle unexpected errors by adding outer try blocks to the service operations or use an IErrorHandler.
An unexpected error has occurred but the caller receives only a general message so cannot tell what the exception is.
Set the includeExceptionDetailInFaults property of the serviceDebug element.
The end user is presented with a very technical error message.
Log the technical error message on the service-side and pass back a more meaningful message to the caller.
People who develop clients for the service are unsure about what errors it may generate.
Define FaultContracts on the operations in the service contract.
Best Practices Related to WCF Error Handling
Supplement or modify the following best practices for your own work situations:
·         Make sure that no exceptions "leak out" of your service by using outer try blocks in the operations or implement a custom error handler on the service behavior.
·         Define FaultContracts for all your domain error conditions.
·         Log technical error detail on the service-side and pass back more meaningful error information to the caller. On the client side, provide the end user with a meaningful and jargon-free message when an error occurs, that indicates if the operation may work if they try again.
·         Disable the includeExceptionDetailInFaults property in a production environment.
·         In the client application, handle CommunicationObjectFaultedException and recreate the proxy object when the channel is in a Faulted state before further messages are sent to the service.
Module 7

Review Questions

1.    What are the three instance context modes available with WCF?
PerCall, PerSession, and Single.
2.    Which instance context mode is the default mode? Explain why you think this is.
PerCall is the default option. This is because it is the safest option when considering concurrency and service-side resource utilization.
3.    Under which instance context mode must you give more thought to security?
The Single life cycle model poses more security questions because in-memory data is potentially shared between callers.
4.    Which WCF setting controls the number of threads in a service instance?
The ConcurrencyMode property on the service behavior can be set to Multiple, Reentrant, or Single.
5.    Which concurrency mode is the default mode? Explain why you think this is.
Single is the default option. This is because it is the safest option in terms of concurrency.
6.    What effect does service throttling have on perceived user performance?
It limits the number of users that can access system resources to maintain a minimum guaranteed level of performance for those callers who get through. However, at peak times, some callers will end up timing out, thereby giving them a poor perception of system performance.
7.    What are the three WCF resources that you can limit by using throttling and how do you throttle them?
You can limit the number of concurrent calls to operations, the number of concurrent service instances, and the number of concurrent sessions by setting the serviceThrottling child element of the service behavior.
8.    What is server-affinity and why is it a problem? What features of WCF can cause server-affinity?
Server-affinity is the situation where a client always calls one particular server. This causes problems if that server fails or becomes overloaded. WCF sessions or ongoing TCP connections can cause server-affinity.
9.    What two mechanisms does WCF offer for transmitting large amounts of binary data?
The two mechanisms WCF offers for transmitting large amounts of binary data are MTOM encoding and streaming.
10. How does MTOM encoding split large binary data from other data in a message?
MTOM uses MIME encoding to encapsulate the SOAP envelope in one MIME part and the binary data in other MIME parts.
11. How do you enable streaming between a service and client?
You must pass a .NET Framework stream as a parameter or return value in a contract. You must then expose this contract over a stream-friendly binding and set the nsferMode of that binding to Streamed, StreamedRequest or StreamedResponse.

Common Issues Related to Instance and Thread Management

Identify the causes for the following common issues related to instance and thread management and fill in the troubleshooting tips. For answers, refer to relevant lessons in the module.
Issue
Troubleshooting tip
Clients are sharing a multithreaded service instance and there are intermittent deadlocks and timeouts.
Change the instancing more to per-call and store shared state in a database.
Set the threading mode to single or re-entrant.
Determine the resource(s) that cause the contention and use .NET Framework threading mechanisms to protect those resources from concurrent access.
Every caller encounters slow response times at peak load.
Set throttling limits to restrict the number of concurrent calls.
When the service is deployed to a set of clustered servers, the clients are not evenly distributed across the servers.
Symptomatic of server-affinity. Try to redesign to remove any use of sessions or TCP connections.
Real-World Issues and Scenarios
1.    You must build up an order through a set of interactions with a service. What are your options and what are the advantages and disadvantages of each approach?
2.    You have a large medical image of a patient to send from service to client. The security policy surrounding your application states that you must encrypt patient information in transit. How would you transmit this file?
Best Practices Related to Service Performance
Supplement or modify the following best practices for your own work situations:
·         Use per-call instance management and store any ongoing state in a persistent store such as a database.
·         Split large binary data into a series of messages that you can send by using MTOM instead of streaming.
·         Only use sessions or TCP connections when required if your service may be deployed in a high-availability cluster.
·         Throttle the number of concurrent calls to maintain a minimum service level for existing callers.
Module 8
Review Questions
1.    How do you specify the security mode for a binding?
You can apply it programmatically.
[Visual Basic]
Dim binding As New BasicHttpBinding(SecurityMode.Transport)
[Visual C#]
BasicHttpBinding binding =
                 new BasicHttpBinding(SecurityMode.Transport);
Alternatively, you can set the mode attribute on the security element in a binding configuration.
<binding name="myBasicHttpBindingConfig">
  <security mode="Transport"/>
</binding>
2.    Give examples of differences between message-level security and transport-level security.

Message-level security provides end-to-end security of message contents; transport-level security protects them only point-to-point.>
Message-level security protects the contents of the message; transport-level protects the entire message including the message headers.
3.    What are the four aspects of security that you usually use to define a security policy?

Authentication, authorization, integrity, and privacy.
4.    Why is claims-based authorization superior to previous types of security?

It is independent of the transport mechanism, authentication mechanism, and client operating system, so it can provide a unified model for authentication.
5.    Give examples of client credential types.

NTLM, Basic, Digest, Issued Token, Certificate, UserName.>
Common Issues Related to WCF Security
Issue
Troubleshooting tip
Protocol exceptions at run time
Ensure that the security settings on the client and service binding match.
SSL/TLS negotiation failed
Check that certificate is correctly installed on server side.
Check validity of certificate.
Real-World Issues and Scenarios
1.    Raw protocols such as NetTcp are significantly faster than Web service protocols but can be blocked by firewalls, so they are suitable only for use on internal networks.
2.    If you use Web service bindings, your services and clients should be able to interoperate with services and applications written in non-WCF technologies such as Java 2 Enterprise Edition (J2EE) and Ruby.
3.    Determine a suitable authentication policy for your service and clients. Ascertain if the locations in which they are deployed are suitable for a particular credential type. For example, will you be able to install client certificates if you choose to use certificates for authentication?
Best Practices Related to WCF Security
Supplement or modify the following best practices for your own work situations:
·         Define protection levels on service contracts to ensure that they are enforced.
·         Choose a suitable credential type for the anticipated deployment scenario; for example, use certificates to authenticate communication across the Internet.
Tools
Tool
Use for
Where to find it
Makecert
Generating certificates
Windows SDK
WCF Configuration Editor
Editing WCF configuration files
Context menu in Visual Studio
Service Trace Viewer
Examining message contents
Windows SDK
Module 9
Review Questions
1.    What role does the Microsoft Distributed Transaction Coordinator (DTC) play in supporting WCF transactions?

It controls the transaction by coordinating the resource managers enlisted as the transaction flows from the client application to the service(s).
2.    Which WCF bindings support the flow of transactions?

NetTcpBinding, NetNamedPipeBinding, WSHttpBinding, WSDualHttpBinding, WSFederationHttpBinding.
3.    Which property must be enabled on both client and service bindings so that they allow transactions to flow across the service boundary?

The transactionFlow property.
4.    Must you define the transactional behavior of an operation in the service contract, in the service implementation, or in both? How?

Both. You set the TransactionFlow attribute of the contract and the TransactionScopeRequired property of the OperationBehavior attribute for an operation.
5.    If an operation is labeled as requiring a transaction scope, what happens if it is called without one?

The WCF runtime starts one.
6.    List some transaction configuration issues that can cause exceptions to occur at runtime.

TransactionFlowOption set as Mandatory but no transaction flows from the client.

TransactionFlowOption set to NotAllowed and a transaction flows from the client.

Mismatching isolation levels defined for the client application and the service.
7.    Is it best to maintain a transaction throughout a sequence of business operations or to keep transactions short?

It is best to keep them short because they frequently lock resources. Long-running transactions can cause contention when other transactions attempt to access locked resources.
Real-World Issues and Scenarios
Service-oriented architectures are typically used to combine existing and potentially, new business services. In this form, applications based on them are often long-running compared to atomic transactions. This therefore poses the question of where distributed atomic transactions fit in this type of application. Several answers to this question exist. In some systems, the application undertakes a workflow to gather information and then applies the changes in one transactional update at the end. In others, operations are grouped together into coarse-grained steps and those steps each execute under transactional control. Often, human intervention will be called on to resolve a step that has failed.
Best Practices Related to Implementing Transactions
Supplement or modify the following best practices for your own work situations:
·         Do not distribute transactions unless you really must. If you must distribute transactions across services, try to host them on the same physical server.
·         Use workflow methods to group together transactional service methods so that the client application has to call only one method. This keeps the transaction on the server side instead of having the client create it and flow it to the server. For more information about this approach, see the Façade design pattern and Martin Fowler's Transaction Script pattern.

·         If you are working in a Windows-only environment, use OLE Transactions unless there is a definite requirement to implement WS-AtomicTransaction transactions.

No comments:

Post a Comment