How to Integrate Keystone with AD (Active Directory) and let all users in AD can use the services of OpenStack on dashboard?

Asked by Bill Chen

Hi All,

We're trying to integrate Keystone with AD (Active Direcotry).

What we want to achieve is to let all users in AD to login Horizon, and use all services of OpenStack on their own.

We now have a test AD server and the setting is reference to: https://wiki.openstack.org/wiki/HowtoIntegrateKeystonewithAD#How_to_Integrate_Keystone_with_Active_Directory

After we configured the AD Server and keystone.conf, we can now use keystone commands to get the user lists, role lists, and tenant lists from AD Server.

But when I want to login with the AD user on Horizon, it shows "Unable to authenticate to any available projects."

Does anybody has experience doing this?

My keystone.conf is as below:
----------------------------------------------
[DEFAULT]
admin_token = admin
log_file = keystone.log
log_dir = /var/log/keystone
log_config = /etc/keystone/logging.conf

[sql]
connection = mysql://keystone:admin@127.0.0.1/keystone

[identity]
driver = keystone.identity.backends.ldap.Identity

[catalog]
driver = keystone.catalog.backends.sql.Catalog

[token]
driver = keystone.token.backends.sql.Token

[policy]
driver = keystone.policy.backends.rules.Policy

[ec2]
driver = keystone.contrib.ec2.backends.sql.Ec2

[ldap]
url = ldap://10.109.37.118:389
user = cn=bill_chen,cn=Users,dc=npt,dc=sd1
password = *******
suffix = cn=npt,cn=sd1
use_dumb_member = True

user_tree_dn = cn=Users,dc=npt,dc=sd1
user_objectclass = top
user_id_attribute = cn
user_name_attribute = cn
dumb_member = cn=bill_chen,ou=Users,dc=npt,dc=sd1

tenant_tree_dn = ou=Tenants,dc=npt,dc=sd1
tenant_objectclass = top

role_tree_dn = ou=Roles,dc=npt,dc=sd1
role_objectclass = top
role_id_attribute = cn
role_member_attribute = cn

[filter:debug]
paste.filter_factory = keystone.common.wsgi:Debug.factory

[filter:token_auth]
paste.filter_factory = keystone.middleware:TokenAuthMiddleware.factory

[filter:admin_token_auth]
paste.filter_factory = keystone.middleware:AdminTokenAuthMiddleware.factory

[filter:xml_body]
paste.filter_factory = keystone.middleware:XmlBodyMiddleware.factory

[filter:json_body]
paste.filter_factory = keystone.middleware:JsonBodyMiddleware.factory

[filter:user_crud_extension]
paste.filter_factory = keystone.contrib.user_crud:CrudExtension.factory

[filter:crud_extension]
paste.filter_factory = keystone.contrib.admin_crud:CrudExtension.factory

[filter:ec2_extension]
paste.filter_factory = keystone.contrib.ec2:Ec2Extension.factory

[filter:s3_extension]
paste.filter_factory = keystone.contrib.s3:S3Extension.factory

[filter:url_normalize]
paste.filter_factory = keystone.middleware:NormalizingFilter.factory

[filter:stats_monitoring]
paste.filter_factory = keystone.contrib.stats:StatsMiddleware.factory

[filter:stats_reporting]
paste.filter_factory = keystone.contrib.stats:StatsExtension.factory

[app:public_service]
paste.app_factory = keystone.service:public_app_factory

[app:admin_service]
paste.app_factory = keystone.service:admin_app_factory

[pipeline:public_api]
pipeline = stats_monitoring url_normalize token_auth admin_token_auth xml_body json_body debug ec2_extension user_crud_extension public_service

[pipeline:admin_api]
pipeline = stats_monitoring url_normalize token_auth admin_token_auth xml_body json_body debug stats_reporting ec2_extension s3_extension crud_extension admin_service

[app:public_version_service]
paste.app_factory = keystone.service:public_version_app_factory

[app:admin_version_service]
paste.app_factory = keystone.service:admin_version_app_factory

