Re: [Openstack] Capture of the Keystone/LDAP Role discussion

2012-02-02 Thread Adam Young

On 02/02/2012 02:38 AM, Vishvananda Ishaya wrote:
Nice summary.  As you said ldap structures are going to vary by 
company.  I am curious if AD has a standard way of dealing with this 
that we could use. FWIW, the nova deprecated ldap auth code uses 
subtrees for roles, and yes it is painful, but it might be the way to 
go if we want something quick and we assume organizations are going to 
have to write their own version anyway.


Based on discussions with numerous people,  It seems that the subtree 
approach (as done by nova deprecated)  is the norm.


What seems to vary the most amongst LDAP servers is not the schema,  but 
the method used to query for membership in nested groups.   In 
OpenLDAP,  the syntax involves sets


http://www.openldap.org/faq/data/cache/1133.html
http://www.openldap.org/faq/data/cache/1134.html

Whereas in Active directory,  it involves  using 
LDAP_MATCHING_RULE_IN_CHAIN rule OID.


In the 389 (Fedora) Directory Server as well as OpenLDAP it is also 
possible to use   the deference control in conjunction with the  
memberof plugin.



However,  we might not need to query for nested group membership.  For 
example, lets assume a tenant has 3 administrative roles:  user 
management,  network management, VM management. In addition,  users that 
do not have an explicit admin role get read only access to the resources 
of that tenant.  So a user that has the right to manage networks for 
that tenant would have to appear in both the members list of that tenant 
as well as in the networkMgmt role.  The first is provided for read only 
access, and the second for the ability to modify the network.  It is a 
little redundant.  We could perhaps put a constraint on the roles that 
they will only allow users that are listed in the general membership for 
that tenancy.


There was some talk about nesting tenancies for resellers.  This is 
somewhat different from nested group member ship, as entry in the lower 
level tenant should *not* provide access to all resources of the 
containing tenancy.  Permissions go the other way around:  if I am an 
admin of the container,  I can manage elements of the contained.  It 
does mean that the Keystone server needs to be smart enough to check all 
of the levels of nesting from lowest to highest to see if a user has the 
appropriate role for the requested operation.


So,  to summarize:  Roles will be entites under tenants,  with a member 
field that indicates the users that have that role.




Vish

On Feb 1, 2012, at 7:56 PM, Adam Young wrote:

As part of the effort to get LDAP support into Keystone Light,  we 
had a bit of a design discussion on IRC.  The discussion focused on 
Roles, and I would like to sum up what was said in that discussion.


When we talk about Roles,  we mean the permissions a given user has 
in a given tenant.  As such,  it is a three way relationship, and 
LDAP does not handle those well.  Group member ship is done using a 
multivalued attribute,  such that a Group has a list of users in an 
attribute named members.This cannot be extended to roles 
directly,  as the attribute would have to hold two values:  the 
user,  and the role.   One proposal was to do just that: to append 
the role name on to the user name,  and them as a single string 
inside a single attribute.  A drawback to this approach is that the 
LDAP rules have no way of enforcing that the values placed into the 
concatenated string are valid values.  Another drawback is that the 
parsing of the string is then placed on the system that consumes the 
roles.



Groups can be containers of other objects.  As such, another 
alternative is to put a collection of  roles under the tenant group,  
and then to add the user names to each of the roles.The drawback 
to this approach is that the tenant then becomes a subtree, and the 
management of subtrees is more involved in  LDAP than the management 
of single objects. /



/Roles tend to map to permissions on external objects.  For example,  
a role might indicate that a given user can create a new network 
inside of quantum,  or deploy a new template image into glance.  If 
the set of roles is known a-priori,  they could be done as a set of 
attributes on the tenant group.  The drawback with this approach is 
that  making changes to the LDAP schema after deployment is generally 
not allowed in large organizations, so adding a new role would be 
impossible/.


If the objects being managed were entirely within the Directory 
Server, one possible solution would be to use the Directory servers 
access controls to manage who could do what.  For example,  in order 
for a user to be able to create a new network, they wound need write 
access to the networks collection for their tenancy.  The reason we 
cannot do that is that many of the objects are maintained in external 
databases,  and not in the directory server.  Plus,  the access 
controls for LDAP are not guaranteed to be consistent across 
different LDAP 

