Connecting to MongoDB over SSL using Node.js

How to connect to MongoDB server via SSL using Node.js?

I read the sources of several drivers ( mongojs , mongodb-native ), and I have been searching the Internet for a long time, but I can’t find any suitable textbooks, manuals or documents.

+9
source share
3 answers

As pointed out in the comments, node-mongodb-native has everything you need.

I ran it and did the following:

 var mongo = require('mongodb'); var server = new mongo.Server('HOSTNAME', 27017, { ssl: true }); var db = new mongo.Db('NAME_OF_MY_DB', server, { w: 1 }); var auth = { user: 'USERNAME', pass: 'PASSWORD' }; db.open(function(err, db) { if (err) return console.log("error opening", err); db.authenticate(auth.user, auth.pass, function(err, result) { if (err) return console.log("error authenticating", err); console.log("authed?", result); db.collection('whatever').count(function(err, count) { if (err) return console.log("error counting", err); console.log("count", count); db.close() }); }); }); 

Edit

You can also make ssl from mongoose :

 mongoose.createConnection(connString, { server: { ssl: true }}) 
+5
source

Step 1: Get MongoDB 3.0

The first thing you need to know is that this SSL is only supported out of the box with MongoDB 3.0 and later. Ubuntu does not have 3.0 in the default repositories, so here is how to do it:

 sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv 7F0CEB10 echo "deb http://repo.mongodb.org/apt/ubuntu trusty/mongodb-org/3.0 multiverse" | sudo tee /etc/apt/sources.list.d/mongodb-org-3.0.list sudo apt-get update sudo apt-get install -y mongodb-org=3.0.7 mongodb-org-server=3.0.7 mongodb-org-shell=3.0.7 mongodb-org-mongos=3.0.7 mongodb-org-tools=3.0.7 

3.0.7 is the latest stable release at the moment, but feel free to replace 3.0.7 with your favorite release.

Step 2: Get the Private Key, Certificate, and PEM Files

PEM contains a public key certificate and its associated private key. These files can be obtained with IRL dollars from the Authroity Certificate or generated with OpenSSL as follows:

 openssl req -newkey rsa:2048 -new -x509 -days 3650 -nodes -out mongodb-cert.crt -keyout mongodb-cert.key cat mongodb-cert.key mongodb-cert.crt > mongodb.pem 

mongodb.pem will be used as the PEM file, mongodb-cert.key is the private key file, and mongodb-cert.crt is the certificate file, which can also be used as a CA file. YOU NEED ALL THREE OF THESE.

Step 3: Configure MongoD

We assume that you have copied these files to your / etc / ssl / folder where they are located. Now we open our MongoDB configuration file:

 sudo vi /etc/mongod.conf 

and change the "# network interfaces" section as follows:

 # network interfaces net: port: 27017 #bindIp: 127.0.0.1 ssl: mode: allowSSL PEMKeyFile: /etc/ssl/mongodb.pem #CAFile: /etc/ssl/mongodb-cert.crt 

PLEASE NOTE: we are commenting on bindIp. This allows external connections to access your Mongo database. We assume that this is your final goal (Why encrypt traffic on the local host?), But you should only do this AFTER SETTING AUTHORIZATION RULES for your MongoDB server.

CAFile is also commented out as it is optional. I will explain how to set up the trust of a certification authority at the end of this post.

As always, you must restart MongoDB for the changes to the configuration file to take effect:

 sudo service mongod restart 

Your server could not start? You are on your own, but there is probably a problem with the certificate files. You can check startup errors by running mongod manually:

 sudo mongod --config /etc/mongod.conf 

Step 4: Verify Your Server Settings

Before we get started with Node configurations, make sure your server settings work correctly by connecting to the mongo command-line client:

 mongo --ssl --sslAllowInvalidHostnames --sslAllowInvalidCertificates 

If the domain name in your certificate is not 127.0.0.1 or localhost, the flag --sslAllowInvalidHostnames is required. Without this, you will probably get this error:

 E NETWORK The server certificate does not match the host name 127.0.0.1 E QUERY Error: socket exception [CONNECT_ERROR] for at connect (src/mongo/shell/mongo.js:179:14) at (connect):1:6 at src/mongo/shell/mongo.js:179 exception: connect failed 

Step 5) Configure Node.JS / Mongoose

