WSE Support for WS-Trust and WS-SecureConversation


WSE version 2.0 adds implementation of WS-Trust and WS-SecureConversation to the WS-Security support provided in version 1.0. WSE implements the following major classes to support the message elements described in these two specifications:

  • SecurityContextToken Represents a security context token object used in a secure conversation.

  • DerivedKeyToken Represents a key derived from the secret key potion of a security context token.

  • RequestedProofToken A proof-of-possession distributed by an STS as a result of a successful RequestSecurityToken message.

  • RequestedSecurityToken A security token distributed by an STS as a result of a successful RequestSecurityToken message.

  • RequestSecurityToken Represents the body of a RequestSecurityToken message.

  • RequestSecurityTokenResponse Represents the body of the RequestSecurityTokenResponse message.

Security Context Token Services

In addition to these programming objects that essentially represent XML elements from WS-Trust and WS-SecureConversation, WSE also provides the base classes needed to create a security token issuing service. The SecurityTokenService class implements a RequestSecurityToken method that can be used when implementing your own custom STS; however, in WSE version 2.0, the SecurityContextService class does not support delegation, proxy, and forwarding features of WS-Trust. While you can create a custom STS, WSE provides an out-of- the-box implementation of a security context token service.

Configuring a Security Context Token Service

You can use the WSE Settings tool to create an STS that distributes security context tokens based on X.509 certificates. The WSE Settings tool adds the required entries to the Web.config file of the selected Web service project, and the STS will be created in this service s virtual directory.

To create a new STS using the WSE Settings tool:

  1. In Visual Studio .NET, select the project for the Web service to which you want to add the STS.

  2. Right-click the project and select WSE Settings 2.0. This opens the WSE Settings tool.

  3. Select the TokenIssuing tab as shown in Figure 8-1.

    click to expand
    Figure 8-1: WSE Settings tool

  4. Click X.509Certificates link to retrieve the certificate from the local machine certificate store associated with the service s private key that the STS will use to sign the SecurityTokenRequestResponse messages. You can also enter this information manually in the ServerTokenKeyInfo field in the following format, but without line breaks:

     <wsse:SecurityTokenReference 
    xmlns:wsse="http://schemas.xmlsoap.org/ws/2002/12/secext">
    <wsse:KeyIdentifier ValueType="...">...</wsse:KeyIdentifier>
    </wsse:SecurityTokenReference>

    For an X.509 certificate, ValueType must be set to wsse:X509v3 and the value of KeyIdentifer must match the identifier of the certificate that you are using to sign the message.

  5. In the ttl field, specify the time-to-live (TTL), in seconds. Based on this value, the service will set appropriate values for the Created and Expired child elements of SecurityContextToken , which together specify the lifetime of the security context token.

  6. You can also specify one or more keys for encrypting a SecurityTokenRequestResponse message by clicking Add under Service Tokens and selecting a token from the current user certificate store. This would be useful if the security context token needed to be forwarded to other applications. If no service tokens are specified, the STS encrypts the RequestSecurityTokenResponse message using either the public key, in the case of X.509, or the shared secret key, in the case of Kerberos, from the RequestSecurityToken message.

For the WSE implementation of the STS, the ASP.NET worker process must have read and write access to any of the cryptographic keys specified in the previous steps. To create an STS in a virtual directory that is not part of an existing Visual Studio .NET Web service project, you can open a standalone instance of the WSE Settings tool, follow the previous steps, and save the resulting Web.config file in the desired virtual directory.

Requesting a Security Context Token

To obtain a security context for a Web service conversation, you request a security context token from a security context token service. WSE enables you to easily access an STS using the SecurityTokenServiceClient proxy class. The following example method uses this class to request a security context token from an example service at http://example.com/DocumentService/secureConversation.ashx , where the request is signed using an X.509 certificate:

 // Set the URI for the security context token service 
private static string sctServiceUri =
"http://example.com/DocumentService/secureConversation.ashx";

private static SecurityContextToken GetSessionToken(string keyString)
{
// instantiate a new security context token
SecurityContextToken myToken;

//Get an X.509 certificate for signing and as the base token
X509SecurityToken myXToken = GetX509Token(keyString);

// Instantiate a client proxy for the security context token service
SecurityTokenServiceClient myTokenProxy = new
SecurityTokenServiceClient(new Uri(sctServiceUri));

// Add X509 token and signature to the outgoing message.
myTokenProxy.RequestSoapContext.Security.Tokens.Add(myXToken);
myTokenProxy.RequestSoapContext.Security.Elements.Add(new
Signature(myXToken));

try
{
// Construct a request security token message to the proxy providing
// our X509 certificate and the URI of the target document service.
RequestSecurityToken myRST = new
RequestSecurityToken(TokenType.SecurityContextToken, myXToken);
RequestSecurityTokenResponse myRSTR =
myTokenProxy.RequestSecurityToken(myRST);
myToken =
(SecurityContextToken)myRSTR.RequestedSecurityToken.SecurityToken;

// Add to the global security context token cache for later use
SecurityContextTokenCache.GlobalCache.Add(myToken);

return myToken;
}
catch(Exception ex)
{
throw new ApplicationException("Unable to obtain a security context " +
"token from " + sctServiceUri);
}
}

