I am writing a mongoose plugin that involves adding a elements to the subschema. I was thinking it would be quite straightforward, but I've been trying unsuccessfully for a few days now.
Below is a simplification of the schema:
var inheritables = require('./inheritables.server.module.js');
var OuFieldTypeSchema = new Schema({
name: String,
desc: String
});
var OuFieldType = mongoose.model('OuFieldType', OuFieldTypeSchema);
var OuSchema = new Schema({
name: String,
fieldTypes: [OuFieldTypeSchema],
});
OuSchema.plugin(inheritables, {inherit: ['fieldTypes']});
mongoose.model('Ou', OuSchema);
Within the body of my Mongoose Plugin, I'd like to iterate over the "inherit" array and add the following to the schemas that represent each of these elements in the Ou schema;
A simplification of my plugin is as follows:
var _ = require('lodash');
module.exports = exports = function(schema, options) {
_.each(options.inherit, function(currItemSchema){
var addToSchema = {inheritedFrom: {name: String}};
//Really want to add this to the OuFieldTypeSchema represented by the fieldTypes element array.
schema.add(addToSchema, currItemSchema + ".");
});
});
Note that the second parameter of add() adds a prefix, but this doesn't work.
I've also tried:
_.each(options.inherit, function(currItemSchema){
var addToSchema = {};
addToSchema[currItemSchema] = {inheritedFrom: {name: String}};
schema.add(addToSchema);
});
The expected behaviour here is that elsewhere in my plugin, I have a method that sets the inheritedFrom schema. No error is received when the item is set, but the resulting output never sees the inheritedFrom elements.
I am currently adding inheritedFrom to each subschema that is used by OuFieldType, but the above is a simplification and is not very DRY.
I'm new to Node.JS - any pointers in the right direction would be greatly appreciated.
Related
My mongoose model schema looks like -
{
email: { type: String},
Date: {type: Date},
isOnboarded: {type: Boolean},
isVip: {type: Boolean},
isAdult: {type: Boolean}
}
In my frontend I have 3 checkboxes for "isVip", "isOnboarded" and "isAdult" options. If they are checked I'm adding them to an array, which I'll pass to the server. Let's say if "isVip" and "isAdult" are checked, I will pass [isVip, isAdult] in post api to server. Now how can I write a query to get all the documents with the fields in array as true i.e in above example how can I retrieve all docs with {isVip: true, isAdult:true}
I'm having trouble because the array values keep changing, it can be only one field or 3 fields. I couldn't find a way to give condition inside mongoose query.
User.find(
{ [req.query.array]: true},
{ projection: { _id: 0 } }
)
User is my mongoose model.
I want something like this (documents with the value 'true' for the fields given in the array) and 'req.query.array' is the array with field names I passed from frontend.
You have to create your object in JS and pass then to mongo in this way:
var query = {}
if(isVip) query["isVip"] = true;
if(isOnboarded) query["isOnboarded"] = true;
if(isAdult) query["isAdult"] = true;
And then you can use the mongoose method you want, for example:
var found = await model.find(query)
And this will return the document that matches the elements.
Also, note that this is to create and object to be read by the query, so you can use this into an aggregation pipeline or whatever you vant
Check the output:
var query = {}
query["isVip"] = true;
query["isOnboarded"] = true;
query["isAdult"] = true;
console.log(query)
Is the same object that is used to do the query here
{
"isVip": true,
"isOnboarded": true,
"isAdult": true
}
Also, to know if your post contains "isVip", "isOnboarded" or "isAdult" is a javascript question, not a mongo one, but you can use something like this (I assume you pass a string array):
var apiArray = ["isVip","isAdult"]
var isVip = apiArray.includes("isVip")
var isAdult = apiArray.includes("isAdult")
var isOnboarded = apiArray.includes("isOnboarded")
console.log("isVip: "+isVip)
console.log("isAdult: "+isAdult)
console.log("isOnboarded: "+isOnboarded)
This is my MongoDB schema, Seems like push operator is not working
locationCoordinate : {
type : [Number],
index: '2d'
},
i am getting Post data from frontend in my Node.js server which is having Longitude and Latitude
var event = new Events({})
(Events is the name of Schema )
I want to push into this array,
so this seems not to be working
Error on this line
event.locationCoordinate.push(req.body.longitude);
event.locationCoordinate.push(req.body.latitude);
And then saving this by
event.save(function(err,result)){
}
The result may be something like
locationCoordinate[1,2]
var array = [];
array.push({"lng":req.body.longitude},{"lat":req.body.latitude}); // or
array.push(req.body.longitude,req.body.latitude); //just try mybe work
var Evnt = new Events()
Evnt.type = array;
Evnt.index = req.body.index;
Evnt.save(function(...){ ... });
Hi i am new to nodejs and mongoose. Just trying to update mongo data with bulk inserts with following methods.
"use strict";
var mongo = require('../models/tracking_mongo');
var Schema = mongo.trackingMasterMongoosePoc.Schema;
//create a schema
var userwise_tracking_events = new Schema({
activities : {},
summary : {},
userId : Number,
counter : Number,
created : Date,
modified : Date
});
let collection = 'userwise_tracking_events';
let UserwiseTrackingEvents = mongo.trackingMasterConnPoc.model(collection, userwise_tracking_events);
UserwiseTrackingEvents.updateCollectionStream = function(condition, params, options, callback){
var Bulk = UserwiseTrackingEvents.collection.initializeUnorderedBulkOp();
Bulk.find(condition).upsert().update(params);
Bulk.execute(callback);
};
module.exports = UserwiseTrackingEvents;
Upper code works fine but this didn't solved my problem for using bulk inserts.
Then i just made a change by making the bulk variable global.
"use strict";
var mongo = require('../models/tracking_mongo');
var Schema = mongo.trackingMasterMongoosePoc.Schema;
//create a schema
var userwise_tracking_events = new Schema({
activities : {},
summary : {},
userId : Number,
counter : Number,
created : Date,
modified : Date
});
let collection = 'userwise_tracking_events';
let UserwiseTrackingEvents = mongo.trackingMasterConnPoc.model(collection, userwise_tracking_events);
var Bulk = UserwiseTrackingEvents.collection.initializeUnorderedBulkOp();
UserwiseTrackingEvents.updateCollectionStream = function(condition, params, options, callback){
Bulk.find(condition).upsert().update(params);
Bulk.execute(callback);
};
module.exports = UserwiseTrackingEvents;
Now getting the error find of undefined is not a function.
When i checked
console.log(UserwiseTrackingEvents.collection);
Gave me result with NativeCollection.collection is null.
Do let me know what i am doing wrong.
I have another methods to work on this but i specifically want what i am doing wrong in this question.
Thanks :)
I would venture to say that your declaration of Bulk is not outside of any function declaration when moved out of the function call. Thus when the exposed function is called , Bulk was not initialized.
According to http://mongoosejs.com/docs/populate.html, if I set a ref property to an object, and not an ID, when getting it, I should get back an object and not an ID. I'm referring to this part of the page:
var guille = new Person({ name: 'Guillermo' });
guille.save(function (err) {
if (err) return handleError(err);
story._creator = guille;
console.log(story._creator.name);
// prints "Guillermo" in mongoose >= 3.6
// see https://github.com/LearnBoost/mongoose/wiki/3.6-release-notes
Here's my sample code:
var T1schema = new mongoose.Schema({
otherModel:{type:mongoose.Schema.Types.ObjectId, ref:"T2"}
});
var T1 = mongoose.model('T1', T1schema);
var T2schema = new mongoose.Schema({
email: {type: String},
});
var T2 = mongoose.model('T2', T2schema);
var t1 = new T1();
var t2 = new T2({email:"foo#bar.com"});
t1.otherModel = t2;
Now when I refer to t1.otherModel, it's just an ObjectId, and not a T2. For example:
console.log(t1.otherModel.email);
prints undefined instead of "foo#bar.com". Any ideas why? Note I'm using Mongoose 3.6.18 according to it's package.json.
Thanks!
I think your expectations here just don't match what mongoose does. The schema is a way of saying "model M's property P will always be of type T". So when you set a value, mongoose uses the schema definitions to cast the set value to the type the schema requires. Here's a little REPL session. Note setting a number property with a string value casts it to a number, but trying to store a boolean in a number field just ignores the errant value.
> var mongoose = require('mongoose')
> var schema = new mongoose.Schema({prop1: Number})
> var Model = mongoose.model('Model', schema)
> var m = new Model
> m.prop1 = 42
42
> m.prop1
42
> m.prop1 = "42"
'42'
> m.prop1
42
> m.prop1 = false
false
> m.prop1
42
So when your schema says something is going to be an ObjectId, if you give it a model instance, mongoose immediately converts it to an ObjectId in preparation for a write to the database, which is the common case. Normally if you just set that model instance, you don't need to get it back out of the parent model before saving the parent model to the database.
So the model instance getter defined properties are always going to return something compatible with the schema, and populate has to do with loading refs from the DB, but for whatever reason mongoose just doesn't work the same comparing a .populated instance with a non-populated instance. I can see why this is confusing and perhaps unexpected/disappointing though.
Mongoose is normalizing the instance to match the Schema, which specifies that otherModel is an ObjectId.
otherModel:{type:mongoose.Schema.Types.ObjectId, ref:"T2"}
So, Mongoose treats t1.otherModel = t2; the same as:
t1.otherModel = t2._id;
The ref isn't used until .populate() is called (either directly on the document or in a query), which needs both objects to be saved:
t2.save(function (err) {
t1.save(function (err) {
console.log(t1.otherModel);
// 7890ABCD...
t1.populate('otherModel', function () {
console.log(t1.otherModel);
// { email: 'foo#bar.com', _id: 7890ABCD..., __v: 0 }
});
});
});
I'm struggling with creating model functions for Mongoose models. I define a method here:
Schema.listingSchema.method('applyPrice', function() {
this.price = priceFromString(this.title);
});
and I access it here:
var listing = new Listing();
// assign all relevant data
listing.title = title;
...
// pull the price out of the title and description
listing.applyPrice(listing);
where
Listing = mongoose.model('Listing', Schema.listingSchema);
and I receive the error:
TypeError: Object #<model> has no method 'applyPrice'
Can anyone see the issue?
How are you defining your schema? Usually you would do something like this:
var listingSchema = new mongoose.Schema({
title: String
});
listingSchema.method('applyPrice', function() {
this.price = priceFromString(this.title);
});
mongoose.model('Listing', listingSchema);
var Listing = mongoose.model('Listing');
var listing = new Listing({ title: 'Title' });
listing.applyPrice();