AWS S3バケット内のすべてのオブジェクトをデフォルトでパブリックにする方法は?


151

PHPライブラリを使用してファイルをバケットにアップロードしています。ACLをpublic-read-writeに設定しましたが、正常に機能しますが、ファイルはまだ非公開です。

GranteeをEveryoneに変更すると、ファイルが公開されることがわかりました。知りたいのは、バケット内のすべてのオブジェクトのデフォルトのGrantee"Everyone"に設定する方法です。または、デフォルトでファイルを公開する別の解決策はありますか?

私が使用しているコードは以下の通りです:

public static function putObject($input, $bucket, $uri, $acl = self::ACL_PRIVATE, $metaHeaders = array(), $requestHeaders = array()) {
    if ($input === false) return false;
    $rest = new S3Request('PUT', $bucket, $uri);

    if (is_string($input)) $input = array(
        'data' => $input, 'size' => strlen($input),
        'md5sum' => base64_encode(md5($input, true))
    );

    // Data
    if (isset($input['fp']))
        $rest->fp =& $input['fp'];
    elseif (isset($input['file']))
        $rest->fp = @fopen($input['file'], 'rb');
    elseif (isset($input['data']))
        $rest->data = $input['data'];

    // Content-Length (required)
    if (isset($input['size']) && $input['size'] >= 0)
        $rest->size = $input['size'];
    else {
        if (isset($input['file']))
            $rest->size = filesize($input['file']);
        elseif (isset($input['data']))
            $rest->size = strlen($input['data']);
    }

    // Custom request headers (Content-Type, Content-Disposition, Content-Encoding)
    if (is_array($requestHeaders))
        foreach ($requestHeaders as $h => $v) $rest->setHeader($h, $v);
    elseif (is_string($requestHeaders)) // Support for legacy contentType parameter
        $input['type'] = $requestHeaders;

    // Content-Type
    if (!isset($input['type'])) {
        if (isset($requestHeaders['Content-Type']))
            $input['type'] =& $requestHeaders['Content-Type'];
        elseif (isset($input['file']))
            $input['type'] = self::__getMimeType($input['file']);
        else
            $input['type'] = 'application/octet-stream';
    }

    // We need to post with Content-Length and Content-Type, MD5 is optional
    if ($rest->size >= 0 && ($rest->fp !== false || $rest->data !== false)) {
        $rest->setHeader('Content-Type', $input['type']);
        if (isset($input['md5sum'])) $rest->setHeader('Content-MD5', $input['md5sum']);

        $rest->setAmzHeader('x-amz-acl', $acl);
        foreach ($metaHeaders as $h => $v) $rest->setAmzHeader('x-amz-meta-'.$h, $v);
        $rest->getResponse();
    } else
        $rest->response->error = array('code' => 0, 'message' => 'Missing input parameters');

    if ($rest->response->error === false && $rest->response->code !== 200)
        $rest->response->error = array('code' => $rest->response->code, 'message' => 'Unexpected HTTP status');
    if ($rest->response->error !== false) {
        trigger_error(sprintf("S3::putObject(): [%s] %s", $rest->response->error['code'], $rest->response->error['message']), E_USER_WARNING);
        return false;
    }
    return true;
}

回答:


299

http://awspolicygen.s3.amazonaws.com/policygen.htmlに移動しここに画像の説明を入力してください ます 。次のような詳細を入力します。アクションで、「GetObject」を選択し、「Add Statement」を選択して、「Generate Policy」を選択します。

テキストの例をコピーします。

{
  "Id": "Policy1397632521960",
  "Statement": [
    {
      "Sid": "Stmt1397633323327",
      "Action": [
        "s3:GetObject"
      ],
      "Effect": "Allow",
      "Resource": "arn:aws:s3:::bucketnm/*",
      "Principal": {
        "AWS": [
          "*"
        ]
      }
    }
  ]
}

次にAWS S3コンソールに移動します。バケットレベルで、[プロパティ]、[アクセス許可の展開]、[バケットポリシーの追加]の順にクリックします。上記の生成されたコードをエディターに貼り付け、保存をクリックします。

