9

Мы пытались использовать проект spark-redshift, следуя третьей рекомендации по предоставлению учетных данных. А именно:Как правильно предоставить учетные данные для искрового красного смещения в экземплярах EMR?

IAM профили экземпляра: Если вы работаете на EC2 и аутентификации на S3 с помощью IAM и экземпляра профилей, то необходимо необходимо настроить temporary_aws_access_key_id, temporary_aws_secret_access_key и temporary_aws_session_token свойства конфигурации, чтобы указать на временного ключи, созданные с помощью службы маркеров безопасности AWS. Эти временные ключи будут переданы в Redshift через команды LOAD и UNLOAD .

Приложение Spark запускается из кластера EMR. Для этой цели, мы попытались получить временные полномочия от внутренних экземпляров этого узла вызывающего getSessionToken так:

val stsClient = new AWSSecurityTokenServiceClient(new InstanceProfileCredentialsProvider())   
val getSessionTokenRequest = new GetSessionTokenRequest() 
val sessionTokenResult = stsClient.getSessionToken(getSessionTokenRequest); 
val sessionCredentials = sessionTokenResult.getCredentials() 

Но это бросает 403 Access Denied, даже если политика с sts:getSessionToken применяются к роли экземпляров ОГО.

Затем мы попробовали следующие две альтернативы. Во-первых, с помощью AssumeRole политики:

val p = new STSAssumeRoleSessionCredentialsProvider("arn:aws:iam::123456798123:role/My_EMR_Role", "session_name") 
val credentials: AWSSessionCredentials = p.getCredentials 
val token = credentials.getSessionToken 

и второй, отбрасывая результат InstanceProfileCredentialsProvider:

val provider = new InstanceProfileCredentialsProvider() 
val credentials: AWSSessionCredentials = provider.getCredentials.asInstanceOf[AWSSessionCredentials] 
val token = credentials.getSessionToken 

Они оба работают, но это ожидаемый способ сделать это? Есть ли что-то ужасно неправильное в том, что вы делаете результат или добавляете политику AssumeRole?

Спасибо!

+0

Каким образом вы предоставляете более подробную информацию о своих решениях, например, импортировали ли какие-либо дополнительные пакеты или мы использовали Java SDK?Когда я просто использую вышеуказанные утверждения в искровой оболочке, он не знает, что такое AWSSessionCredentials. –

ответ

1

GetSessionToken API предназначен для называют IAM пользователей, как сказано в их документации:

Возвращает набор временных учетных данных для учетной записи AWS или IAM пользователя.

На первом примере, вы вызываете API, используя свой экземпляр роли ЭМИ, который является IAM роль (некоторые различия объясняются here). В этом конкретном случае учетными данными роли экземпляра EMR являются учетные данные сеанса, полученные EMR от имени вашего экземпляра.

Какова конкретная формулировка вашей ошибки? Если это Cannot call GetSessionToken with session credentials, это подтвердит все вышеперечисленное.

Когда вы передаете роль экземпляра в токен сеанса, он работает, потому что, как объяснялось выше, оказывается, что учетные данные принятой роли - это учетные данные сеанса, поэтому он просто работает.

Нет ничего плохого в том, чтобы называть AssumeRole явно. Это именно то, что делает служба EMR под капотом. Кроме того, нет ничего плохого в том, что вы отправляете результаты на учетные данные сеанса, так как они в значительной степени гарантируют учетные данные сеанса в вашем случае использования.