CAS for web applications

OVERVIEW

WHAT IS CAS

The Central Authentication Service (CAS) is a web application used by other web applications to authenticate visitors. In addition to providing authentication, CAS implements a single sign-on feature to make it easier for users to move from one authenticated application to another. SFU CAS is a slightly modified version of Jasig CAS. SFU has added a number of extensions to CAS (mostly authorization features such as integration with our mail list system), but has maintained compatibility with Jasig CAS, so applications that support Jasig CAS should work at SFU without modification.

 

WHEN TO USE CAS

Any application in use at SFU, whether running on the cgi.sfu.ca server, or running on a departmental or dedicated server, can use CAS for authentication. Third-party applications customized for SFU should be modified to use CAS whenever possible.

Although CAS can provide some basic authorization, it is an authentication service. It determines that users are who they say they are. CAS can provide information to help an application make authorization decisions, but it is important to understand that some people who possess an SFU computing account may only be loosely affiliated with SFU.

All applications that use SFU CAS must be registered as a service. Fill out the CAS Service Application form to get started.

 

DETAILS

THE EASIEST WAY TO USE CAS

In many cases, using CAS requires no new programming to protect either static web content or dynamic web applications. On systems that run the Apache HTTP Server, a runtime module (mod_auth_cas) is available to provide CAS authentication to the entire server (or a configurable subset of the server’s content).

While CAS simply authenticates users, this module provides both authentication services and access-control services. It lets you grant access to specific users as well as users based on their membership in a maillist. It even lets users on your servers authenticate users and restrict access via local .htaccess files.

 

A PROGRAMMER’S VIEW OF CAS

If you decide that the Apache module is insufficient for your needs, you will need to write a small amount of custom code to handle authentication programmatically. Some client libraries are available to ease the use of CAS even further.

Before you begin to integrate your application with CAS, however, you should understand a few details about the way CAS operates. First and more importantly, CAS is unlike many familiar authentication systems because it is not simply a password-validation tool. In a traditional environment, your web application will ask users for an ID and a password, and it will then call logic to determine whether this ID/password pair is valid. With CAS, however, your application never gains access to the user's password; to improve system-wide security, users supply their passwords only to the CAS server directly.

Therefore, using CAS in your application may be more circuitous than you initially imagine, though be assured that the process is still straightforward and easy to master. When you first encounter a new user (e.g., one that has not yet established a session with your application), you'd normally display a username/password form in HTML. With CAS, you don't do this; instead, you simply redirect the user's browser to CAS's login URL, which is

https://cas.sfu.ca/cas/login

CAS then authenticates the user. If authentication fails – e.g., if the user cannot supply a correct password – then you’ll never hear from the user again. Instead, the user will remain at CAS’s site and will have the option to choose various “help” links that point to IT Services help sites to help them deal with computing account problems.

Only if a user successfully authenticates does that user’s browser return to your application. Specifically, the user returns because CAS redirects the browser back to your application. CAS knows how to find your application because when you initially redirected the user to CAS, you supplied a service parameter, in the form

https://cas.sfu.ca/cas/login?service=http://my/url

(Note that any metacharacters in your service URL, such as question marks, ampersands, and equals signs, must be escaped appropriately using the standard URL encoding algorithm: %26 for &, %3D for =, and %3F for ?. This will be necessary if your service URL contains parameters of its own. Note also that while it is necessary that you use HTTPS to safeguard your own application's authentication in secure environments, CAS's overall security is not weakened if your application merely uses HTTP; instead, CAS still authenticates the user securely.)

When CAS redirects the authenticated user back to your application, it will append a parameter named ticket to your URL. For instance, the URL you supplied CAS may be called as follows:

http://my/url?ticket=ST-92834-m34Aa83f7a3f

We call this ticket opaque because, unlike an X.509 certificate or a Kerberos TGT, it is not possible for your application to decipher its meaning in isolation or from first principles. It has no internal structure useful to your application. The only thing you can do with this ticket is to send it back to CAS, which involves opening an HTTPS connection to

