ablog

不器用で落着きのない技術者のメモ

AWS CLI で VPC エンドポイント経由でアクセスする

事象

原因

  • グローバルエンドポイント(sts.amazonaws.com)が使用されているため。
    • AWS CLI v1 はデフォルトでグローバルエンドポイントが利用される。
    • AWS CLI v2 はデフォルトでリージョンのエンドポイント(sts.ap-northeast-1.amazonaws.com など)が利用される。

解決策

AWS CLI v1 の場合
  • ~/.aws/config で設定する
[profile switchrole]
role_arn = arn:aws:iam::111111111111:role/SwitchRole
source_profile = default
region=ap-northeast-1 ★ココ
output=json
sts_regional_endpoints=regional ★ココ
$ export AWS_STS_REGIONAL_ENDPOINTS=regional
  • --endpoint-url オプションで指定する
aws sts get-caller-identity --endpoint-url https://sts.ap-northeast-1.amazonaws.com
AWS SDK(boto3)の場合
  • STS のクライアントオブジェクト生成時に region_name と endpoint_url に実行するリージョン名とエンドポイントを指定する。例えば、東京リージョンの場合は、"boto3.client('sts')" を "boto3.client('sts', region_name='ap-northeast-1', endpoint_url='https://sts.ap-northeast-1.amazonaws.com')" とする。
# region_name と endpoint_url を指定する
sts_connection = boto3.client('sts', region_name='ap-northeast-1', endpoint_url='https://sts.ap-northeast-1.amazonaws.com') 

補足

  • S3 や Code Commit などで Assume Role 方式でクロスアカウントアクセスする場合も STS にアクセスできる必要がある。
  • AWS CLI でうまく行かない場合は、--debug オプションをつけてデバッグログを出力する。以下はグローバルエンドポイントにアクセスしてタイムアウトしている。
aws s3 cp test.txt s3://arn:aws:s3:ap-northeast-1:123456789012:accesspoint/foo/bar/ --acl bucket-owner-full-control --profile account1 --debug

(中略)

2021-07-29 17:29:45,221 - Thread-3 - botocore.endpoint - DEBUG - Making request for OperationModel(name=PutObject) with params: {'body': <s3transfer.utils.ReadFileChunk object at 0x7f3a4777f110>, 'url': u'https://s3.amazonaws.com/foo/bar/test.txt', 'headers': {'Expect': '100-continue', u'Content-Type': 'text/plain', u'x-amz-acl': 'bucket-owner-full-control', 'User-Agent': 'aws-cli/1.18.147 Python/2.7.18 Linux/4.14.232-177.418.amzn2.x86_64 botocore/1.18.6'}, 'context': {'auth_type': None, 'client_region': 'us-east-1★', 'signing': {'bucket': u'arn:aws:s3:ap-northeast-1:123456789012:accesspoint/foo'}, 'has_streaming_input': True, 'client_config': <botocore.config.Config object at 0x7f3a47896410>, 's3_accesspoint': {'region': u'ap-northeast-1', 'account': u'123456789012', 'partition': u'aws', 'name': u'foo'}}, 'query_string': {}, 'url_path': u'/foo/bar/test.txt', 'method': u'PUT'}

参考

AWS_STS_REGIONAL_ENDPOINTS

AWS CLI クライアントが AWS Security Token Service (AWS STS) と通信するために使用する AWS サービスエンドポイントを AWS CLI がどのように決定するかを指定します。

  • AWS CLI バージョン 1 のデフォルト値はlegacyです。
  • AWS CLI バージョン 2 のデフォルト値はregionalです。

次の 2 つの値のいずれかを指定できます。

  • legacy - 次の AWS リージョンに対してグローバル STS エンドポイントsts.amazonaws.comを使用します。ap-northeast-1、ap-south-1、ap-southeast-1、ap-southeast-2、aws-global、ca-central-1、eu-central-1、eu-north-1、eu-west-1、eu-west-2、eu-west-3、sa-east-1、us-east-1、us-east-2、us-west-1、および us-west-2。他のすべてのリージョンでは、それぞれのリージョンエンドポイントが自動的に使用されます。
  • regional - AWS CLI は、現在設定されているリージョンに対して AWS STS エンドポイントを常に使用します。例えば、クライアントが us-west-2 を使用するように設定されている場合、AWS STS へのすべてのコールは、グローバル sts.amazonaws.com エンドポイントではなく、リージョナルエンドポイント sts.us-west-2.amazonaws.com に対して行われます。この設定が有効なときにグローバルエンドポイントにリクエストを送信するには、リージョンを aws-global に設定します。
AWS CLI を設定する環境変数 - AWS Command Line Interface