mirror of
				https://github.com/therootcompany/greenlock-express.js.git
				synced 2025-11-04 05:52:47 +00:00 
			
		
		
		
	more
This commit is contained in:
		
							parent
							
								
									260f0592be
								
							
						
					
					
						commit
						419b84a1ab
					
				
							
								
								
									
										87
									
								
								README.md
									
									
									
									
									
								
							
							
						
						
									
										87
									
								
								README.md
									
									
									
									
									
								
							@ -1,4 +1,5 @@
 | 
				
			|||||||
# letsencrypt-express
 | 
					# letsencrypt-express
 | 
				
			||||||
 | 
					
 | 
				
			||||||
Free SSL and Automatic HTTPS for node.js with Express, Connect, and other middleware systems
 | 
					Free SSL and Automatic HTTPS for node.js with Express, Connect, and other middleware systems
 | 
				
			||||||
 | 
					
 | 
				
			||||||
## Coming Soon
 | 
					## Coming Soon
 | 
				
			||||||
@ -9,6 +10,78 @@ We're working on it
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
See [examples/express-minimal.js](https://github.com/Daplie/node-letsencrypt/blob/master/examples/express-minimal.js)
 | 
					See [examples/express-minimal.js](https://github.com/Daplie/node-letsencrypt/blob/master/examples/express-minimal.js)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					## Install
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					```
 | 
				
			||||||
 | 
					npm install --save letsencrypt-express
 | 
				
			||||||
 | 
					```
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					## Examples
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					**Minimal**
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					```javascript
 | 
				
			||||||
 | 
					'use strict';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var le = require('letsencrypt-express');
 | 
				
			||||||
 | 
					var express = require('express');
 | 
				
			||||||
 | 
					var app = express();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					app.use('/', function (req, res) {
 | 
				
			||||||
 | 
					  res.send({ success: true });
 | 
				
			||||||
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					le.create('/etc/letsencrypt', app).listen([80], [443, 5001], function () {
 | 
				
			||||||
 | 
					  console.log("ENCRYPT **ALL** THE DOMAINS!");
 | 
				
			||||||
 | 
					});
 | 
				
			||||||
 | 
					```
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					### More Options Exposed
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					```javascript
 | 
				
			||||||
 | 
					'use strict';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var le = require('letsencrypt-express');
 | 
				
			||||||
 | 
					var express = require('express');
 | 
				
			||||||
 | 
					var app = express();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					app.use('/', function (req, res) {
 | 
				
			||||||
 | 
					  res.send({ success: true });
 | 
				
			||||||
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var results = le.create({
 | 
				
			||||||
 | 
					  configDir: '/etc/letsencrypt'
 | 
				
			||||||
 | 
					, onRequest: app
 | 
				
			||||||
 | 
					}).listen(
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  // you can give just the port, or expand out to the full options
 | 
				
			||||||
 | 
					  [80, { port: 8080, address: 'localhost', onListening: function () { console.log('http://localhost'); } }]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  // you can give just the port, or expand out to the full options
 | 
				
			||||||
 | 
					, [443, 5001, { port: 8443, address: 'localhost' }]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  // this is pretty much the default onListening handler
 | 
				
			||||||
 | 
					, function onListening() {
 | 
				
			||||||
 | 
					    var server = this;
 | 
				
			||||||
 | 
					    var protocol = ('requestCert' in server) ? 'https': 'http';
 | 
				
			||||||
 | 
					    console.log("Listening at " + protocol + '://localhost:' + this.address().port);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// In case you need access to the raw servers (i.e. using websockets)
 | 
				
			||||||
 | 
					console.log(results.plainServers);
 | 
				
			||||||
 | 
					console.log(results.tlsServers);
 | 
				
			||||||
 | 
					```
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					### WebSockets with Let's Encrypt
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					Note: you don't need to create websockets for the plain ports.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					```
 | 
				
			||||||
 | 
					results.tlsServers.forEach(function (server) {
 | 
				
			||||||
 | 
					});
 | 
				
			||||||
 | 
					```
 | 
				
			||||||
 | 
					
 | 
				
			||||||
## Options
 | 
					## Options
 | 
				
			||||||
 | 
					
 | 
				
			||||||
If any of these values are `undefined` or `null` the will assume use reasonable defaults.
 | 
					If any of these values are `undefined` or `null` the will assume use reasonable defaults.
 | 
				
			||||||
@ -18,6 +91,9 @@ Partially defined values will be merged with the defaults.
 | 
				
			|||||||
Setting the value to `false` will, in many cases (as documented), disable the defaults.
 | 
					Setting the value to `false` will, in many cases (as documented), disable the defaults.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
```
 | 
					```
 | 
				
			||||||
 | 
					configDir: string               //
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
webrootPath: string             // string     a path to a folder where temporary challenge files will be stored and read
 | 
					webrootPath: string             // string     a path to a folder where temporary challenge files will be stored and read
 | 
				
			||||||
                                // default    os.tmpdir() + path.sep + 'acme-challenge'
 | 
					                                // default    os.tmpdir() + path.sep + 'acme-challenge'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -45,4 +121,15 @@ httpsOptions: object            // object     will be merged with internal defau
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
sniCallback: func               // func       replace the default sniCallback handler (which manages certificates) with your own
 | 
					sniCallback: func               // func       replace the default sniCallback handler (which manages certificates) with your own
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					letsencrypt: object             // object     configure the letsencrypt object yourself and pass it in directly
 | 
				
			||||||
 | 
					                                //
 | 
				
			||||||
 | 
					                                // default    we create the letsencrypt object using parameters you specify
 | 
				
			||||||
```
 | 
					```
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					## Heroku?
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					This doesn't work on heroku because heroku uses a proxy with built-in https
 | 
				
			||||||
 | 
					(which is a smart thing to do) and besides, they want you to pay big bucks
 | 
				
			||||||
 | 
					for https. (hopefully not for long?...)
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										31
									
								
								lib/challenge-handlers.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										31
									
								
								lib/challenge-handlers.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,31 @@
 | 
				
			|||||||
 | 
					'use strict';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var fs = require('fs');
 | 
				
			||||||
 | 
					var path = require('path');
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// TODO handle templating :hostname in letsencrypt proper
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Note: we're explicitly doing this on the filesystem
 | 
				
			||||||
 | 
					// rather than in-memory to support node cluster
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					module.exports = {
 | 
				
			||||||
 | 
					  set: function setChallenge(args, hostname, key, value, cb) {
 | 
				
			||||||
 | 
					    var keyfile = path.join((args.webrootPath || args.webrootTpl).replace(':hostname', hostname), key);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    fs.writeFile(keyfile, value, 'utf8', cb);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					, get: function getChallenge(args, hostname, key, cb) {
 | 
				
			||||||
 | 
					    var keyfile = path.join((args.webrootPath || args.webrootTpl).replace(':hostname', hostname), key);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    fs.readFile(keyfile, 'utf8', cb);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					, remove: function removeChallenge(args, hostname, key, cb) {
 | 
				
			||||||
 | 
					    var keyfile = path.join((args.webrootPath || args.webrootTpl).replace(':hostname', hostname), key);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    // Note: it's not actually terribly important that we wait for the unlink callback
 | 
				
			||||||
 | 
					    // but it's a polite thing to do - and we're polite people!
 | 
				
			||||||
 | 
					    fs.unlink(keyfile, cb);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
@ -1,22 +1,10 @@
 | 
				
			|||||||
'use strict';
 | 
					'use strict';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
var path = require('path');
 | 
					var path = require('path');
 | 
				
			||||||
 | 
					var challengeStore = require('./lib/challange-handlers');
 | 
				
			||||||
 | 
					
 | 
				
			||||||
function getChallenge(args, hostname, key, cb) {
 | 
					function create(obj, app) {
 | 
				
			||||||
  var fs = require('fs');
 | 
					  var LE = require('letsencrypt');
 | 
				
			||||||
  var keyfile = path.join((args.webrootPath || args.webrootTpl).replace(':hostname', hostname), key);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  fs.readFile(keyfile, 'utf8', function (err, text) {
 | 
					 | 
				
			||||||
    if (err) {
 | 
					 | 
				
			||||||
      cb(err);
 | 
					 | 
				
			||||||
      return;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    cb(null, text);
 | 
					 | 
				
			||||||
  });
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
function create(obj) {
 | 
					 | 
				
			||||||
  var https = require('https');
 | 
					  var https = require('https');
 | 
				
			||||||
  var http = require('http');
 | 
					  var http = require('http');
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -26,12 +14,23 @@ function create(obj) {
 | 
				
			|||||||
  if (!obj) {
 | 
					  if (!obj) {
 | 
				
			||||||
    obj = {};
 | 
					    obj = {};
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  else if ('function' === typeof obj) {
 | 
					
 | 
				
			||||||
 | 
					  if ('string' === typeof obj) {
 | 
				
			||||||
 | 
					    obj = {
 | 
				
			||||||
 | 
					      configDir: obj
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if ('function' === typeof obj) {
 | 
				
			||||||
    obj = {
 | 
					    obj = {
 | 
				
			||||||
      onRequest: obj
 | 
					      onRequest: obj
 | 
				
			||||||
    };
 | 
					    };
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if ('function' === typeof app) {
 | 
				
			||||||
 | 
					    obj.onRequest = obj.onRequest || app;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (!obj.getChallenge) {
 | 
					  if (!obj.getChallenge) {
 | 
				
			||||||
    if (false !== obj.getChallenge) {
 | 
					    if (false !== obj.getChallenge) {
 | 
				
			||||||
      obj.getChallenge = getChallenge;
 | 
					      obj.getChallenge = getChallenge;
 | 
				
			||||||
@ -41,11 +40,18 @@ function create(obj) {
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (!obj.onRequest) {
 | 
					  if (!obj.onRequest && false !== obj.onRequest) {
 | 
				
			||||||
    console.warn("You did not specify args.onRequest, using 'Hello, World!'");
 | 
					    console.warn("You should either do args.onRequest = app or server.on('request', app),"
 | 
				
			||||||
    obj.onRequest = function (req, res) {
 | 
					      + " otherwise only acme-challenge requests will be handled (and the rest will hang)");
 | 
				
			||||||
      res.end('Hello, World!');
 | 
					    console.warn("You can silence this warning by setting args.onRequest = false");
 | 
				
			||||||
    };
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if (!obj.letsencrypt) {
 | 
				
			||||||
 | 
					    //LE.merge(obj, );
 | 
				
			||||||
 | 
					    obj.letsencrypt = LE.create(obj, {
 | 
				
			||||||
 | 
					      setChallenge: setChallenge
 | 
				
			||||||
 | 
					    , removeChallenge: removeChallenge
 | 
				
			||||||
 | 
					    });
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  function acmeResponder(req, res) {
 | 
					  function acmeResponder(req, res) {
 | 
				
			||||||
@ -142,7 +148,7 @@ function create(obj) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
    // deleting creates a "slow object", but that's okay (we only use it once)
 | 
					    // deleting creates a "slow object", but that's okay (we only use it once)
 | 
				
			||||||
    return results;
 | 
					    return results;
 | 
				
			||||||
  };
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return {
 | 
					  return {
 | 
				
			||||||
    listen: listen
 | 
					    listen: listen
 | 
				
			||||||
@ -151,4 +157,6 @@ function create(obj) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
module.exports = create;
 | 
					module.exports = create;
 | 
				
			||||||
module.exports.create = create;
 | 
					module.exports.create = create;
 | 
				
			||||||
module.exports.getChallenge = getChallenge;
 | 
					module.exports.setChallenge = challengeStore.set;
 | 
				
			||||||
 | 
					module.exports.getChallenge = challengeStore.get;
 | 
				
			||||||
 | 
					module.exports.removeChallenge = challengeStore.remove;
 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user