Comment créer un serveur HTTPS dans Node.js?

361

Étant donné une clé et un certificat SSL, comment créer un service HTTPS?

murvinlai
la source
2
J'ai utilisé restify.js au lieu d'express.js, mais l'idée est la même. Voici comment j'ai configuré un serveur node.js qui accepte à la fois HTTP et HTTPS qugstart.com/blog/node-js/…
awaage
2
sans express et avec la dernière version de node - regardez ici: stackoverflow.com/a/21809393/388026
pkyeck
1
Qu'est-il arrivé à cette question? Les réponses impliquent qu'il s'agissait à l'origine d'express.js.
doug65536
il est trivial de créer un certificat SSL auto-signé valide et de lancer un serveur HTTPS, en quelques étapes
Lloyd
3
C'est un peu tard mais si quelqu'un a besoin d'un tutoriel https nodejs complet, vous pouvez trouver ici: programmerblog.net/nodejs-https-server
Jason W

Réponses:

151

J'ai trouvé l'exemple suivant.

https://web.archive.org/web/20120203022122/http://www.silassewell.com/blog/2010/06/03/node-js-https-ssl-server-example/

Cela fonctionne pour le nœud v0.1.94 - v0.3.1. server.setSecure()est supprimé dans les versions plus récentes du nœud.

Directement à partir de cette source:

const crypto = require('crypto'),
  fs = require("fs"),
  http = require("http");

var privateKey = fs.readFileSync('privatekey.pem').toString();
var certificate = fs.readFileSync('certificate.pem').toString();

var credentials = crypto.createCredentials({key: privateKey, cert: certificate});

var handler = function (req, res) {
  res.writeHead(200, {'Content-Type': 'text/plain'});
  res.end('Hello World\n');
};

var server = http.createServer();
server.setSecure(credentials);
server.addListener("request", handler);
server.listen(8000);
hvgotcodes
la source
3
setSecureest obsolète. Vérifiez plutôt stackoverflow.com/questions/5136353/node-js-https-secure-error
Larry Battle
7
Voir la réponse expresse officielle ci-dessous par @Jacob Marble.
clayzermk1
21
Cet exemple ne fonctionne plus car l'implémentation HTTPS a été refaite dans Node.JS 0.4. Voir les documents correspondants sur nodejs.org. stackoverflow.com/questions/5136353/…
scottyab
11
Cette réponse est très ancienne et ne fonctionne plus. Veuillez voir la réponse par pkyeck ci-dessous, ou allez sur: nodejs.org/api/https.html
Jay Sheth
2
Le lien est également rompu
TlonXP
484

Le document de l'API Express le dit assez clairement.

De plus, cette réponse donne les étapes pour créer un certificat auto-signé.

J'ai ajouté quelques commentaires et un extrait de la documentation HTTPS de Node.js :

var express = require('express');
var https = require('https');
var http = require('http');
var fs = require('fs');

// This line is from the Node.js HTTPS documentation.
var options = {
  key: fs.readFileSync('test/fixtures/keys/agent2-key.pem'),
  cert: fs.readFileSync('test/fixtures/keys/agent2-cert.cert')
};

// Create a service (the app object is just a callback).
var app = express();

// Create an HTTP service.
http.createServer(app).listen(80);
// Create an HTTPS service identical to the HTTP service.
https.createServer(options, app).listen(443);
Jacob Marble
la source
49
Nice, était sur le point de poster moi-même. Je vous remercie. De plus, j'ai trouvé cet article utile pour générer un certificat auto-signé.
clayzermk1
1
Assurez-vous de mettre le optionspremier https.createServer, pour éviter les erreurs cryptiques.
wberry
1
Je configure un port de serveur https 8888 presque identique et je ne sais pas comment changer les itinéraires. lorsque j'exécute curl curl --insecure localhost: 8888 curl: (35) Erreur de protocole SSL inconnue lors de la connexion à localhost: 8888 de quelle erreur provient-elle et comment la contourner. Lorsque je tape localhost: 8888 dans le navigateur, il se bloque et https: / localhost: 8888 donne une erreur SSL
reza
2
@Costa, vous pouvez rediriger les utilisateurs de http vers https avec express-force-ssl ou un middleware écrit à la main - c'est assez simple
floatdrop
1
@NathanMcKaskle Vous pouvez désactiver le mot de passe: Consultez ce guide, mais si vous utilisez macOS, assurez-vous que la longueur de clé générée est d'au moins 2048:openssl genrsa -out key.pem 2048
sakisk
87

