I’ve got a packstack install, and a Kerberos-capable Keystone. Time to call it from Horizon. Time to set up S4U2Proxy.
I’ll be following the steps laid out by Alexander Bokovoy. This is a work in progress, and I’ll update as I learn more.
First step is to enable Kerberos on the Horizon server, regardless of other login mechanism. I have /etc/httpd/conf.d/wsgi-horizon.conf with
WSGIDaemonProcess horizon_ssl user=fedora group=wheel processes=3 threads=10 home=/opt/stack/horizon
SetEnv APACHE_RUN_USER fedora
SetEnv APACHE_RUN_GROUP wheel
WSGIProcessGroup horizon
DocumentRoot /opt/stack/horizon/.blackhole/
Alias /media /opt/stack/horizon/openstack_dashboard/static
Alias /static /opt/stack/horizon/static
ErrorLog /var/log/httpd/horizon_error.log
LogLevel warn
CustomLog /var/log/httpd/horizon_access.log combined
Options FollowSymLinks
AllowOverride None
Options Indexes FollowSymLinks MultiViews
Require all granted
AllowOverride None
Order allow,deny
allow from all
WSGIProcessGroup horizon_ssl
NSSRequireSSL
AuthType Kerberos
AuthName "Kerberos Login"
KrbMethodNegotiate on
KrbMethodK5Passwd off
KrbServiceName HTTP
KrbAuthRealms IPA.CLOUDLAB.FREEIPA.ORG
Krb5KeyTab /etc/httpd/conf/openstack.keytab
KrbSaveCredentials on
#this next one is needed for S4U2
# KrbConstrainedDelegation on
Require valid-user
WSGISocketPrefix /var/run/httpd
For my server cn=s4u2proxy,cn=etc,$SUFFIX is going to expand to: cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org
$ ldapsearch -Y GSSAPI -H ldap://ipa.cloudlab.freeipa.org -b cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org "" SASL/GSSAPI authentication started SASL username: ayoung@IPA.CLOUDLAB.FREEIPA.ORG SASL SSF: 56 SASL data security layer installed. # extended LDIF # # LDAPv3 # basewith scope subtree # filter: (objectclass=*) # requesting: # # s4u2proxy, etc, ipa.cloudlab.freeipa.org dn: cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org # ipa-http-delegation, s4u2proxy, etc, ipa.cloudlab.freeipa.org dn: cn=ipa-http-delegation,cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,d c=org # ipa-ldap-delegation-targets, s4u2proxy, etc, ipa.cloudlab.freeipa.org dn: cn=ipa-ldap-delegation-targets,cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=f reeipa,dc=org # ipa-cifs-delegation-targets, s4u2proxy, etc, ipa.cloudlab.freeipa.org dn: cn=ipa-cifs-delegation-targets,cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=f reeipa,dc=org
Now, in Alexander’s article he delegates to LDAP. But Keystone is an HTTP server. There is no entry yet for an HTTP delegation target.
lets look at the LDAP one:
$ ldapsearch -Y GSSAPI -H ldap://ipa.cloudlab.freeipa.org -b cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org "(cn=ipa-ldap-delegation-targets)" SASL/GSSAPI authentication started SASL username: ayoung@IPA.CLOUDLAB.FREEIPA.ORG SASL SSF: 56 SASL data security layer installed. # extended LDIF # # LDAPv3 # basewith scope subtree # filter: (cn=ipa-ldap-delegation-targets) # requesting: ALL # # ipa-ldap-delegation-targets, s4u2proxy, etc, ipa.cloudlab.freeipa.org dn: cn=ipa-ldap-delegation-targets,cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=f reeipa,dc=org objectClass: groupOfPrincipals objectClass: top cn: ipa-ldap-delegation-targets memberPrincipal: ldap/ipa.cloudlab.freeipa.org@IPA.CLOUDLAB.FREEIPA.ORG
I’m going to make a rule specific to Keystone, not a general HTTP-to-HTTP delegation, So the first ldif I need should look like this:
dn: cn=ipa-keystone-delegation-targets,cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org objectClass: groupOfPrincipals objectClass: top cn: ipa-http-delegation-targets memberPrincipal: HTTP/ayoungf20packstack.cloudlab.freeipa.org@IPA.CLOUDLAB.FREEIPA.ORG
It means that something can get a service ticket to ayoungf20packstack on behalf of another user. What that something will be defined by another rule. Lets look at an existing one:
$ ldapsearch -Y GSSAPI -H ldap://ipa.cloudlab.freeipa.org -b cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org \ "(cn=ipa-http-delegation)" SASL/GSSAPI authentication started SASL username: ayoung@IPA.CLOUDLAB.FREEIPA.ORG SASL SSF: 56 SASL data security layer installed. # extended LDIF # # LDAPv3 # basewith scope subtree # filter: (cn=ipa-http-delegation) # requesting: ALL # # ipa-http-delegation, s4u2proxy, etc, ipa.cloudlab.freeipa.org dn: cn=ipa-http-delegation,cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org objectClass: ipaKrb5DelegationACL objectClass: groupOfPrincipals objectClass: top cn: ipa-http-delegation memberPrincipal: HTTP/ipa.cloudlab.freeipa.org@IPA.CLOUDLAB.FREEIPA.ORG ipaAllowedTarget: cn=ipa-ldap-delegation-targets,cn=s4u2proxy,cn=etc,dc=ipa,dc =cloudlab,dc=freeipa,dc=org ipaAllowedTarget: cn=ipa-cifs-delegation-targets,cn=s4u2proxy,cn=etc,dc=ipa,dc =cloudlab,dc=freeipa,dc=org
Now, I can’t reuse this rule: it would give Horizon the ability to talk directly to LDAP as the user that logged in, and that is WAY too much power. I’m going to create a new delegation rule.
dn: cn=ipa-keystone-delegation,cn=s4u2proxy,cn=etc,dc=ipa,dc=cloudlab,dc=freeipa,dc=org objectClass: ipaKrb5DelegationACL objectClass: groupOfPrincipals objectClass: top cn: ipa-keystone-delegation memberPrincipal: HTTP/ayoungdevstack20.cloudlab.freeipa.org@IPA.CLOUDLAB.FREEIPA.ORG ipaAllowedTarget: cn=ipa-keystone-delegation-targets,cn=s4u2proxy,cn=etc,dc=ipa,dc =cloudlab,dc=freeipa,dc=org
This may be working. It may not. All I know now is I can still log in with a userid and password, but only if I’ve performed a kinit. The next step is to convert Horizon to use Kerberos to talk to Keystone. That means that Horizon has to make use of a Kerberos Auth plugin. Will this work? Tune in next time and find out.