Sunday, July 24, 2016

WSO2 IDP for Spring SAML Service Provider

Today we are going to see how to add WSO2 Identity Server as an IDP to a Spring application. We are going to do this using the Spring SAML sample provided here. You can download one of the releases of Spring SAML sample from here. I have tested this with 1.0.2.RELEASE.

Sample Application Configurations

Create SAML metadata file like below (wso2.xml). You have to change the entityID, samlsso url and X509Certificate according to your installation of the Identity Server. Below values is the default. You can use this blog post to find the X509Certificate of your Identity Server deployment.

<?xml version="1.0" encoding="UTF-8"?>
<md:EntityDescriptor xmlns:md="urn:oasis:names:tc:SAML:2.0:metadata" xmlns:ds="http://www.w3.org/2000/09/xmldsig#" entityID="localhost" validUntil="2026-05-16T21:51:14.927Z">
   <md:IDPSSODescriptor protocolSupportEnumeration="urn:oasis:names:tc:SAML:2.0:protocol">
      <md:KeyDescriptor use="signing">
         <ds:KeyInfo>
            <ds:X509Data>
                  <ds:X509Certificate>
MIICNTCCAZ6gAwIBAgIES343gjANBgkqhkiG9w0BAQUFADBVMQswCQYDVQQGEwJV
UzELMAkGA1UECAwCQ0ExFjAUBgNVBAcMDU1vdW50YWluIFZpZXcxDTALBgNVBAoM
BFdTTzIxEjAQBgNVBAMMCWxvY2FsaG9zdDAeFw0xMDAyMTkwNzAyMjZaFw0zNTAy
MTMwNzAyMjZaMFUxCzAJBgNVBAYTAlVTMQswCQYDVQQIDAJDQTEWMBQGA1UEBwwN
TW91bnRhaW4gVmlldzENMAsGA1UECgwEV1NPMjESMBAGA1UEAwwJbG9jYWxob3N0
MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCUp/oV1vWc8/TkQSiAvTousMzO
M4asB2iltr2QKozni5aVFu818MpOLZIr8LMnTzWllJvvaA5RAAdpbECb+48FjbBe
0hseUdN5HpwvnH/DW8ZccGvk53I6Orq7hLCv1ZHtuOCokghz/ATrhyPq+QktMfXn
RS4HrKGJTzxaCcU7OQIDAQABoxIwEDAOBgNVHQ8BAf8EBAMCBPAwDQYJKoZIhvcN
AQEFBQADgYEAW5wPR7cr1LAdq+IrR44iQlRG5ITCZXY9hI0PygLP2rHANh+PYfTm
xbuOnykNGyhM6FjFLbW2uZHQTY1jMrPprjOrmyK5sjJRO4d1DeGHT/YnIjs9JogR
Kv4XHECwLtIVdAbIdWHEtVZJyMSktcyysFcvuhPQK8Qc/E/Wq8uHSCo=
                  </ds:X509Certificate>
            </ds:X509Data>
         </ds:KeyInfo>
      </md:KeyDescriptor>
      <md:SingleLogoutService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect" Location="https://localhost:9443/samlsso"/>
      <md:SingleLogoutService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" Location="https://localhost:9443/samlsso"/>
      <md:NameIDFormat>urn:oasis:names:tc:SAML:2.0:nameid-format:transient</md:NameIDFormat>
      <md:SingleSignOnService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect" Location="https://localhost:9443/samlsso"/>
      <md:SingleSignOnService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" Location="https://localhost:9443/samlsso"/>
   </md:IDPSSODescriptor>
</md:EntityDescriptor>

Copy the created wso2.xml metadata file to <SAMPLE_HOME>/sample/src/main/resources/metadata directory. Now you need to refer this metadata file from the application. To do this you need to open <SAMPLE_HOME>/sample/src/main/webapp/WEB-INF/securityContext.xml file and find the bean with id "metadata". In the list add below to include Identity Server as an identity provider.


