def _get_auth_data(username): """ Get authorization data for given user Return: { 'dn': 'user DN', 'clearances': ['U', 'S'], 'formal_accesses': ['AB', 'CD'], 'visas': ['ABC', 'XYZ'], 'duty_org': 'org', 'is_org_steward': False, 'is_apps_mall_steward': False, 'is_metrics_user': True } """ profile = model_access.get_profile(username) # get user's basic data url = settings.OZP["OZP_AUTHORIZATION"]["USER_INFO_URL"] % (profile.dn, profile.issuer_dn) r = requests.get(url) logger.debug("hitting url %s for user with dn %s" % (url, profile.dn)) if r.status_code != 200: raise errors.AuthorizationFailure("Error contacting authorization server: %s" % r.text) user_data = r.json() # convert dutyorg -> duty_org user_data["duty_org"] = user_data["dutyorg"] user_data.pop("dutyorg", None) # convert formalAcccesses -> formal_accesses user_data["formal_accesses"] = user_data["formalAccesses"] user_data.pop("formalAccesses", None) # get groups for user url = settings.OZP["OZP_AUTHORIZATION"]["USER_GROUPS_URL"] % ( profile.dn, settings.OZP["OZP_AUTHORIZATION"]["PROJECT_NAME"], ) r = requests.get(url) if r.status_code != 200: raise errors.AuthorizationFailure("Error contacting authorization server: %s" % r.text) groups = r.json()["groups"] user_data["is_org_steward"] = False user_data["is_apps_mall_steward"] = False user_data["is_metrics_user"] = False for g in groups: if settings.OZP["OZP_AUTHORIZATION"]["APPS_MALL_STEWARD_GROUP_NAME"] == utils.find_between(g, "cn=", ","): user_data["is_apps_mall_steward"] = True if settings.OZP["OZP_AUTHORIZATION"]["ORG_STEWARD_GROUP_NAME"] == utils.find_between(g, "cn=", ","): user_data["is_org_steward"] = True if settings.OZP["OZP_AUTHORIZATION"]["METRICS_GROUP_NAME"] == utils.find_between(g, "cn=", ","): user_data["is_org_steward"] = True return user_data
def _get_profile_by_dn(dn, issuer_dn="default issuer dn"): """ Returns a user profile for a given DN If a profile isn't found with the given DN, create one """ # look up the user with this dn. if the user doesn't exist, create them try: profile = models.Profile.objects.get(dn=dn) if not profile.user.is_active: logger.warning("User %s tried to login but is inactive" % dn) return None return profile except models.Profile.DoesNotExist: logger.info("creating new user for dn: %s" % dn) if "CN=" in dn: cn = utils.find_between(dn, "CN=", ",") else: cn = dn kwargs = {"display_name": cn, "dn": dn, "issuer_dn": issuer_dn} # sanitize username username = cn[0:30] # limit to 30 chars username = username.replace(" ", "_") # no spaces username = username.replace("'", "") # no apostrophes username = username.lower() # all lowercase # make sure this username doesn't exist count = User.objects.filter(username=username).count() if count != 0: username = "******" % (username, count + 1) profile = models.Profile.create_user(username, **kwargs) logger.debug("created new profile for user %s" % profile.user.username) return profile
def _get_profile_by_dn(dn, issuer_dn='default issuer dn'): """ Returns a user profile for a given DN If a profile isn't found with the given DN, create one """ # look up the user with this dn. if the user doesn't exist, create them profile = models.Profile.objects.filter(dn__iexact=dn).first() if profile: if not profile.user.is_active: logger.warning( 'User {0!s} tried to login but is inactive'.format(dn)) return None # update the issuer_dn if profile.issuer_dn != issuer_dn: logger.info('updating issuer dn for user {0!s}'.format( profile.user.username)) profile.issuer_dn = issuer_dn profile.save() return profile else: logger.info('creating new user for dn: {0!s}'.format(dn)) if 'CN=' in dn: cn = utils.find_between(dn, 'CN=', ',') else: cn = dn kwargs = {'display_name': cn, 'dn': dn, 'issuer_dn': issuer_dn} # sanitize username username = cn[0:30] username = username.replace(' ', '_') # no spaces username = username.replace("'", "") # no apostrophes username = username.lower() # all lowercase # make sure this username doesn't exist count = User.objects.filter(username=username).count() if count != 0: new_username = username[0:27] count = User.objects.filter( username__startswith=new_username).count() new_username = '******'.format(new_username, count + 1) username = new_username # now check again - if this username exists, we have a problemce count = User.objects.filter(username=username).count() if count != 0: logger.error( 'Cannot create new user for dn {0!s}, username {1!s} already exists' .format(dn, username)) return None profile = models.Profile.create_user(username, **kwargs) logger.info('created new profile for user {0!s}'.format( profile.user.username)) dispatcher.publish('profile_created', profile=profile) return profile
def get_columns(table): """ Get the columns of a table in an array Columns will be in the same order as the values appear in the data """ with open('%s/%s.sql' % (SQL_FILE_PATH, table), 'r') as f: data = f.read().replace('\n', '') # extract a string like (`id`, `version`, `created_by_id`) columns = utils.find_between(data, "INSERT INTO `%s`" % table, " VALUES") # remove parenthesis, backticks, and spaces columns = re.sub('[`() ]', '', columns) columns = columns.split(',') return columns
def _get_profile_by_dn(dn, issuer_dn='default issuer dn'): """ Returns a user profile for a given DN If a profile isn't found with the given DN, create one """ # look up the user with this dn. if the user doesn't exist, create them profile = models.Profile.objects.filter(dn__iexact=dn).first() if profile: if not profile.user.is_active: logger.warning('User %s tried to login but is inactive' % dn) return None # update the issuer_dn if profile.issuer_dn != issuer_dn: logger.info('updating issuer dn for user %s' % profile.user.username) profile.issuer_dn = issuer_dn profile.save() return profile else: logger.info('creating new user for dn: %s' % dn) if 'CN=' in dn: cn = utils.find_between(dn, 'CN=', ',') else: cn = dn kwargs = {'display_name': cn, 'dn': dn, 'issuer_dn': issuer_dn} # sanitize username username = cn[0:30] username = username.replace(' ', '_') # no spaces username = username.replace("'", "") # no apostrophes username = username.lower() # all lowercase # make sure this username doesn't exist count = User.objects.filter(username=username).count() if count != 0: new_username = username[0:27] count = User.objects.filter(username__startswith=new_username).count() new_username = '******' % (new_username, count + 1) username = new_username # now check again - if this username exists, we have a problem count = User.objects.filter( username=username).count() if count != 0: logger.error('Cannot create new user for dn %s, username %s already exists' % (dn, username)) return None profile = models.Profile.create_user(username, **kwargs) logger.info('created new profile for user %s' % profile.user.username) return profile
def get_columns(table): """ Get the columns of a table in an array Columns will be in the same order as the values appear in the data """ with open('{0!s}/{1!s}.sql'.format(SQL_FILE_PATH, table), 'r') as f: data = f.read().replace('\n', '') # extract a string like (`id`, `version`, `created_by_id`) columns = utils.find_between(data, "INSERT INTO `{0!s}`".format(table), " VALUES") # remove parenthesis, backticks, and spaces columns = re.sub('[`() ]', '', columns) columns = columns.split(',') return columns
def test_find_between(self): result = utils.find_between('a*str-a', '*', '-') self.assertEqual(result, 'str')
def _get_auth_data(self, username): """ Get authorization data for given user Return: { 'dn': 'user DN', 'clearances': ['U', 'S'], 'formal_accesses': ['AB', 'CD'], 'visas': ['ABC', 'XYZ'], 'duty_org': 'org', 'is_org_steward': False, 'is_apps_mall_steward': False, 'is_metrics_user': True } """ profile = model_access.get_profile(username) # get user's basic data url = self.settings.OZP['OZP_AUTHORIZATION']['USER_INFO_URL'] % (profile.dn, profile.issuer_dn) server_crt = self.settings.OZP['OZP_AUTHORIZATION']['SERVER_CRT'] server_key = self.settings.OZP['OZP_AUTHORIZATION']['SERVER_KEY'] r = self.requests.get(url, cert=(server_crt, server_key), verify=False) # logger.debug('hitting url %s for user with dn %s' % (url, profile.dn), extra={'request':request}) if r.status_code != 200: raise errors.AuthorizationFailure('Error contacting authorization server: {0!s}'.format(r.text)) user_data = r.json() user_json_keys = ['dn', 'formalAccesses', 'clearances', 'dutyorg', 'visas'] for user_key in user_json_keys: if user_key not in user_data: raise ValueError('Endpoint {0!s} not return value output - missing key: {1!s}'.format(url, user_key)) # convert dutyorg -> duty_org user_data['duty_org'] = user_data['dutyorg'] user_data.pop('dutyorg', None) # convert formalAcccesses -> formal_accesses user_data['formal_accesses'] = user_data['formalAccesses'] user_data.pop('formalAccesses', None) # get groups for user url = self.settings.OZP['OZP_AUTHORIZATION']['USER_GROUPS_URL'] % (profile.dn, self.settings.OZP['OZP_AUTHORIZATION']['PROJECT_NAME']) # logger.debug('hitting url %s for user with dn %s for group info' % (url, profile.dn), extra={'request':request}) r = self.requests.get(url, cert=(server_crt, server_key), verify=False) if r.status_code != 200: raise errors.AuthorizationFailure('Error contacting authorization server: {0!s}'.format(r.text)) group_data = r.json() if 'groups' not in group_data: raise ValueError('Endpoint {0!s} not return value output - missing key: {1!s}'.format(url, 'groups')) groups = group_data['groups'] user_data['is_org_steward'] = False user_data['is_apps_mall_steward'] = False user_data['is_metrics_user'] = False for g in groups: if self.settings.OZP['OZP_AUTHORIZATION']['APPS_MALL_STEWARD_GROUP_NAME'] == utils.find_between(g, 'cn=', ','): user_data['is_apps_mall_steward'] = True if self.settings.OZP['OZP_AUTHORIZATION']['ORG_STEWARD_GROUP_NAME'] == utils.find_between(g, 'cn=', ','): user_data['is_org_steward'] = True if self.settings.OZP['OZP_AUTHORIZATION']['METRICS_GROUP_NAME'] == utils.find_between(g, 'cn=', ','): user_data['is_org_steward'] = True return user_data
def get_values(table, column_count): """ Get the values of a table in an array of arrays Args: table: name of the database table column_count: number of columns in this table """ values = [] with open('%s/%s.sql' % (SQL_FILE_PATH, table), 'r') as f: data = f.read().replace('\n', '') # extract the data we want values_str = utils.find_between(data, "VALUES ", ");") + ')' # values can contain special chars like paranthesis and commas, so we # have to be smart about how we extract the data while values_str: if values_str[0] != '(': print('Error: each value must start with opening paranthesis') return None # remove leading '(' values_str = values_str[1:] # create empty array that will hold all values for this entry entry_values = [] current_entry_finished = False columns_processed = 0 while not current_entry_finished: # check for hex value if values_str[:2] == '0x': val = '0x' + utils.find_between(values_str, '0x', ',') entry_values.append(val) # remove extracted data from the original string idx = len(val) values_str = values_str[idx:] columns_processed += 1 print('got hex value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: print('Error: comma not found after extracting hex value') return None if columns_processed < column_count: values_str = values_str[1:] # check for a string value elif values_str[0] == "'": # read all chars between this quote and next unescaped quote # remove the leading quote values_str = values_str[1:] # find the index of the next unescaped quote idx = get_index_next_unescaped_quote(values_str) val = values_str[:idx] entry_values.append(val) # remove extracted data from original string idx = len(val) + 1 # +1 for the trailing quote values_str = values_str[idx:] columns_processed += 1 print('got string value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: print('Error: comma not found after extracting string value. string[0]: %s' % values_str[0]) return None if columns_processed < column_count: values_str = values_str[1:] # check for NULL value elif values_str[0:4] == 'NULL': val = None entry_values.append(val) values_str = values_str[4:] columns_processed += 1 print('got NULL value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: print('Error: comma not found after extracting NULL value') return None if columns_processed < column_count: values_str = values_str[1:] # check for integer value elif values_str[0] in ['0','1','2','3','4','5','6','7','8','9']: val = re.findall(r'\d+', values_str)[0] entry_values.append(val) # remove extracted data from original string idx = len(val) values_str = values_str[idx:] columns_processed += 1 print('got integer value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: print('Error: comma not found after extracting integer value') return None if columns_processed < column_count: values_str = values_str[1:] else: print('Error: found invalid character in data: %s' % values_str[0]) return None if columns_processed == column_count: current_entry_finished = True print('completed processing of row') # remove closing parenthesis if values_str[0] != ')': print('Error: closing parenthesis not found at end of row data') return None values_str = values_str[1:] # remove the comma between entries, unless this is the last entry if values_str: values_str = values_str[1:] values.append(entry_values) return values
def get_values(table, column_count): """ Get the values of a table in an array of arrays Args: table: name of the database table column_count: number of columns in this table """ values = [] with open('{0!s}/{1!s}.sql'.format(SQL_FILE_PATH, table), 'r') as f: data = f.read().replace('\n', '') # extract the data we want values_str = utils.find_between(data, "VALUES ", ");") + ')' # values can contain special chars like parenthesis and commas, so we # have to be smart about how we extract the data while values_str: if values_str[0] != '(': logging.error( 'Error: each value must start with opening parenthesis') return None # remove leading '(' values_str = values_str[1:] # create empty array that will hold all values for this entry entry_values = [] current_entry_finished = False columns_processed = 0 while not current_entry_finished: # check for hex value (includes booleans) if values_str[:2] == '0x': val = re.findall(r'0x[0-9ABCDEF]*', values_str)[0] if val == '0x00': entry_values.append(False) elif val == '0x01': entry_values.append(True) else: # assume the hex value is a UUID entry_values.append(uuid.UUID(hex=val[2:])) # remove extracted data from the original string idx = len(val) values_str = values_str[idx:] columns_processed += 1 # logging.debug('got hex value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: logging.error( 'Error: comma not found after extracting hex value') return None if columns_processed < column_count: values_str = values_str[1:] # check for a string value elif values_str[0] == "'": # read all chars between this quote and next unescaped quote # remove the leading quote values_str = values_str[1:] # find the index of the next unescaped quote idx = get_index_next_unescaped_quote(values_str) val = values_str[:idx] entry_values.append(val) # remove extracted data from original string idx = len(val) + 1 # +1 for the trailing quote values_str = values_str[idx:] columns_processed += 1 # logging.debug('got string value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: logging.error( 'Error: comma not found after extracting string value. string[0]: {0!s}' .format(values_str[0])) return None if columns_processed < column_count: values_str = values_str[1:] # check for NULL value elif values_str[0:4] == 'NULL': val = None entry_values.append(val) values_str = values_str[4:] columns_processed += 1 # logging.debug('got NULL value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: logging.error( 'Error: comma not found after extracting NULL value') return None if columns_processed < column_count: values_str = values_str[1:] # check for integer value elif values_str[0] in [ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' ]: val = re.findall(r'\d+', values_str)[0] entry_values.append(val) # remove extracted data from original string idx = len(val) values_str = values_str[idx:] columns_processed += 1 # logging.debug('got integer value: %s' % val) # remove comma if values_str[0] != ',' and columns_processed != column_count: logging.error( 'Error: comma not found after extracting integer value' ) return None if columns_processed < column_count: values_str = values_str[1:] else: logging.error( 'Error: found invalid character in data: {0!s}'.format( values_str[0])) return None if columns_processed == column_count: current_entry_finished = True # logging.debug('completed processing of row') # remove closing parenthesis if values_str[0] != ')': logging.error( 'Error: closing parenthesis not found at end of row data' ) return None values_str = values_str[1:] # remove the comma between entries, unless this is the last entry if values_str: values_str = values_str[1:] values.append(entry_values) return values