[pipeline:public_version_api]
pipeline = stats_monitoring url_normalize xml_body public_version_service

[pipeline:admin_version_api]
pipeline = stats_monitoring url_normalize xml_body admin_version_service

[composite:main]
use = egg:Paste#urlmap
/v2.0 = public_api
/ = public_version_api

[composite:admin]
use = egg:Paste#urlmap
/v2.0 = admin_api
/ = admin_version_api
-----------------------------------------------------

After configuration on AD Server and keystone.conf, we can now use keystone commands to get the user lists, role lists, and tenant lists from AD Server like below:

# keystone --debug --token admin --endpoint http://127.0.0.1:35357/v2.0 user-list

+-----------------------------------------+-----------------------------------------+---------+-------+
| id | name | enabled | email |
+-----------------------------------------+-----------------------------------------+---------+-------+
| Administrator | Administrator | | |
| Allowed RODC Password Replication Group | Allowed RODC Password Replication Group | | |
| Cert Publishers | Cert Publishers | | |
| Denied RODC Password Replication Group | Denied RODC Password Replication Group | | |
| DnsAdmins | DnsAdmins | | |
| DnsUpdateProxy | DnsUpdateProxy | | |
| Domain Admins | Domain Admins | | |
| Domain Computers | Domain Computers | | |
| Domain Controllers | Domain Controllers | | |
| Domain Guests | Domain Guests | | |
| Domain Users | Domain Users | | |
| Enterprise Admins | Enterprise Admins | | |
| Enterprise Read-only Domain Controllers | Enterprise Read-only Domain Controllers | | |
| Group Policy Creator Owners | Group Policy Creator Owners | | |
| Guest | Guest | | |
| RAS and IAS Servers | RAS and IAS Servers | | |
| Read-only Domain Controllers | Read-only Domain Controllers | | |
| Schema Admins | Schema Admins | | |
| bill_chen | bill_chen | | |
| danny kuo | danny kuo | | |
| frank_wu | frank_wu | | |
| glance | glance | | |
| keystone | keystone | | |
| krbtgt | krbtgt | | |
| nova | nova | | |
+-----------------------------------------+-----------------------------------------+---------+-------+

keystone --debug --token admin --endpoint http://127.0.0.1:35357/v2.0 role-list

+------------+------------+
| id | name |
+------------+------------+
| AdminRole | AdminRole |
| MemberRole | MemberRole |
| admin | admin |
+------------+------------+

keystone --debug --token admin --endpoint http://127.0.0.1:35357/v2.0 tenant-list

+------------+------+---------+
| id | name | enabled |
+------------+------+---------+
| DemoTenant | | True |
+------------+------+---------+

Question information

Language:
English Edit question
Status:
Answered
For:
OpenStack Dashboard (Horizon) Edit question
Assignee:
No assignee Edit question
Last query:
Last reply:
Revision history for this message
Bill Chen (abcde1499) said :
#1

And below is the error message in /var/log/apache2/error.log

[Fri Apr 12 23:50:10 2013] [error] unable to retrieve service catalog with token
[Fri Apr 12 23:50:10 2013] [error] Traceback (most recent call last):
[Fri Apr 12 23:50:10 2013] [error] File "/usr/lib/python2.7/dist-packages/keystoneclient/v2_0/client.py", line 132, in _extract_service_catalog
[Fri Apr 12 23:50:10 2013] [error] endpoint_type='adminURL')
[Fri Apr 12 23:50:10 2013] [error] File "/usr/lib/python2.7/dist-packages/keystoneclient/service_catalog.py", line 62, in url_for
[Fri Apr 12 23:50:10 2013] [error] raise exceptions.EndpointNotFound('Endpoint not found.')
[Fri Apr 12 23:50:10 2013] [error] EndpointNotFound: Endpoint not found.
[Fri Apr 12 23:50:10 2013] [error] Request returned failure status.
[Fri Apr 12 23:50:10 2013] [error] None

Below is the service-list and endpoint-list:

