Express.js : regex in route - javascript

I want to get a value in my url.
My url is like :
host/:value.schema
I want to get value.
Exemple :
host/horse.schema value = horse
I have another route without .schema:
host/:value
Exemple :
host/horse value = horse
How tell Express to make the difference ?

You can try something like this:
app.get('/:value.:schema?', function (req, res) {
console.log(req.params);
});
You'll receive this:
http://localhost:3000/horse { value: 'horse', schema: undefined }
http://localhost:3000/horse.schema { value: 'horse', schema: 'schema' }

Related

Mongoose : Cast to ObjectId failed for value "Some String" at path "_id"

New to MongoDB, Javascript stack and need help understanding cause of this error.
I have my model created :
const
Mongoose = require('mongoose');
Schema = Mongoose.Schema,
Model = Mongoose.model;
module.exports = Model('Project',
new Schema({
icon : String,
name : String,
state : String,
number : String
})
);
This is my MongoDB document :
[![MongoDB Document][1]][1]
I am attempting to receive all the documents in the collection when I call the API so therefore as per the Mongoose document I am using the find() method.
Here is my API Implementation:
const Project = require('../../models/project');
router.get('/projects/:page?/:limit?',
function(req, res, next){
const page = Math.max(req.params.page || 1, 1) - 1;
const limit = Math.max(req.params.limit || 20, 20);
//Verified : I am hitting the API
console.log("Reached API /projects");
Project.find()
.populate('icon')
.populate('name')
.populate('state')
.populate('number')
.limit(limit).skip(page * limit).exec(
function(err, project)
{
if (err) { return next(err); }
res.send(project);
}
); //End of exec()
}//End of unction
);
I am successful in making the API call using fetch() but I am receiving "Cast to ObjectId failed error" for all the String values.
I believe there is something really simple within my Mongo DB document that I might be missing. Please help me understand and solve this issue.
**EDIT ---
The error seems to point at the string values of the keys:
**
Thank you
Population is the process of automatically replacing the specified paths in the document with document(s) from other collection(s). So you're Id cast is not valid, because of string, you need to have ObjectId, some changes need to be made before it, Let's debug:
const alldata = await Project.find()
console.log(alldata) // ?
does this return something, I'm using async await here if it return data then the problem is with your populate because your Id case isn't valid as you save in schema string and you're referring here populate, example of using populate:
module.exports = Model('Project',
new Schema({
icon : [{ type: Schema.ObjectId, ref: 'your icon document' }],
name : [{ type: Schema.ObjectId, ref: 'you name document' }],
state : [{ type: Schema.ObjectId, ref: 'state document' }],
number : [{ type: Schema.ObjectId, ref: 'number document' }]
})
);
but it seems to me that you don't need to use the populate because you have simple data, name, number... so you should be good to go with the above example
Resources: mongoose fetching data, using populate, relation

How get all data if field in query string is empty Node and Sequelize with Postgres

