单机 Docker-Compose+Nginx+Keycloak 部署 MinIO 对象储存

欢迎在 Fediverse 上查看这篇文章!https://neko.lzc256.com/@lzc256/pages/deploying-minio-with-nginx-and-keycloak

国庆补课培优期间疯狂摸鱼部署了个 MinIO,踩了一些坑,记录一下  ̄へ ̄

1. 基础部署

---
version: '3' 

services:
  minio:
    image: quay.io/minio/minio:RELEASE.2023-09-30T07-02-29Z
    command: server --console-address ":1631" --address ":1630" /data
    environment:
      MINIO_ROOT_USER: admin
      MINIO_ROOT_PASSWORD: adminpassword # 建议设置成非常、非常、非常长的密码!如果你也和我一样要部署 OIDC,非常建议这样设置!
      MINIO_BROWSER_REDIRECT_URL: https://s3.example.com/minio/ui # 反代后的管理界面 URL。很坑!必须要是 `/minio/ui` !不然会导致管理界面没法访问!
      MINIO_SERVER_URL: https://s3.example.com   # 反代后的 URL,建议不要带路径
      MINIO_REGION_NAME: region-hk    # 随便写
    healthcheck:
      test: ["CMD", "curl", "-f", "http://localhost:1630/minio/health/live"]
      interval: 30s
      timeout: 20s
      retries: 3
    volumes:
      - ./data:/data
    ports:
      - "127.0.0.1:1630:1630"
      - "127.0.0.1:1631:1631"
    restart: always

nginx 反代配置:

   # Allow special characters in headers
   ignore_invalid_headers off;
   # Allow any size file to be uploaded.
   # Set to a value such as 1000m; to restrict file size to a specific value
   client_max_body_size 0;
   # Disable buffering
   proxy_buffering off;
   proxy_request_buffering off;

   location / {
      proxy_set_header Host $http_host;
      proxy_set_header X-Real-IP $remote_addr;
      proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
      proxy_set_header X-Forwarded-Proto $scheme;

      proxy_connect_timeout 300;
      # Default is HTTP/1, keepalive is only enabled in HTTP/1.1
      proxy_http_version 1.1;
      proxy_set_header Connection "";
      chunked_transfer_encoding off;
      proxy_cache_convert_head off;

      proxy_pass http://127.0.0.1:1630/; # This uses the upstream directive definition to load balance
   }

   location /minio/ui/ {
      rewrite ^/minio/ui/(.*) /$1 break;
      proxy_set_header Host $http_host;
      proxy_set_header X-Real-IP $remote_addr;
      proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
      proxy_set_header X-Forwarded-Proto $scheme;
      proxy_set_header X-NginX-Proxy true;

      # This is necessary to pass the correct IP to be hashed
      real_ip_header X-Real-IP;

      proxy_connect_timeout 300;

      # To support websockets in MinIO versions released after January 2023
      proxy_http_version 1.1;
      proxy_set_header Upgrade $http_upgrade;
      proxy_set_header Connection "upgrade";
      # Some environments may encounter CORS errors (Kubernetes + Nginx Ingress)
      # Uncomment the following line to set the Origin request to an empty string
      proxy_set_header Origin '';
      proxy_cache_convert_head off;

      chunked_transfer_encoding off;

      proxy_pass http://127.0.0.1:1631/; # This uses the upstream directive definition to load balance
   }

折腾反代可折腾死我了,特别是后台管理界面一定得是 /minio/ui,不然会没法访问!折腾了半天才搞定,可气死我了 qaq

基础部署完成后,应该已经有了一个可以正常使用的 MinIO 了。

如果将 Bucket 设置为 public,访问 https://s3.example.com/bucketname/filename.ext 即可访问到文件。

如果要设置公共读私有写,可以在 Settings/Administrator/Buckets/<bucketname>/Anonymous 中,Add Access Rule,设置好 PrefixAccessreadonly 即可。需要注意的是,以这种方式设置,外部拥有列出桶内文件的权限。建议再到 Summary 一栏中,修改 Access Policy,删掉 ListBucket 权限喵

2. Keycloak Integration

MinIO 内部账户不支持 2FA,都 3202 年了,账户还没有 2FA 就显得有点不礼貌了。但是集成外部 OIDC Provider,就可以利用外部 OIDC Provider 实现 2FA 和其他的权限管理功能,非常的优雅!

参考文章:https://www.cnblogs.com/Chinori/p/17091169.html
Web Archive: https://web.archive.org/web/20231004100420/https://www.cnblogs.com/Chinori/p/17091169.html

1. 准备

啊啦……至少得先有 Keycloak 和 MinIO 吧?

2. 新建 Realm & Client

  1. 视情况而定,可以新建一个 Realm。非常不建议使用 master Realm!会有很多权限上的问题~!如果不新建 Realm 的话,也可以使用其他的非 master 的 Realm。~
  2. 然后新建 Client。举例,命名为 minio-1

    • 开启 Client AuthorizationAuthorization
    • Root URL 设置为 https://s3.example.comHome URL 设置为 https://s3.example.com/minio/uiValid Redirect URLS 设置为 https://s3.example.com/minio/ui/oauth_callback

3. Policy & Role 设置

  1. 在 MinIO 中,打开 Policies,添加一个 Policy,名字自定;或者记下想要的 Policy 的名字。Example: 如果想要赋予一个 Keycloak 账户管理员权限,则在本步中先记下 Policy 名字:consoleAdmin
  2. 在 Keycloak 中,打开 Client:minio-01,切换到 Roles,点击 Create Role,名字与 MinIO 中的 Policy 相对应。

4. Client 配置

  1. 在 Realm 设置中,创建 Client Scope,名字自定,如 minio-policy
  2. 打开这个 Client Scope,在 Scope 选项卡下,点 Assign Role,找到前面添加的 Role,如 consoleAdmin
  3. 切换到 Mappers,添加 Mapper。Mapper type 选 User Client Role,名字随便,然后把几个开关全部打开。
  4. 切换到 Client:minio-01,切换到 Client Scopes,Add Client Scope,添加上一步添加的 Client Scope。

5. 用户组配置

  1. 在 Realm 设置中,创建一个用户组,如 minio-consoleadmin
  2. 打开这个用户组,Role Mapping,添加上文提到的 Role。
  3. 添加用户到组。

6. 配置 MinIO OpenID

  1. 打开 MinIO,Settings/Administrator/Identity/OpenID
  2. 按 Create Configuration
  3. 配置如下描述
KeyValue
Name随便
Config URLhttps://oauth.example.com/realms/<realm-name>/.well-known/openid-configuration 老版本的 Keycloak 好像不一样
Client IDExample: minio-01
Client Secret在 Keycloak 中打开相应 Client,在 Credentials 选项卡中,拷贝 Client secret 即可
Redirect URI很坑!一定要设置为 https://s3.example.com/minio/ui/oauth_callback!不然回调的时候会回调到根目录导致出错
其他的随您发挥了喵

7. 安全性

把 root 用户的用户名和密码设置成随机长字符串,不要让别人登录上了。

3. 一些问题

  • 遇到了一些奇奇葩葩的错误,像新建不了桶之类的…好像是版本太旧会导致这个问题,换了个最新镜像就行了,建议使用最新的镜像
  • 显示的储存空间和实际的不一样:可能是因为有文件没上传成功,在上传缓存里存着,过了 24 小时就会自己清除了
  • 日志等级?啊,这玩意没有控制台日志输出的说…不过可以在网页管理界面里,/Settings/Administrator/Monitoring/Logs 里打开日志记录
评论区
头像
文章目录