On my client, during registration, I am sending a "multipart/form-data" POST request via Axios which includes a single image Avatar file and separate text fields for email and password. The form data looks something like the following...
------WebKitFormBoundaryI99ssr3PqTpYzGeF
Content-Disposition: form-data; name="file"; filename="testFile.jpg"
Content-Type: image/jpeg
------WebKitFormBoundaryI99ssr3PqTpYzGeF
Content-Disposition: form-data; name="email"
blahblahblah@gmail.com
------WebKitFormBoundaryI99ssr3PqTpYzGeF
Content-Disposition: form-data; name="password"
abcdefg
------WebKitFormBoundaryI99ssr3PqTpYzGeF--
On my server, in the Multer diskStorage setup function I would like to do some data validation on the email and password fields and check my database to make sure the relevant user doesn't already exist before uploading the file to my uploads folder. Or else there would be a bunch of junk images uploaded that correspond to nothing (failed user registration requests or server errors).
I am running into the following problem and I am not sure how to solve it...
1. The req.body object is not being populated soon enough so I don't have access to the email and password field to test validation or findOrCreate a user in my database... this is clearly stated in the documentation itself, "Note that req.body might not have been fully populated yet. It depends on the order that the client transmits fields and files to the server"
2. It seems a bit odd having to stick all of my routing middleware function logic inside of the multer disk storage function. Before this, I had them all neat and tidy as separate functions following the typical (req, res, next) => {//do something... next()) workflow. Is there a better way to structure this or do I just have to shove it all into the Multer function to make sure the upload only goes through if necessary.
const storage = multer.diskStorage({
destination: async (req, file, cb) => {
var {email, password} = req.body;
//validate incoming email and password fields
var result = authSchema.validate({email: email, password: password});
if(result.error) {
cb(new Error('Validation Error in multer function!'));
return;
}
//Find or create user (image should only save to folder if a new user is created)
try {
var avatarSrc = `http://localhost:3001/public/avatarUploads/${file.filename}`;
var [user, created] = await User.findOrCreate({ where: { email: email }, defaults: { password: password, avatarSrc: avatarSrc } });
//Upload image to folder if new user is created
if(created) {
cb(null, './public/avatarUploads');
}
else {
cb(new Error('User already exists'));
return;
}
}
catch(error)
{
cb(new Error('Server error'));
return;
}
}
})