# keystone --debug --token admin --endpoint http://127.0.0.1:35357/v2.0 service-list
+----------------------------------+----------+----------+------------------+
| id | name | type | description |
+----------------------------------+----------+----------+------------------+
| 230b231ef7884e29a614ce63f1875c25 | volume | volume | Volume Service |
| 3eb04b0514b04b5ab499250bc1a0014c | keystone | identity | Identity Service |
| 671170f386c44b90a8df9402d33dfe32 | glance | image | Image Service |
| 85696e942a4e424387529382f3691d29 | nova | compute | Compute Service |
+----------------------------------+----------+----------+------------------+

# keystone --debug --token admin --endpoint http://127.0.0.1:35357/v2.0 endpoint-list
+----------------------------------+-----------+---------------------------------------------+---------------------------------------------+---------------------------------------------+
| id | region | publicurl | internalurl | adminurl |
+----------------------------------+-----------+---------------------------------------------+---------------------------------------------+---------------------------------------------+
| 946ab30a62c64baa92ed41163dc9c1d3 | RegionOne | http://10.109.37.143:8776/v1/%(DemoTenant)s | http://10.109.37.143:8776/v1/%(DemoTenant)s | http://10.109.37.143:8776/v1/%(DemoTenant)s |
| c7ee34ac07ac42319558b97606dc6fc7 | RegionOne | http://10.109.37.143:35357/v2.0 | http://10.109.37.143:35357/v2.0 | http://10.109.37.143:35357/v2.0 |
| f28ef789a2da4391a9cc30701d23ec6a | RegionOne | http://10.109.37.143:9292 | http://10.109.37.143:9292 | http://10.109.37.143:9292 |
| fcbdc791035f4a32a51a78b6382122a9 | RegionOne | http://10.109.37.143:8774/v2/%(DemoTenant)s | http://10.109.37.143:8774/v2/%(DemoTenant)s | http://10.109.37.143:8774/v2/%(DemoTenant)s |
+----------------------------------+-----------+---------------------------------------------+---------------------------------------------+---------------------------------------------+

Any idea?

Revision history for this message
Lin Hua Cheng (lin-hua-cheng) said :
#2

The endpoint-list looks okay, except there is missing service_id column.. I assume you just forgot to copy that part?

It would be helpful if you can copy here the Token response when keystone-client authenticated with Keystone.

It looks like something:

