如何在Node.js中使用单个路由上传图像和视频到S3?

huangapple go评论187阅读模式
英文:

how can i upload images and video to s3 in one single route using nodejs

问题

这是我上传视频的方式:

  1. router.post('/vid', upload.array('files', 5), async (req, res) => {
  2. try {
  3. const video = new Video();
  4. video.url = [];
  5. req.files.forEach((file) => {
  6. video.url.push(file.location);
  7. });
  8. const savedVideo = await video.save();
  9. res.json({
  10. message: '视频上传成功',
  11. video: savedVideo
  12. });
  13. } catch (error) {
  14. }
  15. });

这是我上传图片的方式:

  1. router.post('/products', upload.array("photos", 10), async (req, res) => {
  2. try {
  3. let product = new Product();
  4. product.photos.push(...req.files.map(({ location }) => location));
  5. await product.save();
  6. } catch (error) {
  7. }
  8. });

这是我的中间件:

  1. const aws = require("aws-sdk");
  2. const multer = require("multer");
  3. const multerS3 = require("multer-s3");
  4. aws.config.update({
  5. secretAccessKey: process.env.AWSSecretKey,
  6. accessKeyId: process.env.AWSAccessKeyId,
  7. region: 'eu-north-1', // 更新为 'eu-north-1' 区域
  8. correctClockSkew: true
  9. });
  10. const s3 = new aws.S3();
  11. const upload = multer({
  12. storage: multerS3({
  13. s3: s3,
  14. bucket: 'ajibs',
  15. acl: 'public-read',
  16. metadata: (req, file, cb) => {
  17. cb(null, { fieldName: file.fieldname });
  18. },
  19. key: (req, file, cb) => {
  20. cb(null, Date.now().toString())
  21. }
  22. })
  23. })
  24. module.exports = upload;

如果想在一个路由中同时上传图片和视频,可以使用以下方式:

  1. router.post('/combined', upload.fields([{ name: 'photos', maxCount: 10 }, { name: 'files', maxCount: 5 }]), async (req, res) => {
  2. try {
  3. // 处理上传的图片和视频
  4. const video = new Video();
  5. const product = new Product();
  6. if (req.files['files']) {
  7. video.url = req.files['files'].map(file => file.location);
  8. await video.save();
  9. }
  10. if (req.files['photos']) {
  11. product.photos = req.files['photos'].map(file => file.location);
  12. await product.save();
  13. }
  14. res.json({
  15. message: '图片和视频上传成功',
  16. video: video,
  17. product: product
  18. });
  19. } catch (error) {
  20. }
  21. });

这个路由使用了upload.fields来处理不同类型的文件上传,可以上传多个文件,并根据文件类型分别处理。

英文:

this is how i upload videos

  1. router.post('/vid', upload.array('files', 5), async (req, res) => {
  2. try {
  3. const video = new Video();
  4. video.url = [];
  5. req.files.forEach((file) => {
  6. video.url.push(file.location);
  7. });
  8. const savedVideo = await video.save();
  9. res.json({
  10. message: 'Video uploaded successfully',
  11. video: savedVideo
  12. });
  13. } catch (error) {
  14. }
  15. });

this how i upload pictures

  1. router.post(`/products`, upload.array("photos", 10), async (req, res) => {
  2. try {
  3. let product = new Product();
  4. product.photos.push(...req.files.map(({
  5. location
  6. }) => location));
  7. await product.save();
  8. } catch (error) {
  9. }
  10. });

this is my middleware

  1. const aws = require("aws-sdk");
  2. const multer = require("multer");
  3. const multerS3 = require("multer-s3");
  4. aws.config.update({
  5. secretAccessKey: process.env.AWSSecretKey,
  6. accessKeyId: process.env.AWSAccessKeyId,
  7. region: 'eu-north-1', // Update the region to 'eu-north-1'
  8. correctClockSkew: true
  9. });
  10. const s3 = new aws.S3();
  11. const upload = multer({
  12. storage: multerS3({
  13. s3: s3,
  14. bucket: 'ajibs',
  15. acl: 'public-read',
  16. metadata: (req, file, cb) => {
  17. cb(null, { fieldName: file.fieldname });
  18. },
  19. key: (req, file, cb) => {
  20. cb(null, Date.now().toString())
  21. }
  22. })
  23. })
  24. module.exports = upload;

both video and picture upload works fine if i use it in seperate route
please how can i upload both pictures and videos in one route

if i do this

  1. upload.array(["photos","files"], 10)

i get this error

  1. MulterError: Unexpected field

please how can i go about this

答案1

得分: 2

以下是翻译好的部分:

这是一个工作示例,您需要做的是将数组更改为字段,以获取照片和视频,不要忘记在模式中添加照片名称。

英文:

this a working example ,what you'll need to do is change array to fields to get both photos and video, dont forget to add the photos name in your schema

  1. router.post('/media', upload.fields([{ name: 'videos', maxCount: 5 }, { name: 'photos', maxCount: 10 }]), async (req, res) => {
  2. try {
  3. const video = new Video();
  4. video.title = req.body.title;
  5. video.url = [];
  6. video.photos = [];
  7. // Process uploaded videos
  8. if (req.files['videos']) {
  9. req.files['videos'].forEach((file) => {
  10. video.url.push(file.location);
  11. });
  12. }
  13. // Process uploaded photos
  14. if (req.files['photos']) {
  15. req.files['photos'].forEach((file) => {
  16. video.photos.push(file.location);
  17. });
  18. }
  19. console.log(video);
  20. // Save the video to the database
  21. const savedVideo = await video.save();
  22. res.json({
  23. message: 'Media uploaded successfully',
  24. video: savedVideo
  25. });
  26. } catch (error) {
  27. console.error(error);
  28. res.status(500).json({
  29. error: 'An error occurred while uploading the media'
  30. });
  31. }
  32. });

huangapple
  • 本文由 发表于 2023年7月3日 03:34:59
  • 转载请务必保留本文链接:https://go.coder-hub.com/76600499.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定