i'm studing Sequelize with Node, and i have a question..
I have the follow URL with params:
http://localhost:9000/api/get/Joao/""
The first parameter is name and the second is manager, respectively Joaoand "" (i'm considering like empty)..
What i want is:
If the second parameter is empty i want to get all data that has the name Joao..
Already put undefined, nullin the code of the Sequelize but not working..
Someone could help me, please?
My code of Sequelize:
getCubikMembers(req, res) {
return Cubik
.findAll({
where: {
name: req.params.name,
manager: null // what i put here to happen what i want?
}
})
.then(success => res.status(201).send(success))
.catch(err => res.status(err).send(err))
}
My api:
app.get('/api/get/:name/:manager',CubikersController.getCubikMembers);
You can use or statement. I think possible solution would be like below. I have not tested the code.
getCubikMembers(req, res) {
const manager = req.params.manager;
return Cubik
.findAll({
where: {
[Op.or]: [
{manager: manager ? manager : null },
{name: req.params.name }
]
}
})
.then(success => res.status(201).send(success))
.catch(err => res.status(err).send(err))
}
Here is the docs for operators in sequelizejs.
http://docs.sequelizejs.com/manual/tutorial/models-usage.html#complex-filtering-or-not-queries
i got to do, but i have that to change the "" to undefined, i dont know but the value empty is different in Sequelize..
My code was:
where: {
name: req.params.name === 'undefined' ? {
[Op.ne]: 'undefined'
} : req.params.name,
manager: req.params.manager === 'undefined' ? {
[Op.ne]: 'undefined'
} : req.params.manager
},
Like this if some field is undefined it is ignored in the filter..
I hope to have helped someone.

Upsert data with a dynamic field name

I just try to do something simple with Mongo but it doesn't work:
I want to upsert datas in an object like: module.xxx.yyy then I tried many things like :
UsersRights.upsert({
condoId: condoId,
userId: manager._id,
}, {
condoId: condoId,
userId: manager._id,
module: {
[defaultRight.xxx] : {
[defaultRight.yyy] : defaultRight.default
}
}
});
but when I want to add a new xxx or a new yyy, it will erase and replace the entire module object and not only add a new key.
I also tried this :
UsersRights.upsert({
condoId: condoId,
userId: manager._id,
}, {
condoId: condoId,
userId: manager._id,
["module." + defaultRight.module + "." + defaultRight.right] : defaultRight.default,
});
but the server show me an error like: MinimongoError: Key module.xxx.yyy must not contain '.'
You need to use the following form:
YourCollection.upsert({
_id: id, (can be other selectors as well)
}, {
$set: setter
});
Setter is an object you create before and should have the following form:
const setter = {};
setter[`${#1Level}.${#2Level}`] = data;
Where #1Level & #2Level are vars naming the fields you want to modify or to add.

Merging req.params and req.url in express

First of all, I have the following route:
route: '/list/:param1'
Im sending the following request to the server:
url: '/list/someParam?param2=foo&param3=bar
After that, express is giving to me two important objects that i need, the req.url and the req.params.
I want to get an object that merges both url and params. Im using the following code:
module.exports = function (req, res, next) {
var url = require('url');
var queryObject = url.parse(req.url, true).query;
console.log(queryObject);
console.log(req.params);
console.log(req.params.length);
}
So it logs something like:
{ param2: 'foo', param3: 'bar' }
[ param1: 'someParam' ]
0
Now, assuming that I dont know the name of the params, I need to have an object with the information from both req.url and req.params. Here are my questions:
1) How can I do to get something like:
{ param1: 'someParam', param2: 'foo', param3: 'bar' }
2) Why is req.params logging something like an array? And if it is an array, why is it returning me 0 as its length?
Thanks in advance.
Use req.query instead of parsing the URL again.
I'm guessing Express has a custom toString implementation for that particular object.
You can also look up both in order of importance using req.param(name)

How to display the results of an aggregation in jade

How do you display the results of a mongodb aggregation query using node.js, express & jade
I'm not sure what I've done wrong or even if this is the correct approach.
When I attempt to access the page - it just times out?
Any idea? Or is there a better way?
app.js
var mongo = require('mongodb');
var monk = require('monk');
var db = monk('localhost:27017/soundevents');
var timeroute = require('./routes/timers');
app.get('/time/starttimer', timeroute.starttimer);
my routes/timers.js looks like this:
exports.starttimer = function(db) {
return function(req, res) {
var aEvent = db.get('event');
aEvent.aggregation([{$group:{_id:{"EventName":"$EventName"}}}],{}, function(e,docs) {
res.render('time/starttimer', {title: 'Stat Timer',
"eventlist" : docs});
});
};
};
output from mongo
db.event.aggregate([{$group:{_id:{"EventName":"$EventName"}, UpdateTime:{$max: "$UpdateTime"}}}])
{"result" : [{"_id" : {
"EventName" : "MtnBikeRace 1"},
"UpdateTime" : 1392265180.069293},
{"_id" : {
"EventName" : "Student League"},
"UpdateTime" : 1392047321724}],
"ok" : 1}
This example can help you.
https://github.com/visionmedia/express/blob/master/examples/jade/index.js
// Dummy users
var users = [
new User('tj', 'tj#vision-media.ca')
, new User('ciaran', 'ciaranj#gmail.com')
, new User('aaron', 'aaron.heckmann+github#gmail.com')
];
app.get('/', function(req, res){
res.render('users', { users: users });
})
// user.jade
extends ../layout
block content
h1 Users
#users
for user in users
.user
h2= user.name
.email= user.email
I landed here because I was looking for a way to aggregate results using monk.
For future reference: as of now, monk has no .aggregate() method, therefore this part of your code will not work (as you've indicated in a comment):
// there's no aggregation method.
aEvent.aggregation([{$group:{_id:{"EventName":"$EventName"}}}],{}, function(e,docs) {
res.render('time/starttimer', {title: 'Stat Timer',
"eventlist" : docs});
});
However,
this answer shows the correct way to perform an aggregation with monk. It uses the underlying native driver. In your case this would be something like the following:
aEvent.col.aggregate([{$group:{_id:{"EventName":"$EventName"}}}],{}, function(e,docs) {
res.render('time/starttimer', {title: 'Stat Timer',
"eventlist" : docs});
});
If you aggregate this way, I guess you can accept fundon's answer.

Categories