If you use the node-mongodb-native package in your Node application, stop working immediately and start using Mongoose. It is not that difficult. However, mongoose.connect () has almost the same API as mongodb.connect (), so replace it accordingly.

  var fs = require('fs') , mongoose = require('mongoose') , mongoUri = "mongodb://127.0.0.1:27017?ssl=true" , mongoOpt = { "sslValidate": false, "sslKey": fs.readFileSync('/etc/ssl/mongodb.pem'), "sslCert": fs.readFileSync('/etc/ssl/mongodb-cert.crt') } ; mongoose.connect(mongoUri, mongoOpt); 

Step 6) [Optional] Verify your certificates through a certification authority

To verify your SSL certificates, you need to get a CA file (or set) from your certificate authority. This will be very similar to your certificate file, but often will contain several certificates (which form trusts to make sure the certificate is valid). If you use a self-signed certificate, you can use mongodb-cert.crt as a CA file.

You also need to make sure that your MongoDB server name matches the one used to create the certificate.

Step 6.3) Update your mongod configuration

 sudo vi /etc/mongod.conf 

and change the "# network interfaces" section as follows:

 # network interfaces net: port: 27017 #bindIp: 127.0.0.1 ssl: mode: allowSSL PEMKeyFile: /etc/ssl/mongodb.pem CAFile: /etc/ssl/mongodb-ca.crt sudo service mongod restart 

Step 6.4) Check your server settings

 mongo --ssl --sslAllowInvalidHostnames --sslCAFile /etc/ssl/mongodb-ca.crt --sslPEMKeyFile /etc/ssl/mongodb.pem 

Mongo clients can also transfer a CA file to ensure that they are communicating with the correct server. This is done using the --sslCAFile option

Mongo servers configured using CAFile require clients to have a valid certificate and private key for the server. In the Mongo shell client, this is done by passing the --sslPEMKeyFile parameter.

Without the PEM file (which contains the server certificate) you can see this error:

 I NETWORK DBClientCursor::init call() failed E QUERY Error: DBClientBase::findN: transport error: 127.0.0.1:27017 ns: admin.$cmd query: { whatsmyuri: 1 } at connect (src/mongo/shell/mongo.js:179:14) at (connect):1:6 at src/mongo/shell/mongo.js:179 exception: connect failed 

The server can be configured to accept requests from clients without a PEM file by enabling net.ssl.weakCertificateValidation, but you will weaken your security without real benefits.

Step 6.5) Configure Node.JS / Mongoose

There are a couple of mistakes here, so bear with me.

First, you NEED to have node-mongodb-native 2.0 or later. If you are using Mongoose, then you need Mongoose 4.0 or later. Previous versions of Mongoose used node-mongodb-native 1. *, which does not support certificate verification under any circumstances.

Secondly, there is no sslAllowInvalidHostnames or similar option in the node-mongodb-native file. This is not something that node-mongodb-native developers can fix (I would do it now), because the native TLS library is available in Node 0.10. *, Does not offer any option for this. At nodes 4. * and 5. * there is a checkServerIdentity option that gives hope, but switching from the original Node branch to the branch after the io.js merge may cause a little headache for the time being.

So let's try this:

 var fs = require('fs') , mongoose = require('mongoose') , mongoUri = "mongodb://127.0.0.1:27017?ssl=true" , mongoOpt = { "server": { "sslKey": fs.readFileSync('/etc/ssl/mongodb.pem'), "sslCert": fs.readFileSync('/etc/ssl/mongodb-cert.crt'), "sslCa": fs.readFileSync('/etc/ssl/mongodb-ca.crt') } } ; 

If you get host / IP name mismatch errors, either correct your certificate or cancel all this hard work by disabling sslValidate:

 var fs = require('fs') , mongoose = require('mongoose') , mongoUri = "mongodb://127.0.0.1:27017?ssl=true" , mongoOpt = { "server": { "sslValidate": false, "sslKey": fs.readFileSync('/etc/ssl/mongodb.pem'), "sslCert": fs.readFileSync('/etc/ssl/mongodb-cert.crt'), "sslCa": fs.readFileSync('/etc/ssl/mongodb-ca.crt') } } ; 

Source: http://www.bainweb.com/2015/11/connecting-to-mongodb-over-tlsssl-with.html

+10
source

If you want to authenticate using a certificate using node-mongodb-native :

 var buffer = require('fs').readFileSync("mongodb.pem"); var MongoClient = require('mongodb').MongoClient; MongoClient.connect("mongodb://hostname:27017/test?ssl=true", { sslKey: buffer, sslCert: buffer, sslValidate: false //in case of self-generated certificate }, function(err, db) { console.log(err); console.log(db); db.close(); }); 
+4
source

Source: https://habr.com/ru/post/971276/


All Articles