Querying auth_state_attributes
fails on EAS enabled Active Directories
#300
Labels
auth_state_attributes
fails on EAS enabled Active Directories
#300
Bug description
We query the user's login name, uid, and gid from the Active Directory used for authentication to create files and folders with a consistent ownership inside a Dockerised JupyterHub/-Lab and the host mapping these volumes into the containers:
c.LDAPAuthenticator.auth_state_attributes = ["uid", "uidNumber", "gidNumber"]
This worked fine in a previous version of JupyterHub 4.1, but fails after the update to 5, due to Active Directory returning multiple containers for a single user. I don't know whether this is the case for every Active Directory combined with Exchange Servers or only for users who set up Exchange Active Sync (EAS) clients.
How to reproduce
As this issue is caused by an Exchange Active Sync enabled Active Directory, it is reproducible by the MWE at the bottom of the README and does not need Jupyter. Except from copying my Hub config, I added a logger (
import logging; logger = logging.getLogger(__name__);logging.basicConfig(level=logging.DEBUG)
) to get more output:When adding a bit of debugging to output
conn.entries
inget_user_attributes()
, one can observe that this is caused by ExchangeActiveSync adding a container sharing the CN of the user:I failed to find an
ldapsearch
query which could provide information about these containers beneath the users, but it is possible to query them via PowerShell on a Domain Controller:Expected behaviour
I would like
get_user_attributes()
to ignore the EAS specific containers, they are not useful for authentication purposes or provide any additional attributes needed for spawned containers. Possibilities would be to changesearch_filter
to((objectClass=user)
or make it user configurable (c.LDAPAuthenticator.search_filter
?). Perhaps the most specific filter addressing this issue would exclude the two EAS ObjectClasses:(&(!(objectClass=msExchActiveSyncDevice))(!(objectClass=msExchActiveSyncDevices))(objectClass=*))
The text was updated successfully, but these errors were encountered: