[openstack-dev] [Keystone] - Cloud federation on top of the Apache
Marek Denis
marek.denis at cern.ch
Mon Jan 27 17:26:41 UTC 2014
Dear all,
We have Identity Provider and mapping CRUD operations already merged, so
it's a good point to prepare Keystone and Apache to handle SAML (as a
starter) requests/responses.
For the next OpenStack release it'd be the Apache that handles SAML
communication. In order to force SAML authentication, an admin defines
so called 'protected resources', hidden behind certain URLs. In order to
get access to aforementioned resources a SAML authenticated session is
required. In terms of Keystone and federation this 'resource' would be
just a token, ready to be later used against other OpenStack services.
For obvious reasons we cannot make mod_shib watch all the Keystone URLs
clients can access, so I think a dedicated URL should be used. That's
right, a client who'd want to grab a token upon SAML authn would need to
hit
https://keystone:5000/v3/OS-FEDERATION/tokens/identity_provider/<idp>/protocol/<protocol>
.Such a URL would albo be kind of dynamic, because this would later let
Keystone distinguish* what (already registered) IdP and federation
protocol (SAML, OpenID, etc) is going to be used .
A simplified workflow could look like this:
Pre-req: Apache frontend is configured to protect URLs matching regex
/OS-FEDERATION/tokens/identity_provider/(.*?)/protocol/(.*?)
1) In order to get a valid token upon federated authentication a client
enters protected resource, for instance
https://keystone:5000/v3/OS-FEDERATION/tokens/identity_provider/{idp}/protocol/{protocol}
2) After the client is authenticated (with ECP/similar extension) the
request enters Keystone public pipeline.
3) Apache modules store parsed parameters from a SAML assertion in a
wsgi environment,
4) A class inheriting from wsgi.Middleware checks whether the
REQUEST_URL (or similar) environment variable matches aforementioned
regexp (e.g. /OS-FEDERATION/tokens/identity_provider/.*?/protocol/.*?)
and if the match is positive, fetches env parameters starting with
certain value (a prefix configurable in the keystone.conf, say 'ADFS_'
). The parameters are stored as a dictionary and passed in a structure,
later available to other filters/middleware objects in the pipeline (TO
BE CONFIRMED, MAYBE REWRITING PARAMS IS NOT REQUIRED).
5) keystone/contrib/federation/routers.py has defined URL routes and
fires keystone/contrib/federation/controllers.py methods that fetch IdP,
protocol entities as well as the corresponding mapping entity with the
mapping rules included. The rules are applied on the assertion
parameters and list of local users/groups is issued. The OpenStack token
is generated, stored in the DB and returned to the user (formed as a
valid JSON response).
6) The token can now be used for next operations on the OpenStack cloud.
*)
At first I though the dynamic URLs
(OS-FEDERATION/tokens/identity_provider/(.*?)/protocol/(.*?)) could be
replaced with a one static, and information about the IdP and protocol
could be sent as a HTTP POST input, but from what I have already noticed
after the client is redirected to the IdP (and to the SP again) the
initial input is lost.
I am looking forward to hear feedback from you.
Thanks,
--
Marek Denis
[marek.denis at cern.ch]
More information about the OpenStack-dev
mailing list