[openstack-dev] [keystone][oslo] Handling contexts and policy enforcement in services
Adam Young
ayoung at redhat.com
Tue Dec 2 19:02:14 UTC 2014
On 12/01/2014 09:09 AM, Doug Hellmann wrote:
> On Nov 30, 2014, at 8:51 PM, Jamie Lennox <jamielennox at redhat.com> wrote:
>
>> TL;DR: I think we can handle most of oslo.context with some additions to
>> auth_token middleware and simplify policy enforcement (from a service
>> perspective) at the same time.
>>
>> There is currently a push to release oslo.context as a
>> library, for reference:
>> https://github.com/openstack/oslo.context/blob/master/oslo_context/context.py
>>
>> Whilst I love the intent to standardize this
>> functionality I think that many of the requirements in there
>> are incorrect and don't apply to all services. It is my
>> understanding for example that read_only, show_deleted are
>> essentially nova requirements, and the use of is_admin needs
>> to be killed off, not standardized.
>>
>> Currently each service builds a context based on headers
>> made available from auth_token middleware and some
>> additional interpretations based on that user
>> authentication. Each service does this slightly differently
>> based on its needs/when it copied it from nova.
>>
>> I propose that auth_token middleware essentially handle the
>> creation and management of an authentication object that
>> will be passed and used by all services. This will
>> standardize so much of the oslo.context library that I'm not
>> sure it will be still needed. I bring this up now as I am
>> wanting to push this way and don't want to change things
>> after everyone has adopted oslo.context.
> We put the context class in its own library because both oslo.messaging and oslo.log [1] need to have input into its API. If the middleware wants to get involved in adding to the API that’s fine, but context is not only used for authentication so the middleware can’t own it.
I think oslo context is mixing in the auth/access info with the rest of
the request. In policy, the acces info is on the left, and the target is
on the right. The target should be exposed by the end service, but the
access info comes from the token.
I took a swag at what this should really look like from a keystone
perspective. I started with a core domain model in pure python objects:
Spec is here.
https://review.openstack.org/#/c/135774/
Code is here.
https://review.openstack.org/#/c/137231/
However, I am going to move that code to the keystoneclient repository.
It will be populated from the token JSON and available for consumption
by keystonemiddleware.auth_token, policy (whereever that ends up living)
as well as any other code that wants it.
Policy enforcement should not make use of the Oslo Context code. It
will be a complete, self contained library. Instead, each of the
services will start with the access info from KC and then provide their
own data for the target side of policy.
We have a chain of specs. I provided an overview of where policy
enforcement is going here:
https://adam.younglogic.com/2014/11/dynamic-policy-in-keystone/
>
> [1] https://review.openstack.org/132551
>
>
>> The current release of auth_token middleware creates and
>> passes to services (via env['keystone.token_auth']) an auth
>> plugin that can be passed to clients to use the current user
>> authentication. My intention here is to expand that object
>> to expose all of the authentication information required for
>> the services to operate.
>>
>> There are two components to context that I can see:
>>
>> - The current authentication information that is retrieved
>> from auth_token middleware.
>> - service specific context added based on that user
>> information eg read_only, show_deleted, is_admin,
>> resource_id
>>
>> Regarding the first point of current authentication there
>> are three places I can see this used:
>>
>> - communicating with other services as that user
>> - associating resources with a user/project
>> - policy enforcement
> One of the specific logging requests we’ve had from operators is to have the logs show the authentication context clearly and consistently (i.e., the same format whether domains are used in the deployment or not). That’s an aspects of the spec linked above.
>
>> Addressing each of the 'current authentication' needs:
>>
>> - As mentioned for service to service communication
>> auth_token middleware already provides an auth_plugin
>> that can be used with (at this point most) of the
>> clients. This greatly simplifies reusing an existing
>> token and correctly using the service catalog as each
>> client would do this differently. In future this plugin
>> will be extended to provide support for concepts such as
>> filling in the X-Service-Token [1] on behalf of the
>> service, managing the request id, and generally
>> standardizing service->service communication without
>> requiring explicit support from every project and client.
>>
>> - Given that this authentication plugin is built within
>> auth_token middleware it is a fairly trivial step to
>> provide public properties on this object to give access
>> to the current user_id, project_id and other relevant
>> authentication data that the services can access. This is
>> fairly well handled today but it means it is done without
>> the service having to fetch all these objects from
>> headers.
> That sounds like a good source of data to populate the context object.
>
>> - With upcoming changes to policy to handle features such
>> as the X-Service-Token the existing context will need to
>> gain a bunch of new entries. With the keystone team
>> looking to wrap policy enforcement into its own
>> standalone library it makes more sense to provide this
>> authentication object directly to policy enforcement.
>> This will allow the keystone team to manipulate policy
>> data from both auth_token and the enforcement side,
>> letting us introduce new features to policy transparent
>> to the services. It will also standardize the naming of
>> variables within these policy files.
>>
>> What is left for a context object after this is managing
>> serialization and deserialization of this auth object and
>> any additional fields (read_only etc) that are generally
>> calculated at context creation time. This would be a very
>> small library.
> That’s not all it will do, but it will be small. As I mentioned above, we isolated it in its own library to control dependencies because several aspects of the system want to add to the API.
>
>> There are still a number of steps to getting there:
>>
>> - Adding enough data to the existing authentication plugin
>> to allow policy enforcement and general usage.
>> - Making the authentication object serializable for
>> transmitting between services.
>> - Extracting policy enforcement into a library.
>>
>> However I think that this approach brings enough benefits to
>> hold off on releasing and standardizing the use of the
>> current context objects.
>>
>> I'd love to hear everyone thoughts on this, and where it
>> would fall down. I see there could be some issues with how
>> the context would fit into nova's versioned objects for
>> example - but I think this would be the same issues that an
>> oslo.context library would face anyway.
>>
>> Jamie
>>
>>
>> [1] This is where service->service communication includes
>> the service token as well as the user token to allow smarter
>> policy and resource access. For example, a user can't access
>> certain neutron functions directly however it should be
>> allowed when nova calls neutron on behalf of a user, or an
>> object that a service made on behalf of a user can only be
>> deleted when the service makes the request on behalf of that
>> user.
>>
>>
>>
>> _______________________________________________
>> OpenStack-dev mailing list
>> OpenStack-dev at lists.openstack.org
>> http://lists.openstack.org/cgi-bin/mailman/listinfo/openstack-dev
>
> _______________________________________________
> OpenStack-dev mailing list
> OpenStack-dev at lists.openstack.org
> http://lists.openstack.org/cgi-bin/mailman/listinfo/openstack-dev
More information about the OpenStack-dev
mailing list