Cross Account Access to S3 Buckets in AWS
Tags: aws, s3, crossaccount, bucketpolicy
Published: 2019-01-07 18:28:55

---
title: Cross Account Access to S3 Buckets in AWS
published: true
description: 
tags: AWS, S3, Cross Account, Bucket policy
---

There may be cases when you want to read/write to an S3 bucket in a different AWS account, this is something that you can easily achieve by adding some tweaks to the S3 bucket policies and updating a user policy.


### Scenario
![Cross-account access overview](https://thepracticaldev.s3.amazonaws.com/i/0qapyvv1ym2f3l4jvg3p.png)

Let's think of a possible scenario, we will assume that we have two AWS Accounts, **AWS account A** and **AWS account B**.

You already have an access key in **account A** and want to write files to one or multiple S3 buckets in **account B**, you prefer to keep using the same access key that is used to write to multiple accounts instead of creating a new access key in **account B**, since that might complicate our code and make key rotations more complicated.

There may be more reasons why you want to do this, but the bottom line is to be able to access buckets in multiple AWS Accounts with a single user/access key.

### Prerequisites
- Have more than one AWS Account
- Permission to update bucket policies in **account A**
- Permission to update user policies in **account B**
- ARN of user in **account B**, you can find it by calling `aws sts get-caller-identity` in the CLI

### Getting Started

As an example, we will give read and write permissions for an S3 bucket in **account A** to a user in **account B**.

#### Attach bucket policy to account A bucket granting access to account B

The first step is to attach a bucket policy to the bucket we want to access, you can add the policy in the permissions section of the bucket, `bucket name > permissions > bucket policy`:

Add the following policy, fill `{ACCOUNT_B_USER_ARN}` with your user ARN and feel free to set the `Action` to the actions you want to allow.

```JSON
{
   "Version": "2012-10-17",
   "Statement": [
      {
         "Sid": "Read and Write Account Permissions",
         "Effect": "Allow",
         "Principal": {
            "AWS": "{ACCOUNT_B_USER_ARN}"
         },
         "Action": [
            "s3:PutObjectAcl",
            "s3:PutObject",
            "s3:List*",
            "s3:Get*"
         ],
         "Resource": [
            "arn:aws:s3:::account_a_bucket"
         ]
      }
   ]
}
```
With this policy we're letting the bucket know that a new user will have the given permissions. In our case add, get and list objects to `account_a_bucket`.

Now we test our new permissions, you can try to list objects using the console:

```sh
aws s3 ls s3://account_a_bucket --profile AccountBUser
```

You should get an `AccessDenied` error. This is fine, it means that we still need to give permissions to `Account B User` through a policy.

#### Add policy to account B user
To access `account_a_bucket`, we attach a policy in **account B** to the **account B** user

```JSON
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "",
            "Effect": "Allow",
            "Action": [
                "s3:PutObjectAcl",
                "s3:PutObject",
                "s3:List*",
                "s3:Get*"
            ],
            "Resource": [
                "arn:aws:s3:::account_a_bucket/*",
                "arn:aws:s3:::account_a_bucket"
            ]
        }
    ]
}
```

Save and test again, you should now have access to `account_a_bucket`

```sh
aws s3 ls s3://account_a_bucket --profile AccountBUser
```

### Best practices
In the previous example, we gave permissions from the bucket policy directly to a user, but it's a better practice to give permissions in the bucket policy to `root` in the **account B**, that way the root user can delegate the required access to users in its account using policies and no changes are required in **account A**

![Overview with root granting access](https://thepracticaldev.s3.amazonaws.com/i/iwas5548xihvcg8cig22.png)


### Additional Documentation

[AWS: Bucket Owner Granting Cross-Account Bucket Permissions](https://docs.aws.amazon.com/AmazonS3/latest/dev/example-walkthroughs-managing-access-example2.html)