GoogleCloudPlatform / python-docs-samples

Code samples used on cloud.google.com
Apache License 2.0
7.44k stars 6.43k forks source link

AWS Workload Identity Federation sample code misleads the end-user #7401

Closed loicsikidi closed 2 years ago

loicsikidi commented 2 years ago

In which file did you encounter the issue?

Path in the documentation Path in the repo

Did you change the file? If so, how?

- def create_token_aws(project_id: str, pool_id: str, provider_id: str) -> None:
+ def create_token_aws(project_number: str, pool_id: str, provider_id: str) -> None:  
    # Prepare a GetCallerIdentity request.
    request = AWSRequest(
        method="POST",
        url="https://sts.amazonaws.com/?Action=GetCallerIdentity&Version=2011-06-15",
        headers={
            "Host": "sts.amazonaws.com",
-            "x-goog-cloud-target-resource": f"//iam.googleapis.com/projects/{project_id}/locations/global/workloadIdentityPools/{pool_id}/providers/{provider_id}"
+            "x-goog-cloud-target-resource": f"//iam.googleapis.com/projects/{project_number}/locations/global/workloadIdentityPools/{pool_id}/providers/{provider_id}" 
        })

    # Set the session credentials and Sign the request.
    # get_credentials loads the required credentials as environment variables.
    # Refer:
    # https://boto3.amazonaws.com/v1/documentation/api/latest/guide/credentials.html
    SigV4Auth(boto3.Session().get_credentials(), "sts", "us-east-1").add_auth(request)

    # Create token from signed request.
    token = {
        "url": request.url,
        "method": request.method,
        "headers": []
    }
    for key, value in request.headers.items():
        token["headers"].append({"key": key, "value": value})

    # The token lets workload identity federation verify the identity without revealing the AWS secret access key.
    print("Token:\n%s" % json.dumps(token, indent=2, sort_keys=True))
    print("URL encoded token:\n%s" % urllib.parse.quote(json.dumps(token)))

def main():
    # TODO(Developer): Replace the below credentials.
-   project_id = "my-project-id"
+   project_number = "my-project-number"
    pool_id = "my-pool-id"
    provider_id = "my-provider-id"

-   create_token_aws(project_id, pool_id, provider_id)
+   create_token_aws(project_number, pool_id, provider_id)

Describe the issue

AWS Workload Identity Federation code sample misleads the end-user because Workload Identity Pool Provider resource name expect GCP project number and not the project id.

The documentation available here underlines this fact.

A GetCallerIdentity token looks similar to the following:

{
  "url": "https://sts.amazonaws.com?Action=GetCallerIdentity&Version=2011-06-15",
  "method": "POST",
  "headers": [
    {
      "key": "Authorization",
      "value" : "AWS4-HMAC-SHA256 Credential=<REDACTED>/us-east-1/sts/aws4_request, SignedHeaders=host;x-amz-date,Signature=abcedefdfedfd"
    },
    {
      "key": "host",
      "value": "sts.amazonaws.com"
    },
    {
      "key": "x-amz-date",
      "value": "20200228T225005Z"
    },
    {
      "key": "x-goog-cloud-target-resource",
      "value": "//iam.googleapis.com/projects/12345678/locations/global/workloadIdentityPools/my-pool/providers/my-aws-provider"
    },
    {
      "key": "x-amz-security-token",
      "value": "<REDACTED>"
    }
  ]
}
//iam.googleapis.com/projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/POOL_ID/providers/PROVIDER_ID
busunkim96 commented 2 years ago

Thank you for the report @LoicSikidi!

@Sita04 Could you take a look and update the sample as necessary?