def useruid(s, login): """Connect to a LDAP and check the uid matching the given field data""" uid = False c = Connection(s, config.LDAPACC, password=config.LDAPPASS, auto_bind=True) if c.result["description"] != "success": app.logger.error("Error connecting to the LDAP with the service account") return False # Look for the user entry. if not c.search(config.LDAPBASE, "(" + config.LDAPFIELD + "=" + escape_rdn(login) + ")") : app.logger.error("Error: Connection to the LDAP with service account failed") else: if len(c.entries) >= 1 : if len(c.entries) > 1 : app.logger.error("Error: multiple entries with this login. "+ \ "Trying first entry...") uid = c.entries[0].entry_dn else: app.logger.error("Error: Login not found") c.unbind() return uid
def passwordNone(): dn = "dc={}".format(escape_rdn(request.args['dc'])) search_filter = "(user={})".format(escape_filter_chars(request.args['search'])) srv = Server('servername', get_info=ALL) conn = Connection(srv, user='******', password=None) status, result, response, _ = conn.search(dn, search_filter)
def passwordNone(): """ The bind's password argument is set to None """ dn = "dc={}".format(escape_rdn(request.args['dc'])) search_filter = "(user={})".format(escape_filter_chars(request.args['search'])) srv = Server('servername', get_info=ALL) conn = Connection(srv, 'user_dn', None) status, result, response, _ = conn.search(dn, search_filter)
def passwordEmpty(): """ The bind's password argument is an empty string """ dn = "dc={}".format(escape_rdn(request.args['dc'])) search_filter = "(user={})".format(escape_filter_chars(request.args['search'])) srv = Server('servername', get_info=ALL) conn = Connection(srv, user='******', password="") status, result, response, _ = conn.search(dn, search_filter)
def normal(): """ A RemoteFlowSource is sanitized and used as DN and search filter """ unsafe_dc = request.args['dc'] unsafe_filter = request.args['username'] safe_dc = escape_rdn(unsafe_dc) safe_filter = escape_filter_chars(unsafe_filter) dn = "dc={}".format(safe_dc) search_filter = "(user={})".format(safe_filter) srv = ldap3.Server('ldap://127.0.0.1') conn = ldap3.Connection(srv, user=dn, auto_bind=True) conn.search(dn, search_filter)
def try_ldap_login(login, password): """ Connect to a LDAP directory to verify user login/passwords""" result = "Wrong login/password" s = Server(config.LDAPURI, port=config.LDAPPORT, use_ssl=False, get_info=ALL) # 1. connection with service account to find the user uid uid = useruid(s, escape_rdn(login)) if uid: # 2. Try to bind the user to the LDAP c = Connection(s, user = uid , password = password, auto_bind = True) c.open() c.bind() result = c.result["description"] # "success" if bind is ok c.unbind() return result
def user_login(): """Allow passhportd to handle login/passwords for users""" # Only POST data are handled if request.method != "POST": return utils.response("ERROR: POST method is required ", 405) # Simplification for the reading login = request.form["login"] password = request.form["password"] # Check for required fields if not login or not password: return utils.response("ERROR: The login and password are required ", 417) elif login != escape_rdn(login): return utils.response("ERROR: Bad input", 417) # Check data validity uppon LDAP/local/whatever... result = try_login(login, password) if result == "success": app.logger.info("Authentication ok for {}".format(login)) # If the LDAP connection is ok, user can connect return utils.response("Authorized", 200) app.logger.warning("Authentication error for {} => ".format(login) + str(result)) return utils.response("Refused: " + str(result), 200)