Multer: Return promise when callback not provided

Created on 9 Nov 2015  路  6Comments  路  Source: expressjs/multer

In the example of custom error handling on the project page, it is

var upload = multer().single('avatar')

app.post('/profile', function (req, res) {
  upload(req, res, function (err) {
    if (err) {
      // An error occurred when uploading 
      return
    }

    // Everything went fine 
  })
})

I'm using ES7 async/await through Babel, and if the upload function returns a Promise when the error callback isn't provided, it would be possible to have something like

var upload = multer().single('avatar')

app.post('/profile', wrap(async function (req, res) {
  try {
    await upload(req, res);
    // Everything went fine
    console.log(req.file);
  } catch(err) {
    // An error occurred when uploading 
    return
  }
}));

Or at least make it possible to use along with packages like https://www.npmjs.com/package/thenify or https://www.npmjs.com/package/thenify-all. I tried but couldn't get it to work.

  var uploadsingle = require('thenify')(upload.single.bind(upload));
  await uploadsingle('file');  // It hangs at this statement

Most helpful comment

Can we reopen this please? The latest express package already supports Promises.

All 6 comments

You're almost there! This should work:

const pify = require('pify')
const multer = require('multer')

const upload = pify(multer().single('avatar'))

app.post('/profile', wrap(async function (req, res) {
  try {
    await upload(req, res)
    // Everything went fine
    console.log(req.file)
  } catch(err) {
    // An error occurred when uploading 
    return
  }
}))

Is this an acceptable solution?

_I think that pify and thenify works the same, whichever should work_

p.s.

How awesome would it be if express accepted a Request => Promise<Response>?

app.get('/', async req => { status: 200, body: 'test' })

Your solution works great, thanks!

Do you suppose you might end up returning a Promise (when a callback isn't provided) so that there would be no need to install the extra package (one less thing to install, update, etc).

How awesome would it be if express accepted a Request => Promise?

Just curious, in the example you gave, what's the purpose of the function being async, since there's no await?

At the moment, I think that including native Promise support is a bit out the scope for multer. We are still supporting Node.js 0.10 which doesn't have promises so including this support would mean including a promise polyfill.

Since Node.js core isn't supporting promises in core, you still need to include something like pyfi so I don't see this as a big deal.

This might change in the future, especially if we drop 0.10 support, or if there is a really strong demand for it.

Just curious, in the example you gave, what's the purpose of the function being async, since there's no await?

Making the function async makes it return a resolved promise instead of just a value. The code I posted is equivalent to this:

app.get('/', req => Promise.resolve({ status: 200, body: 'test' }))

Can we reopen this please? The latest express package already supports Promises.

Almost 4 years and promises would be awesome? Or did I miss something and there is a way?

Was this page helpful?
0 / 5 - 0 ratings