Re: [Openstack] Capture of the Keystone/LDAP Role discussion

2012-02-02 Thread Adam Young

On 02/02/2012 11:50 AM, Ryan Lane wrote:

Based on discussions with numerous people,  It seems that the subtree
approach (as done by nova deprecated)  is the norm.


It's a normal approach taken by a number of applications, yes. It's
not a bad way to handle this, and we are already doing it in nova. The
plus of doing it this way, rather than key-value pairs on users, is
that when a tenant is deleted, all of the roles are deleted with it.
Also, referential integrity plugins can remove userdns from tenants
and roles when a user is deleted.

It'll still be necessary for admins to remove users from roles when
removed from tenants, and we can't depend on that, so we should handle
that case.


I'll make sure that gets in.




What seems to vary the most amongst LDAP servers is not the schema,  but the
method used to query for membership in nested groups.   In OpenLDAP,  the
syntax involves sets

http://www.openldap.org/faq/data/cache/1133.html
http://www.openldap.org/faq/data/cache/1134.html

Whereas in Active directory,  it involves  using LDAP_MATCHING_RULE_IN_CHAIN
rule OID.

In the 389 (Fedora) Directory Server as well as OpenLDAP it is also possible
to use   the deference control in conjunction with the  memberof plugin.


However,  we might not need to query for nested group membership.  For
example, lets assume a tenant has 3 administrative roles:  user management,
network management, VM management. In addition,  users that do not have an
explicit admin role get read only access to the resources of that tenant.
So a user that has the right to manage networks for that tenant would have
to appear in both the members list of that tenant as well as in the
networkMgmt role.  The first is provided for read only access, and the
second for the ability to modify the network.  It is a little redundant.  We
could perhaps put a constraint on the roles that they will only allow users
that are listed in the general membership for that tenancy.


It shouldn't be necessary to do nested searching. When searching for
tenant roles for a user, it should be enough to search for the user as
a member of roles using the tenant as a base.

Even if nested group searching is necessary, it's possible to do
nested searching without support for it on the LDAP server side. A
recursive search works here. memberOf is also a possibility, but it
needs to be supported on the server side; also, some servers use
memberOf, and some use isMemberOf, so we'd have to make that
configurable.




It's likely best to assume some server in use won't support plugins or
extensions. We can discover capabilities from the server and use a
more efficient method if it's available, while falling back to the
less efficient method. Short-lived caches of the results can also
alleviate performance problems due to inefficient queries.


Right.   First step is getting something to function, and then we can 
performance tune.



There was some talk about nesting tenancies for resellers.  This is somewhat
different from nested group member ship, as entry in the lower level tenant
should *not* provide access to all resources of the containing tenancy.
Permissions go the other way around:  if I am an admin of the container,  I
can manage elements of the contained.  It does mean that the Keystone server
needs to be smart enough to check all of the levels of nesting from lowest
to highest to see if a user has the appropriate role for the requested
operation.

So,  to summarize:  Roles will be entites under tenants,  with a member
field that indicates the users that have that role.



We still need some way to differentiate between roles and tenants,
otherwise subtree searches will cause problems.

In nova we handled this by assigning the owner attribute on tenants,
but no owner on roles. This allowed tenants to be found via a search
like this:

   ((objectclass=groupofnames)(owner=*))

Roles are then discovered by a search like this, using the tenant as a base:

   (objectclass=groupofnames)

Alternatively, we could add schema for roles and projects. It seems a
little overkill to add schema just to differentiate these for subtree
searches, though.


