Search code examples
amazon-web-servicesboto3amazon-iam

AWS IAM: BOTO3: Unable to assume role across accounts


not sure if title made sense.

I have a python service on a kubernetes pod in account A, that needs to assume role in account B.

The error I get is:

An error occurred (AccessDenied) when calling the AssumeRole operation: User: arn:aws:sts::accountA:assumed-role/worker_role/botocore-session-123456 is not authorized to perform: sts:AssumeRole on resource: arn:aws:iam::accountB:role/target_role

The accout B trust relationship for arn:aws:iam::accountB:role/target_role is setup this way:

"Effect": "Allow",
"Principal": {
                "AWS": [
                    "arn:aws:iam::accountA:role/worker_role"
                ]
             },
             "Action": "sts:AssumeRole"

and the trust relationship for arn:aws:iam::accountA:role/worker_role is:

"Statement": [
    {
        "Sid": "",
        "Effect": "Allow",
        "Principal": {
            "Service": "ec2.amazonaws.com"
        },
        "Action": "sts:AssumeRole"
    },
    {
        "Sid": "",
        "Effect": "Allow",
        "Principal": {
            "Federated": "arn:aws:iam::accountA:oidc-provider/oidc.eks.us-east-1.amazonaws.com/id/clusterID"
        },
        "Action": "sts:AssumeRoleWithWebIdentity",
        "Condition": {
            "StringEquals": {
                "oidc.eks.us-east-1.amazonaws.com/id/clusterID:sub": "system:serviceaccount:k8s_serviceaccount_name"

So essentially, I can't see what I've done wrong here. From what I can tell, my kubernetes pod on my cluster is correctly assuming the worker_role in accountA, as that shows up in the error message (and an STS get caller identity call), and the trust relationship shows that it should be able to assume target_role in accountB.

My only thought is that it comes across as assumed-role/worker_role/botocore-session-123456 as the identity, and not worker_role.

Otherwise I'm stumped, any help would be appreciated.


Solution

  • Role-A also requires permission to call AssumeRole on Role-B. This must be added as a policy in Role-A itself (much like you would give it permission to access an S3 bucket).

    The policy would look something like:

    {
      "Version": "2012-10-17",
      "Statement": {
        "Effect": "Allow",
        "Action": "sts:AssumeRole",
        "Resource": "arn:aws:iam::accountB:role/target_role"
      }
    }