简介

对象存储和 Web 服务是开发者必备工具。MinIO 凭借高性能和 S3 兼容性成为存储领域的“顶流”,Caddy 则以自动 HTTPS 和极简配置深受开发者喜爱。结合 Docker Compose,只需 5 分钟,你就能搭建一个安全、高效的对象存储服务!MinIO 文件同步的方案可以参考 https://wiki.waringid.me/x/VIDM

前提要求

  • 大硬盘 VPS:运行 MinIO 服务。
  • 大带宽机器(如腾讯云锐驰 200):运行 Caddy,代理 MinIO 服务。
  • 组网服务(如 Tailscale/EasyTier):确保内网互联互通

为啥选择 MinIO + Caddy

  • MinIO:开源、S3 兼容、支持分布式存储,轻松应对海量数据。
  • Caddy:自动 HTTPS、配置简洁,专为高并发优化,支持丰富插件。
  • Docker Compose:一键部署多容器,省时省力。
  • 组合优势:Caddy 为 MinIO 提供安全访问和负载均衡,Docker Compose 确保部署简单,完美适配静态文件托管、API 服务或私有云存储。

快速部署

根据需求,可选择在同一机器上部署或分布式部署。

Minio.yml

version: "3"
services:
  minio:
    image: bitnami/minio:2025
    # image: ccr.ccs.tencentyun.com/k7scn/minio:2025
    container_name: minio
    restart: always
    environment:
      - MINIO_ROOT_USER=homes4
      - MINIO_ROOT_PASSWORD=aiy0ooCheephai0ohNahmu3Aijee6eiv
      - MINIO_DEFAULT_BUCKETS=homes4
    ports:
      - '9000:9000'
      - '9001:9001'
    volumes:
      - '/volume1/docker/minio/data:/bitnami/minio/data'

注意:可能遇到目录权限问题,可运行以下命令解决:chmod 777 /volume1/docker/minio/data -R

访问 MinIO 管理界面

在浏览器输入 http://NAS_IP:9001 或 http://域名:9001,进入 MinIO 登录页面,使用 MINIO_ROOT_USER 和 MINIO_ROOT_PASSWORD 登录。

安装客户端

提供 Linux/amd64 的 mc 客户端下载链接:https://min.io/docs/minio/linux/reference/minio-mc.html#quickstart

caddy.yaml

services:
  caddy:
    image: ysicing/caddy2
    # image: ccr.ccs.tencentyun.com/k7scn/caddy2
    container_name: caddy
    restart: always
    # 可选host或者端口映射
    network_mode: host
    volumes:
      - '/data/caddy/cfg:/etc/caddy'
      - '/data/caddy/data:/data'
      - '/data/caddy/config:/config'
      - '/data/caddy/log:/var/log/caddy'

此 Caddy 镜像为定制版,内置以下常用插件:

xcaddy build \
    --with github.com/caddy-dns/cloudflare \
    --with github.com/caddy-dns/tencentcloud \
    --with github.com/caddy-dns/alidns \
    --with github.com/caddy-dns/dnspod \
    --with github.com/ysicing/caddy2-geocn \
    --with github.com/mholt/caddy-l4 \
    --with github.com/mholt/caddy-ratelimit

Caddy 配置

配置文件位于 /data/caddy/cfg,目录结构如下:

/data/caddy/cfg# tree
.
├── Caddyfile
├── load.sh
└── site
    ├── cr.caddy
    ├── dev.caddy
    ├── hub.caddy
    ├── http.caddy
    └── minio.caddy

Caddyfile 示例


(LOG) {
    log {
        output file "{args[0]}" {
            roll_size 50M
            roll_uncompressed
            roll_local_time
            roll_keep 3
            roll_keep_for 7d
        }
        format json
    }
}

(COMCFG) {
    encode zstd gzip
}

(ERR) {
    handle_errors {
        # 异常重定向
        redir https://dxgw-{err.status_code}.caddy.local
    }
}

{
    debug
    # admin off
}

