I've set up a single-sign-on for two of our sites that live on the same domain: a.domain.com and b.domain.com

I did it through cookies, but they are domain-dependant. And - as it is written in the Great Book - now the need for single-sign-on on different domains has raised its ugly head :)
I'm 99% sure i can forget about using OpenId (they don't like external services here, i couldn't even get them to accept reCaptcha)

I'd like to be able to identify somebody on different websites (a.domain.com, b.anotherdomain.com, etc). What are the recommended ways to setup/manage single-sign-on on multiple domains? Any specific security concerns i should be aware of before drafting a proposal?

6 Answers
6

The way that single sign-on has been implemented for the Stack Exchange Network is very interesting. It makes use of HTML 5 Local Storage. Depending on the browser support that you require you maybe able to use a similar method.

You don't have to use an external service for OpenId. You could host an OpenId server internally and use it for your SSO. This would allow you to leverage open source code and all the work that has gone into making OpenId secure.

PS: OpenId can be used to have a unique identity used by many sites but you still have to "manually" login on each domain.

Perhaps ADFSv2 (A free download for Windows 2008R2) will help you with the common domain cookie. Here is an excerpt of the web.config located in C:\inetpub\adfs\ls that you will need to configure to achieve the desired effect.

<!--
Common domain cookie. A common domain cookie stores a list of recently visited Claims Providers
(also called Identity Providers), as described in Section 4.3.1 of Profiles for the OASIS Security
Assertion Markup Language (SAML) V2.0. It is recommended that you enable common domain cookies by
including the <commonDomainCookie> element in the web.config file.
1.The writer attribute of the <commonDomainCookie> element specifies the address of the writer
service that a Claims Provider uses to set the common domain cookie once it has authenticated a user.
This address should be a valid URL.
2.The reader attribute of the the <commonDomainCookie> element specifies the address of the reader
service that a claims-aware service (also called a Service Provider) uses to get the list of Claims
Providers that it should present to the user. This address should be a valid URL.
The following configuration enables the use of common domain cookies and specifies writer and reader
services as described previously.
A common Domain Cookie is named "_saml_idp" in 4.3.1 http://docs.oasis-open.org/security/saml/v2.0/saml-profiles-2.0-os.pdf
Space delimited URI encoded
RULES:
Must be secure
Must have path = /
Must be leading period as in .domain.com
Can be session or persistant
All providers should be configured similarly
TODO-->
<commonDomainCookie writer="" reader="" />

Though I don't think any of these are really trivial to implement, without learning a bit more about them.

Better yet would be implementing a proper web-SSO product - though it seems from your question that that is not an option (though I would urge you to reconsider, and try to convince your higher-ups).

One pretty simplistic solution that I've seen, and in fact some web-SSO products use this trick too (note that I don't necessarily recommend this approach in all situations, see below):
Have a third, "authentication" domain that issues an "identity cookie" (after authenticating the user). Websites on other domains can submit a simple POST request to the authentication domain, which will of course include the user's cookie for that domain. The returned response would basically tell the original domain, whether the user is authenticated, and if needed what his identity is.
If the user is not yet authenticated - he'd be redirected to a page on the authentication domain to submit his password etc.

While this is pretty simple to set up, note that there are some challenges around making it actually secure.
For example, as defined, any website can retrieve your identity. Also, the relying website can be "tricked" by modifying the returned response.
Of course, the most straightforward way of solving these issues is - you guessed it - SAML/OpenId/etc.

I've just signed up, but find it surprising you've not found an answer elsewhere.
As you've already found out, you can't pass surrogate authentication tokens using cookies.

You've not provided any details on how authentication for your current site is implemented nor the tools you have available for programming the sites. But I'll assume that the authentication mechanism is written in a language which runs on the webserver and uses a cookie to keep track of the session.

In that case, you've already got code on every url which requires authentication to check if the session has been authenticated, and then take the appropriate action - either actioning the request or redirecting to a login page. All you need to do is deal with the scenario where there is no authenticated session and there is an encrypted variable passed in the URL (i.e. as a GET). You decrypt the value, check its valid and create a session at this point. Then on your login page, after a successful login, you redirect, appending the appropriate key/value pair to the URL.

That's a brief overview - there are some tweaks you need to think about (e.g. do you want the same session data shared across all sites, do you want to rebind the session for different sessions to ensure that it doesn't expire server-side) and you also need to think about how you prevent replay attacks (e.g. including a TTL in the encrypted payload, including a randomly generated challenge, but beware of using the client IP address).

Since you're only encrypting/decrypting server-side, symmetric encryption is adequate.

You're missing out on several points, such as the fact that it might be different servers, in which case your solution flies out the window. Also, passing this "secret token" in the URL is a Bad Idea.
–
AviD♦Nov 30 '10 at 13:03