In this example, the WSE generates the following RequestSecurityToken message, which is sent to the specified security context token service:

 <soap:Envelope xmlns:wsu="http://schemas.xmlsoap.org/ws/2002/07/utility" 
xmlns:wsse="http://schemas.xmlsoap.org/ws/2002/12/secext"
xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Header>

<wsu:Timestamp>
<wsu:Created
wsu:Id="Id-0b7e1eb0-0384-4b95-ab30-070e5949f789">
2003-08-09T07:48:33Z</wsu:Created>
<wsu:Expires
wsu:Id="Id-9edcffb2-548f-402d-a2ac-809ed0228dd5">
2003-08-09T07:53:33Z</wsu:Expires>
</wsu:Timestamp>
<wsse:Security soap:mustUnderstand="1">
<wsse:BinarySecurityToken ValueType="wsse:X509v3"
EncodingType="wsse:Base64Binary"
xmlns:wsu="http://schemas.xmlsoap.org/ws/2002/07/utility"
wsu:Id="SecurityToken-5cc594bb-44bb-4e47-9377-d8ebc10507e2"
>AMTFFdTRTJRdWlja1N0YXJ0U2VydmVyMI...</wsse:BinarySecurityToken>
<Signature xmlns="http://www.w3.org/2000/09/xmldsig#">
<SignedInfo>
<CanonicalizationMethod
Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" />
<SignatureMethod
Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" />
<Reference URI="#Id-454b39ba-fdc7-4f8f-9fbc-9e17e5a66f84">
<Transforms>
<Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" />
</Transforms>
<DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" />
<DigestValue>R3Iymwi+qZUsVuANDQG/6aREMZQ=</DigestValue>
</Reference>

</SignedInfo>
<SignatureValue>zTcd1hKcYXgMakT+buGkoMUFRRxgK...</SignatureValue>
<KeyInfo>
<wsse:SecurityTokenReference>
<wsse:Reference
URI="#SecurityToken-5cc594bb-44bb-4e47-9377-d8ebc10507e2" />
</wsse:SecurityTokenReference>
</KeyInfo>
</Signature>
</wsse:Security>
</soap:Header>
<soap:Body wsu:Id="Id-454b39ba-fdc7-4f8f-9fbc-9e17e5a66f84">
<wsse:RequestSecurityToken>
<wsse:TokenType>wsse:SecurityContextToken</wsse:TokenType>
<wsse:RequestType>wsse:ReqIssue</wsse:RequestType>
<wsse:Base>
<wsse:Reference
URI="#SecurityToken-5cc594bb-44bb-4e47-9377-d8ebc10507e2" />
</wsse:Base>
</wsse:RequestSecurityToken>
</soap:Body>
</soap:Envelope>

After positively authenticating the request, the security context token service returns the security context token in a RequestSecurityTokenResponse message, where the body of the message containing the token is encrypted for added security:

 <soap:Envelope xmlns:wsu="http://schemas.xmlsoap.org/ws/2002/07/utility" 
xmlns:wsse="http://schemas.xmlsoap.org/ws/2002/12/secext"
xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Header>