https://cas.sfu.ca/cas/serviceValidate

and sending two query parameters: service, which must match the service URL you initially supplied to CAS when redirecting the user there, and ticket, which is the ticket you just received. CAS then responds either with an explicit refutation of the ticket (think “it’s not meaningful to me and does not represent a valid user”) or an acknowledgment that the ticket proves authentication. In the latter case, CAS also supplies information about the user in an XML document, most notably the account that the user logged in with.

Note that this final connection to CAS occurs directly between your application and CAS; your application opens a socket connection and retrieves information from the CAS server. You do not redirect the browser; you speak directly to CAS, effectively closing the loop and completing the authentication process. The CAS client libraries focus on making the HTTPS communication simple in a variety of languages; you don’t need to know details about how to write an SSL or HTTPS client, nor do you need to know any details about how CAS’s response is formatted textually.

 

WHAT TO DO ONCE YOU AUTHENTICATE A USER WITH CAS

CAS is not a session-management mechanism; it provides no facility for helping you keep track of users once they’re authenticated. Typically, applications will want to track users just as they would if they’d validated a user’s password themselves. That is, you’ll probably want to establish your own session – using application-specific, in-memory cookies or a similar mechanism – right after you validate a user’s authenticity with CAS.

CAS is a single sign-on facility; once a user authenticates to CAS, the user need not continue to supply a password for other applications that redirect the user to CAS. However, CAS is not a “single sign-off” facility; a user that logs out of CAS will still have access to your application if your application keeps a persistent session with the user. CAS does offer a Single Sign Out option, which, when activated, will notify an application that a user has logged out of CAS.  The application can then terminate any remaining local sessions as well. See the Jasig documentation for more details.

CAS does provide a “logout” URL that the user may visit; loading the URL causes CAS to forget about the user’s prior authentication. Applications may link to this URL at

https://cas.sfu.ca/cas/logout

 

OTHER THINGS CAS CAN DO

CAS lets applications opt out of its single sign-on facility. For applications that consider their data especially sensitive, this facility may be appropriate to ensure that a CAS-authenticated user is still present and hasn’t, for instance, walked away from a public kiosk. Note that using this feature makes it difficult to integrate your application into a campus-wide portal and may disappoint users’ expectations of single sign on. To use this option, you would add the parameter

renew=true

to the login and serviceValidate URLs.

CAS also lets applications choose to not force a user to log in if they are not already logged in. This will guarantee that the user will not be interrupted by a login page, and allow the application to put up a generic (or gateway) page if the user is not currently logged in. This option is chosen by adding the parameter

gateway=true
to the login URL.

 

OTHER CAS OPTIONS

CAS offers some other options to allow applications to modify how they interact with CAS. The following options are extensions added to the SFU version of CAS, and are not available in the Jasig version of CAS.

These options are:

error=error+message – If the application has determined that the user who has been successfully authenticated does not have access to the application, it can redirect to the login page again, this time using the renew=true option along with the error option to explain to the user why they need to try another user account.

message=message+from+application – The application can choose to put a message to the user up on the login page. If this is not set, CAS will put a default "You have requested access to a site that requires authentication" message

app=AppName – The application can specify its name so that CAS can put up a more specific "Login required" message.

allow=handler1,handler2,… – CAS can use one or more “handlers” to authenticate a user. Each of the specified handlers will be tried in turn until it can be determined that the authentication has succeeded or failed. By default, the sfuhandler alone is used. If this option is used, it must be passed to both the login and serviceValidate URLs.

The handlers that are available are:

1.     sfu – This is the default (i.e. if no allow list is given), and will match any SFU account. The serviceValidate call-back, will return a response like the following:

<cas:serviceResponse>
  <cas:authenticationSuccess>
    <cas:user>userID</cas:user>
    <cas:authtype>sfu</cas:authtype>
  </cas:authenticationSuccess>
