Can't access fields of MongoDB document in Node.Js - node.js

I'm using mongoose and express on my nodejs project.
Trying to get the data from here
app.get('/offers/:id', (req, res) =>{
//store the id from the url
var id = req.params.id;
//just a placeholder
var data = {title: "title", description:"description"};
//store the returned object in a variable
var oop = offers.findById(id, function (err, user) {
if(err){
return err;
}else{
title = user.title;
description = user.description;
this.obj = {
title:title,
description:description
}
console.log(obj)
return obj;
}
} );
console.log(oop)
res.render('single', {data:data});
});
so my idea is to grab the post id from the url, find it in the database, then display the title and description in the corresponding place on the ejs template, but for some reason I can't access the returned data, and what I get is a long list of objects that belongs to mongodb, without the presence of "title" or "description"

Try this, your code has couple of issues & also you need use .lean() to get raw Js objects rather than mongoDB documents :
app.get('/offers/:id', (req, res) => {
//store the id from the url
var id = req.params.id;
//just a placeholder
var data = { title: "title", description: "description" };
//store the returned object in a variable
offers.findById(id).lean().exec((err, user) => {
if (err) {
console.log(err);
res.send(err)
} else {
data.title = user.title;
data.description = user.description;
this.obj = {
title: title,
description: description
}
console.log(obj);
res.render('single', { data: data });
// (Or) res.render('single', { data: obj });
}
});
});

I just modified your code and added comments (all starting with "***").
app.get('/offers/:id', (req, res) =>{
//store the id from the url
var id = req.params.id;
//just a placeholder
var data = {title: "title", description:"description"};
//store the returned object in a variables
// var oop = ***no need for this, the data you want will be in the user variable.
offers.findById(id, function (err, user) {
if(err){
return err;
}else{
// ***this needs to be changed to...
// title = user.title;
// description = user.description;
// ***that...
data.title = user.title;
data.description = user.description;
// ***what's that for??
// this.obj = {
// title:title,
// description:description
// }
// ***this needs to be inside mongoose's callback
res.render('single', {data:data});
}
});
});

Related

buffer Array to String and then saving in directory

