我正在尝试将图像上传到 s3 Bucket。并在网上尝试了很多解决方案,但我收到上述错误。我不想在本地存储图像,而是想将它们直接上传到 s3 存储桶。任何帮助将不胜感激。
这是Upload.js文件
const AWS = require('aws-sdk');
const Keys = require('../Config/dev');
const { v4: uuidv4 } = require('uuid');
const axios = require('axios').default;
const multer = require('multer');
const multerS3 = require('multer-s3');
const s3 = new AWS.S3({
accessKeyId: Keys.accessKeyId,
secretAccessKey: Keys.secretAccessKey,
region : 'ap-south-1'
});
var upload = multer({
storage: multerS3({
s3: s3,
bucket: 'thebucketname',
acl : "public-read",
metadata: function (req, file, cb) {
cb(null, {fieldName: file.fieldname});
},
key: function (req, file , cb){
cb(new Date().toISOString().replace(/[-T:\.Z]/g, "") + file.originalname);
}
})
});
module.exports = upload;
这是路由器代码
const express = require('express');
const Router = express.Router();
const controllers = require('../controllers/controllers.js');
const uploader = require('../controllers/Upload');
const singleUpload = uploader.single('img');
Router.post('/single-image',(req, res)=>{
singleUpload(req, res , (err)=>{
if(!req.file){
console.log(req.file);
}else
{
console.log(req.file);
return res.json({'imageUrl': req.file.location});
}
});
});
这就是我使用 postman 进行 api 请求的方式。我还在 postman 的 header 内将 Content-Type 设置为 Multipart/form-data 。当我这样做时,我收到 req.file 的错误“未定义”。
另外,如果我使用
app.use(multer({dest:'./public/uploads/'}).single('file'));
我的文件存储在“uploads”文件夹中,但随后出现错误“req.file.location undefined”,并且文件未上传到 aws。
最佳答案
首先,如果你想上传文件到s3而不是存储在你的服务器上,你可以store the uploaded file as an in-memory buffer而不是将其写入您的服务器然后上传到 s3。 注意:对于大文件或大量小文件,不建议使用这种内存方法,因为您需要确保您的服务器有足够的内存来处理上传。
然后您可以将缓冲区传递给 s3 上传函数。我对您显然使用过的名为 multer-s3
的软件包了解不多,所以我没有使用它。我已经为一组文件制作了它,但它也应该适用于单个文件。我将您的代码与我的一些代码结合起来,得出以下结果:
//aws-sdk for node
const AWS = require('aws-sdk');
AWS.config.update({ region: <your region here> });
//S3
const S3 = new AWS.S3({});
const express = require('express');
const Router = express.Router();
const controllers = require('../controllers/controllers.js');
const uploader = require('../controllers/Upload');
//import multer
const multer = require("multer");
//make multer ready for in-memory storage of uploaded file
const multerMemoryStorage = multer.memoryStorage();
const multerUploadInMemory = multer({
storage: multerMemoryStorage
});
//using multer.single as a middleware is what I prefer
Router.post('/single-image',multerUploadInMemory.single("filename"),async(req, res)=>{
try{
if(!req.file || !req.file.buffer){
throw new Error("File or buffer not found");
}
const uploadResult = await S3.upload({
Bucket: "yourBucketName",
Key: "WhateverKeynameYouWantToGive",
Body: req.file.buffer,
ACL: 'public-read'
}).promise();
console.log(`Upload Successful!`);
res.send({
message: "file uploaded"
})
}catch(e){
console.error(`ERROR: ${e.message}`);
res.status(500).send({
message: e.message
})
}
});
您可以首先使用 console.log(req.file)
来查看它是否未定义(它不应该是),然后您可以检查是否在文件。
此外,它在“警告”中说 here您永远不应该将 multer 添加为全局中间件,因此 app.use(multer({dest:'./public/uploads/'})
是禁忌。
关于node.js - 将文件上传到 aws 存储桶时,Multer 将 req.file 返回为未定义,并将 req.file.location 返回为位置未定义,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62147839/