diff --git a/canaille/__init__.py b/canaille/__init__.py index 7a5b7198..6d0e1860 100644 --- a/canaille/__init__.py +++ b/canaille/__init__.py @@ -96,12 +96,18 @@ def setup_logging(app): def setup_ldap_models(app): LDAPObject.root_dn = app.config["LDAP"]["ROOT_DN"] + user_base = app.config["LDAP"]["USER_BASE"] if user_base.endswith(app.config["LDAP"]["ROOT_DN"]): user_base = user_base[: -len(app.config["LDAP"]["ROOT_DN"]) - 1] User.base = user_base + User.id = app.config["LDAP"].get("USER_ID_ATTRIBUTE", "cn") + group_base = app.config["LDAP"].get("GROUP_BASE") + if group_base.endswith(app.config["LDAP"]["ROOT_DN"]): + group_base = group_base[: -len(app.config["LDAP"]["ROOT_DN"]) - 1] Group.base = group_base + Group.id = app.config["LDAP"].get("GROUP_ID_ATTRIBTUE", "cn") def setup_ldap_connection(app): diff --git a/canaille/conf/config.sample.toml b/canaille/conf/config.sample.toml index a6906d93..c33a2e6f 100644 --- a/canaille/conf/config.sample.toml +++ b/canaille/conf/config.sample.toml @@ -59,23 +59,30 @@ TIMEOUT = # Where to search for users? USER_BASE = "ou=users,dc=mydomain,dc=tld" +# The object class to use for creating new users +USER_CLASS = "inetOrgPerson" + +# The attribute to identify an object in the User dn. +USER_ID_ATTRIBUTE = "cn" + # Filter to match users on sign in. Supports a variable # {login} that can be used to compare against several fields: USER_FILTER = "(|(uid={login})(mail={login}))" -# The object class to use for creating new users -USER_CLASS = "inetOrgPerson" - # Where to search for groups? GROUP_BASE = "ou=groups" # The object class to use for creating new groups GROUP_CLASS = "groupOfNames" +# The attribute to identify an object in the User dn. +GROUP_ID_ATTRIBUTE = "cn" + # The attribute to use to identify a group GROUP_NAME_ATTRIBUTE = "cn" # A filter to check if a user belongs to a group +# A 'user' variable is available. GROUP_USER_FILTER = "member={user.dn}" # You can define access controls that define what users can do on canaille diff --git a/canaille/models.py b/canaille/models.py index 19422e84..6ed7a7ae 100644 --- a/canaille/models.py +++ b/canaille/models.py @@ -13,8 +13,6 @@ from .ldaputils import LDAPObject class User(LDAPObject): - id = "cn" - def __init__(self, *args, **kwargs): self.read = set() self.write = set() @@ -176,8 +174,6 @@ class User(LDAPObject): class Group(LDAPObject): - id = "cn" - @classmethod def available_groups(cls, conn=None): conn = conn or cls.ldap() diff --git a/demo/conf/canaille.toml b/demo/conf/canaille.toml index ec10e0ef..7c58e917 100644 --- a/demo/conf/canaille.toml +++ b/demo/conf/canaille.toml @@ -61,23 +61,30 @@ TIMEOUT = 10 # Where to search for users? USER_BASE = "ou=users,dc=mydomain,dc=tld" +# The object class to use for creating new users +USER_CLASS = "inetOrgPerson" + +# The attribute to identify an object in the User dn. +USER_ID_ATTRIBUTE = "uid" + # Filter to match users on sign in. Supports a variable # {login} that can be used to compare against several fields: USER_FILTER = "(|(uid={login})(mail={login}))" -# A class to use for creating new users -USER_CLASS = "inetOrgPerson" - # Where to search for groups? GROUP_BASE = "ou=groups" # The object class to use for creating new groups GROUP_CLASS = "groupOfNames" +# The attribute to identify an object in the User dn. +GROUP_ID_ATTRIBUTE = "cn" + # The attribute to use to identify a group GROUP_NAME_ATTRIBUTE = "cn" # A filter to check if a user belongs to a group +# A 'user' variable is available. GROUP_USER_FILTER = "member={user.dn}" # You can define access controls that define what users can do on canaille diff --git a/demo/ldif/bootstrap-data.ldif b/demo/ldif/bootstrap-data.ldif index d634252f..f692eb8f 100644 --- a/demo/ldif/bootstrap-data.ldif +++ b/demo/ldif/bootstrap-data.ldif @@ -6,7 +6,7 @@ dn: ou=groups,dc=mydomain,dc=tld objectclass: organizationalUnit ou: groups -dn: cn=Jane Doe,ou=users,dc=mydomain,dc=tld +dn: uid=admin,ou=users,dc=mydomain,dc=tld objectclass: top objectclass: inetOrgPerson cn: Jane Doe @@ -18,7 +18,7 @@ telephoneNumber: 555-000-000 employeeNumber: 1000 userPassword: {SSHA}7zQVLckaEc6cJEsS0ylVipvb2PAR/4tS -dn: cn=Jack Doe,ou=users,dc=mydomain,dc=tld +dn: uid=moderator,ou=users,dc=mydomain,dc=tld objectclass: top objectclass: inetOrgPerson cn: Jack Doe @@ -30,7 +30,7 @@ telephoneNumber: 555-000-002 employeeNumber: 1002 userPassword: {SSHA}+eHyxWqajMHsOWnhONC2vbtfNZzKTkag -dn: cn=John Doe,ou=users,dc=mydomain,dc=tld +dn: uid=user,ou=users,dc=mydomain,dc=tld objectclass: top objectclass: inetOrgPerson cn: John Doe @@ -42,7 +42,7 @@ telephoneNumber: 555-000-001 employeeNumber: 1001 userPassword: {SSHA}Yr1ZxSljRsKyaTB30suY2iZ1KRTStF1X -dn: cn=James Doe,ou=users,dc=mydomain,dc=tld +dn: uid=james,ou=users,dc=mydomain,dc=tld objectclass: top objectclass: inetOrgPerson cn: James Doe @@ -55,18 +55,18 @@ telephoneNumber: 555-000-003 dn: cn=users,ou=groups,dc=mydomain,dc=tld objectclass: groupOfNames cn: users -member: cn=Jane Doe,ou=users,dc=mydomain,dc=tld -member: cn=John Doe,ou=users,dc=mydomain,dc=tld +member: uid=admin,ou=users,dc=mydomain,dc=tld +member: uid=user,ou=users,dc=mydomain,dc=tld dn: cn=admins,ou=groups,dc=mydomain,dc=tld objectclass: groupOfNames cn: admins -member: cn=Jane Doe,ou=users,dc=mydomain,dc=tld +member: uid=admin,ou=users,dc=mydomain,dc=tld dn: cn=moderators,ou=groups,dc=mydomain,dc=tld objectclass: groupOfNames cn: moderators -member: cn=Jack Doe,ou=users,dc=mydomain,dc=tld +member: uid=moderator,ou=users,dc=mydomain,dc=tld dn: oauthClientID=1JGkkzCbeHpGtlqgI5EENByf,ou=clients,ou=oauth,dc=mydomain,dc=tld objectclass: oauthClient