I have setup a new Node.js / Express development environment on a CentOS 7 VM. I ‘ll describe the details in another post later.
To test my setp, I created a new Express application “helloworld”. The application listens on port 3000 and I was able to connect to the application using a browser.
Next, I configured NGINX as reverse proxy to use port 80 to access the helloworld application.
[root@nodejs ~]# getsebool -a | grep httpd httpd_anon_write --> off httpd_builtin_scripting --> on httpd_can_check_spam --> off httpd_can_connect_ftp --> off httpd_can_connect_ldap --> off httpd_can_connect_mythtv --> off httpd_can_connect_zabbix --> off httpd_can_network_connect --> off httpd_can_network_connect_cobbler --> off httpd_can_network_connect_db --> off httpd_can_network_memcache --> off httpd_can_network_relay --> off httpd_can_sendmail --> off
So, httpd_can_network_connect was set to “Off”. This blocks the connection from the reverse proxy to the node.js application. As a result, you get the 502 Bad gateway error.
To enable the setting, execute the following command from the shell.
[root@nodejs ~]# setsebool -P httpd_can_network_connect on
Fixing memory leaks may not be not the shiniest skill on a CV, but when things go wrong on production, it’s better to be prepared! After reading this article, you’ll be able to monitor, understand, and debug the memory consumption of a Node.js application.
Modify ExecStart and WorkingDirectory to point to the correct path in your installation.
Save domino-db.service and set execution rights to 744.
Check app.js for proper execution right (744).
Edit app.js and add
#!/usr/bin/env node
as the first line in the code.
Enable the service
systemctl enable domino-db
Created symlink from /etc/systemd/system/multi-user.target.wants/domino-db.service to /etc/systemd/system/domino-db.service.
Check with
systemctl status domino-db
● domino-db.service - domino-node-list sample
Loaded: loaded (/etc/systemd/system/domino-db.service; enabled; vendor preset: disabled)
Active: active (running) since Sun 2018-12-30 10:24:04 CET; 4min 15s ago
Main PID: 7163 (node)
Tasks: 7
CGroup: /system.slice/domino-db.service
└─7163 node /git/domino-node-list/app.js
Dec 30 10:24:04 serv02.fritz.box systemd[1]: Started domino-node-list sample.
Dec 30 10:24:04 serv02.fritz.box systemd[1]: Starting domino-node-list sample...
Dec 30 10:24:05 serv02.fritz.box app.js[7163]: Example app listening at http://:::3000
You can now start and stop the service at any time using
Due to my misunderstanding and also a lack in documentation, I was not able to get PROTON with PROTON_SSL=1 and PROTON_AUTHENTICATION=client_certs running.
But thanks to our great community and a little help from Jan Krejcárek (SUTOL), I was finally able to solve the puzzle.
I must admit that I am not an expert in this field. So please bare with me if things are obvious for you. They are (not yet) for me.
My understanding of using TLS/SSL with PROTON was that I could use my existing Let’s Encrypt certificate to communicate via HTTPS instead of HTTP with my server URL.
But this is not the case. TLS/SSL encryption only enables a secured communication between the domino.db module and the PROTON addin sitting on the Domino server.
Here is an image.
The second thing that I got wrong was the fact that the existing certificate and it’s CA would be enough to enable the secured communication. In my first test, I had set PROTON_AUTHENTICATION=anonymous.
So why bother with client certificates if they are not needed at this point?
I followed Jan’s advice to try with a new generated self-signed certificate. The AppDevPack contains shell scripts to create some sample certs and also lets you create a keyring file that can be used with PROTON.
I have modified the make_keyring.sh file a bit because it complained about missing environment variables.
to define the serverConfig. This must be enhanced, if you are going the secure way.
I created a new module using Jan’s code
const fs = require('fs');
const path = require('path');
/**
* Internal functions that reads a content of a file to a buffer.
* @param {string} fileName
*/
const readFile = fileName => {
return fs.readFileSync(path.resolve(fileName));
}
/**
* (c) Jan Krejcárek
* Creates an object in a structure required for the DominoDB module
* to initialize o connection to the Domino server.
* @param {string} serverHostName Host name of the Domino server
* @param {string} port TCP port number where a Proton task listens for connection requests
* @param {string} rootCertificatePath Path to the certificate used to establish a TLS connection
* @param {string} clientCertificatePath Path to the application certificate used to authenticate the application
* @param {string} clienKeyPath Path to the private key of the application
*/
const config = (serverHostName, port, rootCertificatePath, clientCertificatePath, clienKeyPath) => {
const rootCertificate = readFile(rootCertificatePath);
const clientCertificate = readFile(clientCertificatePath);
const clientKey = readFile(clienKeyPath);
const serverConfig = {
hostName: serverHostName,
connection: {
port: port,
secure: true
},
credentials: {
rootCertificate,
clientCertificate,
clientKey
}
};
return serverConfig;
};
module.exports = config;
All parts in the credentials section are mandatory. Even if you use PROTON_AUTHENTICATION=anonymous with PROTON_SSL=1, you must have certificates and keys for the client as well.