I don't love this solution, as it is not really very self documenting, 
and it would be easy enough for someone to mess it up.


  objectClasses: ( 2.5.6.9 NAME 'groupOfNames'
  SUP top
  STRUCTURAL
  MUST ( cn )
  MAY ( member $
businessCategory $
seeAlso $
owner $
ou $
o $
description )

Seems like what we really want is organizationalRole  from 
http://www.ietf.org/rfc/rfc4519.txt


3.10.  'organizationalRole'

   The 'organizationalRole' object class is the basis of an entry that
   represents a job, function, or position in an organization.
   (Source: X.521 [X.521])

  ( 2.5.6.8 NAME 'organizationalRole'
 SUP top
 STRUCTURAL
 MUST cn
 MAY ( x121Address $ registeredAddress $ destinationIndicator $
   preferredDeliveryMethod 

Re: [Openstack] Capture of the Keystone/LDAP Role discussion

2012-02-02 Thread Yee, Guang
Sorry I am a little late to this thread.

 When we talk about Roles,  we mean the permissions a given user has in a
given tenant.  As such,  it is a three way relationship, and LDAP does not
handle those well.

Have we also consider services and global roles? There was security bug
regarding tenant role conflicts/overlaps.

https://bugs.launchpad.net/keystone/+bug/890411

How are they being handled in your LDAP design?



Guang



-Original Message-
From: openstack-bounces+guang.yee=hp@lists.launchpad.net
[mailto:openstack-bounces+guang.yee=hp@lists.launchpad.net] On Behalf Of
Adam Young
Sent: Thursday, February 02, 2012 12:55 PM
To: Ryan Lane; openstack@lists.launchpad.net
Subject: Re: [Openstack] Capture of the Keystone/LDAP Role discussion

On 02/02/2012 11:50 AM, Ryan Lane wrote:
 Based on discussions with numerous people,  It seems that the subtree
 approach (as done by nova deprecated)  is the norm.

 It's a normal approach taken by a number of applications, yes. It's
 not a bad way to handle this, and we are already doing it in nova. The
 plus of doing it this way, rather than key-value pairs on users, is
 that when a tenant is deleted, all of the roles are deleted with it.
 Also, referential integrity plugins can remove userdns from tenants
 and roles when a user is deleted.

 It'll still be necessary for admins to remove users from roles when
 removed from tenants, and we can't depend on that, so we should handle
 that case.

I'll make sure that gets in.


 What seems to vary the most amongst LDAP servers is not the schema,  but
the
 method used to query for membership in nested groups.   In OpenLDAP,  the
 syntax involves sets

 http://www.openldap.org/faq/data/cache/1133.html
 http://www.openldap.org/faq/data/cache/1134.html

 Whereas in Active directory,  it involves  using
LDAP_MATCHING_RULE_IN_CHAIN
 rule OID.

 In the 389 (Fedora) Directory Server as well as OpenLDAP it is also
possible
 to use   the deference control in conjunction with the  memberof plugin.


 However,  we might not need to query for nested group membership.  For
 example, lets assume a tenant has 3 administrative roles:  user
management,
 network management, VM management. In addition,  users that do not have
an
 explicit admin role get read only access to the resources of that tenant.
 So a user that has the right to manage networks for that tenant would
have
 to appear in both the members list of that tenant as well as in the
 networkMgmt role.  The first is provided for read only access, and the
 second for the ability to modify the network.  It is a little redundant.
We
 could perhaps put a constraint on the roles that they will only allow
users
 that are listed in the general membership for that tenancy.

 It shouldn't be necessary to do nested searching. When searching for
 tenant roles for a user, it should be enough to search for the user as
 a member of roles using the tenant as a base.

 Even if nested group searching is necessary, it's possible to do
 nested searching without support for it on the LDAP server side. A
 recursive search works here. memberOf is also a possibility, but it
 needs to be supported on the server side; also, some servers use
 memberOf, and some use isMemberOf, so we'd have to make that
 configurable.


 It's likely best to assume some server in use won't support plugins or
 extensions. We can discover capabilities from the server and use a
 more efficient method if it's available, while falling back to the
 less efficient method. Short-lived caches of the results can also
 alleviate performance problems due to inefficient queries.

Right.   First step is getting something to function, and then we can 
performance tune.

 There was some talk about nesting tenancies for resellers.  This is
somewhat
 different from nested group member ship, as entry in the lower level
tenant
 should *not* provide access to all resources of the containing tenancy.
 Permissions go the other way around:  if I am an admin of the container,
I
 can manage elements of the contained.  It does mean that the Keystone
server
 needs to be smart enough to check all of the levels of nesting from
lowest
 to highest to see if a user has the appropriate role for the requested
 operation.

 So,  to summarize:  Roles will be entites under tenants,  with a member
 field that indicates the users that have that role.


 We still need some way to differentiate between roles and tenants,
 otherwise subtree searches will cause problems.

 In nova we handled this by assigning the owner attribute on tenants,
 but no owner on roles. This allowed tenants to be found via a search
 like this:

((objectclass=groupofnames)(owner=*))

 Roles are then discovered by a search like this, using the tenant as a
base:

(objectclass=groupofnames)

 Alternatively, we could add schema for roles and projects. It seems a
 little overkill to add schema just to differentiate these for subtree
 searches, though.

I don't love

Re: [Openstack] Capture of the Keystone/LDAP Role discussion

2012-02-02 Thread Adam Young
Had a chat with some long time Identity Management developers.  They 
cautioned me against using organizationalRole as it is often abused in 
organizations and we might have conflicts..  However, it seems like 
using organizationalUnit for tenants is corrent, and very much in 
keeping with what happens is many hosting providers.


So I now suggest that tenants become objectType organizationalUnit and 
roles are done as groupOfNames within the tenants.



On 02/02/2012 03:54 PM, Adam Young wrote:

We still need some way to differentiate between roles and tenants,
otherwise subtree searches will cause problems.

In nova we handled this by assigning the owner attribute on tenants,
but no owner on roles. This allowed tenants to be found via a search
like this:

   ((objectclass=groupofnames)(owner=*))

Roles are then discovered by a search like this, using the tenant as 
a base:


   (objectclass=groupofnames)

Alternatively, we could add schema for roles and projects. It seems a
little overkill to add schema just to differentiate these for subtree
searches, though.


I don't love this solution, as it is not really very self documenting, 
and it would be easy enough for someone to mess it up.


  objectClasses: ( 2.5.6.9 NAME 'groupOfNames'
  SUP top
  STRUCTURAL
  MUST ( cn )
  MAY ( member $
businessCategory $
seeAlso $
owner $
ou $
o $
description )

Seems like what we really want is organizationalRole  from 
http://www.ietf.org/rfc/rfc4519.txt


3.10.  'organizationalRole'

   The 'organizationalRole' object class is the basis of an entry that
   represents a job, function, or position in an organization.
   (Source: X.521 [X.521])

  ( 2.5.6.8 NAME 'organizationalRole'
 SUP top
 STRUCTURAL
 MUST cn
 MAY ( x121Address $ registeredAddress $ destinationIndicator $
   preferredDeliveryMethod $ telexNumber $
   teletexTerminalIdentifier $ telephoneNumber $
   internationalISDNNumber $ facsimileTelephoneNumber $
   seeAlso $ roleOccupant $ preferredDeliveryMethod $
   street $ postOfficeBox $ postalCode $ postalAddress $
   physicalDeliveryOfficeName $ ou $ st $ l $
   description ) )


With the users going in the  roleOccupant  field.  This is in  
core.ldif  in the schema 



___
Mailing list: https://launchpad.net/~openstack
Post to : openstack@lists.launchpad.net
Unsubscribe : https://launchpad.net/~openstack
More help   : https://help.launchpad.net/ListHelp


[Openstack] Capture of the Keystone/LDAP Role discussion

2012-02-01 Thread Adam Young
As part of the effort to get LDAP support into Keystone Light,  we had a 
bit of a design discussion on IRC.  The discussion focused on Roles, and 
I would like to sum up what was said in that discussion.


When we talk about Roles,  we mean the permissions a given user has in a 
given tenant.  As such,  it is a three way relationship, and LDAP does 
not handle those well.  Group member ship is done using a multivalued 
attribute,  such that a Group has a list of users in an attribute named 
members.This cannot be extended to roles directly,  as the 
attribute would have to hold two values:  the user,  and the role.   One 
proposal was to do just that: to append the role name on to the user 
name,  and them as a single string inside a single attribute.  A 
drawback to this approach is that the LDAP rules have no way of 
enforcing that the values placed into the concatenated string are valid 
values.  Another drawback is that the parsing of the string is then 
placed on the system that consumes the roles.



Groups can be containers of other objects.  As such, another alternative 
is to put a collection of  roles under the tenant group,  and then to 
add the user names to each of the roles.The drawback to this 
approach is that the tenant then becomes a subtree, and the management 
of subtrees is more involved in  LDAP than the management of single 
objects. /



/Roles tend to map to permissions on external objects.  For example,  a 
role might indicate that a given user can create a new network inside of 
quantum,  or deploy a new template image into glance.  If the set of 
roles is known a-priori,  they could be done as a set of attributes on 
the tenant group.  The drawback with this approach is that  making 
changes to the LDAP schema after deployment is generally not allowed in 
large organizations, so adding a new role would be impossible/.


If the objects being managed were entirely within the Directory Server, 
one possible solution would be to use the Directory servers access 
controls to manage who could do what.  For example,  in order for a user 
to be able to create a new network, they wound need write access to the 
networks collection for their tenancy.  The reason we cannot do that is 
that many of the objects are maintained in external databases,  and not 
in the directory server.  Plus,  the access controls for LDAP are not 
guaranteed to be consistent across different LDAP management systems.

/
One point that came up repeatedly is that different organizations are 
going to have very different LDAP structures,  and the Keystone 
architecture would ideally be flexible enough to map to what any given 
organization has implemented, albeit with some customization.


___
Mailing list: https://launchpad.net/~openstack
Post to : openstack@lists.launchpad.net
Unsubscribe : https://launchpad.net/~openstack
More help   : https://help.launchpad.net/ListHelp


Re: [Openstack] Capture of the Keystone/LDAP Role discussion

2012-02-01 Thread Vishvananda Ishaya
Nice summary.  As you said ldap structures are going to vary by company.  I am 
curious if AD has a standard way of dealing with this that we could use. FWIW, 
the nova deprecated ldap auth code uses subtrees for roles, and yes it is 
painful, but it might be the way to go if we want something quick and we assume 
organizations are going to have to write their own version anyway.

Vish

On Feb 1, 2012, at 7:56 PM, Adam Young wrote:

 As part of the effort to get LDAP support into Keystone Light,  we had a bit 
 of a design discussion on IRC.  The discussion focused on Roles, and I would 
 like to sum up what was said in that discussion.
 
 When we talk about Roles,  we mean the permissions a given user has in a 
 given tenant.  As such,  it is a three way relationship, and LDAP does not 
 handle those well.  Group member ship is done using a multivalued attribute,  
 such that a Group has a list of users in an attribute named members.
 This cannot be extended to roles directly,  as the attribute would have to 
 hold two values:  the user,  and the role.   One proposal was to do just 
 that: to append the role name on to the user name,  and them as a single 
 string inside a single attribute.  A drawback to this approach is that the 
 LDAP rules have no way of enforcing that the values placed into the 
 concatenated string are valid values.  Another drawback is that the parsing 
 of the string is then placed on the system that consumes the roles.
 
 
 Groups can be containers of other objects.  As such, another alternative is 
 to put a collection of  roles under the tenant group,  and then to add the 
 user names to each of the roles.The drawback to this approach is that the 
 tenant then becomes a subtree, and the management of subtrees is more 
 involved in  LDAP than the management of single objects.   
 
 
 Roles tend to map to permissions on external objects.  For example,  a role 
 might indicate that a given user can create a new network inside of quantum,  
 or deploy a new template image into glance.  If the set of roles is known 
 a-priori,  they could be done as a set of attributes on the tenant group. 
  The drawback with this approach is that  making changes to the LDAP schema 
 after deployment is generally not allowed in large organizations, so adding a 
 new role would be impossible.
 
 If the objects being managed were entirely within the Directory Server, one 
 possible solution would be to use the Directory servers access controls to 
 manage who could do what.  For example,  in order for a user to be able to 
 create a new network, they wound need write access to the networks collection 
 for their tenancy.  The reason we cannot do that is that many of the objects 
 are maintained in external databases,  and not in the directory server.  
 Plus,  the access controls for LDAP are not guaranteed to   be consistent 
 across different LDAP management systems.
 
 One point that came up repeatedly is that different organizations are going 
 to have very different LDAP structures,  and the Keystone architecture would 
 ideally be flexible enough to map to what any given organization has 
 implemented, albeit with some customization.
 
 ___
 Mailing list: https://launchpad.net/~openstack
 Post to : openstack@lists.launchpad.net
 Unsubscribe : https://launchpad.net/~openstack
 More help   : https://help.launchpad.net/ListHelp

___
Mailing list: https://launchpad.net/~openstack
Post to : openstack@lists.launchpad.net
Unsubscribe : https://launchpad.net/~openstack
More help   : https://help.launchpad.net/ListHelp