</cas:serviceResponse>

 

2.     alumni – This will match any alumni email address and password. The user must enter id@alumni.sfu.ca and their password. The following will be returned from the serviceValidate call-back:

<cas:serviceResponse>
  <cas:authenticationSuccess>
    <cas:user>userID@alumni.sfu.ca</cas:user>
    <cas:authtype>alumni</cas:authtype>
  </cas:authenticationSuccess>
</cas:serviceResponse>

 

3.     staff

4.     faculty

5.     student

6.     sponsored

7.     apache - This was added to CAS to allow the Apache CAS module to authenticate accounts from a .htpasswd file serviceValidate call-back for this option:


Some people have found it useful to use this from an application calling CAS directly to implement their own "accounts". Because CAS can't do the authentication for you, the password will be returned to your application. Because a password will be returned to you, CAS will not allow you to have an "apache" account that has the same id and password as an SFU account. The following would be returned from the 

<cas:serviceResponse>
  <cas:authenticationSuccess>
    <cas:user>id</cas:user>
    <cas:authtype>apache</cas:authtype>
    <cas:password>password</cas:password>
  </cas:authenticationSuccess>
</cas:serviceResponse>

 

9.     !mail-list - This allows access to members of a mail list. You specify an allow option with an exclamation mark followed by the mail list name. If you use the parameter:

allow=!sfu-cas

the following would be returned from the serviceValidate call-back  if a member of that mail list logged in:

<cas:serviceResponse>
  <cas:authenticationSuccess>
    <cas:user>ray</cas:user>
    <cas:authtype>sfu</cas:authtype>
    <cas:maillist>sfu-cas</cas:maillist>
  </cas:authenticationSuccess>
</cas:serviceResponse>

What Gets Passed Back By serviceValidate

The serviceValidate URL will pass back an XML document indicating the success or failure of the validation. On failure, an error like the following will be returned:

<cas:serviceResponse>
  <cas:authenticationFailure code='...'>
    Optional authentication failure message
  </cas:authenticationFailure>
</cas:serviceResponse>

indicating that the ticket was invalid and why, or:

<cas:serviceResponse>
  <cas:authenticationSuccess>
    <cas:user>userID</cas:user>
    <cas:authtype>sfu</cas:authtype>
  </cas:authenticationSuccess>
</cas:serviceResponse>

indicating that the validation succeeded. The number and types of keyword/value pairs varies depending on the application. The user and authtype keywords are always returned. Other items may be returned (e.g., see the allow option above).

 

PROXY AUTHENTICATION

In a multi-tier CAS installation, an agent acting on behalf of a user, but without direct access to the user's cookie cache, may need to convince a third party that it represents the user legitimately. For example, a WebMail application that connects to a POP server to collect the user’s email, would have to convince the POP server that it is acting legitimately on behalf of a particular user. Using proxy tickets, a back-end service may determine (a) what user is being impersonated; (b) who is handling the impersonation. These two determinations allow service to accept proxied credentials selectively.

 

THE PLAYERS

A few definitions are in order:

CAS

The Central Authentication Service: a trusted arbiter of authenticity.

Service

A web application that authenticates users via CAS.

Proxy

A service that wants to impersonate users to other services.

Target (or back-end service)

A service that accepts impersonated (proxied) credentials from at least one particular proxy.

 

TICKETS

Parties involved in a CAS authentication make use of tickets, or opaque strings that prove some assertion to CAS. CAS uses the following tickets:

Ticket-granting cookie (TGC)

A ticket encapulated by a cookie that is sent to the user's web browser and returned only to CAS, and only over a secured channel. This ticket establishes the user's identity with CAS and lets CAS act as a single sign-on system for the web.

Service ticket (ST)

A ticket sent by CAS, through the user's browser, to a service. Each ST may be used only once, and must be combined with the unique identifier for one specific service in order to be useful. (Put another way, a service that knows its own unique identifier will refuse to accept STs intended for another service. This prevents one service from mounting a "man in the middle" attack against another.)

