I have 2 schemas:
var pollSchema = new mongoose.Schema({
title: String,
created: {
type: Date, default: Date.now
},
options: [{
label: String,
count: {
type: Number, default: 0
},
backgroundColor: {
type: String, default: '#fff'
}
}],
author:{
id:{
type: mongoose.Schema.Types.ObjectId,
ref: "User"
},
username: String
}
});
var userSchema = new Schema({
username: {type: String, unique:true},
email: {type: String, unique:true, lowercase: true},
password: String
});
Now each poll will store data of it's author.
Questions:
How can I redesign my schemas - so I will be able to find all the polls belong to particular user?
Or should I leave the schemas the same and find another approach?
you can still find all the polls belonging to a particular user . You have the author.id for that.
Also you can keep an array as var userSchema = new Schema({
username: {type: String, unique:true},
email: {type: String, unique:true, lowercase: true},
password: String,
polls: []
});
And every time a user polls, push the userId inside the polls array, which you can later populate or get the count.
Related
const walletTransactionSchema = new mongoose.Schema({
a: {type: Boolean, required: true},
},
{timestamps: {createdAt: 'created_at', updatedAt: 'updated_at'}});
const walletSchema = new Schema({
b: {type: Boolean, required: true},
transactions: [{type: walletTransactionSchema}],
});
walletSchema.index({'transactions': 1}, {sparse: true});
module.exports.Wallet = mongoose.model('Wallet', walletSchema, 'wallets');
module.exports.WalletTransaction = mongoose.model('WalletTransaction', walletTransactionSchema);
I'm trying to create a model for a subdocument (WalletTransaction) without creating a collection for it. Unfortunately mongoose is automatically creating that collection. How can I prevent that behavior and just define a sub-model without creating a collection. I prefer to organize my schemas by refactoring them instead of just embedding them.
I used to do this without trouble with above definitions. I guess after updating to mongoose 6.0.8 (from 5.13) this is happend.
if you wanna create another model inside a model
You should go with the following approach
const mongoose = require('mongoose');
const userSchema = mongoose.Schema({
_id: mongoose.Schema.Types.ObjectId,
email: {
type: String,
required: true},
about:{type:String},
password: {type: String, required: true},
friends: [new mongoose.Schema({
user: {type: String}
}, {strict: false})],
profileImage: {type: String, default: "default.jpg"},
userName: {type: String, required: true},
matches: {type: Number, default: 0},
wins: {type: Number, default: 0},
losses: {type: Number, default: 0},
backgroundImage: {type: String, default: "default.jpg"},
resetPasswordToken: {type: String, required: false},
resetPasswordExpires: {type: Date, required: false},
isDeleted: {type: Boolean, default: false},
deletedAt: {type: Date, default: null},
}, {timestamps: true}, {strict: false});
module.exports = mongoose.model('User', userSchema);
Like this I create another model in my User model with name Friends in which each entry has one specific id
Here actually I want to make the service collection that contain the array of references of the ratings. when a user rate a service than an element is pushed in the array containing reference of user , service ID no and the rating.
Service Model like this:
var ServiceSchema = new Schema({
user_id:{
type: String,
required: [true, 'please provide user id']
},
name: {
type: String,
required: [true, 'please enter your name']
},
rating : [{ type: Schema.Types.ObjectId, ref: 'rating' }],
});
Rating schema:
var RatingSchema = Schema({
S_id : { type: Schema.Types.ObjectId},
Rating : Number,
By : { type: Schema.Types.ObjectId}
});
user schema:
var UserSchema = new Schema({
id: {
type: String,
unique: true,
required: [true, 'please enter your id']
},
password: {
type: String,
required: [true, 'please enter your password']
},
name: {
type: String,
required: [true, 'please enter your name']
},
type: {
type: [{
type: String,
enum: ['visitor', 'seller']
}],
default: ['visitor']
},
});
and I have defined the export as:
module.exports = mongoose.model('user', UserSchema, 'users');
module.exports = mongoose.model('service', ServiceSchema, 'service');
module.exports = mongoose.model('rating', RatingSchema, 'rating');
I want to make a function called rate but I am not getting how to make it.
exports.rate = function(req, res) {
var curr_service = new Service(req.body, result);
new_service.save(function(err, service) {
if (err)
res.send(err);
res.json(service);
});
};
So far I have done this.
Can someone help me to understand what should I do now? because I haven't find that much about mongoose to add ref in array...
In my case. This error was happening because instead of putting {es_indexed: true} inside the object declaration, I was putting it in the object that was using. For example:
const Client: Schema({
name: {type: String, es_indexed: true},
address: {type: Adress, es_indexed: true} //Wrong, causing error
})
Adress: Schema({
address: {type: String},
zipCode: {type: Number}
})
The correct way to use, is putting es_indexed: true into primitive types inside "Adress" schema declaration.
const Client: Schema({
name: {type: String, es_indexed: true},
address: {type: Adress} //Right way
})
Adress: Schema({
address: {type: String, es_indexed: true},
zipCode: {type: Number, es_indexed: true}
})
I hope it was helpful
I want to display in my user/myarticlesview only articles by logged in user.
How can i do that:
Here is my User model and Article schema:
let userSchema = mongoose.Schema(
{
email: {type: String, required: true, unique: true},
passwordHash: {type: String, required: true},
salt: {type: String, required: true},
articles: [{type: ObjectId, ref: 'Article'}],
roles: [{type: ObjectId, ref: 'Role'}]
}
);
let articleSchema = mongoose.Schema (
{
author: {type: ObjectId, ref: 'User'},
title: {type: String, required: true },
content: {type: String, required: true },
phone: {type: Number, required: true },
date: {type: Date, default: Date.now() }
}
);
I want to do this in my userController and passed it to the view:
myArticlesGet: (req, res) => {
if (!req.isAuthenticated()) {
res.redirect('/');
return;
}
res.render('user/myarticles')
}
I cant figure it out how to make the query.Thank you.
As you are using express sessions you can store userId in the express session when the user is authenticated and then you can get user articles from user like that
User.find({_id: req.session.userId}).populate('articles')
Could you help me please.
I searched the internet and could not find any solutions.
How create query for a child to use the parameters of the parent?
var Photos = new Schema({
photo_id: {type: String, required: true},
photo_path_low: { type: String, required: true }
});
var Users = new Schema({
user_id: { type: String, required: true },
count_coins: { type: Number, default: 20 },
photos_relation: [Photos]
});
...
... some code
...
PhotoModel.findOne().where('parent.count_coins').gt(1)..... // parent for Example
For this case there are Object-references:
var Photos = new Schema({
photo_id: {type: String, required: true},
photo_path_low: { type: String, required: true }
createdBy: {type: mongoose.Schema.Types.ObjectId, ref: 'User'},
});
Then, when you make your query, you can populate references like this:
Photo.findOne({_id: 123})
.populate('createdBy')
.exec(function(err, post) {
// do stuff with post
});
You can find more in this mongoose documentation.
I have 2 models:
Here is the User Model:
const userSchema = new mongoose.Schema({
email: { type: String, unique: true, required: true },
password: { type: String, required: true },
passwordResetToken: String,
passwordResetExpires: Date,
facebook: String,
twitter: String,
tokens: Array,
profile: {
name: String,
gender: String,
location: String,
website: String,
picture: String
}
}, { timestamps: true });
And here is the Revive Model:
const reviveSchema = new mongoose.Schema({
reviveShowName: {type: String, required: true},
reviveTitle: {type: String, required: true},
reviveCategory: {type: String, required: true},
reviveGoal: {type: Number, required: true},
revivePhoto: {type: String, required: true},
reviveVideo: {type: String},
reviveStory: {type: String},
author: {
id: {
type: mongoose.Schema.Types.ObjectId,
ref: "User"
},
name: String
}
}, { timestamps: true });
In the Revive model, I'm trying to the reference the author and get the author's id and that works... How do I also get the name from profiles -> name...? Clearly name: String is wrong...
Mongoose relations work, based on the ref and type value of the nested object. In your case you have associated the id property of author to point to the User model.
If you want to populate the author with the user information, you should just do :
author: {
type: mongoose.Schema.Types.ObjectId,
ref: "User"
}
Then in your query you just use populate
Revive.find({})
.populate( 'author' )
.exec( function( error, docs ) {
console.log( docs ); // will have `[{author:{profile:{...}}}]` data
} );