web-dev-qa-db-ja.com

multerを使用して複数のファイルをアップロードしますが、異なるフィールドからアップロードしますか?

複数のファイルタイプフィールドのファイルをmulterで受け入れるにはどうすればよいですか?

Node.jsのmulterを使用して単一のファイルをアップロードする次のコードがあります。

var storage =   multer.diskStorage({
  destination: function (req, file, callback) {
    callback(null, './public/uploads');
  },
  filename: function (req, file, callback) {
    callback(null, file.fieldname + '-' + Date.now());
  }
});

var upload = multer({ storage : storage });

app.post('/rest/upload', upload.array('video', 1), function(req, res, next){
    ...
}

次のフォームから、条件ではビデオフィールドのみに値があります(両方を指定すると、「予期しないフィールド」エラーが発生します)。

<form action="/rest/upload" method="post" enctype="multipart/form-data">
   <label>Video file: </label> <input type="file" name="video"/> 
   <label>Subtitles file: </label> <input type="file" name="subtitles"/> 
   <input type="submit"/>
</form>

ドキュメントからこれにどのように取り組むかは明らかではありませんか?任意の提案をいただければ幸いです。ところで、私は成功せずに次のパラメーターのバリエーションを試しました:

app.post('/rest/upload', [upload.array('video', 1), upload.array('subtitles', 1)] ...
app.post('/rest/upload', upload.array('video', 1), upload.array('subtitles', 1), ...
app.post('/rest/upload', upload.array(['video', 'subtitles'], 1),  ...
14
Andre M

あなたが欲しいのは upload.fields()

app.post('/rest/upload',
         upload.fields([{
           name: 'video', maxCount: 1
         }, {
           name: 'subtitles', maxCount: 1
         }]), function(req, res, next){
  // ...
}
26
mscdex

multer()。any() を使用しようとしましたか?

3
Roman Dibikhin

異なるページにある別々のフォームの2つのフィールドからMulter Uploadファイルを使用するこの例では、再開と画像の2つのフィールドがあります。 1つの形式で再開し、別の形式で画像を再開します。どちらも別のページにあります。最初の依存関係のインポート

const path = require('path'); // for getting file extension
const multer = require('multer'); // for uploading files
const uuidv4 = require('uuidv4'); // for naming files with random characters

FileStorageおよびfileFilterを定義しますconst fileStorage = multer.diskStorage({destination:(req、file、cb)=> {//ファイルの保存先の設定

    if (file.fieldname === "resume") { // if uploading resume
      cb(null, 'resumes');
    } else { // else uploading image
      cb(null, 'images');
    }
  },
  filename: (req, file, cb) => { // naming file
    cb(null, file.fieldname+"-"+uuidv4()+path.extname(file.originalname));
  }
});

const fileFilter = (req, file, cb) => {
  if (file.fieldname === "resume") { // if uploading resume
    if (
      file.mimetype === 'application/pdf' ||
      file.mimetype === 'application/msword' ||
      file.mimetype === 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'
    ) { // check file type to be pdf, doc, or docx
      cb(null, true);
    } else {
      cb(null, false); // else fails
    }
  } else { // else uploading image
    if (
      file.mimetype === 'image/png' ||
      file.mimetype === 'image/jpg' ||
      file.mimetype === 'image/jpeg'
    ) { // check file type to be png, jpeg, or jpg
      cb(null, true);
    } else {
      cb(null, false); // else fails
    }
  }
};

Multerのミドルウェア

app.use(
  multer(
    { 
      storage: fileStorage, 
      limits:
        { 
          fileSize:'2mb' 
        }, 
      fileFilter: fileFilter 
    }
  ).fields(
    [
      { 
        name: 'resume', 
        maxCount: 1 
      }, 
      { 
        name: 'image', 
        maxCount: 1 
      }
    ]
  )
);

そして、あなたのルートを呼び出します。セキュリティのために、これに加えてcsrf保護または認証を追加する必要がある場合があります。しかし、これはうまくいくはずです。

1