fenghuo/test-minio-config.js

262 lines
7.6 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#!/usr/bin/env node
/**
* MinIO配置测试脚本
* 基于用户提供的具体配置进行测试
*/
const { S3 } = require('@aws-sdk/client-s3');
const fs = require('fs');
const path = require('path');
async function testMinIOConfig() {
console.log('🔍 开始测试MinIO配置...\n');
// 用户提供的配置
const config = {
endpoint: 'http://localhost:9000',
region: 'us-east-1',
credentials: {
accessKeyId: '7Nt7OyHkwIoo3zvSKdnc',
secretAccessKey: 'EZ0cyrjJAsabTLNSqWcU47LURMppBW2kka3LuXzb',
},
forcePathStyle: true,
};
const bucketName = 'test123';
const uploadDir = '/opt/projects/nice/uploads';
console.log('📋 配置信息:');
console.log(` Endpoint: ${config.endpoint}`);
console.log(` Region: ${config.region}`);
console.log(` Bucket: ${bucketName}`);
console.log(` Upload Dir: ${uploadDir}`);
console.log(` Access Key: ${config.credentials.accessKeyId}`);
console.log(` Force Path Style: ${config.forcePathStyle}`);
console.log();
try {
const s3Client = new S3(config);
// 1. 测试基本连接和认证
console.log('📡 测试连接和认证...');
try {
const buckets = await s3Client.listBuckets();
console.log('✅ 连接和认证成功!');
console.log(`📂 现有存储桶: ${buckets.Buckets?.map((b) => b.Name).join(', ') || '无'}`);
} catch (error) {
console.log('❌ 连接失败:', error.message);
if (error.message.includes('ECONNREFUSED')) {
console.log('💡 提示: MinIO服务可能未运行请检查localhost:9000是否可访问');
} else if (error.message.includes('Invalid')) {
console.log('💡 提示: 检查访问密钥和密钥是否正确');
}
return false;
}
// 2. 检查目标存储桶
console.log(`\n🪣 检查存储桶 "${bucketName}"...`);
let bucketExists = false;
try {
await s3Client.headBucket({ Bucket: bucketName });
console.log(`✅ 存储桶 "${bucketName}" 存在并可访问`);
bucketExists = true;
} catch (error) {
if (error.name === 'NotFound') {
console.log(`❌ 存储桶 "${bucketName}" 不存在`);
console.log('🔧 尝试创建存储桶...');
try {
await s3Client.createBucket({ Bucket: bucketName });
console.log(`✅ 存储桶 "${bucketName}" 创建成功`);
bucketExists = true;
} catch (createError) {
console.log(`❌ 创建存储桶失败: ${createError.message}`);
return false;
}
} else {
console.log(`❌ 检查存储桶时出错: ${error.message}`);
return false;
}
}
if (!bucketExists) {
return false;
}
// 3. 检查上传目录
console.log(`\n📁 检查上传目录 "${uploadDir}"...`);
try {
if (!fs.existsSync(uploadDir)) {
console.log('📁 上传目录不存在,正在创建...');
fs.mkdirSync(uploadDir, { recursive: true });
console.log('✅ 上传目录创建成功');
} else {
console.log('✅ 上传目录存在');
}
} catch (error) {
console.log(`❌ 检查/创建上传目录失败: ${error.message}`);
}
// 4. 测试文件上传
console.log('\n📤 测试文件上传...');
const testFileName = `test-upload-${Date.now()}.txt`;
const testContent = `这是一个测试文件
创建时间: ${new Date().toISOString()}
用户: nice1234
MinIO测试成功`;
try {
await s3Client.putObject({
Bucket: bucketName,
Key: testFileName,
Body: testContent,
ContentType: 'text/plain',
Metadata: {
'test-type': 'config-validation',
'created-by': 'test-script',
},
});
console.log(`✅ 文件上传成功: ${testFileName}`);
} catch (error) {
console.log(`❌ 文件上传失败: ${error.message}`);
console.log('错误详情:', error);
return false;
}
// 5. 测试文件下载验证
console.log('\n📥 测试文件下载验证...');
try {
const result = await s3Client.getObject({
Bucket: bucketName,
Key: testFileName,
});
// 读取流内容
const chunks = [];
for await (const chunk of result.Body) {
chunks.push(chunk);
}
const downloadedContent = Buffer.concat(chunks).toString();
if (downloadedContent === testContent) {
console.log('✅ 文件下载验证成功,内容一致');
} else {
console.log('❌ 文件内容不一致');
return false;
}
} catch (error) {
console.log(`❌ 文件下载失败: ${error.message}`);
return false;
}
// 6. 测试分片上传
console.log('\n🔄 测试分片上传功能...');
const multipartKey = `multipart-test-${Date.now()}.dat`;
try {
const multipartUpload = await s3Client.createMultipartUpload({
Bucket: bucketName,
Key: multipartKey,
Metadata: {
'test-type': 'multipart-upload',
},
});
console.log(`✅ 分片上传初始化成功: ${multipartUpload.UploadId}`);
// 清理测试
await s3Client.abortMultipartUpload({
Bucket: bucketName,
Key: multipartKey,
UploadId: multipartUpload.UploadId,
});
console.log('✅ 分片上传测试完成并清理');
} catch (error) {
console.log(`❌ 分片上传测试失败: ${error.message}`);
return false;
}
// 7. 列出存储桶中的文件
console.log('\n📂 列出存储桶中的文件...');
try {
const listResult = await s3Client.listObjectsV2({
Bucket: bucketName,
MaxKeys: 10,
});
console.log(`✅ 存储桶中共有 ${listResult.KeyCount || 0} 个文件`);
if (listResult.Contents && listResult.Contents.length > 0) {
console.log('最近的文件:');
listResult.Contents.slice(-5).forEach((obj, index) => {
const size = obj.Size < 1024 ? `${obj.Size}B` : `${Math.round(obj.Size / 1024)}KB`;
console.log(` ${index + 1}. ${obj.Key} (${size})`);
});
}
} catch (error) {
console.log(`❌ 列出文件失败: ${error.message}`);
}
// 8. 清理测试文件
console.log('\n🧹 清理测试文件...');
try {
await s3Client.deleteObject({
Bucket: bucketName,
Key: testFileName,
});
console.log('✅ 测试文件清理完成');
} catch (error) {
console.log(`⚠️ 清理测试文件失败: ${error.message}`);
}
console.log('\n🎉 所有测试通过您的MinIO配置完全正确');
console.log('\n📝 配置摘要:');
console.log('- ✅ 连接正常');
console.log('- ✅ 认证有效');
console.log('- ✅ 存储桶可用');
console.log('- ✅ 文件上传/下载正常');
console.log('- ✅ 分片上传支持');
console.log('\n💡 您可以在应用中使用这些配置:');
console.log('STORAGE_TYPE=s3');
console.log(`UPLOAD_DIR=${uploadDir}`);
console.log(`S3_ENDPOINT=${config.endpoint}`);
console.log(`S3_REGION=${config.region}`);
console.log(`S3_BUCKET=${bucketName}`);
console.log(`S3_ACCESS_KEY_ID=${config.credentials.accessKeyId}`);
console.log('S3_SECRET_ACCESS_KEY=***');
console.log('S3_FORCE_PATH_STYLE=true');
return true;
} catch (error) {
console.log(`❌ 测试过程中发生未预期错误: ${error.message}`);
console.log('错误堆栈:', error.stack);
return false;
}
}
// 主函数
async function main() {
console.log('🚀 MinIO S3存储配置测试\n');
// 检查依赖
try {
require('@aws-sdk/client-s3');
} catch (error) {
console.log('❌ 缺少必要依赖 @aws-sdk/client-s3');
console.log('请运行: npm install @aws-sdk/client-s3');
process.exit(1);
}
const success = await testMinIOConfig();
if (success) {
console.log('\n✅ 测试完成MinIO配置正确可以正常使用');
process.exit(0);
} else {
console.log('\n❌ 测试失败:请检查上述错误并修复配置');
process.exit(1);
}
}
main().catch((error) => {
console.error('❌ 脚本执行失败:', error);
process.exit(1);
});