Reputation:
I am using React-Redux-Express, and I'm trying to upload an image with express-fileupload
. Here is my logic for uploading images in my Express server:
In my Express route I do this with Sequelize
router.put('/:id', function(req, res, next) {
models.Projects.update(
{
title: req.body.title,
img: req.body.img,
description: req.body.description,
},
{
returning: true,
plain: true,
where: {
id: req.params.id,
},
}
)
.then(() => {
if (req.files) {
req.files.imgFile.mv(toRelative(req.body.img), function(err) {
if (err) {
throw new Error('Image saving failed');
}
});
}
})
.then(() => {
models.Projects.findById(req.params.id).then((result) => {
return res.send({
Project: result,
});
});
})
.catch((error) => {
return res.send(String(error));
});
});
The problem is that the last then
is triggered before req.files.imgFile.mv
method is finished moving the image, so the React input component can't find it in the frontend.
Does anyone know how can I create a promise inside the first then
, so only when req.files.imgFile.mv
is finished moving the image the second is triggered?
Thanks!
Upvotes: 0
Views: 134
Reputation: 370799
The general idea when you have something callback-based rather than Promise-based is to explicitly construct a Promise so it can be used in the larger Promise chain:
.then(() => {
if (!req.files) return; // resolve immediately if there are no files
return new Promise((resolve, reject) => {
req.files.imgFile.mv(toRelative(req.body.img), function(err) {
if (err) return reject('Image saving failed');
resolve();
});
});
})
But, in this case, it would be easier to omit the callback function to force req.files.imgFile.mv(
returns a Promise
itself:
.then(() => {
// if there are files, then the outer Promise chain will wait
// for the returned Promise to resolve before continuing with the next .then:
if (req.files) return req.files.imgFile.mv(toRelative(req.body.img));
})
Upvotes: 5