Creates a private S3 bucket with good defaults:
- Private only objects
- Encryption
- Versioning
- Access logging
- Storage analytics
The following policy rules are set:
- Deny uploading public objects.
- Deny updating policy to allow public objects.
The following ACL rules are set:
- Retroactively remove public access granted through public ACLs
- Deny updating ACL to public
The following lifecycle rules are set:
- Incomplete multipart uploads are deleted after 14 days.
- Expired object delete markers are deleted.
- Noncurrent object versions transition to the Standard - Infrequent Access storage class after 30 days.
- Noncurrent object versions expire after 365 days.
module "aws-s3-bucket" {
source = "trussworks/s3-private-bucket/aws"
bucket = "my-bucket-name"
logging_bucket = "my-aws-logs"
tags = {
Name = "My bucket"
Environment = "Dev"
}
}
Name | Version |
---|---|
terraform | >= 1.0 |
aws | >= 3.75.0 |
Name | Version |
---|---|
aws | >= 3.75.0 |
No modules.
Name | Type |
---|---|
aws_s3_bucket.private_bucket | resource |
aws_s3_bucket_accelerate_configuration.private_bucket | resource |
aws_s3_bucket_acl.private_bucket | resource |
aws_s3_bucket_analytics_configuration.private_analytics_config | resource |
aws_s3_bucket_cors_configuration.private_bucket | resource |
aws_s3_bucket_inventory.inventory | resource |
aws_s3_bucket_lifecycle_configuration.private_bucket | resource |
aws_s3_bucket_logging.private_bucket | resource |
aws_s3_bucket_ownership_controls.private_bucket | resource |
aws_s3_bucket_policy.private_bucket | resource |
aws_s3_bucket_public_access_block.public_access_block | resource |
aws_s3_bucket_server_side_encryption_configuration.private_bucket | resource |
aws_s3_bucket_versioning.private_bucket | resource |
aws_caller_identity.current | data source |
aws_iam_account_alias.current | data source |
aws_iam_policy_document.supplemental_policy | data source |
aws_partition.current | data source |
Name | Description | Type | Default | Required |
---|---|---|---|---|
abort_incomplete_multipart_upload_days | Number of days until aborting incomplete multipart uploads | number |
14 |
no |
additional_lifecycle_rules | List of additional lifecycle rules to specify | list(any) |
[] |
no |
bucket | The name of the bucket. | string |
n/a | yes |
bucket_key_enabled | Whether or not to use Amazon S3 Bucket Keys for SSE-KMS. | bool |
false |
no |
control_object_ownership | Whether to manage S3 Bucket Ownership Controls on this bucket. | bool |
true |
no |
cors_rules | List of maps containing rules for Cross-Origin Resource Sharing. | list(any) |
[] |
no |
custom_bucket_policy | JSON formatted bucket policy to attach to the bucket. | string |
"" |
no |
enable_analytics | Enables storage class analytics on the bucket. | bool |
true |
no |
enable_bucket_force_destroy | If set to true, Bucket will be emptied and destroyed when terraform destroy is run. | bool |
false |
no |
enable_bucket_inventory | If set to true, Bucket Inventory will be enabled. | bool |
false |
no |
enable_s3_public_access_block | Bool for toggling whether the s3 public access block resource should be enabled. | bool |
true |
no |
expiration | expiration blocks | list(any) |
[ { "expired_object_delete_marker": true } ] |
no |
inventory_bucket_format | The format for the inventory file. Default is ORC. Options are ORC or CSV. | string |
"ORC" |
no |
kms_master_key_id | The AWS KMS master key ID used for the SSE-KMS encryption. If blank, bucket encryption configuration defaults to AES256. | string |
"" |
no |
logging_bucket | The S3 bucket to send S3 access logs. | string |
"" |
no |
noncurrent_version_expiration | Number of days until non-current version of object expires | number |
365 |
no |
noncurrent_version_transitions | Non-current version transition blocks | list(any) |
[ { "days": 30, "storage_class": "STANDARD_IA" } ] |
no |
object_ownership | Object ownership. Valid values: BucketOwnerEnforced, BucketOwnerPreferred or ObjectWriter. | string |
"BucketOwnerEnforced" |
no |
s3_bucket_acl | Set bucket ACL per AWS S3 Canned ACL list. | string |
null |
no |
schedule_frequency | The S3 bucket inventory frequency. Defaults to Weekly. Options are 'Weekly' or 'Daily'. | string |
"Weekly" |
no |
tags | A mapping of tags to assign to the bucket. | map(string) |
{} |
no |
transfer_acceleration | Whether or not to enable bucket acceleration. | bool |
null |
no |
transitions | Current version transition blocks | list(any) |
[] |
no |
use_account_alias_prefix | Whether to prefix the bucket name with the AWS account alias. | string |
true |
no |
use_random_suffix | Whether to add a random suffix to the bucket name. | bool |
false |
no |
versioning_status | A string that indicates the versioning status for the log bucket. | string |
"Enabled" |
no |
Name | Description |
---|---|
arn | The ARN of the bucket. Will be of format arn:aws:s3:::bucketname. |
bucket_domain_name | The bucket domain name. |
bucket_regional_domain_name | The bucket region-specific domain name. |
id | The name of the bucket. |
name | The Name of the bucket. Will be of format bucketprefix-bucketname. |
Version 6.x.x updates the module to account for changes made by AWS in April 2023 to the default security settings of new S3 buckets.
Version 6.x.x of this module adds the following resource and variables. How to use the new variables will depend on your use case.
New resource:
aws_s3_bucket_ownership_controls.private_bucket
New variables:
control_object_ownership
object_ownership
s3_bucket_acl
Steps for updating existing buckets managed by this module:
-
Option 1: Disable ACLs. In order to update an existing bucket to use the new AWS recommended defaults, use this module's default values for the new input variables. Using those settings will disable S3 access control lists for the bucket and set object ownership to
BucketOwnerEnforced
. -
Option 2: Continue using ACLs. To continue using ACLs, set
s3_bucket_acl
to"private"
andobject_ownership
to"ObjectWriter"
or"BucketOwnerPreferred"
.
See Controlling ownership of objects and disabling ACLs for your bucket for further details and migration considerations.
Removed variables:
sse_algorithm
. Ifkms_master_key_id
is not passed, the module will fall back to AES256 for the bucket encryption configuration.
Version 4.x.x enables the use of version 4 of the AWS provider. Terraform provided an upgrade path for this. To support the upgrade path, this module now includes the following additional resources:
aws_s3_bucket_policy.private_bucket
aws_s3_bucket_acl.private_bucket
aws_s3_bucket_versioning.private_bucket
aws_s3_bucket_lifecycle_configuration.private_bucket
aws_s3_bucket_logging.private_bucket
aws_s3_bucket_server_side_encryption_configuration.private_bucket
aws_s3_bucket_cors_configuration.private_bucket
This module version removes the enable_versioning
variable (boolean) and replaces it with the versioning_status
variable (string). There are three possible values for this variable: Enabled
, Disabled
, and Suspended
. If at one point versioning was enabled on your bucket, but has since been turned off, you will need to set versioning_status
to Suspended
rather than Disabled
.
Additionally, this version of the module requires a minimum AWS provider version of 3.75, so that you can remain on the 3.x AWS provider while still gaining the ability to utilize the new S3 resources introduced in the 4.x AWS provider.
There are two general approaches to performing this upgrade:
- Upgrade the module version and run
terraform plan
followed byterraform apply
, which will create the new Terraform resources. - Perform
terraform import
commands, which accomplishes the same thing without runningterraform apply
. This is the more cautious route.
If you choose to take the route of running terraform import
, you will need to perform the following imports. Replace example
with the name you're using when calling this module and replace your-bucket-name-here
with the name of your bucket (as opposed to an S3 bucket ARN). Also note the inclusion of ,private
when importing the new aws_s3_bucket_acl
Terraform resource; if you are setting the s3_bucket_acl
input variable, use that value instead of private
. If you have not configured a target bucket using the logging_bucket
input variable, then you don't need to import the aws_s3_bucket_logging
Terraform resource.
terraform import module.example.aws_s3_bucket_policy.private_bucket your-bucket-name-here
terraform import module.example.aws_s3_bucket_acl.private_bucket your-bucket-name-here,private
terraform import module.example.aws_s3_bucket_versioning.private_bucket your-bucket-name-here
terraform import module.example.aws_s3_bucket_lifecycle_configuration.private_bucket your-bucket-name-here
terraform import module.example.aws_s3_bucket_server_side_encryption_configuration.private_bucket your-bucket-name-here
terraform import module.example.aws_s3_bucket_cors_configuration.private_bucket your-bucket-name-here
# Optionally run these two commands if you have configured the logging_bucket input variable.
terraform import module.example.aws_s3_bucket_logging.private_bucket your-bucket-name-here
terraform state mv 'module.example.aws_s3_bucket_logging.private_bucket' 'module.example.aws_s3_bucket_logging.private_bucket[0]'
After this, you will need to run a terraform plan
and terraform apply
to apply some non-functional changes to lifecycle rule IDs.
Install dependencies (macOS)
brew install pre-commit go terraform terraform-docs
This terraform module is undergoing an experiment where we keep a CHANGELOG for it. We're still trying to figure out how to automate this process and, for now, are manually running the command.
The changelog should be updated every time a new GitHub release is cut.
To do so, you should have a Github token with "repo" scope that can be loaded in as an environment variable. You can find more info here.
export CHANGELOG_GITHUB_TOKEN="«your-40-digit-github-token»"
The command to run on your terminal:
docker run --env CHANGELOG_GITHUB_TOKEN="$CHANGELOG_GITHUB_TOKEN" --rm -v "$(pwd)":/usr/local/src/your-app ferrarimarco/github-changelog-generator -u trussworks -p terraform-aws-s3-private-bucket