Apereo CAS 6.1.x - Credential Caching & Proxy AuthN

Posted by Misagh Moayyed on March 25, 2019 · 10 mins read ·
Content Unavailable
Your browser is blocking content on this website. Please check your browser settings and try again.
This blog post was originally posted on Apereo GitHub Blog.

Overview

Authentication attributes in CAS are defined separately from principal attributes. They capture and convey additional information, or metadata if you prefer, about the authentication transaction itself. Examples would include attributes such as What time did this authentication attempt occur?, or What type of credentials were used for authentication?, etc. This collection of attributes may also be enhanced via each authentication protocol such as CAS, OpenID Connect, SAML, etc to include even more protocol-specific details.

Hey!
Again, remember that authentication attributes are different from principal attributes. The former describes authentication metadata, while the latter is related to person identity and identifying information.

An attractive candidate as an authentication attributes is the proxyGrantingTicket attribute that of course plays a key role in CAS proxy authentication scenarios. When dealing with proxied authentication attempts, invoking a callback URL to receive the proxy granting ticket may not be all too desirable especially if the proxied application itself is clustered. In such scenarios, CAS may be configured to return the proxy granting ticket directly in the validation response as an authentication attribute. In order to successfully establish trust between the CAS server and the application, private/public key pairs are generated by the client application and then the public key distributed and configured inside CAS. CAS will use the public key to encrypt the proxy granting ticket id and will issue a new attribute in the validation response, only if the service is authorized to receive it.

Another interesting candidate is the capturing and caching of user’s credential to be passed along as an authentication attribute. CAS historically came out with this feature, so named ClearPass, that was very much built on top of proxy authentication capabilities. The original ClearPass idea, developed as an extension outside of CAS, was that an application may obtain cleartext credentials for an authenticated user by presenting a valid proxy ticket obtained specifically for the CAS cleartext extension service endpoint. To simplify this process, newer CAS versions begin to capture and release the credential as an authentication attribute, removing the need for callbacks and proxy authentication. Just as before, in order to successfully establish trust between the CAS server and the application, private/public key pairs are generated by the client application and then the public key distributed and configured inside CAS. CAS will use the public key to encrypt the credential password and will issue a new attribute in the validation response, only if the service is authorized to receive it.

In this post, we will be reviewing a few strategies to release proxy-granting tickets to applications. We will also be reviewing the configuration required to make ClearPass work and may briefly touch upon release strategies that affect authentication attributes in general.

Our starting position is based on:

Proxy-granting Tickets

To release the proxy-granting ticket to an application as an attribute, we need to establish trust between the CAS server and the application, using private/public key pairs generated by the client application. CAS will use the public key to encrypt the proxy granting ticket id and will issue a new attribute in the validation response, only if the service is authorized to receive it.

Note
The return of the proxy-granting ticket id is only carried out by the CAS validation response, provided the client application issues a request to the /p3/serviceValidate or /p3/proxyValidate endpoints.

Once you have generated the key pair, the service definition for the application authorized to receive the proxy-granting ticket may look like this:

{
  "@class" : "org.apereo.cas.services.RegexRegisteredService",
  "serviceId" : "^https://sample.example.org:9443/sample.*",
  "name" : "Sample",
  "id" : 1,
  "attributeReleasePolicy" : {
    "@class" : "org.apereo.cas.services.ReturnAllowedAttributeReleasePolicy",
    "authorizedToReleaseProxyGrantingTicket" : true
  },
  "publicKey" : {
    "@class" : "org.apereo.cas.services.RegisteredServicePublicKeyImpl",
    "location" : "file:/etc/cas/config/clearpass/public.key"
  },
  "proxyPolicy" : {
    "@class" : "org.apereo.cas.services.RegexMatchingRegisteredServiceProxyPolicy",
    "pattern" : "^https://sample.example.org:9443/sample/.+"
  }
}

Note the proxyPolicy block which controls whether the application is allowed to exercise proxy authentication in general. Per the docs:

Each registered application in the registry may be assigned a proxy policy to determine whether the service is allowed for proxy authentication. This means that a PGT will not be issued to a service unless the proxy policy is configured to allow it. Additionally, the policy could also define which endpoint URLs are in fact allowed to receive the PGT.

Once the public key is taught to CAS using the publicKey block, the only thing that remains is the authorizedToReleaseProxyGrantingTicket switch which controls the release of the proxy-granting ticket as an attribute encapsulated inside the service’s attribute release policy.

Test

If you run through the application, you should ultimately expect the following attributes in the CAS response:

image

ClearPass

Configuring CAS to release the credential password as an attribute is very similar. As the first step, we will enable and assign encryption and signing keys to ClearPass in order to capture the password and encrypt it while cached in memory so as to not leak the plaintext password in case data and memory are compromised or somehow shared externally.

cas.clearpass.cacheCredential=true
cas.clearpass.crypto.encryption.key=AZ5y...
cas.clearpass.crypto.signing.key=cAPyo...

Once that’s done, we can just enable the application to receive the password using the authorizedToReleaseCredentialPassword switch:

{
  "@class" : "org.apereo.cas.services.RegexRegisteredService",
  "serviceId" : "^https://sample.example.org:9443/sample.*",
  "name" : "Sample",
  "id" : 1,
  "attributeReleasePolicy" : {
    "@class" : "org.apereo.cas.services.ReturnAllowedAttributeReleasePolicy",
    "authorizedToReleaseProxyGrantingTicket" : true,
    "authorizedToReleaseCredentialPassword" : true
  },
  "publicKey" : {
    "@class" : "org.apereo.cas.services.RegisteredServicePublicKeyImpl",
    "location" : "file:/etc/cas/config/clearpass/public.key"
  },
  "proxyPolicy" : {
    "@class" : "org.apereo.cas.services.RegexMatchingRegisteredServiceProxyPolicy",
    "pattern" : "^https://sample.example.org:9443/sample/.+"
  }
}

Test

If you run through the application, you should ultimately expect the following attributes in the CAS response:

image

Authentication Attributes

There are of course many other types of attributes that could be collected as part of the authentication event itself. The release of such attributes to applications is controlled globally via CAS settings. For example, you can decide to never release any authentication-level attributes to any applications:

cas.authn.authenticationAttributeRelease.enabled=false

Or let’s say that you only prefer to send a handful of authentication attributes to all applications:

cas.authn.authenticationAttributeRelease.enabled=false
cas.authn.authenticationAttributeRelease.neverRelease=credentialType,authenticationDate

So…

I hope this review was of some help to you and I am sure that both this post as well as the functionality it attempts to explain can be improved in any number of ways. Please know that all other use cases, scenarios, features, and theories certainly are possible as well. Feel free to engage and contribute as best as you can.

Happy Coding,

Misagh Moayyed