<wsu:Timestamp>
<wsu:Created
wsu:Id="Id-22ef8eaf-b45b-47f1-9e19-050a5402a4ac"
>2003-08-11T15:02:00Z</wsu:Created>
<wsu:Expires
wsu:Id="Id-2cd89c35-b5c1-4f26-af92-d54171689b9a"
>2003-08-11T15:07:00Z</wsu:Expires>
</wsu:Timestamp>
<wsse:Security soap:mustUnderstand="1">
<xenc:EncryptedKey xmlns:xenc="http://www.w3.org/2001/04/xmlenc#">
<xenc:EncryptionMethod
Algorithm="http://www.w3.org/2001/04/xmlenc#rsa-1_5" />
<KeyInfo xmlns="http://www.w3.org/2000/09/xmldsig#">
<wsse:SecurityTokenReference>
<wsse:KeyIdentifier ValueType="wsse:X509v3"
>gBfo0147lM6cKnTbbMSuMVvmFY4=</wsse:KeyIdentifier>
</wsse:SecurityTokenReference>
</KeyInfo>
<xenc:CipherData>
<xenc:CipherValue>3L0zn///SOcjTps7DhzEgl+...</xenc:CipherValue>
</xenc:CipherData>
<xenc:ReferenceList>
<xenc:DataReference
URI="#EncryptedContent-0f23f63d-ba5d-471e-9e58-94bcb979c086" />
</xenc:ReferenceList>
</xenc:EncryptedKey>
<wsse:BinarySecurityToken ValueType="wsse:X509v3"
EncodingType="wsse:Base64Binary"
xmlns:wsu="http://schemas.xmlsoap.org/ws/2002/07/utility"
wsu:Id="SecurityToken-d2cff568-c00a-428b-8ff5-d191d2ba31cd"
>0IEFnZW5jeTAeFw0wMzA3MDgxODQ4MTBa...</wsse:BinarySecurityToken>
<Signature xmlns="http://www.w3.org/2000/09/xmldsig#">
<SignedInfo>
<CanonicalizationMethod
Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" />
<SignatureMethod
Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" />
<Reference URI="#Id-36547252-1b7a-43eb-afd9-4627e339d964">
<Transforms>
<Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" />
</Transforms>
<DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" />
<DigestValue>Duyyeo1ddaifzUCAxghPmUKFbEs=</DigestValue>
</Reference>

</SignedInfo>
<SignatureValue>MF1TSSqun+PtHA8rumSoOXFXUZ/...</SignatureValue>
<KeyInfo>
<wsse:SecurityTokenReference>
<wsse:Reference
URI="#SecurityToken-d2cff568-c00a-428b-8ff5-d191d2ba31cd" />
</wsse:SecurityTokenReference>
</KeyInfo>
</Signature>
</wsse:Security>
</soap:Header>
<soap:Body wsu:Id="Id-36547252-1b7a-43eb-afd9-4627e339d964">
<xenc:EncryptedData
Id="EncryptedContent-0f23f63d-ba5d-471e-9e58-94bcb979c086"
Type="http://www.w3.org/2001/04/xmlenc#Content"
xmlns:xenc="http://www.w3.org/2001/04/xmlenc#">
<xenc:EncryptionMethod
Algorithm="http://www.w3.org/2001/04/xmlenc#tripledes-cbc" />
<xenc:CipherData>
<xenc:CipherValue>3+pEg6OLsJlbqyvVwFngDNiQ...</xenc:CipherValue>
</xenc:CipherData>
</xenc:EncryptedData>
</soap:Body>
<soap:Envelope>

This returned security context token can now be used to sign and encrypt messages within the established security context. However, before the security context is fully established, the token must be sent securely to the other participants in a RequestSecurityTokenResponse message. In this example, the security context token service resides in the same virtual directory as the Web service endpoint, so the service knows where to send the related RequestSecurityTokenResponse message. If the target service is a different virtual directory, then the AppliesTo property of the RequestSecurityToken object must be used to specify the target Web service.

Using the SecurityContextToken Object

WSE enables you to send the security context token to other participants in the conversation, add it to the token cache, or use it to sign and encrypt messages in the conversation. The following example uses an obtained SecurityContextToken to digitally sign a request message:

 // Create a new SoapContext for the request message 
SoapContext myContext = myService.RequestSoapContext;

// Get the security context token to use
SecurityContextToken myToken = GetSecurityContextToken();

if (myToken != null)
{
// Add the token to the Tokens collection in the Security object
// in the SoapContext of the request message
myContext.Security.Tokens.Add(myToken);

// Verify that the token can be used for signing
if (myToken.SupportsDigitalSignature)
{
// Add signature obtained with the username token
// to the security collection
myContext.Security.Elements.Add(new Signature(myToken));
}
else
{
// Throw an exception since we cant sign the message
}

// Call the GetDocument method on the Web service
myService.GetDocument(docID);
}
else
{
// Throw an exception if we dont have a security token
}

You can also add this security context token to the security context token cache, as I demonstrated with an X.509SecurityToken in Chapter 6. When added to the cache and when an outgoing policy requires that a security context token be added to outgoing request messages, WSE will use this security context token to sign outgoing messages. When the security context is no longer needed, this token should be removed from the token cache. SecurityContextTokens are added to the cache and assigned an identifier obtained from the Id value in the token. This enables us to retrieve the correct token programmatically, or the WSE can get it automatically to enforce a send policy.




Understanding Web Services Specifications and the WSE
Understanding Web Services Specifications and the WSE (Pro Developer)
ISBN: 0735619131
EAN: 2147483647
Year: 2006
Pages: 79

Similar book on Amazon

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net