Work with SAML in IRIS
When a company is quite large and many different applications used by employees. But while those applications are mostly completely different, how to make it possible to not force users to enter credentials as many times as many applications they would like to use. The best way is to use SSO, so, it will be possible to have a portal, where users could launch any application used in a company. There are many different ways how to give access to your application by using the SSO mechanism, and some of them are:
SAML is an open standard for exchanging authentication and authorization data between parties, in particular, between an identity provider and a service provider.
In authentication with SAML participating three parties:
- Service Provider (SP) - web-based application. In our case, it will be our IRIS based application
- Identity Provider (IdP) - any external software with a role as Identity Provider. It can be
- Microsoft Azure, myapps.microsoft.com
- and so on
- User Agent - browser where your user use to work with your application
Before we start to speak how to use SAML, in your application, add just a few words about terms, used in SAML in the context of using in the authentication process.
- Service Provider (SP) - is a system entity that receives and accepts authentication assertions in conjunction with a single sign-on (SSO) profile
- Identity Provider (IdP) - is a system entity that issues authentication assertions in conjunction with a single sign-on (SSO) profile
- SAMLRequest - a message in form of XML, prepared by Service Provider and sent to Identity Provider
- SAMLResponse - a message in form of XML, prepared and signed by Identity Provider and sent to Service Provider
- EntityID - some unique value for SP or IdP, which identifies this particular instance, in most cases in the form of URI
- ACS URL, Assertion Consumer Service URL - URL on SP side, which can process queries with parameter SAMLResponse, should validate SAMLResponse and create a session for the user
- Certificate - issued and used by IdP, to sign SAMLResponse. Service Provider should store issued by IdP certificate, to validate SAMLResponse
- IdP Login/SSO URL - URL on Idp side, accepts queries containing SAMLRequest, validates and redirects to the authentication page if needed, and redirects back to SP
- IdP Metadata - XML-based metadata contains some settings from IdP, such as SSO URL, and Certificate
The interaction scheme itself on the picture
And there are two cases of interaction
- The user opens your application directly, for the first time in the current session. The application prepares a message for Identity Provider, and redirects to Login Url, when processed authentication, and redirects back with a specially formed response.
- First of all, the user goes to Identity Provider's portal, already authorized, and opens desired our application, and IdP forms URL with the response and redirects the user to the application.
From theory go to practice. I've published the new repository, https://github.com/daimor/iris-saml-example which contains an example of how it can be used in InterSystems IRIS. In can be started with docker. In my examples below I will show how to use it with GSuite, with any other Identity Provider, settings should be very similar, just keep in mind some caveats, described at the end of this article.
Start a simple Service Provider, in this role will be my example. So, just clone this repo, and start it with docker-compose
$ git clone https://github.com/daimor/iris-saml-example.git $ cd iris-saml-example $ docker-compose up -d --build
After a while after build will be completed, and IRIS will start, our test application will be available by URL http://localhost:19092/csp/irisapp/MyApp.cls. Google and some other IdP may require that your application should be used over HTTPS. To have access over https to my local application I'm using ngrok project. Let's start secure tunnel to our application.
$ ngrok http 19092
It should output something like this.
So, our application now available by link http://b571ff3e.ngrok.io/csp/irisapp/MyApp.cls, and should show such page
The next step will be to configure IdP, in my case G-Suite, go to Admin Console, Apps, SAML Apps, SETUP MY OWN CUSTOM APP
Where google issued a new certificate for our new application. We need IDP Metadata file.
Next, define the name of the application
Then we should fill ACS URL and Entity ID with values from our application. And select Name ID Format, EMAIL, or any other value, which can be used as a login in your system.
On the next step, just finish the configuration.
And finally, we should enable it, for the users in our organization
Return back to our application, in the file field choose previously downloaded metadata file, and press submit.
It should parse that file, and store it in our format on the IRIS side.
Below it contains a simple SAMLRequest, which will be used when you press the Login button.
By Login button, it makes a POST a form with SSO URL provided by Identity provider as action URL, and SAMLRequest field which contains an XML from above encoded as Base64.
Identity Provider, should validate our SAMLRequest, offer form login form if the user not authorized yet. And redirect back. So in our application, we should see something like this.
Here shown SAMLResponse provided by IdP, and it contains a signature, which has to be validated with the certificate which we got from the metadata file. When SAMLRequest validated, it shows the status and NameID (email) of the user.
Validation may fail with the error like this:
Validation: ERROR #6390: Signature validation failed: Failed NotBefore/NotOnOrAfter (/2020-05-09T15:17:48.525Z) date time verification with clock skew of 0 seconds.
SAMLResponse can contain one or two signatures. The Assertion or the whole Response can be signed. But you should keep in mind that IRIS does not validate SAMLResponse if only Response signed it returns ERROR #6390: Signature validation failed: No Assertion.
So, our application is now available from the list of Google applications
This article does not contain information on how to authorize users in your application, it just shows how to retrieve user's info, so then you can use own mechanism or delegated authorization.
- Namespace should be Ensemble enabled. Validation of SAML lies in class Ens.Util.XML.SecuritySignature
- InterSystems IRIS (tested version 2020.2) and below does not validate if only Response signed, and requires Assertion to be signed.
- SAMLResponse sent by URL's query, while encoded with Base64 can be too long, and in some cases truncated. Some IdP supports Response and Assertion signed at the same time, so, recommend switching off signing Response.
- SAMLResponse and SAMLRequest by standard support compression before encoding with Base64. IRIS does not support such compression directly.