Mongoose findById returns the empty doc - node.js

I'm trying to implement CRUD operations using MEAN stack. I'm facing a problem on getting user by Id. It's showing the status true but it returns an empty document.
This is my model:
const userSchema = new mongoose.Schema({
fullName: {
type: String,
required: 'Full name can\'t be empty '
},
userName: {
type: String,
required: 'user name can\'t be empty ',
unique: true
},
email: {
type: String,
required: 'email can\'t be empty ',
unique: true
});
mongoose.model('User', userSchema);
in my controller:
const mongoose = require('mongoose');
const passport = require('passport');
var ObjectId = require('mongoose').Types.ObjectId;
const User = mongoose.model('User');
module.exports.getuser = (req, res, next) => {
if(!ObjectId.isValid(req.params.id))
return res.status(400).send(`No record with given id : ${req.params.id}`);
User.findById(req.params.id, (err, user) => {
if(!err){ res.status(200).json({status: true, user}); }
else{ console.log('Error in retriving User :' + JSON.stringify(err, undefined, 2)); }
});
}
This is the route:
router.get('/:id', jwtHelper.verifyJwtToken, ctrlUser.getuser);
while checking in the postman I'm getting status: true but it returns a blank document.
I'm not getting what's going on anyone please help.
Thanks in advance!!

There could be several reasons why you're not able to find and return a user. I'd go through this checklist to see what might be occurring:
When you define your schema the required field takes a boolean or a function, not a string. To be safe it would make sense to change your strings to true in order to make sure all new db records contain these fields. (https://mongoosejs.com/docs/schematypes.html#schematype-options)
When you import the model in your controller there is no need to call mongoose.model again; this step is performed in your model file. Make sure you're exporting the mongoose.model('User', userSchema) object in the model file/module and then do a normal const User = require(<pathToModelFile>); in the controller module.
If this still doesn't work...
You'll want to make sure your record is in fact saved in your db. Run a mongo shell in terminal by running $ mongo and use commands found here to use your db and search the User collection: https://docs.mongodb.com/manual/reference/mongo-shell/
This is how I would normally code my model and controllers (with routes):
Model file - Note you do need to require Mongoose
const mongoose = require('mongoose');
const userSchema = new mongoose.Schema({
fullName: {
type: String,
required: true
},
userName: {
type: String,
required: true,
unique: true
},
email: {
type: String,
required: true,
unique: true
});
module.exports = mongoose.model('User', userSchema);
Controller/Router -
const express = require('express');
const router = express.Router();
const mongoose = require('mongoose');
const passport = require('passport');
const User = require('User');
router.get('/:id', jwtHelper.verifyJwtToken, async (req, res) => {
try {
const user = await User.findById(req.params.id);
res.status(200).json({status: true, user});
} catch (e) {
res.status(400).json({err: e});
}
});
module.exports = router;

Related

how to reference a model in another model using mongoose?

I'm pretty new to node and mongoose, still learning a lot. Basically I am trying to create a forum page. I have a forumpost schema and I have recently added in a new field that I would like to show which user posted it. I have read other questions on this online and I was able to follow the code on there however mine is still not working. When i check my data in atlas it is still missing the new 'submitted by' field that I added. I have already deleted the 'collection' and have started over but it is still missing. Any help would be appreciated. Heres my models below as well as a screencap of how the data is being posted to the db.
**Post Form Schema**
const mongoose = require('mongoose');
const PostSchema = new mongoose.Schema({
title: {
type: String,
required: true
},
body: {
type: String,
required: true,
},
date: {
type: Date,
default: Date.now,
required: true,
},
submittedBy: { *(this is where I would like to get the user who submitted the form)*
type: mongoose.Schema.Types.ObjectId,
ref: 'User',
},
extraInfo: {
type: String,
default: 'Other info goes here',
}
})
const Post = mongoose.model('Post', PostSchema);
module.exports = Post;
**Users Form Schema**
const mongoose = require('mongoose');
const UserSchema = new mongoose.Schema({
name: {
type: String,
required: true
},
email: {
type: String,
required: true
},
password: {
type: String,
required: true
},
date: {
type: Date,
default: Date.now
}
});
const User = mongoose.model('User', UserSchema);
module.exports = User;
EDIT: heres my newpost route
const express = require('express');
const Post = require('../models/post');
const router = express.Router();
const {ensureAuthenticated} = require("../config/auth.js");
router.get('/', ensureAuthenticated, (req, res) => {
res.render('newPost')
})
router.post('/', ensureAuthenticated, (req, res) => {
const post = new Post(req.body);
console.log(req.body)
post.save()
.then((result) => {
res.redirect('/dashboard')
})
.catch((err) => {
console.log(err)
})
})
module.exports = router;
If I'm not mistaken, you validate if is authenticated with the "ensureAuthenticated" middleware (the user ID should be there) but when creating the "Post" you only do it with the body data.
It is something like this ( you should replace "userId" with your property name):
const post = new Post({ ...req.body, submittedBy: userId })

Getting error while adding record into mongodb using mongoose and Node.js

I am getting the following error while adding some record into mongodb.
Error:
User.create is not a function /--/ "TypeError: User.create is not a
function\n at module.exports.createUsers
Here I am sending some data from postman and my aim is add them into mongodb database. I am explaining my mongo connect file first.
mongo.js:
const mongoose = require('mongoose').Mongoose;
const config = require('../config/settings');
const { MONGO_DB } = require('../config/settings');
const mongooseInstance = new mongoose();
const url = `mongodb://${config.MONGO_USER}:${config.MONGO_PWD}#${config.MONGO_URL}/${MONGO_DB}`;
const options = {
useNewUrlParser: true,
useCreateIndex: true,
connectTimeoutMS: 5000000,
poolSize: 10000,
useUnifiedTopology: true
};
/*
1- Connect to mongo server
*/
mongooseInstance.connect(url, options, (err) => {
if(!err) {
console.log('Mongodb connection successed');
} else {
console.log('Error in DB connection:' + JSON.stringify(err, undefined, true));
}
})
module.exports = mongooseInstance;
The above file used to make connection to my mongodb. I am explaining my code below.
user.js:
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
const User = new Schema({
name: {type: String},
mobile: { type: String},
email: { type: String},
city: { type: String}
}, {
timestamps: {
CreatedAt: 'CreatedAt',
UpdatedAt: 'UpdatedAt'
},
collection : 'user'
});
module.exports = User;
The above file is my model file. my controller file is given below.
user-controller.js:
const User = require('../models/user');
/*
1- Add user.
*/
module.exports.createUsers = function (req, res,next) {
const data = req.body;
user = User.create(data);
if(!user) {
return res.status(400).json({ success: false, res: []}).end('');
} else {
return res.status(200).json({ success: true, res: user}).end('');
}
}
Here I am trying to create the record but getting the above issue. I need to add record to user collection. Please help me to resolve this issue.
You need to create a model first of your schema.
Simply create it with the following command and export the variable:
const userModel = mongoose.model('user', User);
module.exports = userModel;
In user.js change...
module.exports = User;
to...
module.exports = mongoose.model("User", User)
In your user.js file, you need to update module.exports = User with module.exports = mongoose.model("User", User). Because in Mongoose, models are defined by passing a Schema instance to mongoose.model.
Try to modify your modals' export statement as
const User = module.exports = mongoose.model('User', User);

schema.methods is not a function

I have been trying to create a method on my user schema in mongoose, however it keeps saying method is not a function and I have no idea why. I am fairly new to mongoose and express, and I'm pretty sure I have my files set up currently so I don't know what could be causing this issue. As a last attempt, I tried switching to arrow functions , but that didn't work either.
user routes file
const router = require("express").Router();
let user = require("../models/user_model");
const Joi = require("#hapi/joi");
// GET dreams
// POST dreams
// DELETE dreams
// UPDATE dreams
router.route("/").get((req, res) => {
console.log(user.addType());
res.send("hello this is a users page");
});
user model file
const mongoose = require("mongoose");
const Schema = mongoose.Schema;
const userSchema = new Schema(
{
username: {
type: String,
required: true,
unique: true,
trim: true,
min: 3
},
password: {
type: String,
trim: true,
required: true,
min: 6
}
},
{
timestamps: true
}
);
userSchema.methods.addTypes = function() {
console.log("woof");
};
userSchema.methods.joiValidate = data => {
let Joi = require("#hapi/joi");
const schema = {
username: Joi.string()
.min(6)
.required(),
password: Joi.string()
.min(6)
.required()
};
return schema.validate(data);
};
module.exports = mongoose.model("User", userSchema);
UPDATE! Other than having typo on your code, you also need to create an instance of your model ('user'). You cannot just call the function of the model.
let user = new user({ // Create an instance first
username: 'Tester',
password: '12345678'
})
console.log(user.addType())
you declared
addTypes()
Cheers

Mongoose populate not working for nested object

Client.js
const mongoose = require("mongoose");
var Schema = mongoose.Schema;
const clientSchema = new mongoose.Schema(
{
name: { type: String, required: true, default: "" },
}, {
timestamps: true
}
);
module.exports = mongoose.model("Client", clientSchema);
User.js
const mongoose = require("mongoose");
var Schema = mongoose.Schema;
const userSchema = new mongoose.Schema({
name: { type: String, required: true, default: "" },
clients: [{
client: {
type: Schema.Types.ObjectId,
ref: "Client",
default: null
},
user_group: {
type: Number
default: null
}
}]
}, { timestamps: true });
module.exports = mongoose.model("User", userSchema);
auth.js (Where trying to populate Clients)
const express = require("express");
const router = express.Router();
const User = require("../models/User");
const Client = require("../models/Client");
router.post("/users", (req, res) => {
let params = req.body;
let total_client = [];
User.findOne({
email: params.email
})
.populate({
path: "clients.client",
model: Client
})
.exec((err, user) => {
console.log(user);
res.send(user);
});
});
module.exports = router;
Please check the above code. I have given code examples of my two models user.js and client.js. In user schema, I have referenced client inside an array object. While querying user, the client is not population. Please help me to get this thing done. Thanks in advance.
The following expects you to provide a name in the json body of your post request (your example uses email which does not exist in the user model). Also, your model is already defining the ref: Client and so you can simplify your request to just include the path clients.client.
router.post("/users", async (req, res) => {
const { name } = req.body;
const user = await User.findOne({ name: name }).populate('clients.client').exec();
res.send(user);
});
Solved this problem just adding an extra parameter in module export of client.js file
module.exports = mongoose.model("Client", clientSchema, "client");

Error while saving data in MongoDB atlas with mongoose

I'm trying to save data in the MongoDB atlas with node.js and mongoose.
Every time I use MySchema.save(), Data is inserting But I'm also getting the error:
UnhandledPromiseRejectionWarning: MongoWriteConcernError: No write concern mode named 'majority;' found in replica set configuration
Also, there is no duplicate entry, Data is also inserting But I'm also getting the error
let User = require('../models/users.models');
const username = req.body.username;
const newUser = new User({username});
newUser.save()
.then(() => res.json('user added!'))
.catch(err => res.status(400).json('Error: ' + err));
User model
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
var userSchema = new Schema({
username: {
type: String,
required: true,
unique: true,
trim: true,
minlength: 3
},
},
{
timestamps: true
});
const User = mongoose.model('User', userSchema);
module.exports = User;
I know it was asked 2 months ago, but for those who will encounter the same issue.
You are mistakenly entering a wrong char at the end of the URI string:
mongodb+srv://${ user }:${ password }#track-mkahl.mongodb.net/test?retryWrites=true&w=majority;
You need to delete the ; after the word majority.
This helped me.
const schema = new Schema({ name: String }, {
writeConcern: {
w: 'majority',
j: true,
wtimeout: 1000
}
});
https://mongoosejs.com/docs/guide.html#writeConcern
"mongoURI" : "mongodb+srv://${ user }:${ password }#cluster0.mde0j.mongodb.net/cluster0?retryWrites=true&w=majority "
I get the same error with this in default.json its simple error just delete the &w=majority part at the end and it will be solved
for me it was also in the URI string like #Yossi Saadi has suggested, it's just that I had majoritys written there instead of majority
I think there's something wrong with this line.
let User = require('../models/users.models');
I have created a solution for you.
/models/user.js
const mongoose = require('mongoose')
const Schema = mongoose.Schema
mongoose.connect("mongodb://localhost/stack-overflow", { useNewUrlParser: true })
var userSchema = new Schema({
username: {
type: String,
required: true,
unique: true,
trim: true,
minlength: 3
},
},
{
timestamps: true
});
const User = mongoose.model('User', userSchema);
module.exports = User
/routes/userroute.js
const User = require("../models/user")
// Imagine run() as an asynchronous request handler
async function run() {
try {
const user1 = new User({ username: "lidafafnus" })
user1.save((err,result) => {
console.log(err, result)
})
} catch(error) {
console.log(error)
}
}
run()

Resources