Como tornar todos os objetos no bucket do AWS S3 públicos por padrão?


151

Estou usando uma biblioteca PHP para fazer upload de um arquivo para o meu bucket. Eu configurei a ACL para public-read-write e ela funciona bem, mas o arquivo ainda é privado.

Descobri que, se eu alterar o Beneficiário para Todos , o arquivo será público. O que eu quero saber é como faço para que o Beneficiário padrão em todos os objetos no meu bucket seja definido como "Todos" . Ou existe outra solução para tornar os arquivos públicos por padrão?

O código que estou usando está abaixo:

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;
}

Respostas:


299

Vá para http://awspolicygen.s3.amazonaws.com/policygen.html Preencha os detalhes como: insira a descrição da imagem aqui Em ação, selecione "GetObject" Selecione "Adicionar instrução" e selecione "Gerar política"

Copie o exemplo de texto:

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

Agora vá para o console do AWS S3. No nível do bucket, clique em Propriedades, Expanda Permissões e selecione Adicionar política de bucket. Cole o código gerado acima no editor e pressione Salvar.

Todos os seus itens no balde serão públicos por padrão.


8
Esta é a resposta correta. Diferentemente da resposta anterior, este post também me ensinou como criar políticas e o que elas fazem. Depois de ler isso, posso escrever uma política manualmente.
Jason Cheladyn

2
Votei esta resposta pelo mesmo motivo que @liyicky, as instruções detalhadas foram uma boa introdução, em vez de apenas receberem a resposta.
brendo 25/03

O mesmo aqui. A AWS tende a ser opaca às vezes e provavelmente por um motivo muito bom. Essa forma de resposta é útil do ponto zero.
Jerome

Isso funciona quando você adiciona novos arquivos ao bucket, mas preciso alterar os arquivos já existentes no bucket para serem públicos.
Radenko Zec

137

Se você deseja tornar todos os objetos públicos por padrão, a maneira mais simples é fazê-lo através de uma Política de Balde em vez das Listas de Controle de Acesso (ACLs) definidas em cada objeto individual.

insira a descrição da imagem aqui

Você pode usar o AWS Policy Generator para gerar uma política de bucket para seu bucket.

Por exemplo, a política a seguir permitirá que qualquer pessoa leia todos os objetos no seu bucket S3 (substitua <bucket-name>pelo nome do seu bucket):

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

A Política de Bucket contém uma lista de Statementse cada declaração possui um Effect( Allowou Deny) para uma lista deActions que são executados pelo Principal(usuário) no especificado Resource(identificado por um Amazon Resource Nameou ARN).

A Idé apenas um ID de política opcional eo Sidé um opcional Unique ID comunicado.

Para diretivas de balde S3, os ARNs de recurso assumem a forma:

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

O exemplo acima permite que ( Effect: Allow) qualquer pessoa ( Principal: *) acesse ( Action: s3:GetObject) qualquer objeto no bucket ( Resource: arn:aws:s3:::<bucket-name>/*).


Não existe uma maneira com o painel de controle?
Ianaz 3/03

2
@ianaz Você pode adicionar esta política balde para um balde através do console AWS (painel de controle)
dcro

@ianaz veja minha resposta abaixo.
jaxxbo

Observe também que há um link "exemplo de políticas" no link acima que fornece as informações exatas necessárias para recortar e colar no gerador de políticas. À medida que o aws atualiza as APIs, é mais provável que ele permaneça correto. Funcionou como um encanto para mim esta manhã.
keithpjolley

Principal: *me ajudou muito. Obrigado!
iedmrc

2

Meu problema era um pouco diferente, mas como essa pergunta está no topo da pesquisa do Google, deixarei minha solução, talvez ajude alguém.

Eu já tinha acesso total ao bucket do S3 antes, mas um dia ele começou a retornar Access Denieda todos os meus arquivos. A solução foi direta e simples.

  1. Ir para Services-S3
  2. Clique no seu balde S3
  3. Alterne para a Permissionsguia e vá para a Bucket Policyguia
  4. E clique no Savebotão

Ele deve reatribuir permissão em todos os seus arquivos.

insira a descrição da imagem aqui

De qualquer forma, aqui está cheio bucket policyque permite tornar todos os objetos públicos

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "AllowPublicRead",
            "Effect": "Allow",
            "Principal": {
                "AWS": "*"
            },
            "Action": "s3:GetObject",
            "Resource": "arn:aws:s3:::enter-here-your-media-bucket-name/*"
        }
    ]
}
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.