From 9df7d53dce0553e1944ee2845321ce96039726f7 Mon Sep 17 00:00:00 2001 From: Cameron Sharp Date: Mon, 11 Nov 2019 23:43:39 +0000 Subject: [PATCH] do it my own way --- octoprint_auth_ldap/__init__.py | 73 +++++++++++++++++++++++++-------- 1 file changed, 56 insertions(+), 17 deletions(-) diff --git a/octoprint_auth_ldap/__init__.py b/octoprint_auth_ldap/__init__.py index c452d4b..b0fbe86 100644 --- a/octoprint_auth_ldap/__init__.py +++ b/octoprint_auth_ldap/__init__.py @@ -5,8 +5,16 @@ import octoprint.plugin from octoprint.users import FilebasedUserManager, User from octoprint.settings import settings import ldap +import ldap3 +import ldap3.utils.dn import uuid +LDAP_SERVER = ldap3.Server("pool.ldap.ehlab.uk", tls=ldap3.Tls(validate=ssl.CERT_REQUIRED, version=ssl.PROTOCOL_TLSv1_2)) +LDAP_BASE = 'dc=edinburghhacklab,dc=com' +LDAP_GROUPS = ["octoprint"] + + + class LDAPUserManager(FilebasedUserManager, octoprint.plugin.SettingsPlugin, @@ -17,27 +25,59 @@ class LDAPUserManager(FilebasedUserManager, # - chaeckPassword called, if it return True # - login_user called with User returned by previous findUser + def ldapify_groups(self, groups): + output = [] + for group in groups: + output.append('cn={},ou=Groups,ou=People,dc=edinburghhacklab,dc=com'.format(group)) + return output + + + def check_auth(self, username, password): + if username in [None, ''] or password in [None, '']: + return None + ldap_conn = ldap3.Connection(LDAP_SERVER, auto_bind=ldap3.AUTO_BIND_TLS_BEFORE_BIND) + ldap_conn.search(search_base=LDAP_BASE, + search_filter='(&(objectClass=account)(uid={}))'.format(username), + search_scope=ldap3.SUBTREE, + attributes=['uid', 'memberOf']) + if len(ldap_conn.response) > 0: + dn = ldap_conn.response[0]['dn'] + try: + bind_conn = ldap3.Connection(LDAP_SERVER, user=dn, password=password, auto_bind=ldap3.AUTO_BIND_TLS_BEFORE_BIND) + if bind_conn: + return ldap_conn.response[0]['attributes'] + except ldap3.core.exceptions.LDAPBindError: + pass + return None + def checkPassword(self, username, password): try: - connection = self.getLDAPClient() - - username = self.escapeLDAP(username) - dn = self.findLDAPUser(username) - if dn is None: - return False - connection.bind_s(dn, password) - connection.unbind_s() - - user = FilebasedUserManager.findUser(self, username) - if not user: - self._logger.debug("Add new user") - self.addUser(username, str(uuid.uuid4()), True) - return True + #connection = self.getLDAPClient() + + #username = self.escapeLDAP(username) + #dn = self.findLDAPUser(username) + #if dn is None: + # return False + #connection.bind_s(dn, password) + #connection.unbind_s() + + data = check_auth(self, username, password) + + for group in ldapify_groups(LDAP_GROUPS): + if group in data.get('memberOf', []): + user = FilebasedUserManager.findUser(self, username) + if not user: + self._logger.debug("Add new user") + self.addUser(username, str(uuid.uuid4()), True) + return True + else: + self._logger.error("LDAP-CAMERON: user or password incorrect."") + return False except ldap.INVALID_CREDENTIALS: self._logger.error("LDAP : Your username or password is incorrect.") return FilebasedUserManager.checkPassword(self, username, password) - except ldap.LDAPError, e: + except Exception as e: if type(e.message) == dict: for (k, v) in e.message.iteritems(): self._logger.error("%s: %sn" % (k, v)) @@ -54,9 +94,8 @@ class LDAPUserManager(FilebasedUserManager, local_user = FilebasedUserManager.findUser(self, userid, apikey, session) #If user not exists in local database, search it on LDAP if userid and not local_user: - if(self.findLDAPUser(userid)): #Return a fake user instance - return User(userid, str(uuid.uuid4()), True, ["user"]) + return User(userid, str(uuid.uuid4()), True, ["user"]) else: return None