J'ai trouvé cette question lors de la recherche sur "nœud https", mais l'exemple de la réponse acceptée est très ancien - tiré des documents de la version actuelle (v0.10) du nœud, il devrait ressembler à ceci:

var https = require('https');
var fs = require('fs');

var options = {
  key: fs.readFileSync('test/fixtures/keys/agent2-key.pem'),
  cert: fs.readFileSync('test/fixtures/keys/agent2-cert.pem')
};

https.createServer(options, function (req, res) {
  res.writeHead(200);
  res.end("hello world\n");
}).listen(8000);
pkyeck
la source
A fonctionné comme un charme. Ces informations m'ont été très utiles lorsque j'ai exécuté un outil node.js (PDFJS) au-dessus d'une application PHP qui a récemment été forcée de s'exécuter sur https. L'iframe était très mécontent de charger mon application node.js sur un autre port non https.
lewsid
2
Cela semble bien, mais comment puis-je générer les fichiers dont vous avez besoin ( *.pem)? J'ai essayé de suivre cette page , mais lors de l'ouverture localhost:8000dans le navigateur, aucune donnée n'est reçue (juste chargement ...).
Ionică Bizău
7
@ IonicăBizău, pour générer des clés, installez openssl, puis dans l'invite cmd, tapezopenssl req -x509 -newkey rsa:2048 -keyout key.pem -out cert.pem -days 3001
mido
2
@ IonicăBizău vous devez aller directement à https://localhost:8080. HTTP n'est PAS HTTPS.
Florian Wendelborn
Est-il possible de créer un serveur https avec dossier? Vous pouvez donc y mettre un fichier et y accéder comme localhost: 81 / main.js
FrenkyB
47

Les réponses ci-dessus sont bonnes mais avec Express et node cela fonctionnera bien.

Puisque express crée l'application pour vous, je vais sauter cela ici.

var express = require('express')
  , fs = require('fs')
  , routes = require('./routes');

var privateKey = fs.readFileSync('cert/key.pem').toString();
var certificate = fs.readFileSync('cert/certificate.pem').toString();  

// To enable HTTPS
var app = module.exports = express.createServer({key: privateKey, cert: certificate});
nu1silva
la source
C'est techniquement la réponse la plus correcte, car la question était de savoir comment le faire avec Express.js
Kato
12
Cela semble obsolète car "les applications n'héritent plus de http.Server"
Merlyn Morgan-Graham
2
Pourquoi tu te mets module.exports? Il n'y a pas besoin de ça
Matej
1
@matejkramny, probablement parce que cela facilite le test.
Justin
21

La configuration minimale pour un serveur HTTPS dans Node.js serait quelque chose comme ceci:

var https = require('https');
var fs = require('fs');

var httpsOptions = {
    key: fs.readFileSync('path/to/server-key.pem'),
    cert: fs.readFileSync('path/to/server-crt.pem')
};

var app = function (req, res) {
  res.writeHead(200);
  res.end("hello world\n");
}

https.createServer(httpsOptions, app).listen(4433);

Si vous souhaitez également prendre en charge les requêtes http, vous devez simplement effectuer cette petite modification:

var http = require('http');
var https = require('https');
var fs = require('fs');

var httpsOptions = {
    key: fs.readFileSync('path/to/server-key.pem'),
    cert: fs.readFileSync('path/to/server-crt.pem')
};

var app = function (req, res) {
  res.writeHead(200);
  res.end("hello world\n");
}

http.createServer(app).listen(8888);
https.createServer(httpsOptions, app).listen(4433);
John Slegers
la source
18

Mise à jour

Utilisez Let's Encrypt via Greenlock.js

Message d'origine

J'ai remarqué qu'aucune de ces réponses ne montre que l'ajout d'une autorité de certification racine intermédiaire à la chaîne, voici quelques exemples de configuration zéro pour jouer avec pour voir que:

Fragment:

