44import re
55import sys
66import json
7- #import ldap3
87import getopt
98import urllib .error
109import urllib .request
10+ from ldap3 import Server , Connection , ALL , ALL_ATTRIBUTES , SAFE_SYNC
1111
1212SCRIPT = os .path .basename (__file__ )
1313ENDPOINT = "https://registry-test.cilogon.org/registry/"
14+ LDAP_SERVER = "ldaps://ldap.cilogon.org"
15+ LDAP_USER = "uid=readonly_user,ou=system,o=OSG,o=CO,dc=cilogon,dc=org"
1416OSG_CO_ID = 8
1517UNIX_CLUSTER_ID = 10
1618LDAP_TARGET_ID = 9
3537 -c OSG_CO_ID specify OSG CO ID (default = { OSG_CO_ID } )
3638 -g CLUSTER_ID specify UNIX Cluster ID (default = { UNIX_CLUSTER_ID } )
3739 -l LDAP_TARGET specify LDAP Provsion ID (defult = { LDAP_TARGET_ID } )
40+ -p LDAP authtok specify LDAP server authtok
3841 -d passfd specify open fd to read PASS
3942 -f passfile specify path to file to open and read PASS
4043 -e ENDPOINT specify REST endpoint
@@ -68,6 +71,7 @@ class Options:
6871 provision_target = LDAP_TARGET_ID
6972 outfile = None
7073 authstr = None
74+ ldap_authtok = None
7175 min_timeout = MINTIMEOUT
7276 max_timeout = MAXTIMEOUT
7377 project_gid_startval = PROJECT_GIDS_START
@@ -169,6 +173,16 @@ def get_datalist(data, listname):
169173 return data [listname ] if data else []
170174
171175
176+ def get_ldap_groups ():
177+ ldap_group_osggids = set ()
178+ server = Server (LDAP_SERVER , get_info = ALL )
179+ connection = Connection (server , LDAP_USER , options .ldap_authtok , client_strategy = SAFE_SYNC , auto_bind = True )
180+ _ , _ , response , _ = connection .search ("ou=groups,o=OSG,o=CO,dc=cilogon,dc=org" , "(cn=*)" , attributes = ALL_ATTRIBUTES )
181+ for group in response :
182+ ldap_group_osggids .add (group ["attributes" ]["gidNumber" ])
183+ return ldap_group_osggids
184+
185+
172186def identifier_from_list (id_list , id_type ):
173187 id_type_list = [id ["Type" ] for id in id_list ]
174188 try :
@@ -216,7 +230,7 @@ def ldap_provision_group(gid):
216230
217231def parse_options (args ):
218232 try :
219- ops , args = getopt .getopt (args , "u:c:d:f:e:o:t:T:h" )
233+ ops , args = getopt .getopt (args , "u:c:g:l:p: d:f:e:o:t:T:h" )
220234 except getopt .GetoptError :
221235 usage ()
222236
@@ -237,6 +251,8 @@ def parse_options(args):
237251 options .ucid = int (arg )
238252 if op == "-l" :
239253 options .provision_target = int (arg )
254+ if op == "-p" :
255+ options .ldap_authtok = arg
240256 if op == "-d" :
241257 passfd = int (arg )
242258 if op == "-f" :
@@ -267,6 +283,8 @@ def update_highest_osggid(highest_osggid, group):
267283 # If this group has a osggid, keep a hold of the highest one we've seen so far
268284 if osggid is not None :
269285 return max (highest_osggid , int (osggid ))
286+ else :
287+ return highest_osggid
270288
271289
272290def get_comanage_data ():
@@ -287,28 +305,60 @@ def get_comanage_data():
287305 return comanage_data
288306
289307
290- def get_projects_to_setup (project_groups ):
291- projects_to_setup = {
292- "Need Identifiers" : [],
293- "Need Cluster Groups" : [],
294- "Need Provisioning" : [],
295- }
296-
297- # CO Groups associated with a UNIX Cluster Group
298- clustered_group_ids = get_unix_cluster_groups_ids (options .ucid )
299-
308+ def get_projects_needing_identifiers (project_groups ):
309+ projects_needing_identifiers = []
300310 for project in project_groups :
301311 # If this project doesn't have an osggid already assigned to it...
302312 if identifier_from_list (project ["ID_List" ], "osggid" ) is None :
303313 # Prep the project to have the proper identifiers added to it
304- projects_to_setup ["Need Identifiers" ].append (project )
314+ projects_needing_identifiers .append (project )
315+ return projects_needing_identifiers
305316
306- # If this project doesn't have a UNIX Cluster Group associated with it...
307- if not project ["Gid" ] in clustered_group_ids :
308- # Prep it to have one made for it and to be provisioned in LDAP
309- projects_to_setup ["Need Cluster Groups" ].append (project )
310- projects_to_setup ["Need Provisioning" ].append (project )
311317
318+ def get_projects_needing_cluster_groups (project_groups ):
319+ # CO Groups associated with a UNIX Cluster Group
320+ clustered_group_ids = get_unix_cluster_groups_ids (options .ucid )
321+ try :
322+ # All project Gids
323+ project_gids = set (project ["Gid" ] for project in project_groups )
324+ # Project Gids for projects without UNIX cluster groups
325+ project_gids_lacking_cluster_groups = project_gids .difference (clustered_group_ids )
326+ # All projects needing UNIX cluster groups
327+ projects_needing_unix_groups = (
328+ project
329+ for project in project_groups
330+ if project ["Gid" ] in project_gids_lacking_cluster_groups
331+ )
332+ return projects_needing_unix_groups
333+ except TypeError :
334+ return set ()
335+
336+
337+ def get_projects_needing_provisioning (project_groups ):
338+ # project groups provisioned in LDAP
339+ ldap_group_osggids = get_ldap_groups ()
340+ try :
341+ # All project osggids
342+ project_osggids = set (identifier_from_list (project ["ID_List" ], "osggid" ) for project in project_groups )
343+ # project osggids not provisioned in ldap
344+ project_osggids_to_provision = project_osggids .difference (ldap_group_osggids )
345+ # All projects that aren't provisioned in ldap
346+ projects_to_provision = (
347+ project
348+ for project in project_groups
349+ if identifier_from_list (project ["ID_List" ], "osggid" ) in project_osggids_to_provision
350+ )
351+ return projects_to_provision
352+ except TypeError :
353+ return set ()
354+
355+
356+ def get_projects_to_setup (project_groups ):
357+ projects_to_setup = {
358+ "Need Identifiers" : get_projects_needing_identifiers (project_groups ),
359+ "Need Cluster Groups" : get_projects_needing_cluster_groups (project_groups ),
360+ "Need Provisioning" : get_projects_needing_provisioning (project_groups ),
361+ }
312362 return projects_to_setup
313363
314364
0 commit comments