12

Given that logging-in with aws login sso is successful.

Successully logged into Start URL: *****

From here I want to start my service that requires the following environment variables with AWS credentials to be set:

  • AWS_ACCESS_KEY_ID
  • AWS_SECRET_ACCESS_KEY
  • AWS_SESSION_TOKEN

How can I extract those variables into the current shell?

A workaround which I am currently using:

I found a possible workaround that works for me: I noticed that after I login and run aws sts get-caller-identity it creates files in the ~/.aws directory, from where it can be parsed with script like:

#!/usr/bin/env bash

set -e

AWS_ACCESS_KEY_ID=$(cat ~/.aws/cli/cache/*.json | jq '.Credentials.AccessKeyId' --raw-output)
AWS_SECRET_ACCESS_KEY=$(cat ~/.aws/cli/cache/*.json | jq '.Credentials.SecretAccessKey' --raw-output)
AWS_SESSION_TOKEN=$(cat ~/.aws/cli/cache/*.json | jq '.Credentials.SessionToken' --raw-output)

>&2 echo "✨ you need to eval output of this script in your current window:"
>&2 echo '    eval $('$0')'
>&2 echo ""
echo "export AWS_ACCESS_KEY_ID=${AWS_ACCESS_KEY_ID}"
echo "export AWS_SECRET_ACCESS_KEY=${AWS_SECRET_ACCESS_KEY}"
echo "export AWS_SESSION_TOKEN=${AWS_SESSION_TOKEN}"

After evaluating the output of this script with eval $(./parse-aws-cache.sh) the environment variables are set, and I can start my service consuming AWS credentials.

It works for me for today, but I have some doubts about this solution:

  • I cannot see where this behavior is documented in AWS;
  • also reading from a directory named something cache does not seem reliable;
  • I have no idea how portable it is to work on other machines with a different configuration.

Ideally, I would expect an answer which either:

  • provides another, more reliable way of sourcing those environment variables;
  • or gives a reasonable confirmation that the method of parsing those variables from the cache file is actually ok to use.
Luke 10X
  • 1,071
  • 2
  • 14
  • 30
  • 2
    I am curious why this important. The default credential chain in the SDK should detect and use the sso credentials. This would only not work if something explicitly bypassed the usual chain lookup for and forced env vars. – jordanm Aug 21 '21 at 04:27
  • My service runs in a Docker container. The AWS credentials are passed to the container as environment variables. When the service runs outside of the container the SDK can figure the logged in account settings ( my guess it reads them from ~/.aws), but to pass them to a service running in a container only env vars method is available. – Luke 10X Aug 21 '21 at 12:31
  • Given python is available, then the environment can be printed with `python3 -m aws_sso -p MY_PROFILE -env` – Luke 10X Aug 24 '21 at 00:34
  • This question is great, and the provided solution in the question works. This should be in the aws-cli! @jordanm it's important because when you work with legacy software you don't want to be porting the credentials before you get it running. – amir Oct 28 '22 at 13:16

4 Answers4

28

This can now be done using built-in functionality of the AWS CLI.

Simply run eval "$(aws configure export-credentials --profile your-profile-name --format env)" and you should be good to go.

Chrest
  • 776
  • 1
  • 9
  • 11
0

The credential values can be fetched from the SDK, instead of parsing cache files.

Here is Javascript code that prints out the AWS credentials:

const { fromSSO } = require("@aws-sdk/credential-provider-sso");
const getCredentials = fromSSO({ profile: "-MY-AWS-PROFILE" });

getCredentials().then(credentials => {
  console.error('✨ you need to eval output of this script in your current window');
  console.error(`  eval $(node ${__filename})`);

  console.log(`export AWS_ACCESS_KEY_ID=${credentials.accessKeyId}`);
  console.log(`export AWS_SECRET_ACCESS_KEY=${credentials.secretAccessKey}`);
  console.log(`export AWS_SESSION_TOKEN=${credentials.sessionToken}`);
}).catch(e => {
  console.error('Error parsing credentials', e);
});

The only problem with it is that it depends on NodeJs, and SDK library needs to be installed.

Luke 10X
  • 1,071
  • 2
  • 14
  • 30
  • As @jordanm suggested in a comment next to the question, SDK can be used to parse the credential values. Inspired by this SO answer https://stackoverflow.com/a/66962825/296988 I ported my bash script to Javascript using the SDK, so it is less of a hack. But I wish it was a solution using only the AWS CLI client, so that it does not require NodeJs. – Luke 10X Aug 21 '21 at 20:52
0

I have 2 possible solutions here:

  1. Use something like aws-vault to expose the credentials.
  2. Modify your docker container to use the default credential chain and mount your ~./aws directory into the container.
Daniel Scott
  • 7,418
  • 5
  • 39
  • 58
0

After installing aws2-wrap, I was able to export the AWS environment variables and pass them to a container using

eval "$(aws2-wrap --export)"
docker run -e AWS_ACCESS_KEY_ID -e AWS_SECRET_ACCESS_KEY -e AWS_SESSION_TOKEN -e AWS_DEFAULT_REGION my-image-name

I found out about aws2-wrap in a Docker Github issue to add support for AWS SSO. See that thread for an alternative suggestion for how to use AWS SSO with docker by creating a docker context.

garpet
  • 1