Chris Chris - 1 month ago 6
Javascript Question

How to use an external variable in MongoDB 'where' query via Javascript?

I have a MongoDB query that searches all properties for a value defined in the search variable. It works the following way:

db.collection.findOne({
$where: function() {
var search = 'searchstring';
for (var key in this) {
if (this[key] === search) {
return true;
}
return false;
}
}
});


However, I would like to define the search variable outside the query.

But when I do so, I get an error that it is not referenced (i.e. scoping issue):

"ReferenceError: search is not defined near '[key] === search


How can I use or pass the variable to the query filter?

Answer

search is a variable that you define in your client, may be the shell, or any client API.

The function that you define for the $where clause, will not be executed on the client side, but on the mongodb server. so, when the function is being interpreted in the server side and it looks for the search variable, it was never defined on the server and hence you get the error.

In your case, you want the variable search, to be replaced with its content, by the client, before being executed on the server. And this is not possible, unless you build the function content itself in the client side.

The client never really interprets anything you write inside the anonymous function. The server does. The error you see is from the server. You can validate it by firing this query and looking onto the server logs:

2015-12-22T19:03:44.011-0800 I QUERY    [conn1] assertion 16722 ReferenceError:
searc is not defined
    at _funcs1 (_funcs1:1:39) near 's.key === searc){retu'  ns:test.t query:{ $w
here: function (){if(this.key === searc){return true}} }

There is a better way to write what you wish to achieve using the $exists operator.

var search = "title";
var find = {};
find[search] = {$exists:true};
db.collection.findOne(find);

This works, because, you build the query parameter fully on the client side, before passing it on to the findOne() method.

Comments