var options = {
  // this is the private key only
  key: fs.readFileSync(path.join('certs', 'my-server.key.pem'))

// this must be the fullchain (cert + intermediates)
, cert: fs.readFileSync(path.join('certs', 'my-server.crt.pem'))

// this stuff is generally only for peer certificates
//, ca: [ fs.readFileSync(path.join('certs', 'my-root-ca.crt.pem'))]
//, requestCert: false
};

var server = https.createServer(options);
var app = require('./my-express-or-connect-app').create(server);
server.on('request', app);
server.listen(443, function () {
  console.log("Listening on " + server.address().address + ":" + server.address().port);
});

var insecureServer = http.createServer();
server.listen(80, function () {
  console.log("Listening on " + server.address().address + ":" + server.address().port);
});

C'est l'une de ces choses qui est souvent plus facile si vous n'essayez pas de le faire directement via connect ou express, mais laissez le httpsmodule natif le gérer et ensuite l'utiliser pour vous servir de l'application connect / express.

De plus, si vous utilisez server.on('request', app)au lieu de passer l'application lors de la création du serveur, cela vous donne la possibilité de passer l' serverinstance à une fonction d'initialisation qui crée l'application connect / express (si vous voulez faire des websockets sur ssl sur le même serveur, pour exemple).

CoolAJ86
la source
Ceci est une belle explication mais, le lien fourni dans la section de mise à jour est cassé (donne une erreur de 500)
Chucky
8

Pour activer votre application pour écouter les deux httpet httpssur les ports 80et 443respectivement, procédez comme suit

Créez une application express:

var express = require('express');
var app = express();

L'application renvoyée par express()est une fonction JavaScript. Il peut être transmis aux serveurs HTTP de Node en tant que rappel pour gérer les demandes. Cela facilite la fourniture des versions HTTP et HTTPS de votre application en utilisant la même base de code.

Vous pouvez le faire comme suit:

var express = require('express');
var https = require('https');
var http = require('http');
var fs = require('fs');
var app = express();

var options = {
  key: fs.readFileSync('/path/to/key.pem'),
  cert: fs.readFileSync('/path/to/cert.pem')
};

http.createServer(app).listen(80);
https.createServer(options, app).listen(443);

Pour plus de détails, voir le doc

cmd
la source
0

Vous pouvez également l'archiver avec le framework Fastify:

const { readFileSync } = require('fs')
const Fastify = require('fastify')

const fastify = Fastify({
  https: {
    key: readFileSync('./test/asset/server.key'),
    cert: readFileSync('./test/asset/server.cert')
  },
  logger: { level: 'debug' }
})

fastify.listen(8080)

(et lancez openssl req -nodes -new -x509 -keyout server.key -out server.certpour créer les fichiers si vous avez besoin d'écrire des tests)

Manuel Spigolon
la source
-4
  1. Téléchargez le fichier rar pour openssl configuré à partir d'ici: https://indy.fulgan.com/SSL/openssl-0.9.8r-i386-win32-rev2.zip
  2. Copiez simplement votre dossier dans le lecteur c.
  3. Créez le fichier openssl.cnf et téléchargez leur contenu depuis: http://web.mit.edu/crypto/openssl.cnf openssl.cnf peut être placé n'importe où, mais le chemin doit être correct lorsque nous donnons l'invite de commande.
  4. Ouvrez la commande propmt et définissez le chemin openssl.cnf C: \ set OPENSSL_CONF = d: /openssl.cnf 5. Exécutez-le dans cmd: C: \ openssl-0.9.8r-i386-win32-rev2> openssl.exe
  5. Exécutez ensuite OpenSSL> genrsa -des3 -out server.enc.key 1024
  6. Ensuite, il vous demandera des phrases de passe: entrez 4 à 11 caractères comme mot de passe pour le certificat
  7. Exécutez ensuite ce fichier OpenSL> req -new -key server.enc.key -out server.csr
  8. Ensuite, il vous demandera des détails comme le nom de l'État du code du pays, etc., remplissez-le librement. dix . Exécutez ensuite Openssl> rsa -in server.enc.key -out server.key
  9. Exécutez OpenSSL> x509 -req -days 365 -in server.csr -signkey server.key -out server.crt puis utilisez le code précédent qui se trouve sur le débordement de la pile Merci
Er Shubham Patidar
la source
1
c'est OT . La question du PO est claire. Les certificats sont déjà donnés.
Martin Schneider