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
- Lesson 2: Applying Overall Security Requirements
to a Binding
- Lesson 3: Specifying Required Client and Service
Credentials
- Lesson 4: Working with Security Information
- Lab: Protecting a Service
·
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-Policy, see "Web
Services Policy Framework (WS-Policy) and Web Services Policy Attachment
(WS-PolicyAttachment)".
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
- Lesson 2: Creating Transactional Service
Operations
- Lesson 3: Enabling the Flow of Transactions from
Client to Service
- Lab: Implementing Transactions for a Service
·
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:
- The Patient Letters Service
at http://localhost:8001/Contoso,
specifying PatientLetterServiceReference
as the namespace.
- The Appointment Service at http://localhost:8000/Contoso,
specifying AppointmentServiceReference
as the namespace.
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
- TechNet and MSDN content
- Knowledgebase
- Books
- Communities
- Review and Takeaway Questions and Answers
Microsoft Learning
This section describes various Microsoft Learning programs and offerings.
Describes the skills assessment options available
through Microsoft.
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
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
- Service Oriented Architecture
- Principles of Service Design: Service Patterns
and Anti-Patterns
- WCF Messaging Fundamentals
- Windows Communication Foundation Binding and
Channels
- see Endpoints: Addresses, Bindings, and Contracts
- Designing Service Contracts
- Implementing Service Contracts
- Using Data Contracts
- ServiceModel Metadata Utility Tool (Svcutil.exe)
- Configuration Editor Tool (SvcConfigEditor.exe)
- Hosting Services
- Hosting and Consuming WCF Services
- Client Architecture
- Configuring Services Using Configuration Files
- System.servicemodel
- Windows Communication Foundation Configuration
Schema
- How to: Host a WCF Service in a Managed Windows
Service
- How to: Host a WCF Service in IIS
- How to: Host a WCF Service in WAS
- How to: Install and Configure WCF Activation
Components
- Configuring System-Provided Bindings
- WCF Bindings In Depth
- BasicHttpBinding Class
- NetTcpBinding Class
- NetNamedPipeBinding Class
- NetMsmqBinding Class
- MsmqIntegrationBinding Class
- Specifying an Endpoint Address
- Multiple Contracts
- How to: Specify a Service Binding in
Configuration
- Specifying Service Runtime Behavior
- Message Inspectors
- Web Services Protocols Interoperability Guide
- Interoperability with ASP.NET Web Services
- Web Services Specifications
- Web Services Protocols Supported by
System-Provided Interoperability Bindings
- Creating User-Defined Bindings
- Administration and Diagnostics
- Message Logging
- Configuring Message Logging
- Message logging
- Security Concerns for Message Logging
- Viewing Message Logs
- Configuring Tracing
- Service Trace Viewer Tool (SvcTraceViewer.exe)
- Emitting User-Code Traces
- Activity Tracing and Propagation for End-To-End
Trace Correlation
- Sessions, Instancing, and Concurrency
- Discover Mighty Instance Management Techniques
For Developing WCF Apps
- InstanceContextMode Enumeration
- What Every Dev Must Know About Multithreaded Apps
- Managed Threading
- ConcurrencyMode Enumeration
- ServiceThrottlingBehavior Class
- Load Balancing
- Large Data and Streaming
- How to: Enable Streaming
- Defining and Specifying Faults
- FaultException(TDetail) Generic Class
- IErrorHandler Interface
- serviceDebug
- The Handling Faults section of Sending and
Receiving Faults
- FaultException Generic Class
- FaultException Class
- Specifying and Handling Faults in Contracts and
Services
- Microsoft patterns & practices Security
Guidance for Applications Index
- Explained: Windows Authentication in ASP.NET 2.0
- Access Control Mechanisms
- MSDN Webcast: Windows Communication Foundation
Top to Bottom (Part 11 of 15): Federated Security (Level 200)
- Distributed Application Security
- Exchange Data More Securely with XML Signatures
and Encryption
- Securing Services and Clients
- Federation
- Programming WCF Security
- Security of basicHttpBinding
- Bindings
- Transport Security Overview
- Message Security in WCF
- Understanding Protection Level
- Transport
- Selecting a Credential Type
- Federation and Issued Tokens
- How To: Specify the Client Credential Type
- How To: Specify Client Credential Values
- Using CardSpace in Windows Communication
Foundation
- How To: Examine the Security Context
- WindowsIdentity class
- How To: Use the ASP.NET Role Provider with a
Service
- Managing Claims and Authorization with the
Identity Model
- Security Briefs: Exploring Claims-Based Identity
- Delegation and Impersonation with WCF
- How To: Impersonate a Client on a Service
- Transaction Processing Fundamentals
- ACID Properties
- Two-Phase Commit
- Transaction Management in Windows
- WCF Transaction Propagation
- Compensating Transactions
- Distributed Transaction Coordinator in COM+
Documentation
- OLE Transactions Standard
- WS-Atomic Transaction Configuration Utility
- Windows Communication Foundation Transactions
Overview
- Enabling Transaction Flow
- TransactionFlowAttribute Class
- System.Transactions Namespace
- ServiceModel Transaction Attributes
- OperationBehaviorAttribute.TransactionScopeRequired
Property
- Features Provided by System.Transactions
- TransactionScope Class
- Service Interface
- Using Message Contracts
- Using the Message Class
- MSDN Webcast: Windows Communication Foundation
Top to Bottom (Part 07 of 15): Messaging Patterns (Level 200)
- Service Versioning
- Best Practices: Data Contract Versioning
- ServiceContractAttribute Class
- How to: Create a One-Way Contract
- OperationContractAttribute Class
- How to: Create a Duplex Contract
- Types Supported by the Data Contract Serializer
- How to: Create a Basic Data Contract for a Class
or Structure
- DataContractAttribute Class
- see DataMemberAttribute Class
- Forward-Compatible Data Contracts
Product/technology content
- WCF sessions, instancing,
and reliable messaging
- SOAP Message Transmission
Optimization Mechanism
- The section about SOAP faults in the SOAP 1.2
specification
- The Interface Fault
Reference section of the Web Services Description Language (WSDL) Version
2.0 Part 1: Core Language specification
- Patterns for the
Generation, Handling and Management of Errors
- More Patterns for the
Generation, Handling and Management of Errors
- Refactoring: Improving the Design of Existing
Code
- RFC 2660
- [Algorithm Suite] Property
- Web Services Security
Policy Language (WS-SecurityPolicy)
- Web Services Policy Framework (WS-Policy) and Web
Services Policy Attachment (WS-PolicyAttachment)
- Web Services Metadata
Exchange (WS-MetadataExchange)
- RFC 2617
- Web Services Atomic Transaction
(WS-AtomicTransaction) specification
- Web Services Coordination
(WS-Coordination) specification
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.
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.
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.
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.>
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).
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.
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.
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.
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.
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.
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.
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