Minio
-MinIO是一个高性能、兼容S3的对象存储。
优势:
- 轻量
- 高性能:世界上速度最快的对象存储(官网说的,真的好牛逼)
- 部署简单
- Kubernetes可用
安装配置 MinIO
1. 下载 MinIO 服务
官方下载地址:[min.io/download]
- window 的这里=》:dl.min.io/server/mini…
- Linux 的这里=》:
# 下载minio到主文件夹
wget https://dl.min.io/server/minio/release/linux-amd64/minio
# 将minio设置为可执行权限
chmod +x minio
2. 启动 MinIO 服务
window:
我的文件目录是这样的,可以参考一下
- cmd 中执行命令
minio.exe server D:\code\my-minio\minio-data --console-address ":9001"
注意: D:\code\my-minio\minio-data替换成你的minio数据的文件夹
- 然后你会看到这样的启动信息
- minio API访问地址:http://127.0.0.1:9000
- minio控制台地址: http://localhost:9001
- 默认控制台账号密码:
-
RootUser: minioadmin
-
RootPass: minioadmin
-
开搞,打开控制台地址,输入账号密码:minioadmin,进入管理页面
Linux(centos 7)
- 在主文件夹目录创建一个minio-data文件夹
- 终端执行cd命令切换到当前目录下,然后执行下面的命令
#MINIO_ROOT_USER=控制台登录用户名 MINIO_ROOT_PASSWORD=控制台登录密码 ./minio(执行程序地址) server ./minio-data(minio数据存储地址) --console-address ":9001"(控制台启动端口)
MINIO_ROOT_USER=admin MINIO_ROOT_PASSWORD=password ./minio server ./minio-data --console-address ":9001"
后面的操作跟window一致啦~
3. 创建 Access Keys
- 点击右上角的按钮
- 然后就会出现创建界面
-
minio会自动生成accessKey和secretKey,像我这么懒的人当然就是什么配置都不动,直接点确认.如果想改成自己想要的字符串也行。
-
这个时候弹出个对话框,可以下载和复制,我这么懒,当然是直接将 credentials.json 下载到本地
-
打开一看,有这样的信息,留着等一下对接js用
{
"url": "http://localhost:9001/api/v1/service-account-credentials",
"accessKey": "O3UKQM4t5dDKJR7SsT1Q",
"secretKey": "3mllG17sXFP866iq4DafwxGnCSgXKIGT5w35FFXc",
"api": "s3v4",
"path": "auto"
}
4. 配置 Buckets
- 点击右上角创建Bucket
- 输入bucket名称resources(爱叫什么都行,我这里示例而已),直接确定
- 然后你就可以看到minio数据的文件夹里面就多了个resources
JS 接入
官网JS接入地址:min.io/docs/minio/…
1. 安装 minio,js 客户端
npm install --save minio
2. 创建 minio 客户端
const Minio = require('minio');
let minioClient;
function initMinio(host, port, useSSL = false, accessKey, secretKey, option = {}) {
minioClient = new Minio.Client({
endPoint: host, //主机域名或ip地址
port: port, //端口
useSSL: useSSL, //需要https访问就开启true,像我这样懒的就不开了
//配置accessKey secretKey
accessKey: accessKey,
secretKey: secretKey,
...(option || {})
});
}
3. 上传个文件
function uploadFile(bucketName, fileName, file, type) {
return new Promise((resolve, reject) => {
//设置文件类型
const metaData = {
// 'Content-Type': 'application/octet-stream'//二进制文件
// 'Content-Type': 'image/png' //图片
'Content-Type': type
};
minioClient.fPutObject(bucketName, fileName, file, metaData, function (err, objInfo) {
if (err) return reject(err);
resolve(objInfo);
});
});
}
文件将上传到 minio 数据的文件夹 resources/image-test.png
//objInfo
{
etag: '4ae15d293a07312b36f657b4fc679266',
versionId: 'c6e05d0c-1851-4977-ab83-736784a58338'
}
objInfo:etag 用于协商缓存的,有需要的话存一下。versionId 要在 bucket 配置 Current Status 开启才能用,可以实现历史版本文件。
- 点开Object Browser对象浏览器的时候发现文件就在那里
- 点击文件可以进行一些操作
- 如果没有开启历史版本,文件上传到同一个地址会覆盖掉旧的。
开启对象历史版本
- 打开文件夹配置,然后编辑Current Status,将弹框的Versioning Status勾选可用,然后就可以了
- 当你重复几次上传文件为同一个文件名的时候,就是该文件的不同历史版本。可以打开Object Browser对象浏览器的Object Versions查看
4. 访问文件
- 你打算使用文件地址
http://localhost:9000/resources/image-test.png
去访问的时候发现失败了
开放访问权限
- 点开 bucket 的 resources 文件夹配置 Anonymous 匿名访问
2. 添加一个访问设置,prefix 为/
(斜杆,意思是当前文件夹下的所有文件,如果要特定开放某个子目录就写对应文件夹名称),访问权限为 readonly。
然后那个文件地址就能可以访问到了!
注意:
-
这样开放文件夹访问权限是永久的。并且图片链接开启了协商缓存,第二次访问若未修改直接读取浏览器缓存。
-
默认访问的就是最新的文件,即便开启历史版本,只会显示最新。
-
如果需要访问特定版本文件,要加上 versionId,比如 http://localhost:9000/resources/image-test.png?versionId=2f71c0dc-4dee-463a-9510-12f8c9c0e652
如果不想文件公开访问,可以创建临时访问链接
function getTempUrl(bucketName, fileName, seconds, versionId) {
return new Promise((resolve, reject) => {
minioClient.presignedUrl(
'GET',
bucketName,
fileName,
seconds,
versionId ? { versionId: versionId } : {}, //如果没有开启历史版本,这行可以去掉,默认就是最新文件
function (err, presignedUrl) {
if (err) return reject(err);
resolve(presignedUrl);
}
);
});
}
返回一个临时链接,在有效时间内可以访问,过了时效就访问失败了。
http://127.0.0.1:9000/resources/image-test.png?versionId=2f71c0dc-4dee-463a-9510-12f8c9c0e652&X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=O3UKQM4t5dDKJR7SsT1Q%2F20240220%2Fus-east-1%2Fs3%2Faws4_request&X-Amz-Date=20240220T134902Z&X-Amz-Expires=1000&X-Amz-SignedHeaders=host&X-Amz-Signature=3b2898cbfdcf5426d07859c82ab94186133bd18b8ad840c70e7b111b7da21b59
5. 下载文件
function getFile(bucketName, fileName, filePath, versionId) {
return new Promise((resolve, reject) => {
minioClient.fGetObject(
bucketName,
fileName,
filePath,
versionId ? { versionId: versionId } : {}, //如果没有开启历史版本,这行可以去掉,默认就是最新文件
function (err) {
if (err) {
return reject(err);
}
console.log('getFile ok');
resolve();
}
);
});
}
6. 删除文件
function removeFile(bucketName, fileName, versionId) {
return new Promise((resolve, reject) => {
minioClient
.removeObject(
bucketName,
fileName,
versionId ? { versionId: versionId } : {} //如果没有开启历史版本,这行可以去掉,默认就是最新文件
)
.then((err) => {
if (err) {
reject(err);
return;
}
console.log('removeFile ok');
resolve();
});
});
}
- 如果有历史版本,但删除的时候没有指定版本,默认会删除掉最新的版本,历史版本还是可以访问的。
- 在Object Browser对象浏览器里面默认显示当前状态最新的文件,此时删除文件看不见,勾选show deleted objects就可以看到了。
- 查看该删除文件历史记录可以看到最新版本已经被删除,但历史版本还在。
- 已删除的某个版本文件虽然记录还在,却不可进行操作了。
彻底删除文件以及其历史版本
function removeAllFile(bucketName, fileName) {
return new Promise((resolve, reject) => {
//查找所有版本的文件
const stream = minioClient.listObjects(
bucketName,
fileName,
true, //找子目录
{ IncludeVersion: true } //包含历史版本
);
const files = [];
stream.on('data', function (obj) {
//查找到对应数据
files.push(obj);
});
stream.on('end', function (obj) {
//查找结束
// console.log(files);
//批量删除所有文件
minioClient.removeObjects(bucketName, files, function (e) {
if (e) {
return reject(e);
}
console.log('removeAllFile ok');
resolve();
});
});
stream.on('error', function (err) {
// console.log(err);
reject(err);
});
});
}
7.使用
const MinioUtil = require('./index.js');
const minioConfig = require('./credentials.json');
const file = './images/test.png'; //上传文件地址
const bucketName = 'resources';
const fileName = 'image-test.png'; //上传后的文件名
const filePath = './test11.png'; //下载文件地址
(async function () {
await MinioUtil.initMinio('127.0.0.1', 9000, false, minioConfig.accessKey, minioConfig.secretKey);
// console.log(await MinioUtil.uploadFile(bucketName, fileName, file, 'image/png'));//上传
// console.log(await MinioUtil.getTempUrl(bucketName, fileName, 10));//临时访问
// await MinioUtil.getFile(bucketName, fileName, filePath);//下载
// await MinioUtil.removeFile(bucketName, fileName);//删除单个
// await MinioUtil.removeAllFile(bucketName, fileName);//删除该文本全部历史版本
})();
总结
Minio配置很方便,功能真的好强大。还有更多惊喜操作可以看官方文档!
官方JS API文档:min.io/docs/minio/…
Github地址
原文链接:https://juejin.cn/post/7337533680237887542 作者:敲敲敲敲暴你脑袋