Use Cases (Atualizado: 01/06/2026)

Claude Code × AWS S3: sync, imagens, backups e URLs pré-assinadas com menor privilégio

Guia Claude Code e AWS S3: IAM menor privilégio, aws s3 sync, site estático, imagens, backups e URLs pré-assinadas.

Claude Code × AWS S3: sync, imagens, backups e URLs pré-assinadas com menor privilégio

S3 parece apenas um lugar para guardar arquivos, mas em uma aplicação real aparecem permissões, exposição pública, sync, cache, exclusão e custo. Claude Code acelera scripts e helpers, mas um prompt vago pode gerar uma policy ampla demais.

Este guia é para quem quer usar S3 perto de produção com segurança. Vamos cobrir site estático, upload de imagens, backups e URLs pré-assinadas. A regra central é least privilege: cada script recebe apenas a action e o prefix necessários.

Os comandos seguem a documentação oficial: AWS CLI S3 reference, aws s3 sync reference, Boto3 presigned URL guide, Claude Code common workflows.

Para contexto adicional, veja também: IAM, security, context.

Separar os usos do S3 antes do código

use case 1 é site estático. dist vai para site/ e CloudFront entrega. use case 2 é imagem. O admin envia para uploads/ ou assets/images/. use case 3 é backup. Dumps e PDFs usam prefixo de data e não usam —delete. use case 4 é download privado com URL curta pré-assinada.

Se tudo fica misturado, s3:* parece tentador. Defina prefixos como site/, assets/images/, uploads/, backups/ e assets/private-reports/. Com essas fronteiras, Claude Code gera algo mais fácil de revisar.

Identidade e IAM com menor privilégio

Coloque bucket e região em variáveis para que você e o Claude Code revisem o mesmo alvo.

export AWS_REGION=ap-northeast-1
export S3_BUCKET=claudecode-lab-assets-prod
aws sts get-caller-identity
aws s3 ls "s3://${S3_BUCKET}/" --region "${AWS_REGION}"

Essa policy lê apenas assets, grava apenas uploads e evita permissão ampla de exclusão.

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "ReadPublicAssetsOnly",
      "Effect": "Allow",
      "Action": ["s3:GetObject"],
      "Resource": "arn:aws:s3:::claudecode-lab-assets-prod/assets/*"
    },
    {
      "Sid": "WriteUploadsOnly",
      "Effect": "Allow",
      "Action": ["s3:PutObject", "s3:AbortMultipartUpload"],
      "Resource": "arn:aws:s3:::claudecode-lab-assets-prod/uploads/*"
    },
    {
      "Sid": "ListLimitedPrefixes",
      "Effect": "Allow",
      "Action": ["s3:ListBucket"],
      "Resource": "arn:aws:s3:::claudecode-lab-assets-prod",
      "Condition": {
        "StringLike": {
          "s3:prefix": ["assets/*", "uploads/*", "backups/*"]
        }
      }
    }
  ]
}

Esse é o formato básico para sites estáticos ou pastas de imagens. Comece sempre com dryrun.

# 1. Preview changes first. This should become a habit.
aws s3 sync ./dist "s3://${S3_BUCKET}/site/" \
  --region "${AWS_REGION}" \
  --delete \
  --cache-control "public,max-age=300" \
  --dryrun

# 2. Deploy only after the preview looks right.
aws s3 sync ./dist "s3://${S3_BUCKET}/site/" \
  --region "${AWS_REGION}" \
  --delete \
  --cache-control "public,max-age=300"

# 3. Upload long-lived images with a different cache policy.
aws s3 sync ./public/images "s3://${S3_BUCKET}/assets/images/" \
  --region "${AWS_REGION}" \
  --exclude "*.psd" \
  --cache-control "public,max-age=31536000,immutable"

Uma URL pré-assinada mantém o bucket privado e libera download por pouco tempo.

import { S3Client, GetObjectCommand } from "@aws-sdk/client-s3";
import { getSignedUrl } from "@aws-sdk/s3-request-presigner";

const s3 = new S3Client({ region: process.env.AWS_REGION ?? "ap-northeast-1" });

export async function createDownloadUrl(key: string, filename: string) {
  if (!key.startsWith("assets/private-reports/")) {
    throw new Error(`Unexpected S3 key prefix: ${key}`);
  }

  const command = new GetObjectCommand({
    Bucket: process.env.S3_BUCKET_NAME,
    Key: key,
    ResponseContentDisposition: `attachment; filename="${filename}"`,
  });

  return getSignedUrl(s3, command, { expiresIn: 900 });
}