I am new to React and I am currently facing an issue that I have API written in Express.js in which I am receiving ur fetching whatever it is called an image uploaded from mobile device in a buffer Array and now I have to convert it into string and add extension to it (let say .jpg) and store it into MongoDB Atlas here is my API written in Express ```module.exports.submitFormDataFile = async (req, res) => {
var hkeyArray = [];
const body = req.body;
const collection_name = body.form_collect_name;
const formstructureresult = await FormsStructure.findOne({
collection_name: collection_name
});
formstructureresult.formdata.forEach((eachData) => {
if (eachData.element === 'file') hkeyArray.push(eachData.hkey);
});
// console.log(hkeyArray)
hkeyArray.forEach((element) => {
//In this part I was supposed to convert it in string and save with extension
console.log(req.files[element].data);
});
if (body._id != '' && body._id != null) {
try {
const result = db.collection(
collection_name
);
const results = await result.findOne({
_id: mongoose.Types.ObjectId(body._id)
});
if (!results) {
res.status(200).json({
ERROR: 1,
MESSAGE: 'Invalid Record'
});
} else {
delete body._id;
var newvalues = { $set: body};
const resu = await result.updateOne(results, newvalues);
if (!resu) {
res.status(404).json({
ERROR: '1',
MESSAGE: 'Unable to update'
});
} else {
res.status(200).json({
SUCCESS: '1',
MESSAGE: 'Record Updated Successfully'
});
}
}
} catch (error) {
console.log(error, 'error');
}
}
};
As everything is dynamic so I am fetching hkey which are the name in MongoDB from a collection and fetching other collection based on req.body received and byteArray is also received from req.body and conversion of it into a string I have to update document as shown in the code
Probleum solved! In my case solution was simple I just changed the code accordingly
hkeyArray.forEach((element) => {
//In this part I was supposed to convert it in string and save with extension
var imagedata = req.files[element].data;
let buff = new Buffer.from(imagedata , 'base64');
fs.writeFile(`element+'.jpg'`,buff, function (err) {
if (err) throw err;
console.log('Saved!');
});
body[element] = element+'.jpg'
});

passing name in url in nodejs

The code which i have written takes id from url and then gives me the output.
api?category=4556 here 4556 is the id.
I have one Products controller having
product_name
price
category_id:i am passing category id manually from category generated.
and in category controller i have category_name.
here i want to get in this way
api?category=games
is there any way to do so.
exports.getProducts = function(req, res) {
// Use the Prod model to find all products
/*
Prod.find(function(err, prods) {
if (err)
res.send(err);
res.json(prods);
next();
});
*/
var cat=req.query.category;
var condition = {};
if (cat) {
condition.cat_id = cat;
}
Prod.find(condition).then(function(cat) {
res.json({cat});
})
.catch((err) => {
console.log('error', err);
res.status(500).send();
});
};
This code checks for the products having cat_id similar to the id provided by url as ?category=4556
i want to check it as ?category=games ,
if there is some way please help it would be great pleasure.thanks in advance
I found one answer and this really works using populate
var cat=req.query.category;
var condition = {};
if (cat) {
condition.cat_id = cat;
}
Prod.find(condition).populate('cat_id').then(function(cat) {
res.json({cat});
})
.catch((err) => {
console.log('error', err);
res.status(500).send();
});
};
and did a bit change in Schema
var ProductSchema=new mongoose.Schema({
name:String,
category:String,
price:Number,
cat_id:{
type : mongoose.Schema.Types.ObjectId,
ref : 'Cat'
}
});
// Export the Mongoose model
module.exports=mongoose.model('Prod',ProductSchema);
You will have to retrieve first the category ID from the name that was supplied in the query.
When no category with the supplied name is found, you may want to return an empty products dataset. I also make the assumption that category name are unique.
Example :
exports.getProducts = function(req, res) {
var categoryName = req.query.category;
var condition = {};
if (categoryName) {
condition.name = categoryName;
}
Category.find(condition).then(function(categories) {
if(categories.length === 0) return {}
return Product.find({ category_id: categories[0].id })
}).then(function(products) {
res.json(products);
}).catch((err) => {
console.log('error', err);
res.status(500).send();
});
};
If you want to find correspond to your category name rather than your id then you have to do only one change. Fetch category name from request query (as currently you are fetching id from request query). Rest your code will be same.
I am thinking that your category name is unique also.
exports.getProducts = function(req, res) {
// Use the Prod model to find all products
/*
Prod.find(function(err, prods) {
if (err)
res.send(err);
res.json(prods);
next();
});
*/
var cat=req.query.categoryName;
var condition = {};
if (cat) {
condition.cat_Name = cat;
}
Prod.find(condition).then(function(cat) {
res.json({cat});
})
.catch((err) => {
console.log('error', err);
res.status(500).send();
});
};
Hope it will work for you.
Thanks.

deleting route for an array in mongodB using node.js

var userSchema=new mongoose.Schema({
username:String,
password:String,
email:String,
tasks:[{
task: String
}]
});
This is my database schema.I want to create a delete route for the task to be removed.Can anyone tell me how to do so. Right now I am able to fetch the task id.
Here is link to my c9 project https://ide.c9.io/akspan12/newprojectworkspace
var express = require('express');
var router = express();
//I will take static values you can give dynamic values by using req.body
router.post('/Delete_User_Task',function(req,res){
var UserSchema = require('/path/to/Schema.js');//your schema model path
var username = 'akshansh123'; //assume it is present in db
//If you want to remove all task of this user and set one task as empty string your query and changes will be like below
var query = {
'username' :username
};
var changes = {
$set:{
'tasks':[{
task:''
}]
}
};
//If you completely want to remove json array tasks from user document than your query and changes will be like below
var query = {
'username' :username
};
var changes = {
$unset:{
'tasks':''
}
};
//If you want to remove particular task suppose say sleeping from user document than your query and changes will be like below
var query = {
'username' :username
};
var changes = {
$pull:{
'tasks':{
'task':'sleeping'
}
}
};
//If you want to remove selected tasks suppose say sleeping,walking,drinking from user document than your query and changes will be like below
var query = {
'username' :username
};
var changes = {
$pull:{
'tasks':{
'task':{
$in:['sleeping','walking','drinking']
}
}
}
};
UserSchema.update(query,changes,function(err,Result){
if(!err){
res.send('Successfully Removed tasks');
}else{
res.send('something went wrong');
console.log(err);
}
})
})
Hope this may solve your issue!!!
app.patch("/todo/:id",function(req,res){
User
.findById(req.user.id, function(err, foundUser) {
if(err){
req.flash("error",err.message);
console.log(err);
return res.redirect("back");
} if(!foundUser) {
req.flash("error","User not found");
return res.redirect("back");
} else {
foundUser.update({$pull: {tasks: {_id: req.params.id}}}, function(err) {
if(err) {
req.flash("error",err.message);
console.log(err);
return res.redirect("back");
} else {
req.flash("success","Task removed");
return res.redirect("/todo");
}
});
}
});
});
This is the delete route I used.

How to save nested array in MongoDB using Mongoose and NodeJS

Can anyone explain me how to save the nested array items into mongodb with mongoose and nodejs?.
Here is a schema I am using.
var demoSchema = ({
"r_id": Number,
"r_label": String,
"entity": [{
"d_label": String,
"d_type": String
}
]
})
And here is Nodejs function I am using to save the data into db
app.route("/mypages/rooms")
.post(function(req, res) {
var db = mongoOp.demo();
var response = {};
req.checkBody("r_id", "Enter a valid r_id address.").notEmpty();
req.checkBody("r_label", "Enter a valid label address.").notEmpty();
var errors = req.validationErrors();
if (errors) {
console.log(errors);
console.log(req.body);
res.status(500);
res.end('500 Server Error');
//res.render('addrooms',{flag:1});
return;
} else {
db.r_id = req.body.r_id;
db.r_label = req.body.r_label;
db.entity = req.body.entity;
db.save(function(err) {
if (err) {
findfromdb(req, res, 2); //own function for implementation purpose
} else {
findfromdb(req, res, 1);
}
});
//var middleVar = req.body.resources;
// console.log(middleVar[0].d_rgb);
}
});
set entity with array []
db.entity = [{}];
app.route("/mypages/rooms")
.post(function(req, res) {
var db = mongoOp.demo();
var response = {};
req.checkBody("r_id", "Enter a valid r_id address.").notEmpty();
req.checkBody("r_label", "Enter a valid label address.").notEmpty();
var errors = req.validationErrors();
if (errors) {
console.log(errors);
console.log(req.body);
res.status(500);
res.end('500 Server Error');
//res.render('addrooms',{flag:1});
return;
} else {
db.r_id = req.body.r_id;
db.r_label = req.body.r_label;
db.entity = [{
"d_label": req.body.label_type,
"d_type": req.body.d_type
}];
db.save(function(err) {
if (err) {
findfromdb(req, res, 2); //own function for implementation purpose
} else {
findfromdb(req, res, 1);
}
});
//var middleVar = req.body.resources;
// console.log(middleVar[0].d_rgb);
}
});
The below operation adds the element label_type and d_type to entity array if they does not exist in the array, if they exists, then they won't be added
https://docs.mongodb.com/manual/reference/operator/update/addToSet/
Model.update(
query, // { _id: 1 }
{
$addToSet: {
"enity": {
"d_label": req.body.label_type,
"d_type": req.body.d_type
}
}
}
)
have a look at this answer
Pushing item to Mongodb collection array

How to Iterate over array using async and foreach

I am trying to create an api that will create a group with members in expressjs. This is how it works till now:
Make a post request with a JSON object in req.body, using which I will create a new group. If the members array of the req.body object contains member id, add it to the group members array, else create a new user and then add its id to the array.
Basically an existing user just gets added, new user will be created and then added. For this I need to loop through the members array in the req.body and check for an object.
But the code below doesn't seem to work properly. I am getting strange results for console.log(group_info.members);. I am expecting this to contain objects with id in an array, but getting random results. Something seems to be wrong in the foreach loop. Please help me figure it out.
var express = require('express');
var router = express.Router();
var Group = require('../models/GroupModel');
var User = require('../models/UserModel');
var async = require("async");
router.post('/', function (req, res, next) {
var group_members = [];
var group_info = req.body;
//see if a member object is sent, create user for that else just add the user id to group_members array
async.forEach(group_info.members, function (member, callback) {
if (typeof member == "object") {
//create new user and add the _id to members array
var user = new User(member);
user.save(function (err) {
if (err) return res.status(500).send(err);
var member_object = {id: user._id};
group_members.push(member_object);
}).then(callback);
} else {
var member_object = {id: member };
group_members.push(member_object);
callback();
}
}, function (err) {
//final call back
group_info.members = group_members; //replace the original array in request body with the new array of users
console.log(group_info.members);
var group = new Group(group_info);
group.save(function (err) {
if (err) return res.status(500).send(err);
res.json(group);
});
});
});
Looks like you made a mistake its eachSeries not forEach, so just replace :
async.forEach(group_info.members, function (member, callback)
with:
async.eachSeries(group_info.members, function (member, callback)
Update
As pointed out in the comments forEach is an alias for async each API, You can read the docs here,Thank You #megawac for pointing this out.
var group_members = [];
var group_info = req.body;
var todo = group_info.members.length;
var done = 0;
if(todo == 0)
{
return saveGroup(res, group_members);
}
else
{
group_info.members.forEach(function (member, index, array) {
if (typeof member == "object") {
//create new user and add the _id to members array
var user = new User(member);
user.save(function (err, savedObject) {
if (err || !savedObject)
{
return res.status(500).send(err);
}
else
{
var member_object = {id: savedObject._id};
group_members.push(member_object);
if(++done >= todo)
{
return saveGroup(res, group_info, group_members);
}
}
});
} else {
var member_object = {id: member };
group_members.push(member_object);
if(++done >= todo)
{
return saveGroup(res, group_info, group_members);
}
}
});
}
function saveGroup(res, group_info, group_members)
{
group_info.members = group_members; //replace the original array in request body with the new array of users
console.log(group_info.members);
var group = new Group(group_info);
group.save(function (err) {
if (err) return res.status(500).send(err);
res.json(group);
});
}

Resources