def _validate_source_profile(self, parent_profile_name, source_profile_name): profiles = self._loaded_config.get('profiles', {}) if source_profile_name not in profiles: raise InvalidConfigError(error_msg=( 'The source_profile "{source_profile}" referenced in the profile ' '"{parent_profile}" does not exist.'.format( source_profile=source_profile_name, parent_profile=parent_profile_name, ), ), ) source_profile = profiles[source_profile_name] if not self._source_profile_has_credentials(source_profile): raise InvalidConfigError(error_msg=( 'The source_profile "{source_profile}" must specify static ' 'credentials.'.format( source_profile=source_profile_name, ), ), ) if source_profile_name not in self._visited_profiles: return if source_profile_name != parent_profile_name: raise InfiniteLoopConfigError( source_profile=source_profile_name, visited_profiles=self._visited_profiles, ) if not self._has_static_credentials(source_profile): raise InfiniteLoopConfigError( source_profile=source_profile_name, visited_profiles=self._visited_profiles, )
def _get_role_config_values(self): # This returns the role related configuration. profiles = self._loaded_config.get('profiles', {}) try: source_profile = profiles[self._profile_name]['source_profile'] role_arn = profiles[self._profile_name]['role_arn'] mfa_serial = profiles[self._profile_name].get('mfa_serial') except KeyError as e: raise PartialCredentialsError(provider=self.METHOD, cred_var=str(e)) external_id = profiles[self._profile_name].get('external_id') role_session_name = \ profiles[self._profile_name].get('role_session_name') if source_profile not in profiles: raise InvalidConfigError( error_msg=('The source_profile "%s" referenced in ' 'the profile "%s" does not exist.' % (source_profile, self._profile_name))) source_cred_values = profiles[source_profile] return { 'role_arn': role_arn, 'external_id': external_id, 'source_profile': source_profile, 'mfa_serial': mfa_serial, 'source_cred_values': source_cred_values, 'role_session_name': role_session_name }
def print_environment_variables(profile=None, include_region=False, **kwargs): """ Prints AWS credentials as environment variables. This uses the get_session() function to reuse MFA sessions. """ # Work with profile or profile_name. if profile: kwargs['profile_name'] = profile session = get_session(**kwargs) creds = session.get_credentials() if not creds: raise InvalidConfigError( error_msg='No credentials found for {}'.format(kwargs), ) frozen_creds = creds.get_frozen_credentials() expiry_time = getattr(creds, '_expiry_time', None) print('AWS_ACCESS_KEY_ID={}'.format(frozen_creds.access_key)) print('AWS_SECRET_ACCESS_KEY={}'.format(frozen_creds.secret_key)) if expiry_time: print('AWS_SESSION_EXPIRATION={}'.format(_serialize_if_needed(expiry_time))) if frozen_creds.token: print('AWS_SESSION_TOKEN={}'.format(frozen_creds.token)) if include_region and session.region_name: print('AWS_DEFAULT_REGION={}'.format(session.region_name)) print('AWS_REGION={}'.format(session.region_name))
async def _assume_role_with_web_identity(self): token_path = self._get_config('web_identity_token_file') if not token_path: return None token_loader = self._token_loader_cls(token_path) role_arn = self._get_config('role_arn') if not role_arn: error_msg = ( 'The provided profile or the current environment is ' 'configured to assume role with web identity but has no ' 'role ARN configured. Ensure that the profile has the role_arn' 'configuration set or the AWS_ROLE_ARN env var is set.') raise InvalidConfigError(error_msg=error_msg) extra_args = {} role_session_name = self._get_config('role_session_name') if role_session_name is not None: extra_args['RoleSessionName'] = role_session_name fetcher = AioAssumeRoleWithWebIdentityCredentialFetcher( client_creator=self._client_creator, web_identity_token_loader=token_loader, role_arn=role_arn, extra_args=extra_args, cache=self.cache, ) # The initial credentials are empty and the expiration time is set # to now so that we can delay the call to assume role until it is # strictly needed. return AioDeferredRefreshableCredentials( method=self.METHOD, refresh_using=fetcher.fetch_credentials, )
async def _resolve_credentials_from_profile(self, profile_name): profiles = self._loaded_config.get('profiles', {}) profile = profiles[profile_name] if self._has_static_credentials(profile) and \ not self._profile_provider_builder: return self._resolve_static_credentials_from_profile(profile) elif self._has_static_credentials(profile) or \ not self._has_assume_role_config_vars(profile): profile_providers = self._profile_provider_builder.providers( profile_name=profile_name, disable_env_vars=True, ) profile_chain = AioCredentialResolver(profile_providers) credentials = await profile_chain.load_credentials() if credentials is None: error_message = ( 'The source profile "%s" must have credentials.' ) raise InvalidConfigError( error_msg=error_message % profile_name, ) return credentials return self._load_creds_via_assume_role(profile_name)
def _load_sso_config(self): """Load sso config.""" loaded_config = self._load_config() profiles = loaded_config.get("profiles", {}) profile_name = self._profile_name profile_config = profiles.get(self._profile_name, {}) if all(c not in profile_config for c in self._SSO_CONFIG_VARS): return None config = {} missing_config_vars = [] for config_var in self._SSO_CONFIG_VARS: if config_var in profile_config: config[config_var] = profile_config[config_var] else: missing_config_vars.append(config_var) if missing_config_vars: missing = ", ".join(missing_config_vars) raise InvalidConfigError(error_msg=( 'The profile "%s" is configured to use SSO but is missing ' "required configuration: %s" % (profile_name, missing))) return config
def _validate_credential_source(self, profile_name, credential_source): if self._credential_sourcer is None: raise InvalidConfigError(error_msg=( 'The credential source "{credential_source}" is specified in profile ' '"{profile_name}", but no source_provider was configured.'. format( credential_source=credential_source, profile_name=profile_name, ), ), ) if not self._credential_sourcer.is_supported(credential_source): raise InvalidConfigError(error_msg=( 'The credential source "{credential_source}" referenced in profile ' '"{profile_name}" is not valid.'.format( credential_source=credential_source, profile_name=profile_name, ), ), )
def _get_mfa_config(self, profile_name): profiles = self._loaded_config.get('profiles', {}) profile = profiles[profile_name] source_profile = profile.get('source_profile') credential_source = profile.get('credential_source') mfa_config = { 'mfa_serial': profile.get('mfa_serial'), 'source_profile': source_profile, 'credential_source': credential_source, } if credential_source is not None and source_profile is not None: raise InvalidConfigError(error_msg=( 'The profile "{profile_name}" contains both source_profile and ' 'credential_source.'.format(profile_name=profile_name)), ) elif credential_source is None and source_profile is None: raise PartialCredentialsError( provider=self.METHOD, cred_var='source_profile or credential_source', ) elif credential_source is not None: self._validate_credential_source(profile_name, credential_source) else: self._validate_source_profile(profile_name, source_profile) return mfa_config
def update_location(options: dict): """ Updates a DataSync location's metadata Args: options (dict): A dictionary containing LocationArn, Type, and Config properties - LocationArn [string] - Type [string] - nfs - object_storage - smb - Config [dict] - Conforms to the request syntax for the UpdateLocation APIs - nfs: https://docs.aws.amazon.com/datasync/latest/userguide/API_UpdateLocationNfs.html - object_storage: https://docs.aws.amazon.com/datasync/latest/userguide/API_UpdateLocationObjectStorage.html - smb: https://docs.aws.amazon.com/datasync/latest/userguide/API_UpdateLocationSmb.html Raises: InvalidConfigError: If LocationArn is not specified, or an invalid Type is specified Returns: [string]: The updated location's ARN """ location_arn = options.get("LocationArn") type = options.get("Type", "").lower() config = options.get("Config", {}) if location_arn is None: raise InvalidConfigError("Please specify a location ARN") config.update(LocationArn=location_arn) if type == "nfs": datasync_client.update_location_nfs(**config) elif type == "object_storage": datasync_client.update_location_object_storage(**config) elif type == "smb": datasync_client.update_location_smb(**config) else: raise InvalidConfigError("Please specify a valid location type") return location_arn
def create_location(options): """ Creates a DataSync location Args: options (dict): [description] - Type [string] - efs - fsx_windows - nfs - object_storage - s3 - smb - Config [dict] - Conforms to the request syntax for the CreateLocation APIs - efs: https://docs.aws.amazon.com/datasync/latest/userguide/API_CreateLocationEfs.html - fsx_windows: https://docs.aws.amazon.com/datasync/latest/userguide/API_CreateLocationFsxWindows.html - nfs: https://docs.aws.amazon.com/datasync/latest/userguide/API_CreateLocationNfs.html - object_storage: https://docs.aws.amazon.com/datasync/latest/userguide/API_CreateLocationObjectStorage.html - s3: https://docs.aws.amazon.com/datasync/latest/userguide/API_CreateLocationS3.html - smb: https://docs.aws.amazon.com/datasync/latest/userguide/API_CreateLocationSmb.html Raises: InvalidConfigError: If an invalid Type or Config is specified Returns: [string]: The new location's ARN """ type = options.get("Type", "").lower() config = options.get("Config", {}) if type == "efs": return datasync_client.create_location_efs(**config)["LocationArn"] elif type == "fsx_windows": return datasync_client.create_location_fsx_windows( **config)["LocationArn"] elif type == "nfs": return datasync_client.create_location_nfs(**config)["LocationArn"] elif type == "object_storage": return datasync_client.create_location_object_storage( **config)["LocationArn"] elif type == "s3": return datasync_client.create_location_s3(**config)["LocationArn"] elif "type" == "smb": return datasync_client.create_location_smb(**config)["LocationArn"] else: raise InvalidConfigError("Please specify a valid location type")
def main(task_config): # ensure log group exists if "CloudWatchLogGroup" in task_config: cloudwatch_log_group = create_cloudwatch_log_group( task_config.get("CloudWatchLogGroup")) task_config.update("CloudWatchLogGroupArn", cloudwatch_log_group["arn"]) if "CloudWatchLogGroupArn" not in task_config: raise InvalidConfigError( "Please specify a CloudWatchLogGroup or CloudWatchLogGroupArn") if task_config.get("TaskArn"): task_arn = update_task(task_config) logging.info(f"[created] {task_arn}") else: task_arn = create_task(task_config) logging.info(f"[updated] {task_arn}")