こんにちは。2015年新卒入社の橋本です。
今回はS3のよくありそうなバケットポリシーの書き方とそのポイントについて解説してみることにします。
要件
割とよくありそうな感じの要件かと思います。以下の通りです。
- my-public-bucket バケットの /contents/ 以下に配置されたコンテンツをPublicにしたい。
- /contents/admin/ 以下のコンテンツは社内ネットワークからしかアクセスできないようにしたい。
解答例
対象バケットに対して、下記のようなバケットポリシーを当てます。
解説
ポリシーの中身について解説していきます。
Action について
今回はWeb上のコンテンツとしてアクセスされることを想定しているので、設定が必要な Action は "s3:GetObject" のみとなります。
Principal について
Pricipal には「誰を対象にするか」を記述します。AWSアカウントを対象にすることも可能ですが、今回はAWSアカウントでの制限をかけることを想定していないため任意を表す "*" を指定します。
Statement について
Statement の1つ目のブロックは /contents/ 以下を公開するためのものです。
Resouce でS3のパスを指定しています。この設定では /contents/admin/ も公開されてしまうので、それを打ち消す必要があります。
2つ目の Statement では、 /contents/admin/ 以下のアクセスを制限します。
1つ目の Statementブロックで公開されるポリシーが適用されてしまうので、明示的なDenyを書くことで許可を打ち消しています。
しかしながら、社内からのアクセス(=許可したいソースIP)である場合に限っては "s3:GetObject" 権限を打ち消す必要はありません。これは "Condition" にソースIPの条件を書いてあげることで実現できます。
2つ目の Statement ブロックによって、社外からのアクセスである場合のみ /contents/admin/ 以下に対する "s3:GetObject" 権限が打ち消され、結果として社内のアクセスのみが許可されます。 NotIpAddress を利用しているのがポイントかと思います。
まとめ
Not*系を使うことで「特定のユーザーにだけxxxの許可を与える」といった制限はすっきり書くことができます。
今回は、よくありそうなケースとして「ソースIPによるアクセス制限」を題材にしましたが、似たような要件が発生することは非常に多いと思います。
Not* も活用して、見通しの良い綺麗なバケットポリシーを書きましょう。