Cannot read properties of undefined (reading 'path') - node.js

route file
const storage = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, './uploads');
},
filename: function (req, file, cb) {
cb(null, new Date().toISOString() + file.originalname);
},
});
const fileFilter = (req, file, cb) => {
// reject a file
if (file.mimetype === 'image/jpg' || file.mimetype === 'image/png') {
cb(null, true);
} else {
cb(null, false);
}
};
const upload = multer({
storage: storage,
limits: {
fileSize: 1024 * 1024 * 5,
},
fileFilter: fileFilter,
});
router.post('/hiring', upload.single('resume'), (req, res, next) => {
console.log(req.file);
const hiring = new Hiring({
_id: new mongoose.Types.ObjectId(),
username: req.body.username,
email: req.body.gender,
mobile: req.body.mobile,
resume: req.file.path,
});
hiring
.save()
.then((result) => {
console.log(result);
res.status(200).json({
message: 'Created user successfully',
createdUser: {
_id: result._id,
username: result.username,
email: result.email,
mobile: result.mobile,
resume: result.resume,
},
});
})
.catch((err) => {
console.log(err);
res.status(500).json({
error: err,
});
});
});
I am trying to post data in database through postman but it is getting error 'path undefined'. I tried to change folder path like './uploads/', '/uploads', 'uploads/' and 'uploads' but the problem is not solving.
error
TypeError: Cannot read properties of undefined (reading 'path')
please give the solution for this problem.

It appears req.file is undefined. which itself meant you are not uploading file via postman.
You have to attach file in postman with 'resume' as keyword after selecting mutlipart in body section.
check this screenshot
With dothttp
It would look like this
POST 'http://localhost:3000/hiring'
multipart(
'resume'< '<replace path to the resume here>',
)

Related

Req.body is Empty inside express router

I have this router and I'm using multer to store files. I need to varify is 'Key' Exists in the server. Only after that server will store the file.
router.post('/', (req, res) => {
console.log(req.body.key); // empty here
upload(req, res, async (err) => {
if (err) {
console.log(err);
res.send({ error: err.message });
} else {
console.log(req.body.key); //shows the key
store(req.file.filename, {filename: req.file.filename, downloaded: 0, key: req.body.key});
res.send({ success: true, downlink: req.file.filename});
}
});
});
let storage = multer.diskStorage({
destination: (req, file, cb) => cb(null, 'uploads/'),
filename: (req, file, cb) => {
const filename = `${uuid()}-${file.originalname}`;
cb(null, filename);
}
});
let upload = multer({
storage: storage,
limits: { fileSize: 15000000 },
}).single('file'); //name field name
How can I add a checkpoint to prevent Unauthorized file upload?
https://i.stack.imgur.com/gZAHE.png

Using multer when I upload an image it shows me a message that image has been successfully added but does not added to upload folder

Here's my code to upload and save image in database , when I do this
on postman it gives an error of 'undefined' but 'file uploaded
successfully' and neither did my image/file is stored in upload folder
//multerfile
const multer = require('multer');
const storage = multer.diskStorage({
destination: (req, file, cb) => {
cb(null, 'originalname');
},
filename: (req, file, cb) => {
cb(null, new Date().toISOString().replace(/:/g, '-') + '-' + file.originalname);
}
});
const filefilter = (req, file, cb) => {
if (file.mimetype === 'image/png' || file.mimetype === 'image/jpg'
|| file.mimetype === 'image/jpeg'){
cb(null, true);
}else {
cb(null, false);
}
}
const upload = multer({storage: storage, fileFilter: filefilter});
module.exports = {upload}
//imagedata model
const mongoose=require('mongoose');
const imageSchema=new mongoose.Schema({
fileName: {
type: String,
required: true
},
filePath: {
type: String,
required: true
},
fileType: {
type: String,
required: true
},
fileSize: {
type: String,
required: true
}
}, {timestamps: true});
module.exports=mongoose.model('imagedata', imageSchema);
//post controller
exports.uploadimage = async (req, res, next) => {
try{
const file= req.file;
console.log(file);
res.status(201).json({messsage:"file uploaded successfully"})
}catch(error){
res.status(400).send(error.message)
}
u have not specified the destination where u want to save the file
create a folder named uploads in ur project and make changes as I have mentioned below:
destination: (req, file, cb) => {
cb(null, 'uploads/originalname');
},

why image is saving as text file in node js

Here i'm trying to save the image in database using multer but image type is saving as a text format but not in .png , .jpeg, .jpg format,
PLease help me where i'm doing wrong thanks in advance
Schema:-
module.exports = mongoose => {
const Role = mongoose.model(
"role",
mongoose.Schema(
{
roleType : { type:String },
image: { type: String,
data: Buffer}
}
)
);
return Role;
};
controller (Creating an instance):-
exports.addRoleFields = async (req, res) => {
const rolesList = new Role ({
roleType : req.body.roleType,
roleImg : req.file.path,
});
rolesList
.save(rolesList)
.then(data => {
res.status(200).send({ data, statusCode: "200" });
})
.catch(err => {
res.status(500).send({
message: err.message || "Some error occurred while creating.",
statusCode: "500"
});
})
}
}
routes:-
module.exports = app => {
const multer = require("multer"),
storage = multer.diskStorage({
destination: function(req, file, cb) {
cb(null, 'uploads')
},
filename: function(req, file, cb) {
cb(null, file.fieldname + '-' + Date.now())
}
})
const uploadImg = multer({storage: storage}).single('image');
const roles = require("../controllers/roles.js");
var router = require("express").Router();
router.post("/addRole", uploadImg , roles.addRoleFields);
app.use('/api/roles', router);
};
I simply changed this
filename: function(req, file, cb) {
cb(null, file.fieldname + '-' + Date.now())
}
to
filename: function (req, file, cb) {
cb(null, file.originalname);
}
its working and saving the file
try this for mongodb client
const storage = multer.diskStorage({
destination: async function (req, file, cb) {
let path = 'uploads/' + req.body.path;
if (!fs.existsSync(path)) {
fs.mkdirSync(path, { recursive: true }, (err) => {
if (err) throw err;
});
}
await cb(null, path);
},
filename: function (req, file, cb) {
cb(null, req.body.filename)
}
});
var upload = multer({ storage: storage })
const router = express.Router();
// Upload Image
router.post("/upload", upload.single('image'), (req, res, next) => {
return res.json({
image: req.file.path
});
});
in this upload.single('image'), file should be the name in which formdata carries the file.
in your case,
router.post("/addRole", uploadImg('image'), (req, res)=>{
});
mongoose model
const imgSave = new mongoose.Schema({
img:{
data: Buffer,
contentType: String
}
});