<bean class="org.springframework.security.saml.metadata.ExtendedMetadataDelegate">
    <constructor-arg>
        <bean class="org.opensaml.saml2.metadata.provider.ResourceBackedMetadataProvider">
            <constructor-arg>
                <bean class="java.util.Timer"/>
            </constructor-arg>
            <constructor-arg>
                <bean class="org.opensaml.util.resource.ClasspathResource">
                    <constructor-arg value="/metadata/wso2.xml"/>
                </bean>
            </constructor-arg>
            <property name="parserPool" ref="parserPool"/>
        </bean>
    </constructor-arg>
    <constructor-arg>
        <bean class="org.springframework.security.saml.metadata.ExtendedMetadata">
        </bean>
    </constructor-arg>
</bean>

Identity Server Configurations

Create a service provider. Go to Inbound Authentication Configuration and SAML2 Web SSO Configuration. Add the below configurations.
  • Issuer: http://localhost:8080/spring-security-saml2-sample/saml/metadata
  • Assertion Consumer URLs: http://localhost:8080/spring-security-saml2-sample/saml/SSO
  • Enable Response Signing.
  • Enable Single Logout.
  • SLO Response URL: http://localhost:8080/spring-security-saml2-sample/saml/SingleLogout
  • Enable Attribute Profile.
  • Include Attributes in the Response Always.
It will look like below.


Working with the sample.

Go to <SAMPLE_HOME>/sample from the terminal and run below command to build the project.
                 mvn package
Now run the below command to start the tomcat server and start the application.
                 mvn tomcat7:run

Go to the below url.
                 http://localhost:8080/spring-security-saml2-sample
You will be redirected to below page which is the index page of the sample application.


You can see the localhost as an IDP here. Its because the entityID of the metadata file we created is localhost. From the list select localhost and click "Start single sign-on" button. Now you will be redirected to the login page of the Identity Server.


Insert the username and password in the Identity Server and click Sign In. You will be redirected back to the sample application. Now you are logged in to the application and you can see the details of the authenticated user.


6 comments:

  1. Dear Maduranga,

    I tried your example but got an error messsage "Incoming SAML message is invalid"

    I used keytool to export wso2carbon.cert (alias) from WSO2 IS 5.1.0 then put it into wso2.xml as you instructed. The sample started ok, redirected to WSO2 IS ok but after coming back to http://localhost:8080/spring-security-saml2-sample/saml/SSO, it showed the error page with stacktrace
    aused by: org.opensaml.ws.security.SecurityPolicyException: Validation of protocol message signature failed
    at org.opensaml.common.binding.security.SAMLProtocolMessageXMLSignatureSecurityPolicyRule.doEvaluate(SAMLProtocolMessageXMLSignatureSecurityPolicyRule.java:138)
    at org.opensaml.common.binding.security.SAMLProtocolMessageXMLSignatureSecurityPolicyRule.evaluate(SAMLProtocolMessageXMLSignatureSecurityPolicyRule.java:107)

    ReplyDelete
    Replies
    1. Hi,

      What is the KeyStore configured in your carbon.xml. By default it has wso2carbon alias. You have exported the wso2carbon.cer alias. Try with the correct KeyStore you have configured in the carbon.xml.

      Delete
  2. Dear Maduranga,

    I have made all the configuration suggested by you,however spring along with wso2 is not able to do SLO to other service provider. It is only logging out the service provider from where SPinitiatedSLO is requested.

    I have gone through various post on google as well as wso2 official JIRA where it is showing the issue is not resolved.

    Do you have any workaround for that or you have any idea how it is done.
    I am using spring saml ver 1.0.2.Release and wso2 5.3.0.

    Please suggest

    ReplyDelete
    Replies
    1. use wso2 5.4.0 version and under Identity Resident you will get option SAML Metadata download click on this and paste at ur project metadata folder

      Delete
  3. what will be the username and password for this?

    ReplyDelete
    Replies
    1. You mean the username and password to enter at the login page? You can use the admin user (admin/admin) or create any other user from the management console of the identity server.

      Delete