本文主要记录在 MinIO 上实现「匿名可读、指定 Access Key 可写/管理」的 IAM 策略写法,以及用 mc 附加用户策略与桶策略的步骤。

场景假设:

  • 桶名:<bucket>(示例曾用业务名,此处泛化)
  • 用户 / Access Key:<access-key>
  • mc 别名:myminio(指向你的 MinIO 集群)

策略 JSON 遵循 S3 兼容的 IAM 语法;MinIO 版本不同时,mc admin policy / mc anonymous / mc policy 子命令名称可能有差异,以当前 mc --help 与发行说明为准。密钥一律占位,勿把真实 Access Key 写进仓库。

目标权限

主体期望
匿名 / *可读对象、可 List 桶(按需)、不可写删
<access-key>对该桶对象具备上传、删除等管理能力(或 s3:*

公开读意味着对象 URL 可被未认证客户端下载,勿用于含隐私/未授权版权的数据

推荐:用户策略 + 桶策略

职责拆分:用户策略保证该 AK 有权操作桶;桶策略声明匿名读与(可选)写主体。

用户策略(绑到 Access Key)

user-policy.json

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": ["s3:*"],
      "Resource": [
        "arn:aws:s3:::<bucket>",
        "arn:aws:s3:::<bucket>/*"
      ]
    }
  ]
}

创建并附加:

mc admin policy create myminio <bucket>-full-access user-policy.json
mc admin policy attach myminio <bucket>-full-access --user <access-key>

桶策略(绑到 Bucket)

bucket-policy.json

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": "*",
      "Action": [
        "s3:GetObject",
        "s3:GetBucketLocation",
        "s3:ListBucket"
      ],
      "Resource": [
        "arn:aws:s3:::<bucket>",
        "arn:aws:s3:::<bucket>/*"
      ]
    },
    {
      "Effect": "Allow",
      "Principal": {
        "AWS": ["arn:aws:iam::*:user/<access-key>"]
      },
      "Action": [
        "s3:PutObject",
        "s3:DeleteObject",
        "s3:DeleteObjectVersion",
        "s3:PutObjectTagging",
        "s3:DeleteObjectTagging"
      ],
      "Resource": ["arn:aws:s3:::<bucket>/*"]
    }
  ]
}

应用(命令随 mc 版本二选一或查文档):

# 常见写法之一
mc anonymous set-json bucket-policy.json myminio/<bucket>
# 或旧文档中的:
# mc policy set-json bucket-policy.json myminio/<bucket>

若写操作已完全由用户策略 s3:* 覆盖,桶策略里第二段可省略,仅保留匿名读;保留第二段可在用户策略被误删时仍限制写主体(取决于 MinIO 如何合并评估,以实测为准)。

简化:仅桶策略

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": "*",
      "Action": [
        "s3:GetObject",
        "s3:GetBucketLocation",
        "s3:ListBucket"
      ],
      "Resource": [
        "arn:aws:s3:::<bucket>",
        "arn:aws:s3:::<bucket>/*"
      ]
    },
    {
      "Effect": "Allow",
      "Principal": {
        "AWS": ["arn:aws:iam::*:user/<access-key>"]
      },
      "Action": ["s3:*"],
      "Resource": [
        "arn:aws:s3:::<bucket>",
        "arn:aws:s3:::<bucket>/*"
      ]
    }
  ]
}
mc anonymous set-json single-bucket-policy.json myminio/<bucket>

维护简单,但用户侧若无独立 policy,跨桶授权会不清晰;多用户环境更推荐「用户策略 + 桶策略」。

权限对照

匿名:

  • 允许:GetObjectGetBucketLocationListBucket
  • 拒绝(未授权):PutObjectDeleteObject

指定用户(在推荐方案用户策略为 s3:* 时):

  • 对该桶及对象前缀的完整 S3 API(含读写删、标签等)

桶策略中若只列部分写 Action,则以实际 Statement 并集为准。

验证

mc admin user info myminio <access-key>
mc anonymous get myminio/<bucket>
# 或 mc policy get myminio/<bucket> 等,视 mc 版本

# 匿名读(不应带 AK)
curl -sS -o /dev/null -w "%{http_code}\n" http://<minio-endpoint>/<bucket>/<object-key>

# 认证写
mc cp ./test.txt myminio/<bucket>/test.txt
mc rm myminio/<bucket>/test.txt

期望:匿名 GET 为 200(对象存在且策略生效);无 AK 的 PUT/DELETE 失败;带正确 AK 的上传删除成功。

注意事项

  • Principal 里 user 名需与 MinIO 用户名一致,不一定是 Access Key 字符串;以控制台/用户列表为准(待确认你环境中的对应关系)。
  • 开启版本控制时删除可能需 DeleteObjectVersion 等权限。
  • 公开 ListBucket 会暴露对象键名列表,可按需去掉 List,仅保留 GetObject。
  • 策略改完后客户端与 CDN 可能有缓存,验证时注意。
  • 管理员 mc admin 需要 root/admin 凭据,操作环境与策略文件权限要收紧。

参考资料