header: Vary: X-Auth-Token
header: Content-Type: application/json
header: Content-Length: 1637
header: Date: Wed, 17 Apr 2013 06:18:56 GMT
RESP: {'status': '200', 'content-length': '1637', 'content-location': u'http://localhost:35357/v2.0/endpoints', 'vary': 'X-Auth-Token', 'date': 'Wed, 17 Apr 2013 06:18:56 GMT', 'content-type': 'application/json'}
RESP BODY: {"endpoints": [{"adminurl": "http://localhost:8773/services/Admin", "region": "RegionOne", "internalurl": "http://localhost:8773/services/Cloud", "service_id": "... }

Revision history for this message
Bill Chen (abcde1499) said :
#3

Hi,

Thank you for your reply.

Because I'm using OpenStack Folsom 2012.1, there is no service_id column to show.

And could you tell me where or how can I get the Token response?
Because I can't find it.

Thank you very much!

Revision history for this message
Lin Hua Cheng (lin-hua-cheng) said :
#4

Try setting KEYSTONECLIENT_DEBUG env variable..

# export KEYSTONECLIENT_DEBUG=True
# keystone --debug --token admin --endpoint http://127.0.0.1:35357/v2.0 endpoint-list

Revision history for this message
Bill Chen (abcde1499) said :
#5

Thanks!!

And here's the token response:

header: Vary: X-Auth-Token
header: Content-Type: application/json
header: Date: Thu, 18 Apr 2013 16:00:41 GMT
header: Transfer-Encoding: chunked
RESP: {'status': '200', 'content-location': 'http://10.109.37.143:35357/v2.0/endpoints', 'transfer-encoding': 'chunked', 'vary': 'X-Auth-Token', 'date': 'Thu, 18 Apr 2013 16:00:41 GMT', 'content-type': 'application/json'}
RESP BODY: {"endpoints": [{"adminurl": "http://10.109.37.143:8774/v2/%(tenant_id)s", "region": "RegionOne", "internalurl": "http://10.109.37.143:8774/v2/%(tenant_id)s", "service_id": "85696e942a4e424387529382f3691d29", "id": "58028d92d90c4a00be557adb55bf1533", "publicurl": "http://10.109.37.143:8774/v2/%(tenant_id)s"}, {"adminurl": "http://10.109.37.143:35357/v2.0", "region": "RegionOne", "internalurl": "http://10.109.37.143:35357/v2.0", "service_id": "3eb04b0514b04b5ab499250bc1a0014c", "id": "9c15fa93cdb0410c98e37713ef675d8b", "publicurl": "http://10.109.37.143:35357/v2.0"}, {"adminurl": "http://10.109.37.143:8776/v1/%(tenant_id)s", "region": "RegionOne", "internalurl": "http://10.109.37.143:8776/v1/%(tenant_id)s", "service_id": "230b231ef7884e29a614ce63f1875c25", "id": "b9f91bf0e7744850806539232b740026", "publicurl": "http://10.109.37.143:8776/v1/%(tenant_id)s"}, {"adminurl": "http://10.109.37.143:9292", "region": "RegionOne", "internalurl": "http://10.109.37.143:9292", "service_id": "671170f386c44b90a8df9402d33dfe32", "id": "f28ef789a2da4391a9cc30701d23ec6a", "publicurl": "http://10.109.37.143:9292"}]}

Revision history for this message
Lin Hua Cheng (lin-hua-cheng) said :
#6

Sorry, I gave a bad example..

The token response looks something like this:

reply: 'HTTP/1.1 200 OK\r\n'
header: Vary: X-Auth-Token
header: Content-Type: application/json
header: Content-Length: 5725
header: Date: Thu, 18 Apr 2013 04:40:37 GMT
RESP: {'date': 'Thu, 18 Apr 2013 04:40:37 GMT', 'vary': 'X-Auth-Token', 'content-length': '5725', 'status': '200', 'content-type': 'application/json'}
RESP BODY: {"access": {"token": {"issued_at": "2013-04-18T04:40:37.088796", "expires": "2013-04-19T04:40:37Z", "id": "...", "tenant": {"enabled": true, "description": "", "name": "demo", "id": "5fdcb881d1ca40019a56059e57ae9b92"}}, "serviceCatalog": [{"endpoints": [{"adminURL": "http://localhost:8774/v2/5fdcb881d1ca40019a56059e57ae9b92", "region": "RegionOne", "internalURL": "http://localhost:8774/v2/5fdcb881d1ca40019a56059e57ae9b92", "id": "d70a3d0cd60f46208d07a6877480128f", "publicURL": "http://localhost:8774/v2/5fdcb881d1ca40019a56059e57ae9b92"}], "endpoints_links": [], "type": "compute", "name": "nova"},
...}}

I interested to see the value returned in the "serviceCatalog"

Revision history for this message
Bill Chen (abcde1499) said :
#7

I've searched all of the log files and I didn't see any value of "serviceCatalog"
But I found that when I do

# keystone token-get

It returned

'Client' object has no attribute 'service_catalog'

And actually we did log into the horizon yesterday after we modified the AD Server information.
But now we can't again.
We now have a problem of "Unauthorized: n/a (HTTP 401)" in /var/log/apache2/error.log
We are not sure it is AD Server's problem or the horizon' problem because we had done some modification after we could log into the horizon yesterday.

Anyway, thank you for your help!!

Revision history for this message
Lin Hua Cheng (lin-hua-cheng) said :
#8

Most likely the problem is with keystone. Horizon uses keystone-client as an interface to keystone. So you can just use keystone-client for isolating the problem.

Can you help with this problem?

Provide an answer of your own, or ask Bill Chen for more information if necessary.

To post a message you must log in.