The following document outlines a basic design for implementing single sign-on in a service-oriented architecture with many user-facing apps. I have posted it here hoping to get feedback, so don't be afraid to fork and/or comment with your thoughts.
The design relies on two main components in addition to the user-facing servers (apps) and app-facing servers (services):
- An authentication proxy that sits in front of all apps
- An authentication/authorization service that manages user accounts
A simple HTTP proxy is used to field incoming requests and integrate a central authentication and authorization service with all user-facing applications. The proxy is responsible for handling two basic scenarios, outlined below.
A request from a user that is not authenticated (no auth cookie present) gets passed immediately to the appropriate app. From there, two things can happen:
-
If the app responds with
401 Unauthorized
the proxy responds to the original request with302 Found
, setting theLocation
header to the login/register page of the SSO service. -
If the app responds with any other status code the proxy simply forwards the reponse to the user.
When a request comes in from a user that has an authentication cookie the contents of the cookie are passed to the Auth Service via an HTTP endpoint which responds with the user's account information (unique id, email, roles). The account information is then passed to the app (and every service the app communicates with) via TBD.
- Does this make sense at all? Have we effectively decoupled auth from the various apps and their backing services?
- Is there a better status code to use in place of
401
when apps require authentication? In order to be rfc2616 compliant we would have to specify some arbitraryWWW-Authenticate
header field, which could be bogus (e.g.WWW-Authenticate: Null
) and technically compliant, or meaningful (e.g.WWW-Authenticate: AuthService
) and tightly coupled. - What should we use to pass account info arround the system? Headers? Params? Probably not params...
- Authentication cookie processing needs to be
- SSL for simple auth between services.
- rails-api as the framework of choice for implmenting services.
- active_model_serializers for JSON generation.