[openstack-dev] extending keystone identity

Dolph Mathews dolph.mathews at gmail.com
Wed Jan 29 02:15:43 UTC 2014


On Tue, Jan 28, 2014 at 12:54 PM, Simon Perfer <simon.perfer at hotmail.com>wrote:

> Thanks again, Dolph.
>
> First, is there some good documentation on how to write a custom driver?
> I'm wondering specifically about how a "keystone user-list" is mapped to a
> specific function in identity/backend/mydriver.py.
>

I believe it's calling list_users() in your implementation of the Driver
interface (or raising Not Implemented from the Driver abstract base class
itself).


> I suppose this mapping is why I was getting the 500 error about the action
> not being implemented.
>

(501 Not Implemented - 500 is for unhandled exceptions)


>
> Secondly, before poking around with writing a custom driver, I was decided
> to simply inherit ldap.Identity, as follows:
>
> class Identity(ldap.Identity):
>
>     def __init__(self):
>
>         super(Identity, self).__init__()
>
>         LOG.debug('My authentication module loaded')
>
>
>     def authenticate(self, user_id, password):
>
>         LOG.debug('in auth function')
>
The basic structure of that looks good to me.

   def __init__(self, *args, **kwargs):
       super(Identity, self).__init__(*args, **kwargs)

>
> When I get a list of users, I never get the debug output.
>
What debug output are you expecting? The above code snippet doesn't
override list_users(), so I wouldn't expect any output, except what
ldap.Identity already provides.

> Further, I removed the authenticate method from the Identity class in
> ldap.py and list-users STILL worked.
>
Unsure how this is possible. It seems we're never hitting the authenticate
> method, which is why overridin it in my custom driver doesn't make much of
> a difference in reaching my goal for local users.
>
Correct - list_users() shouldn't require authenticate() ... or vice versa.

>
> Is there another method I'm supposed to be overriding?
>
Not if you only want to change the behavior of authentication. list_users()
should only called by the administrative API.

>
> I appreciate the help -- I know these are likely silly questions to
> seasoned keystone developers.
>
>
>
> ------------------------------
> From: dolph.mathews at gmail.com
> Date: Mon, 27 Jan 2014 22:35:18 -0600
>
> To: openstack-dev at lists.openstack.org
> Subject: Re: [openstack-dev] extending keystone identity
>
> From your original email, it sounds like you want to extend the existing
> LDAP identity driver implementation, rather than writing a custom driver
> from scratch, which is what you've written. The TemplatedCatalog driver
> sort of follows that pattern with the KVS catalog driver, although it's not
> a spectacular example.
>
>
> On Mon, Jan 27, 2014 at 9:11 PM, Simon Perfer <simon.perfer at hotmail.com>wrote:
>
> I dug a bit more and found this in the logs:
>
> (keystone.common.wsgi): 2014-01-27 19:07:13,851 WARNING The action you
> have requested has not been implemented.
>
>
> Despite basing my (super simple) code on the SQL or LDAP backends, I must
> be doing something wrong.
>
>
> -->> I've placed my backend code in /usr/share/pyshared/keystone/identity/backends/nicira.py
> or /usr/share/pyshared/keystone/common/nicira.py
>
>
> -->> I DO see the "my authenticate module loaded" in the log
>
>
> I would appreciate any help in figuring out what I'm missing. Thanks!
>
>
>
> ------------------------------
> From: simon.perfer at hotmail.com
> To: openstack-dev at lists.openstack.org
> Date: Mon, 27 Jan 2014 21:58:43 -0500
>
> Subject: Re: [openstack-dev] extending keystone identity
>
> Dolph, I appreciate the response and pointing me in the right direction.
>
> Here's what I have so far:
>
> <imports here>
> CONF = config.CONF
> LOG = logging.getLogger(__name__)
>
>
> class Identity(identity.Driver):
>     def __init__(self):
>         super(Identity, self).__init__()
>         LOG.debug('My authentication module loaded')
>
>
>     def authenticate(self, user_id, password, domain_scope=None):
>         LOG.debug('in authenticate method')
>
>
> When I request a user-list via the python-keystoneclient, we never make it
> into the authenticate method (as is evident by the missing debug log).
>
>
> Any thoughts on why I'm not hitting this method?
>
>
>
> ------------------------------
> From: dolph.mathews at gmail.com
> Date: Mon, 27 Jan 2014 18:14:50 -0600
> To: openstack-dev at lists.openstack.org
> Subject: Re: [openstack-dev] extending keystone identity
>
> _check_password() is a private/internal API, so we make no guarantees
> about it's stability. Instead, override the public authenticate() method
> with something like this:
>
>     def authenticate(self, user_id, password, domain_scope=None):
>         if user_id in SPECIAL_LIST_OF_USERS:
>            # compare against value from keystone.conf
>            pass
>         else:
>             return super(CustomIdentityDriver, self).authenticate(user_id,
> password, domain_scope)
>
> On Mon, Jan 27, 2014 at 3:27 PM, Simon Perfer <simon.perfer at hotmail.com>wrote:
>
> I'm looking to create a simple Identity driver that will look at
> usernames. A small number of specific users should be authenticated by
> looking at a hard-coded password in keystone.conf, while any other users
> should fall back to LDAP authentication.
>
> I based my original driver on what's found here:
>
> http://waipeng.wordpress.com/2013/09/30/openstack-ldap-authentication/
>
> As can be seen in the github code (
> https://raw.github.com/waipeng/keystone/8c18917558bebbded0f9c588f08a84b0ea33d9ae/keystone/identity/backends/ldapauth.py),
> there's a _check_password() method which is supposedly called at some point.
>
> I've based my driver on this ldapauth.py file, and created an Identity
> class which subclasses sql.Identity. Here's what I have so far:
>
> CONF = config.CONF
> LOG = logging.getLogger(__name__)
>
>
> class Identity(sql.Identity):
>     def __init__(self):
>         super(Identity, self).__init__()
>         LOG.debug('My authentication module loaded')
>
>
>     def _check_password(self, password, user_ref):
>         LOG.debug('Authenticating via my custom hybrid authentication')
>
>
>         username = user_ref.get('name')
>
>         LOG.debug('Username = %s' % username)
>
>
> I can see from the syslog output that we never enter the _check_password()
> function.
>
> Can someone point me in the right direction regarding which function calls
> the identity driver? Also, what is the entry function in the identity
> drivers? Why wouldn't check_password() be called, as we see in the github /
> blog example above?
>
> THANKS!
>
> _______________________________________________
> 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
>
> _______________________________________________ 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
>
>
>
> _______________________________________________ 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
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.openstack.org/pipermail/openstack-dev/attachments/20140128/48268a12/attachment.html>


More information about the OpenStack-dev mailing list