S3 バケットの InvalidBucketAclWithObjectOwnership エラー解決
問題の説明
AWS S3 バケットへのファイルアプロード中に次のエラーが突然発生する場合があります:
##### RightAws::S3Interface returned an error: 400 Bad Request
<Error><Code>InvalidBucketAclWithObjectOwnership</Code>
<Message>Bucket cannot have ACLs set with ObjectOwnership's BucketOwnerEnforced setting</Message>
このエラーは、オブジェクト所有権設定(Object Ownership) と ACL(Access Control List)設定 の互換性問題が原因です。具体的には:
- 2023年4月以降、新規作成されるS3バケットではデフォルトで
BucketOwnerEnforced
が有効化 BucketOwnerEnforced
モードでは ACLが完全に無効 になります- 既存バケットでもバケットポリシーとオブジェクト所有権の整合性がチェックされるようになりました
エラーメッセージにあるように、BucketOwnerEnforced
ではバケット所有者が全オブジェクトを強制的に所有します。この設定が有効なバケットに対しACLを使用した操作を行うと、このエラーが発生します。
解決方法
🛠️ 方法1: ACLを完全に無効化しバケットポリシーを使用
推奨されるアプローチ
AWSのベストプラクティスに沿い、ACLではなくバケットポリシーでアクセス制御を行う方法です。
- 既存のACLをすべて削除(バケットACL設定画面から)
- オブジェクト所有権を
ACLs disabled
(推奨)に設定 - バケットポリシーを設定(公開読み取りが必要なケース):
json
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": "*",
"Action": "s3:GetObject",
"Resource": "arn:aws:s3:::your-bucket-name/*"
}
]
}
- パブリックアクセスブロック設定を調整:
BlockPublicPolicy
をfalse
に設定
⚙️ 方法2: ACLの使用が必要な場合の設定変更
やむを得ずACLを使用する必要がある場合は、オブジェクト所有権モードを変更します。
bash
# オブジェクト所有権モードを変更
aws s3api put-bucket-ownership-controls \
--bucket your-bucket-name \
--ownership-controls "Rules=[{ObjectOwnership=BucketOwnerPreferred}]"
# ACLを再設定
aws s3api put-bucket-acl \
--bucket your-bucket-name \
--acl public-read
🌐 フロントエンドアプリ公開時の特別設定
React Router等のSPAをホスティングする場合、ディレクトリパスへのアクセス許可が必要です:
json
{
"Version": "2012-10-17",
"Statement": [
{
"Action": ["s3:GetObject"],
"Effect": "Allow",
"Principal": "*",
"Resource": "arn:aws:s3:::frontend-bucket/*"
},
{ // ディレクトリスキャン用
"Action": ["s3:ListBucket"],
"Effect": "Allow",
"Principal": "*",
"Resource": "arn:aws:s3:::frontend-bucket"
}
]
}
ListBucket
アクセスを明示的に許可しない場合、ディレクトリパスへの直接アクセスが失敗することがあります。
☁️ CloudFormation ユーザー向け設定
AccessControl
プロパティを削除し、代わりに公開設定を明示します:
yaml
Resources:
MyS3Bucket:
Type: AWS::S3::Bucket
Properties:
BucketName: my-bucket-name
PublicAccessBlockConfiguration:
BlockPublicAcls: false
OwnershipControls:
Rules:
- ObjectOwnership: ObjectWriter
WebsiteConfiguration:
IndexDocument: index.html
ErrorDocument: error.html
技術的背景
2023年4月の変更により、S3バケットのデフォルト設定が更新されました:
設定項目 | 旧設定 | 新設定 |
---|---|---|
パブリックアクセスブロック | 無効 | 有効 |
ACL利用可否 | 有効 | 無効 (BucketOwnerEnforced ) |
設計指針の変化
- ACLは複数アカウント間でのアクセス管理が複雑になるため廃止推奨
- バケットポリシーを使用した方がアクセス制御がシンプルに
バケット設定状態の確認方法
現在の設定はCLIで確認可能です:
bash
# オブジェクト所有権状態確認
aws s3api get-bucket-ownership-controls \
--bucket your-bucket-name
# パブリックアクセスブロック設定確認
aws s3api get-public-access-block \
--bucket your-bucket-name
トラブルシューティングポイント
- 設定変更後の反映に時間がかかることがある(最大数分待機)
- 複数設定が競合していないか確認(ポリシー+ACL)
- ログイン中アカウントが バケットの所有者であることを確認
- 公開アクセスが必要な場合
BlockPublicPolicy=false
必須