(TLS) {
tls {
  dns tencentcloud {
    secret_id AKID***
    secret_key CH85***
  }
}
}

import /etc/caddy/site/*.caddy

MinIO 配置

minio.caddy

域名 {
    import ERR
    # 如果是内网域名可以设置import TLS开启dns签发证书
    # import TLS
    import LOG "/var/log/caddy/minio.log"
    @rootPath {
        path /
    }
    handle @rootPath {
        respond "EdgeONE 451 Forbidden" 451
    }
    # 内网minio地址
    reverse_proxy 100.90.80.2:9000
}

同理,minio 控制台也是一样,通常控制台不对外开放,仅限内网访问。

minio-api.caddy

域名 {
    import ERR
    # 如果是内网域名可以设置import TLS开启dns签发证书
    # import TLS
    import LOG "/var/log/caddy/minio-api.log"
    @denied not remote_ip 192.168.1.0/24
    respond @denied "Access Denied" 403
    # 内网minio api地址
    reverse_proxy 100.90.80.2:9001
}

重新加载配置

curl "http://localhost:2019/load" -H "Content-Type: text/caddyfile" --data-binary @Caddyfile

使用 MinIO

配置 MinIO 客户端(mc)以访问服务:

# 内网
mc alias set home http://100.90.80.2:9000 homes4 aiy0ooCheephai0ohNahmu3Aijee6eiv
# 外网
mc alias set home https://域名 homes4 aiy0ooCheephai0ohNahmu3Aijee6eiv

MinIO 身份与权限管理

聚焦存储桶权限(private、public、custom)的区别和匿名访问的应用,通过清晰的场景示例,实现安全分享,同时保护数据。

MinIO 身份管理基础

MinIO 的身份管理负责用户认证和授权,默认使用内置身份提供者(IDP)。核心概念包括:

  • 用户(User)。用户通过 Access Key(用户名)和 Secret Key(密码)访问 MinIO,可用命令行工具 mc 或 Web 控制台管理。
  • 服务账号(Service Account)。服务账号是为应用程序设计的专用凭证,无法登录控制台,但可通过 API 访问资源,适合自动化脚本或服务集成。
  • 策略(Policy)。JSON 格式的策略定义用户、服务账号或匿名访问对存储桶(Bucket)和对象(Object)的权限,基于 AWS S3 语法。
  • 匿名访问(Anonymous Access)。允许未认证用户(无 Access Key)通过 URL 或 API 访问特定资源,需通过存储桶权限配置。
  • 用户组:可通过 mc admin group 批量管理用户权限。
目标是:安全地让匿名用户或服务账号读取特定内容,限制列出存储桶或文件列表,或有选择地允许列出某个存储桶的内容。

准备工作

  1. 确保 MinIO 运行:假设 MinIO 部署在 http://localhost:9000,管理员账号为 homes4,密码为 aiy0ooCheephai0ohNahmu3Aijee6eiv。
  2. 安装 mc 工具:下载 MinIO 客户端(mc),用于配置权限(支持 Windows、Mac、Linux)。
  3. 配置 mc:
mc alias set homes4 http://localhost:9000 homes4 aiy0ooCheephai0ohNahmu3Aijee6eiv
Added `homes4` successfully.

PS:命令行方式和可视化操作效果是一样的

存储桶权限:Private、Public 和 Custom

MinIO 的存储桶权限控制匿名访问行为,分为 private、public 和 custom 三种模式,可通过 mc anonymous 命令设置。以下是它们的区别

Private(私有)

定义:禁止所有匿名访问,仅允许认证用户或服务账号(有 Access Key 和策略授权)访问。

适用场景:保护敏感数据,如内部文档、用户数据。

效果:匿名用户访问存储桶或对象时,返回 403 Forbidden

配置:mc anonymous set none homes4/web

Public(公开)

注意:风险较高,容易暴露所有文件,慎用。

Custom(自定义)

推荐用

  • 定义:通过 JSON 策略精确控制匿名访问权限,如限制特定路径或操作。
  • 适用场景:部分公开,如只分享某个文件夹,或禁止列出文件列表。
  • 配置:见下文场景示例。
  • 效果:灵活性最高,匿名用户只能执行策略允许的操作。

存储桶权限区别总结

模式匿名访问权限适用场景配置命令
Private禁止匿名访问敏感数据mc anonymous set none
Public读、写或读写(看设置)公开资源mc anonymous set download upload/public
Custom自定义(JSON 策略)部分公开、精确控制mc anonymous set-json

案例说明:安全分享存储内容

要求:

  • 让匿名用户只读特定文件,禁止列出存储桶或文件列表

新建存储桶

先创建一个存储桶,默认创建的存储桶都是私有权限

root@docker:~$ mc mb homes4/cli
Bucket created successfully `homes4/cli`.
root@docker:~$ mc ls homes4
[2025-05-01 11:26:11 EDT]     0B cli/
[2025-05-01 11:23:57 EDT]     0B ddd/
[2025-05-01 10:38:53 EDT]     0B homes4/
[2025-05-01 11:29:06 EDT]     0B web/

场景:只读特定文件,禁止列出存储桶或文件列表

需求:存储桶 web 包含 public/photo.jpg 和 private/secret.pdf。想让匿名用户只读 photo.jpg,但不能列出 web 桶中 的文件列表,也不能访问其他文件或存储桶

操作步骤:

1、设为 Private(默认安全)

mc anonymous set none homes4/web

2、创建自定义策略:只允许匿名读取 public/photo.jpg

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Action": ["s3:GetObject"],
      "Effect": "Allow",
      "Resource": ["arn:aws:s3:::web/public/photo.jpg"],
      "Principal": "*"
    }
  ]
}
  • s3:GetObject:允许读取对象
  • Resource:精确到 photo.jpg, 例如你想某个目录读写 arn:aws:s3:::web/public/*
  • Principal: "*":表示匿名用户
  • 无 s3:ListBucket:禁止列出文件列表

3、应用策略

mc anonymous set-json custom.json homes4/web

控制台可以直接编辑存储桶的 Access Policy,改成 Custom,内容和上面一致

4、查看策略

root@docker:~$ mc anonymous get-json homes4/web
{
 "Statement": [
  {
   "Action": [
    "s3:GetObject"
   ],
   "Effect": "Allow",
   "Principal": {
    "AWS": [
     "*"
    ]
   },
   "Resource": [
    "arn:aws:s3:::web/public/photo.jpg"
   ]
  }
 ],
 "Version": "2012-10-17"
}

5、效果

服务账号:为应用程序配置相同权限

需求:为应用程序(如网站后端)提供只读 public/photo.jpg 的权限,类似上述场景,但通过服务账号实现

步骤:

1、创建用户(服务账号需绑定到用户):

密码长度需要 8-40

mc admin user add homes4 app1user app1pass

web 可视化操作,policy 那里随便选个小权限的,后面需要调整

2、创建服务账号:为 app1user 生成服务账号,绑定 custom.json 策略

mc admin user svcacct add homes4 app1user --access-key svc1 --secret-key svc1pass --policy custom.json

可视化操作创建服务状态,凭证信息会随机生成,且只显示一次

策略信息只能在生成 access key 后才能编辑操作

实用技巧:兼顾安全与便利

  • 优先 Custom 模式:比 public 安全,精确控制分享内容。
  • 避免 Public 模式:除非真想完全公开,否则可能暴露所有文件。
  • 检查权限:定期用 mc anonymous get-json homes4/web 确认存储桶权限
  • 随机存储桶名:用随机名,降低被猜到风险
  • 用预签名 URL 临时分享:生成带有效期的链接,过期失效:
#分享下载链接,下载速度限制10MB/s有效期7天
mc share download --limit-download 10MB homes4/web/private/secret.pdf

  • 无标签

0 评论

你还没有登录。你所做的任何更改会将作者标记为匿名用户。 如果你已经拥有帐户,请登录