Created
June 7, 2020 06:32
-
-
Save aniline/e5b675304fd0b63180895ec137633756 to your computer and use it in GitHub Desktop.
An old directory lookup thingy.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/python3 | |
import ldap, subprocess, sys, re | |
import textwrap | |
CONFIG1 = { 'server' : 'ldap://ad1.office1.com:3268', | |
'base_dn' : 'DC=Office1,DC=com', | |
'bind_dn' : '[email protected]', | |
'pw_prog' : ["Passwordprogram", 'optionforpasswordforoption1'], | |
'pw_verify': 15 } # length of password for sanity check. | |
CONFIG2 = { 'server' : 'ldap://ad.office2.com:3268', # Set the correct AD host | |
'base_dn' : 'DC=Office2,DC=com', | |
'bind_dn' : '[email protected]', # A valid username | |
'pw_prog' : ["Passwordprogram", 'optionforpasswordforoffice2'], # Program and arguments that emits password for the username above, on stdout. | |
'pw_verify': 16 } # length of password for sanity check. | |
class PLook: | |
def __init__(self, server, base_dn, bind_dn, pw_prog, pw_verify): | |
self.server = server | |
self.conn=ldap.initialize(self.server) | |
pw = subprocess.Popen(pw_prog, stdout=subprocess.PIPE).communicate()[0][:-1] | |
if not len(pw) == pw_verify: | |
raise Exception('Password Fail') | |
self.conn.simple_bind_s(bind_dn, pw) | |
self.base_dn = base_dn | |
self.grp_filter_dist = re.compile(r'CN=(.*),OU=Distribution Groups,OU=(.*),DC=(.*),' + base_dn) | |
def search(self, fn, sn=None): | |
if sn: | |
filt_str = '(&(sn='+sn+'*)(givenName='+fn+'*))' | |
else: | |
filt_str = '(|(sn='+fn+'*)(givenName='+fn+'*))' | |
# filt_str = '(&' + filt_str + '(!(extensionAttribute1=??)))' | |
self.attrs = ['givenName', 'sn', 'telephoneNumber', 'mail', 'employeeID', | |
'mobile', 'title', 'company', 'description', 'memberOf'] | |
s_res = self.conn.search_s(self.base_dn, ldap.SCOPE_SUBTREE, filt_str, self.attrs) | |
self.res = list(filter(lambda foo: 'mail' in foo[1], s_res)) | |
return self.res | |
def get_grp(self, grp): | |
res_grp = self.conn.search_s(grp, ldap.SCOPE_SUBTREE, '(objectClass=group)', ['mail']) | |
try: | |
'mail' in res_grp[0][1] | |
return res_grp[0][1]['mail'][0] | |
except Exception as e: | |
return None | |
def details(self, index=0): | |
(dn, alist) = self.res[index] | |
p_list = ['title', 'telephoneNumber', 'mail', | |
'mobile', 'description', 'company'] | |
name = '' | |
if 'givenName' in alist: | |
name = alist['givenName'][0].decode('utf-8') | |
if 'sn' in alist: | |
name = name + ' ' + alist['sn'][0].decode('utf-8') | |
res_l = [name] | |
for m in p_list: | |
if m in alist: | |
if (m == 'title'): | |
title = alist[m][0].decode('utf-8') | |
title = title.replace('Manager', 'Damager') | |
title = title.replace('Leader', 'Ringleader') | |
title = title.replace('Senior', 'Senile') | |
title = title.replace('Engineer', 'Endangerer') | |
title = title.replace('Software', 'Soft-toys') | |
title = title.replace('Technical', 'Temperamental') | |
title = title.replace('Integration', 'Disintegration') | |
title = title.replace('Consultant', 'Wisecracker') | |
title = title.replace('President', 'Top-brass') | |
title = title.replace('CEO', '-*:$ Awesomeness $:*-') | |
title = title.replace('Principal', 'Predominant') | |
title = title.replace('Architect', 'Arranger') | |
title = title.replace('Vice', 'Wise') | |
title = title.replace('Development', 'Derailment') | |
title = title.replace('Director', 'Desperado') | |
title = title.replace('VP', 'WT') | |
title = title.replace('Asst.', '2nd') | |
title = title.replace('Mgr.', 'Dmgr.') | |
title = title.replace('Mkt.', 'Bskt.') | |
title = title.replace('Product', 'By-product.') | |
title = title.replace('Mktg', 'Bsktg') | |
title = title.replace('*', '- ? -') | |
title = title.replace('Team', 'Troupe') | |
alist[m] = [title] | |
else: | |
alist[m] = [alist[m][0].decode('utf-8')] | |
res_l = res_l + alist[m] | |
else: | |
res_l = res_l + [' '] | |
res_g = None | |
if 'memberOf' in alist: | |
res_g = [] | |
for m in alist['memberOf']: | |
if self.grp_filter_dist.match(m.decode('utf-8')): | |
g = self.get_grp(m) | |
if g: | |
res_g = res_g + [g] | |
res_repr = """Name : %s | |
Title : %s | |
Phone : %s | |
Mail : %s | |
Mobile Phone : %s | |
Emp : %s @ %s""" % tuple(res_l) | |
if res_g: | |
res_repr = res_repr + '\nGroups : ' + \ | |
textwrap.fill(' '.join(res_g), width = 80, subsequent_indent=' '*16, break_long_words = False) | |
return res_repr | |
def display(self, p_list = ['telephoneNumber', 'mail', 'mobile', 'title']): | |
""" | |
Create list of repr strings with selected fields | |
""" | |
s_res = [] | |
p_list = ['telephoneNumber', 'mobile', 'mail' ] | |
for entry in self.res: | |
(dn, alist) = entry | |
name = 'Noname' | |
if 'givenName' in alist: | |
name = alist['givenName'][0].decode('utf-8') | |
if 'sn' in alist: | |
name = name + ' ' + alist['sn'][0].decode('utf-8') | |
res_l = [name] | |
for m in p_list: | |
if m in alist: | |
res_l = res_l + [alist[m][0].decode('utf-8')] | |
else: | |
res_l = res_l + [' '] | |
s_res = s_res + [ "%-28s %s %s %s" % tuple(res_l) ] | |
return s_res | |
if __name__ == '__main__': | |
try: | |
p = PLook(**CONFIG2) | |
p.search(*sys.argv[1:3]) | |
if len(p.res) > 1: | |
for n in p.display(): | |
print(n) | |
else: | |
if len(p.res): | |
print(p.details()) | |
except Exception as e: | |
print('BORKED: ', str(e)) | |
raise e |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment