S3バッチオペレーションで既存オブジェクトにオブジェクトロック期間を設定してみた
既存のオブジェクトにオブジェクトロックを設定したい
こんにちは、のんピ(@non____97)です。
皆さんは既存のオブジェクトにオブジェクトロックを設定したいなと思ったことはありますか? 私はあります。
以下記事で紹介しているとおり、既存のS3バケットのオブジェクトロックを行うことは可能です。
ただし、こちらの記事で紹介されている方法でS3バケットでオブジェクトロックを有効化しても、既存のオブジェクトについては、オブジェクトロックは行われていません。
「後からS3バケットでオブジェクトロックを有効にした」ということは、既存のオブジェクトに対してもオブジェクトロックを有効化したいところではないでしょうか。
既存オブジェクトへのオブジェクトロック設定の方法としてバッチオペレーションが挙げられます。
以降実際にバッチオペレーションを用いて既存オブジェクトにオブジェクトロックを設定します。
やってみた
現在のS3バケット
現在のS3バケットの状態を確認します。
オブジェクトロックは以下のとおり、無効です。

各オブジェクトでもオブジェクトロックはかかっていないことを確認します。
> aws s3api list-object-versions --bucket non-97-object-lock --query 'Versions[].Key' --output text | tr '\t' '\n' | while read key; do
echo "=== $key ==="
aws s3api head-object --bucket non-97-object-lock --key "$key" --query '{ObjectLockMode: ObjectLockMode, RetainUntilDate: ObjectLockRetainUntilDate, LegalHold: ObjectLockLegalHoldStatus}' --output json
echo ""
done
=== config/production/prod-config.json ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== config/staging/stage-config.json ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2024/february/report-02.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2024/january/report-01.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2024/summary.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2025/january/report-03.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2025/summary.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/application/app-2024.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/application/app-2025.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/system/sys-2025.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
オブジェクトロックの有効化
それではオブジェクトロックの有効化を行います。
マネジメントコンソールからS3バケットのオブジェクトロックの有効化を行います。

バージョニングの有効化を求められたため、バージョニングの有効化を行います。
デフォルトの保持モードをコンプライアンスモードで、保持期間1日で設定します。

確認を求められるので確認します。

オブジェクトロックが設定されたことを確認します。

ちなみにここで設定可能な保持期間や保持モードはあくまでデフォルトなので、後から変更することが可能です。
以下のようにコンプライアンスモードからガバナンスモードに変更したり、そもそも保持モードを無効にすることも可能です。


デフォルト設定をコンプライアンスモードの保持期間1日に戻しておきます。
各オブジェクトではまだオブジェクトロックの設定はされていないことを確認します。
> aws s3api list-object-versions --bucket non-97-object-lock --query 'Versions[].Key' --output text | tr '\t' '\n' | while read key; do
echo "=== $key ==="
aws s3api head-object --bucket non-97-object-lock --key "$key" --query '{ObjectLockMode: ObjectLockMode, RetainUntilDate: ObjectLockRetainUntilDate, LegalHold: ObjectLockLegalHoldStatus}' --output json
echo ""
done
=== config/production/prod-config.json ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== config/staging/stage-config.json ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2024/february/report-02.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2024/january/report-01.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2024/summary.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2025/january/report-03.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2025/summary.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/application/app-2024.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/application/app-2025.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/system/sys-2025.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
マネジメントコンソールからもオブジェクトロックが設定されていないことを確認しておきます。

バッチオペレーションで既存オブジェクトにオブジェクトロックを設定
それでは、バッチオペレーションで既存オブジェクトにオブジェクトロックを設定します。
バッチオペレーションのジョブを作成します。

以下記事で紹介されているとおり、ジョブを作成する際にマニフェストファイルを事前作成する必要がなくなったので今回はそちらを使用します。
今回はdata/2024/のプレフィックスが付与されたオブジェクトに対してのみオブジェクトロックをかけるようにします。

オペレーションでオブジェクトロックを設定します。デフォルトの保持期間は1日だったので、今回は2日分としました。各オブジェクトが作成されてから2日などの日数ではなく、具体的な日付を指定する形なので注意しましょう。

ジョブ実行タイミングやオブジェクトリストやレポートなどの設定を行います。

ジョブの内容を確認して作成します。

ジョブが作成されたことを確認します。

作成されたジョブを確認します。

現在のS3バケット内のオブジェクト一覧は以下のとおりです。
$ s3-tree non-97-object-lock
non-97-object-lock
├── config
│ ├── production
│ │ └── prod-config.json
│ └── staging
│ └── stage-config.json
├── data
│ ├── 2024
│ │ ├── february
│ │ │ └── report-02.txt
│ │ ├── january
│ │ │ └── report-01.txt
│ │ └── summary.txt
│ └── 2025
│ ├── january
│ │ └── report-03.txt
│ └── summary.txt
├── job-b898a339-f5c0-41d3-bb1d-a32eeb79915c
│ └── manifest.json
├── logs
│ ├── application
│ │ ├── app-2024.log
│ │ └── app-2025.log
│ └── system
│ └── sys-2025.log
└── non-97-object-lock
└── b898a339-f5c0-41d3-bb1d-a32eeb79915c
├── 2026-01-14T02-23Z
│ ├── manifest.checksum
│ └── manifest.json
├── data
│ └── 00ab6e92-7bc6-472a-b55c-380f5eedf983.csv.gz
└── hive
└── dt=2026-01-14-02-23
└── symlink.txt
19 directories, 15 files
マニフェストファイルの確認をします。
> aws s3 cp s3://non-97-object-lock/non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/2026-01-14T02-23Z/manifest.json -
{
"sourceBucket" : "non-97-object-lock",
"destinationBucket" : "arn:aws:s3:::non-97-object-lock",
"version" : "2021-11-30",
"creationTimestamp" : "1768357404157",
"fileFormat" : "CSV",
"fileSchema" : "Bucket, Key, VersionId, IsLatest, IsDeleteMarker",
"files" : [ {
"key" : "non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/data/00ab6e92-7bc6-472a-b55c-380f5eedf983.csv.gz",
"size" : 112,
"MD5checksum" : "05cf3d0c5811bb9730e56d7e92b9f19f"
} ]
}
> aws s3 cp s3://non-97-object-lock/non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/data/00ab6e92-7bc6-472a-b55c-380f5eedf983.csv.gz - \
| gunzip -c
"non-97-object-lock","data/2024/february/report-02.txt","null","true","false"
"non-97-object-lock","data/2024/january/report-01.txt","null","true","false"
"non-97-object-lock","data/2024/summary.txt","null","true","false"
意図したとおり、data/2024/のプレフィックスのオブジェクトが対象となっています。
ジョブを実行します。

数十秒ほどで実行完了となりました。

現在のオブジェクト一覧は以下のとおりです。9163512a65070cf0c92d15ddb6da15d730bd9161.csvと実行結果のオブジェクトが作成されていますね。
$ s3-tree non-97-object-lock
non-97-object-lock
├── config
│ ├── production
│ │ └── prod-config.json
│ └── staging
│ └── stage-config.json
├── data
│ ├── 2024
│ │ ├── february
│ │ │ └── report-02.txt
│ │ ├── january
│ │ │ └── report-01.txt
│ │ └── summary.txt
│ └── 2025
│ ├── january
│ │ └── report-03.txt
│ └── summary.txt
├── job-b898a339-f5c0-41d3-bb1d-a32eeb79915c
│ ├── manifest.json
│ ├── manifest.json.md5
│ └── results
│ └── 9163512a65070cf0c92d15ddb6da15d730bd9161.csv
├── logs
│ ├── application
│ │ ├── app-2024.log
│ │ └── app-2025.log
│ └── system
│ └── sys-2025.log
└── non-97-object-lock
└── b898a339-f5c0-41d3-bb1d-a32eeb79915c
├── 2026-01-14T02-23Z
│ ├── manifest.checksum
│ └── manifest.json
├── data
│ └── 00ab6e92-7bc6-472a-b55c-380f5eedf983.csv.gz
└── hive
└── dt=2026-01-14-02-23
└── symlink.txt
20 directories, 17 files
実行結果のオブジェクトの中身を確認すると、正常に対象のオブジェクトに処理が完了したことが分かりました。
> aws s3 cp s3://non-97-object-lock/job-b898a339-f5c0-41d3-bb1d-a32eeb79915c/results/9163512a65070cf0c92d15ddb6da15d730bd9161.csv -
non-97-object-lock,data/2024/january/report-01.txt,null,succeeded,200,,Successful
non-97-object-lock,data/2024/february/report-02.txt,null,succeeded,200,,Successful
non-97-object-lock,data/2024/summary.txt,null,succeeded,200,,Successful
実際にオブジェクトロックが設定されていることを確認します。
> aws s3api list-object-versions --bucket non-97-object-lock --query 'Versions[].Key' --output text | tr '\t' '\n' | while read key; do
echo "=== $key ==="
aws s3api head-object --bucket non-97-object-lock --key "$key" --query '{ObjectLockMode: ObjectLockMode, RetainUntilDate: ObjectLockRetainUntilDate, LegalHold: ObjectLockLegalHoldStatus}' --output json
echo ""
done
=== config/production/prod-config.json ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== config/staging/stage-config.json ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2024/february/report-02.txt ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T15:00:00+00:00",
"LegalHold": null
}
=== data/2024/january/report-01.txt ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T15:00:00+00:00",
"LegalHold": null
}
=== data/2024/summary.txt ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T15:00:00+00:00",
"LegalHold": null
}
=== data/2025/january/report-03.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== data/2025/summary.txt ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== job-b898a339-f5c0-41d3-bb1d-a32eeb79915c/manifest.json ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:38:13.967000+00:00",
"LegalHold": null
}
=== job-b898a339-f5c0-41d3-bb1d-a32eeb79915c/manifest.json ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:38:13.967000+00:00",
"LegalHold": null
}
=== job-b898a339-f5c0-41d3-bb1d-a32eeb79915c/manifest.json.md5 ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:38:13.945000+00:00",
"LegalHold": null
}
=== job-b898a339-f5c0-41d3-bb1d-a32eeb79915c/results/9163512a65070cf0c92d15ddb6da15d730bd9161.csv ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:38:13.865000+00:00",
"LegalHold": null
}
=== logs/application/app-2024.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/application/app-2025.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== logs/system/sys-2025.log ===
{
"ObjectLockMode": null,
"RetainUntilDate": null,
"LegalHold": null
}
=== non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/2026-01-14T02-23Z/ ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:23:24.188000+00:00",
"LegalHold": null
}
=== non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/2026-01-14T02-23Z/manifest.checksum ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:23:27.608000+00:00",
"LegalHold": null
}
=== non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/2026-01-14T02-23Z/manifest.json ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:23:27.670000+00:00",
"LegalHold": null
}
=== non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/data/00ab6e92-7bc6-472a-b55c-380f5eedf983.csv.gz ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:23:26.454000+00:00",
"LegalHold": null
}
=== non-97-object-lock/b898a339-f5c0-41d3-bb1d-a32eeb79915c/hive/dt=2026-01-14-02-23/symlink.txt ===
{
"ObjectLockMode": "COMPLIANCE",
"RetainUntilDate": "2026-01-15T02:23:27.648000+00:00",
"LegalHold": null
}
設定されていますね。また、S3バケットでオブジェクトロックを設定して以降に作成されたオブジェクトについては、デフォルトのオブジェクトロック保持期間1日が設定されていることが分かります。
マネジメントコンソールからでもオブジェクトロックがかかっていることを確認します。

保持モードをガバナンスモードに変更したり、保持期日を短くすることが良く分かりますね。
オブジェクトロックが設定されたオブジェクトの削除
オブジェクトロックが設定されたオブジェクトの削除をしようとしてみます。
現行バージョンを指定して削除します。

完全に削除しようとしてみます。

はい、失敗しました。

続いて、削除マーカーの追加をする形で削除します。

こちらは削除 = 削除マーカーの追加 が正常に行われました。

削除マーカーが追加されたことを確認します。

削除マーカーを削除して、オブジェクトロックがかかっているバージョンのオブジェクトが最新バージョンになるようにします。

削除されました。

削除マーカーが削除され、オブジェクトロックがかかっているバージョンのオブジェクトが最新バージョンになりました。

バッチオペレーションで簡単にオブジェクトロックをかけることができる
S3バッチオペレーションで既存オブジェクトにオブジェクトロック期間を設定してみました。
マネジメントコンソールのみで簡単に設定できましたね。対象のオブジェクト一覧や成功/失敗の結果も確認しやすいのもありがたいです。
この記事が誰かの助けになれば幸いです。
以上、クラウド事業本部 コンサルティング部の のんピ(@non____97)でした!






