Thursday, August 25, 2016

Retrieving User Claims in SAML Response with Service Provider Claim Configuration in WSO2 Identity Server

WSO2 Identity Server supports SAML authentication and Single Sign On capabilities where it can be used as the Identity Provider for a relying party application (Service Provider). A user would visit the relying party website and when he tries to login, the user would be redirected to the Identity Provider web site. There, the user can login and upon successful authentication, the Identity Provider would send the SAML authentication response to the relying party application. The steps of this authentication flow are given in the diagram below.
samlflow.png

The relying party application can read the SAML response sent by the Identity Provider, process it and get to know the authentication status of the user. If the relying party application needs to know user’s attributes (claims) such as first name, last name… the Identity Provider can include those user claims in the SAML response to be read by the relying party application.

In this article, I am demonstrating how to configure WSO2 Identity Server to send user claims in SAML response. You can refer [1] to know more about user claims in WSO2 servers.

In the SAML configuration of the Service Provider configuration in WSO2 server, you have to make sure the following two checkboxes are selected so that the WSO2 server can include user claims in the SAML response.

Enable Attribute Profile
Include Attributes in the Response Always



Next step is to configure the claim mappings inside the Service Provider configuration in WSO2 server. This has two scenarios which are discussed below.

Service Provider has no specific attribute names for claims

WSO2 servers use a common pattern to identify user claims. The claims of a user in a WSO2 server would follow the pattern http://wso2.org/claims/<claim _name>. For example, the email address claim of a user in WSO2 server would be http://wso2.org/claims/emailaddress.

If the relying party application has no specific names for claims, WSO2 server can just include the user claims with the same claim names in SAML response. When reading the SAML response, the relying party application has to process the SAML response and read the claims using the same claim names that WSO2 servers use. Following diagram explains this scenario.


To configure this, go to the Claim Configuration section of the Service Provider configuration in WSO2 server and select the Use Local Claim Dialect option. Then, add the claims that should be included the the SAML response. The subject of the SAML assertion can be set separately by selecting a particular user claim in the configuration.


Then, when the user gets authenticated to the WSO2 server, it will include these claims in the AttributeStatement section of the SAML response. A sample is given below where user claim attributes are highlighted.  


      
<saml2:AttributeStatement>
   <saml2:Attribute Name="http://wso2.org/claims/im"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >thariyarox
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="http://wso2.org/claims/streetaddress"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Colombo
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="http://wso2.org/claims/country"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Sri Lanka
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="http://wso2.org/claims/lastname"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Edirisinghe
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="http://wso2.org/claims/emailaddress"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >[email protected]
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="http://wso2.org/claims/url"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >http://tharindue.blogspot.com
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="http://wso2.org/claims/givenname"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Tharindu
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="http://wso2.org/claims/organization"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >WSO2
      </saml2:AttributeValue>
   </saml2:Attribute>
</saml2:AttributeStatement>

Then in the relying party application, it has to process this response and read the claims by their attribute names for identifying the user. A sample image is shown below where the travelocity sample SAML relying party application [2] reads these claims and displays for the authenticated user.


Service Provider has specific attribute names for claims

In most of the usecases, the relying party application (Service Provider) would have its own attribute names for user claims. In such cases, no matter how the Identity Provider maintains its own attribute names for claims, it has to transform them to match with the relying party application’s user claims. An example is, in WSO2 servers, the attribute name for email address of a user is http://wso2.org/claims/emailaddress whereas in a relying party application, it would just be email. Following diagram shows an example for such claim transformation.


In a scenario like this, you need to sent the Claim Configuration inside the Service Provider configuration of WSO2 server as shown below.

We have to select the Define Custom Claim Dialect option and add entries for each user claim that you need to receive in the SAML response.


Local Claim is how WSO2 server knows a particular user claim and the Service Provider Claim is the attribute name that the relying party uses for identifying the particular claim. You have to select the Requested Claim check box as well for a claim to be included in the response. Out of the claims you have added, you can select a particular claim as the Subject Claim URI that would be set as the subject of the assertion.

Following is a sample AttributeStatement in the SAML response for above scenario where Identity Provider (WSO2 IS) has transformed its claim names to match with the claim names of the relying party, so that the relying party application can read and understand each claim of the user.

     
      
<saml2:AttributeStatement>
   <saml2:Attribute Name="first_name"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Tharindu
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="address"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Colombo
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="website"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >http://tharindue.blogspot.com
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="email"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >[email protected]
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="company"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >WSO2
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="other_name"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >thariyarox
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="last_name"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Edirisinghe
      </saml2:AttributeValue>
   </saml2:Attribute>
   <saml2:Attribute Name="country"
                            NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:basic"
                            >
      <saml2:AttributeValue
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                                     xsi:type="xs:string"
                                     >Sri Lanka
      </saml2:AttributeValue>
   </saml2:Attribute>
</saml2:AttributeStatement>

When using travelocity sample SAML relying party application, this is what we get after reading all the user claims.



References


Tharindu Edirisinghe
Platform Security Team
WSO2

1 comment:

  1. Hi Tharindu.
    Great post.
    Some time ago I realized the same integration but with inverse roles. Liferay as IDP and WSO2 as SP. You can see step-by-step integration on https://youtu.be/zBDLSrNT5D8

    ReplyDelete