Search code examples
node.jsmongodbexpressmongoosesecurity

How dangerous is a mongo query which is fed directly from a URL query string?


I am playing around with , , and .

For the sake of getting something up and running right now I am passing the Express query string object directly to a mongoose find function. What I am curious about is how dangerous would this practice be in a live app. I know that a RDBMS would be extremely vulnerable to SQL injection. Aside from the good advice of "sanitize your inputs" how evil is this code:

app.get('/query', function (req, res) {
    models.findDocs(req.query, function (err, docs) {
            res.send(docs);
        });
});

Meaning that a a get request to http://localhost:8080/query?name=ahsteele&status=a would just shove the following into the findDocs function:

{
  name: 'ahsteele',
  status: 'a'
}

This feels icky for a lot of reasons, but how unsafe is it? What's the best practice for passing query parameters to mongodb? Does express provide any out of the box sanitization?


Solution

  • As far as injection being problem, like with SQL, the risk is significantly lower... albeit theoretically possible via an unknown attack vector.

    The data structures and protocol are binary and API driven rather than leveraging escaped values within a domain-specific-language. Basically, you can't just trick the parser into adding a ;db.dropCollection() at the end.

    If it's only used for queries, it's probably fine... but I'd still caution you to use a tiny bit of validation:

    • Ensure only alphanumeric characters (filter or invalidate nulls and anything else you wouldn't normally accept)
    • Enforce a max length (like 255 characters) per term
    • Enforce a max length of the entire query
    • Strip special parameter names starting with $, like $where & such
    • Don't allow nested arrays/documents/hashes... only strings & ints

    Also, keep in mind, an empty query returns everything. You might want a limit on that return value. :)