バケット内のすべてのアイテムはデフォルトで公開されます。


8
これは正しい応答です。以前の回答とは異なり、この投稿では、ポリシーを作成する方法とそのポリシーについても学びました。これを読んだ後、ポリシーを手動で作成できます。
Jason Cheladyn、2015年

2
@liyickyと同じ理由でこの回答に賛成しました。詳細な手順は、回答を渡されただけでなく、素晴らしい導入でした。
ブレンド

こっちも一緒。AWSは時々不透明になる傾向があり、おそらく非常に理由があります。この回答形式は、ゼロからの助けになります。
ジェローム2015年

これは、バケットに新しいファイルを追加するときに機能しますが、バケットに既に存在するファイルをパブリックに変更する必要があります。
Radenko Zec 2017

137

すべてのオブジェクトをデフォルトでパブリックにしたい場合、最も簡単な方法は、個々のオブジェクトごとに定義されたアクセス制御リスト(ACL)ではなくバケットポリシーを使用することです。

ここに画像の説明を入力してください

AWS Policy Generatorを使用して、バケットのバケットポリシーを生成できます。

たとえば、次のポリシーでは、誰でもS3バケット内のすべてのオブジェクトを読み取ることができます(バケット<bucket-name>の名前に置き換えるだけです)。

{
  "Id": "Policy1380877762691",
  "Statement": [
    {
      "Sid": "Stmt1380877761162",
      "Action": [
        "s3:GetObject"
      ],
      "Effect": "Allow",
      "Resource": "arn:aws:s3:::<bucket-name>/*",
      "Principal": {
        "AWS": [
          "*"
        ]
      }
    }
  ]
}

バケットポリシーのリストが含まれStatements、各ステートメントがありEffect(いずれかAllowまたはDenyのリストについて)をActionsすることにより行われることをPrincipal指定した上で(ユーザー)Resource(で識別されますAmazon Resource NameARN)。

Idただ、オプションのポリシーIDで、Sidオプションのユニークな文のIDです。

S3バケットポリシーの場合、リソースARNは次の形式を取ります。

arn:aws:s3:::<bucket_name>/<key_name>

上記の例では、(Effect: Allow)誰でも(Principal: *Action: s3:GetObjectがバケット(Resource: arn:aws:s3:::<bucket-name>/*)の任意のオブジェクトにアクセス()できるようにします。


コントロールパネルで方法はありませんか?
ianaz 14

2
@ianaz AWSコンソール(コントロールパネル)からこのバケットポリシーをバケットに追加できます
dcro

@ianaz以下の私の答えを見てください。
jaxxbo 2015年

また、上のリンクに「ポリシーの例」リンクがあり、ポリシージェネレーターにカットアンドペーストするために必要な正確な情報を提供しています。awsがAPIを更新するにつれて、これは正しいままである可​​能性が高くなります。今朝は私にとって魅力のように働きました。
keithpjolley 2017年

Principal: *たくさん助けてくれました。ありがとう!
iedmrc

2

私の問題は少し異なっていましたが、この質問はグーグル検索の一番上にあるので、私は私の解決策を残します、おそらくそれは誰かを助けるでしょう。

以前はS3バケットに完全にアクセスできていましたが、ある日Access Denied、すべてのファイルに戻り始めました。解決策は単純明快でした。

  1. に行くServices-S3
  2. S3バケットをクリックします
  3. 切り替えるPermissionsに行き、その後、タブBucket Policyタブ
  4. そして、Saveボタンをクリックします。

それはあなたのすべてのファイルにアクセス許可を再割り当てする必要があります。

ここに画像の説明を入力してください

とにかく、ここはbucket policyすべてのオブジェクトをパブリックにすることができるフルです

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "AllowPublicRead",
            "Effect": "Allow",
            "Principal": {
                "AWS": "*"
            },
            "Action": "s3:GetObject",
            "Resource": "arn:aws:s3:::enter-here-your-media-bucket-name/*"
        }
    ]
}
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.