Proxy-granting ticket (PGT)

A ticket sent by CAS to a service holding a valid ST (but see below). This ticket (associated with an individual service and an individual user) confers the ability to produce proxy tickets (see below).

Proxy-granting ticket IOU (PGTIOU)

A ticket sent by CAS alone in a service validation response, and with a PGT to the callback URL. It is the web application's responsibility to maintain a table to correlate PGTIOUs and PGTs (see below).

Proxy ticket (PT)

A ticket usable by a proxy to access a target by impersonating a single user. The PT carries information about the proxy or proxies attempting to gain access. For targets that are also (second- or higher-level proxies), a PT may be used to obtain a PGT, but this PGT will preserve information about the linear series of proxies that lie between the user and the ultimate target.

 

PROXY MECHANISM

If an application that is using CAS needs to be a proxy, and so needs a proxy ticket to pass on to a target application, the proxy applicationserviceValidate URL, The  needs to pass an extra query parameter to the proxyCallbackUrl parameter is used to specify a URL that CAS will connect to with two query parameters:

pgtID – the actual value representing the PGT.

pgtIou - the PGTIOU contained in CAS's response to the web application's request.

Your application has the responsibility to maintain a table to correlate PGTIOUs and PGTs. The CAS servicevalidate callback will then respond with the following:

<cas:serviceResponse>
  <cas:authenticationSuccess>
    <cas:user>userID</cas:user>
    <cas:authtype>sfu</cas:authtype>
     <cas:proxyGrantingTicket>PGTIOU</cas:proxyGrantingTicket>
  </cas:authenticationSuccess>
</cas:serviceResponse>

Your application can now match the PGTIOU to get the PGT from the table that was setup by your applications proxyCallbackUrl.

The proxy application can now obtain proxy tickets (PTs) by using the following request/response connection:

Request: The proxy application sends an HTTP request with two query parameters: pgt and targetService, representing respectively a PGT and the unique identifier (URL) corresponding to the target application to which the proxyapplication wishes to gain access. The URL to send the request to is:

https://cas.sfu.ca/cas/proxy

Response: A cas:proxyFailure message can be returned here for invalid or expired PGTs. On success, a message, of the following format, is sent by CAS to the application:

<cas:serviceResponse>
  <cas:proxySuccess>
    <cas:proxyTicket>PT</cas:proxyTicket>
  </cas:proxySuccess>
</cas:serviceResponse>

This PT may then be sent by the application to the target service, which validates it with CAS using the following protocol:

Request: The target application sends an HTTP request with two query parameters: ticket and service, representing respectively the PT and the unique identifier (URL) of the target application. The URL to send the request to is:

https://cas.sfu.ca/cas/proxyValidate

Response: A cas:authenticationFailure message can be returned here for invalid or expired PTs. On success, a message, of the following format, is sent by CAS to the application:

<cas:serviceResponse>
  <cas:authenticationSuccess>
    <cas:user>userID</cas:user>
    <cas:authtype>sfu</cas:authtype>
     <cas:proxyGrantingTicket>PGTIOU</cas:proxyGrantingTicket>
 <cas:proxies>
   <cas:proxy>proxy1</cas:proxy>
   <cas:proxy>proxy2</cas:proxy>
   <cas:proxy>proxy3</cas:proxy>
     ...
 </cas:proxies>
  </cas:authenticationSuccess>
</cas:serviceResponse>

The target service may then make any access-control decisions it needs to make, based both on the username and on the proxy “path” conveyed by the response from CAS.

As the general format of this latest response message suggests, proxies may be "chained" – that is, applied successively – before an ultimate target is reached. This chaining is achieved by the added PGTIOU to this recent message – when target services implement the "proxy granting" protocol. Thus, a target service may act as a proxy as well.

Calls to proxyValidate can also specify allow options. The default allow option is sfu, so if this option is not specified, only SFU accounts will be returned to the application.