本文详解MinIO对象存储的部署配置、S3兼容API使用、分布式集群搭建等实践。
前言
对象存储越来越重要:
- 海量非结构化数据存储
- 图片、视频、备份文件
- 云原生应用标配
MinIO是最流行的开源对象存储:
- S3 API 100%兼容
- 高性能(单节点可达100Gbps)
- 部署简单,轻量级
- 支持分布式、纠删码
用MinIO搭建私有云存储,成本低、速度快。
一、单节点部署
1.1 Docker部署
docker run -d\--name minio\-p9000:9000\-p9001:9001\-eMINIO_ROOT_USER=admin\-eMINIO_ROOT_PASSWORD=admin123456\-v /data/minio:/data\minio/minio server /data --console-address":9001"1.2 Docker Compose部署
# docker-compose.ymlversion:'3.8'services:minio:image:minio/minio:latestcontainer_name:minioports:-"9000:9000"# API端口-"9001:9001"# 控制台端口environment:MINIO_ROOT_USER:adminMINIO_ROOT_PASSWORD:admin123456volumes:-./data:/datacommand:server /data--console-address ":9001"restart:unless-stoppedhealthcheck:test:["CMD","curl","-f","http://localhost:9000/minio/health/live"]interval:30stimeout:20sretries:3docker compose up -d1.3 访问MinIO
控制台:http://服务器IP:9001 API地址:http://服务器IP:9000 用户名:admin 密码:admin123456二、基本操作
2.1 创建Bucket
控制台 → Buckets → Create Bucket - Bucket Name: my-bucket - Versioning: 按需开启 - Object Locking: 按需开启2.2 mc客户端
# 安装mc客户端wgethttps://dl.min.io/client/mc/release/linux-amd64/mcchmod+xmcmvmc/usr/local/bin/# 配置别名mcaliassetmyminio http://192.168.1.100:9000 admin admin123456# 查看bucketmclsmyminio# 创建bucketmcmb myminio/my-bucket# 上传文件mccpmyfile.txt myminio/my-bucket/# 下载文件mccpmyminio/my-bucket/myfile.txt ./# 查看bucket内容mclsmyminio/my-bucket/# 删除文件mcrmmyminio/my-bucket/myfile.txt# 同步目录mcmirror ./local-folder myminio/my-bucket/2.3 S3 API使用
Python示例:
importboto3frombotocore.clientimportConfig# 创建S3客户端s3=boto3.client('s3',endpoint_url='http://192.168.1.100:9000',aws_access_key_id='admin',aws_secret_access_key='admin123456',config=Config(signature_version='s3v4'))# 创建buckets3.create_bucket(Bucket='my-bucket')# 上传文件s3.upload_file('local_file.txt','my-bucket','remote_file.txt')# 下载文件s3.download_file('my-bucket','remote_file.txt','downloaded_file.txt')# 列出对象response=s3.list_objects_v2(Bucket='my-bucket')forobjinresponse.get('Contents',[]):print(obj['Key'])# 生成预签名URL(临时访问链接)url=s3.generate_presigned_url('get_object',Params={'Bucket':'my-bucket','Key':'remote_file.txt'},ExpiresIn=3600# 1小时有效)print(url)Java示例:
importsoftware.amazon.awssdk.auth.credentials.AwsBasicCredentials;importsoftware.amazon.awssdk.auth.credentials.StaticCredentialsProvider;importsoftware.amazon.awssdk.regions.Region;importsoftware.amazon.awssdk.services.s3.S3Client;importsoftware.amazon.awssdk.services.s3.model.*;importjava.net.URI;publicclassMinioExample{publicstaticvoidmain(String[]args){S3Clients3=S3Client.builder().endpointOverride(URI.create("http://192.168.1.100:9000")).credentialsProvider(StaticCredentialsProvider.create(AwsBasicCredentials.create("admin","admin123456"))).region(Region.US_EAST_1).build();// 列出bucketListBucketsResponseresponse=s3.listBuckets();response.buckets().forEach(bucket->System.out.println(bucket.name()));}}三、权限管理
3.1 创建用户
控制台 → Identity → Users → Create User - Access Key: readonly-user - Secret Key: readonly123456 - Policies: readonly(只读)3.2 内置策略
| 策略 | 权限 |
|---|---|
| readonly | 只读所有bucket |
| readwrite | 读写所有bucket |
| diagnostics | 诊断权限 |
| writeonly | 只写权限 |
3.3 自定义策略
{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Action":["s3:GetObject","s3:PutObject","s3:DeleteObject"],"Resource":["arn:aws:s3:::my-bucket/*"]},{"Effect":"Allow","Action":["s3:ListBucket"],"Resource":["arn:aws:s3:::my-bucket"]}]}3.4 Bucket策略(公开访问)
{"Version":"2012-10-17","Statement":[{"Effect":"Allow","Principal":"*","Action":["s3:GetObject"],"Resource":["arn:aws:s3:::public-bucket/*"]}]}四、分布式集群
4.1 集群架构
┌─────────┐ ┌─────────┐ ┌─────────┐ ┌─────────┐ │ Node1 │ │ Node2 │ │ Node3 │ │ Node4 │ │ /data1 │ │ /data1 │ │ /data1 │ │ /data1 │ │ /data2 │ │ /data2 │ │ /data2 │ │ /data2 │ └─────────┘ └─────────┘ └─────────┘ └─────────┘ │ │ │ │ └───────────┼───────────┼───────────┘ │ 纠删码分布存储 (最多允许N/2节点故障)4.2 Docker Compose集群
# docker-compose.ymlversion:'3.8'services:minio1:image:minio/minio:latesthostname:minio1volumes:-./data1-1:/data1-./data1-2:/data2environment:MINIO_ROOT_USER:adminMINIO_ROOT_PASSWORD:admin123456command:server--console-address ":9001" http://minio{1...4}/data{1...2}healthcheck:test:["CMD","curl","-f","http://localhost:9000/minio/health/live"]interval:30stimeout:20sretries:3minio2:image:minio/minio:latesthostname:minio2volumes:-./data2-1:/data1-./data2-2:/data2environment:MINIO_ROOT_USER:adminMINIO_ROOT_PASSWORD:admin123456command:server--console-address ":9001" http://minio{1...4}/data{1...2}minio3:image:minio/minio:latesthostname:minio3volumes:-./data3-1:/data1-./data3-2:/data2environment:MINIO_ROOT_USER:adminMINIO_ROOT_PASSWORD:admin123456command:server--console-address ":9001" http://minio{1...4}/data{1...2}minio4:image:minio/minio:latesthostname:minio4volumes:-./data4-1:/data1-./data4-2:/data2environment:MINIO_ROOT_USER:adminMINIO_ROOT_PASSWORD:admin123456command:server--console-address ":9001" http://minio{1...4}/data{1...2}nginx:image:nginx:latestports:-"9000:9000"-"9001:9001"volumes:-./nginx.conf:/etc/nginx/nginx.conf:rodepends_on:-minio1-minio2-minio3-minio44.3 Nginx负载均衡配置
# nginx.conf events { worker_connections 1024; } http { upstream minio_api { server minio1:9000; server minio2:9000; server minio3:9000; server minio4:9000; } upstream minio_console { server minio1:9001; server minio2:9001; server minio3:9001; server minio4:9001; } server { listen 9000; location / { proxy_pass http://minio_api; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } } server { listen 9001; location / { proxy_pass http://minio_console; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; } } }五、跨站点同步
5.1 场景
需求: - 总部MinIO存储主数据 - 分部MinIO作为副本或缓存 - 两地网络不通5.2 组网方案
使用组网软件(如星空组网)打通网络:
┌─────────────────────────────────────────────────────────┐ │ 组网虚拟局域网 │ │ │ │ ┌──────────────────┐ ┌──────────────────┐ │ │ │ 总部MinIO │ │ 分部MinIO │ │ │ │ 10.10.0.1 │←────→│ 10.10.0.2 │ │ │ │ :9000 │ 同步 │ :9000 │ │ │ └──────────────────┘ └──────────────────┘ │ │ │ └─────────────────────────────────────────────────────────┘5.3 配置站点复制
# 在总部MinIO配置mcadmin replicateaddmyminio http://10.10.0.2:9000\--access-key admin --secret-key admin123456# 或使用mc mirror同步mcmirror --watch myminio/my-bucket remote-minio/my-bucket5.4 客户端访问就近节点
# 应用根据网络环境选择MinIO节点MINIO_ENDPOINTS={'headquarters':'http://10.10.0.1:9000','branch':'http://10.10.0.2:9000'}# 使用就近节点endpoint=MINIO_ENDPOINTS.get(current_location,MINIO_ENDPOINTS['headquarters'])六、与应用集成
6.1 Spring Boot集成
<!-- pom.xml --><dependency><groupId>io.minio</groupId><artifactId>minio</artifactId><version>8.5.7</version></dependency>@ConfigurationpublicclassMinioConfig{@BeanpublicMinioClientminioClient(){returnMinioClient.builder().endpoint("http://192.168.1.100:9000").credentials("admin","admin123456").build();}}@ServicepublicclassFileService{@AutowiredprivateMinioClientminioClient;publicStringuploadFile(MultipartFilefile,Stringbucket){StringfileName=UUID.randomUUID()+"_"+file.getOriginalFilename();minioClient.putObject(PutObjectArgs.builder().bucket(bucket).object(fileName).stream(file.getInputStream(),file.getSize(),-1).contentType(file.getContentType()).build());returnfileName;}publicInputStreamdownloadFile(Stringbucket,StringfileName){returnminioClient.getObject(GetObjectArgs.builder().bucket(bucket).object(fileName).build());}}6.2 文件直传(前端直传)
// 1. 后端生成预签名URL// 2. 前端直接上传到MinIOasyncfunctionuploadFile(file){// 获取预签名URLconstresponse=awaitfetch('/api/presigned-url',{method:'POST',body:JSON.stringify({filename:file.name})});const{url}=awaitresponse.json();// 直接上传到MinIOawaitfetch(url,{method:'PUT',body:file,headers:{'Content-Type':file.type}});}七、监控与告警
7.1 Prometheus指标
# 启用Prometheus指标mcadmin prometheus generate myminio# 配置Prometheusscrape_configs: - job_name: minio metrics_path: /minio/v2/metrics/cluster static_configs: - targets:['192.168.1.100:9000']7.2 关键指标
| 指标 | 说明 |
|---|---|
| minio_bucket_usage_total_bytes | Bucket使用量 |
| minio_node_disk_free_bytes | 磁盘剩余空间 |
| minio_s3_requests_total | 请求总数 |
| minio_s3_requests_errors_total | 错误请求数 |
八、总结
MinIO对象存储要点:
- 部署简单:Docker一行命令
- S3兼容:无缝替换AWS S3
- 分布式:纠删码保证数据安全
- 权限管理:IAM策略控制
- 跨站点:组网后同步复制
使用场景:
☑ 图片/视频存储 ☑ 日志归档 ☑ 数据备份 ☑ AI训练数据集 ☑ 云原生应用存储后端参考资料
- MinIO官方文档:https://min.io/docs/minio/linux/index.html
- MinIO GitHub:https://github.com/minio/minio
- MinIO SDK文档:https://min.io/docs/minio/linux/developers/minio-drivers.html
💡建议:生产环境至少4节点集群,启用纠删码。单节点仅用于开发测试。