Ao pedir ao Claude Code, inclua objetivo, proibições e comandos de verificação.

このリポジトリに AWS S3 連携を追加してください。
目的: public/images を S3 の assets/images/ に同期し、private-reports/ のPDFだけ署名付きURLで配布する。
制約: バケット全体公開は禁止。s3:DeleteObject は付けない。aws s3 sync は必ず --dryrun を先に出す。
成果物: scripts/s3-sync-assets.mjs、lib/s3-presigned-url.ts、READMEの手順、確認コマンド。
確認: npm test、aws s3 ls、aws s3 sync --dryrun の出力で説明してください。
参照: AWS CLI s3/sync docs と Anthropic Claude Code common workflows。

A policy é estreita de propósito: GetObject só em assets, PutObject só em uploads e ListBucket limitado por prefix. Erros comuns são ListBucket em ARN de objeto e s3:* no bucket inteiro.

DeleteObject é outro pitfall. Muitos fluxos não precisam dele. Se for necessário, separe role ou script, com dryrun, contagem de deletes e confirmação humana. Claude Code escreve JSON; o escopo final é revisão humana.

Usar aws s3 sync com segurança

aws s3 sync compara caminho local e prefix S3. Com —delete, remove do remoto o que não existe localmente. Ótimo para deploy estático determinístico, perigoso para backups e pastas compartilhadas.

# Backup use case: append-only, no --delete.
BACKUP_DATE=$(date +%Y-%m-%d)
aws s3 sync ./backups "s3://${S3_BUCKET}/backups/${BACKUP_DATE}/" \
  --region "${AWS_REGION}" \
  --storage-class STANDARD_IA \
  --exclude "*.tmp"

aws s3 ls "s3://${S3_BUCKET}/backups/${BACKUP_DATE}/" --recursive --summarize

Meu padrão é dryrun primeiro. O script deve mostrar bucket, região, prefix e diff. Se houver muitos deletes, ele para. Esse cuidado simples evita o pior caso: pasta errada com —delete.

URL pré-assinada é permissão temporária

Uma presigned URL permite uma ação S3 por tempo limitado. O bucket continua privado. Serve para PDFs, relatórios, exports e downloads por usuário após autenticação.

Três detalhes importam: expiresIn é em segundos, o prefix do key deve ser validado e o nome vindo do navegador não deve virar key final. Gere keys no servidor, como uploads/yyyy/mm/dd/uuid.ext. URL longa demais em produção é failure comum.

Custos, cache e exposição pública

Custo de S3 não é só armazenamento. Requests, transferência, CloudFront, versioning e lifecycle também contam. Assets públicos devem usar CloudFront e cache-control; arquivos privados não devem exigir bucket público.

DRYRUN_OUTPUT=$(aws s3 sync ./dist "s3://${S3_BUCKET}/site/" --delete --dryrun)
echo "$DRYRUN_OUTPUT"
DELETE_COUNT=$(echo "$DRYRUN_OUTPUT" | grep -c "delete:" || true)
if [ "$DELETE_COUNT" -gt 20 ]; then
  echo "Too many deletes: ${DELETE_COUNT}. Stop and review."
  exit 1
fi

Tutoriais antigos usam S3 static website hosting com bucket público. Hoje, private S3 + CloudFront costuma ser mais seguro e mais fácil de explicar em auditorias.

O que delegar ao Claude Code e o que revisar

Claude Code é bom para scripts de sync, helpers TypeScript, README, testes e mensagens de erro. A revisão humana olha conta AWS, bucket, prefix, DeleteObject, public access e CloudFront. Antes de executar, use aws sts get-caller-identity e aws s3 ls.

Nota de verificação do Masa: separar prefixos foi o maior ganho. Com site, assets, uploads, backups e private-reports, a revisão IAM e os prompts ficaram claros. Pedir verification steps junto com o código também aumentou a confiança.

Resumo

Claude Code × AWS S3 funciona muito bem quando as permissões continuam chatas. Separe use cases, use dryrun, evite DeleteObject amplo, mantenha S3 privado e gere URLs pré-assinadas curtas.

Para adaptar isso a um repositório real, use training / consultation.

#claude-code #aws #s3 #iam #aws-cli #security
Grátis

PDF grátis: cheatsheet do Claude Code

Informe seu e-mail e baixe uma página com comandos, hábitos de revisão e workflows seguros.

Cuidamos dos seus dados e não enviamos spam.

Masa

Sobre o autor

Masa

Engenheiro focado em workflows práticos com Claude Code.