Anonymous user [OpenID enabled] [XRI enabled] [LID enabled]

SSO at a Second Site How-To

From LID Wiki

Jump to: navigation, search

This page describes a frequently encountered single-sign-on scenario for LID/Yadis/OpenID URL-based identity. This scenario is typically not encountered on the open internet, but in a corporate environment where both the identity host and the relying parties are known. It occurs frequently enough to warrant a writeup.

Contents

Scenario

There are two websites, site A and site B. The set of possible users is the same at both sites. Users initially access site A, and use a username and password to log on to site A.

The question is: how do I use LID so that users can also access site B, without having to re-enter their username and password? Of course, it needs to be secure that no user can pretend to be somebody else at site B.

For simplicity, assume that users reach site B by clicking on a hyperlink on some page on site A, instead of entering it manually into the browser.

Can it be made to work? Are any protocol extensions needed?

Yes, it works; no protocol extensions are needed.

P.S. This scenario can be implemented more efficiently than it is described, but this way it is easier to explain, so that's what we'll do. Once you understand how it works and why it works, you will probably come up with ideas how to best apply it to your own circumstances yourself.

Basic installation

1. Download NetMesh InfoGrid LID from http://netmesh.org/downloads/. You can probably also make it work in a similar manner with other LID and/or OpenID implementations, but this description is about NetMesh InfoGrid LID.

2. Put the Relying Party code at server B. Depending on your programming language, that may be as easy as a single "include statement" at the beginning of the CGI script, as it is documented for a simple Relying Party in the InfoGrid LID documentation

3. For each user, create a user URL on server A (many applications have that already, some kind of "home page"). That URL becomes the user's identity URL, such as

http://A.example.com/~joe

4. Put the identity hosting code at those user URLs at server A so it runs when a user URL is accessed.

5. On the page on server A that has the hyperlink to server B -- let's assume it is

http://B.example.com/page.cgi

append the identity URL of the user. This can be done that because we assume the user already has a valid session with server A after the login at server A, so it is known who they are. So it looks like this:

http://B.example.com/page.cgi?lid=http://A.example.com/~joe

6. Configure default session expiration as appropriate for server B.

Note: if the users are accessing server B without going through a hyperlink from A, one can hardcode the identity provider URL on server B and accomplish the same thing.

What happens?

1. User accesses site A, and logs in with a username and password, a smart card or whatever other mechanism you have defined for logging in at site A. It is not important what that mechanism is.

User works on site A.

2. User clicks on the hyperlink, on a page on site A, that leads to a page on site B, as described above, such as:

http://B.example.com/page.cgi?lid=http://A.example.com/~joe

3. The Relying Party code at site B examines the incoming request, and determines the following:

a. The page http://B.example.com/page.cgi was requested.
b. The user claimed that their identity is http://A.example.com/~joe
c. No credential has been provided, so the Relying Party needs to set out to obtain one.

4. The Relying Party code redirects the browser session back to site A. The exact URL to which it redirects depends on the particular setup and crypto preferences (OpenID Diffie-Hellman key exchange vs. GPG-based credentials etc.), but is of no further consequence. The important part is that because the user has a valid session at site A, the identity hosting code will generate a cryptographic assertion that it is indeed the user, and redirects the browser right back to the URL it came from, plus the digital signature on the URL, such as:

http://B.example.com/page.cgi?lid=http://A.example.com/~joe&lid-credential=...crypto...

(using the GPG credential)

http://B.example.com/page.cgi?openid.identity=http://A.example.com/~joe&openid.sig=...crypto...

(using the OpenID credential)

Some other arguments, like nonces, were left out for readability.

5. Now, the Relying Party at server B can be certain it was the user with the given identity URL, because it would require a cryptographic genius (or a break-in) to be able to fake the digital signature.

6. We left out one step: the Relying Party will also negotiate a shared secret (OpenID case) or obtain a public key (GPG case) from the identity host. This is performed rather rarely, however, as the Relying Party tends to cache those (and the InfoGrid LID implementation certainly does).

Is this secure?

Yes. Consider what happens if an attacker accesses server B, claiming that the attacker is really Joe, using this request:

http://B.example.com/page.cgi?lid=http://A.example.com/~joe

Just as in case of Joe, the attacker's browser will be redirected to server A. But unlike for Joe, the attacker has not authenticated as Joe at site A and doesn't have a valid session at site A as Joe. Therefore, site A will not calculate a digital signature confirming that the browser session is indeed owned by Joe; instead, it will prompt Joe to authenticate at site A, as Joe, which the attacker doesn't know how to do.

What happens if the attack happens when Joe is using server A?

The attacker cannot impersonate Joe at server A either, because both of them have different sessions/cookies there. (Naturally, otherwise any user of any website could impersonate any other user at the same website -- say at a bank. This is standard web security and has nothing to do with LID.)

Personal tools