How to put image into mongodb using node js

I want to put a profile image into the users collection in mongodb, and I'd like to retrieve this image when user fetch his profile.
var storage = multer.diskStorage({
destination: (req, file, cb) => {
cb(null, 'uploads/')
},
filename: (req, file, cb) => {
cb(null, file.fieldname + '-' + Date.now()+ path.extname(file.originalname));
}
});
var upload = multer({ storage: storage });
router.put('/user/profile/img/:email', upload.single('profileimg'), (req, res, next) => {
// console.log(req.file);
Users.findOneAndUpdate({ email: req.params.email }, req.file.filename).then(() => {
Users.findOne({ email: req.params.email }).then((resp, err) => {
res.send(resp);
})
})
})
Image is being saved in upload folder in my api but it's not saved in db.
The second parameter of the findOneAndUpdate function must be an object with the field to update and the value:
Users.findOneAndUpdate({ email: req.params.email }, { profileimg: req.file.filename }).then(...)
You can do it like this code below:
router.put('/user/profile/img/:email', upload.single('profileimg'), async (req, res, next) => {
try {
// check your file is uploaded
// check your field
console.log(req.file);
const result = await Users.findOneAndUpdate({ email: req.params.email }, {$set: { profileimage : req.file.filename}}, { returnOriginal: false})
res.send(result)
} catch(ex) {
res.status(500).send(ex.message);
}
})
Note: For this {$set: { profileimage : req.file.filename}}
profileimage : change with the field in your mongodb
req.file.filename: make sure to console.log(req.file) then, where the field you want to store, use it in here and change this example.
I hope it can help you.

file still uploads with multer even after failed form validation

I have a form for adding a product which lets a user input product name, description etc. and also allows an image upload.
In my app.js file which is my entry point, I have:
const fileStorage = multer.diskStorage({
destination: (req, file, cb) => {
cb(null, 'uploads');
},
filename: (req, file, cb) => {
cb(null, new Date().toISOString() + '-' + file.originalname);
}
});
const fileFilter = (req, file, cb) => {
if (
file.mimetype === 'image/png' ||
file.mimetype === 'image/jpg' ||
file.mimetype === 'image/jpeg'
) {
cb(null, true);
} else {
cb(null, false);
}
};
app.use(multer({ storage: fileStorage , fileFilter: fileFilter, limits: { fileSize: 100000} }).single('image'));
Here is my controller:
exports.postAddListing = (req, res, next) => {
const title = req.body.title;
const category = req.body.category;
const description = req.body.description;
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(422).render('account/add-listing', {
pageTitle: 'Add Item',
path: '/account/add-listing',
errorMessage: errors.array(),
successMessage: null,
oldInput: {
title: title,
description: description
}
});
}
const image = req.file;
const imageUrl = image.path;
const product = new Product({
title: title,
category: category,
description: description,
userId: req.user,
datePosted: Date.now(),
imageUrl: imageUrl
});
product.save()
.then(result => {
const successMessage = req.flash('success', 'Item sucessfully added');
res.redirect('/account/add-listing');
})
.catch(err => console.log(err));
};
I am using express-validator for form validation. The problem I have is that if I for example leave all fields empty but choose an image, validation will fire and I will get error messages but the image will still upload. If form validation fails I don't want the image to upload but not sure how to achieve that.

Resources