the-shepherd
Version:
Control a herd of wild processes.
200 lines (176 loc) • 5.62 kB
JavaScript
// Generated by CoffeeScript 2.5.1
(function() {
var $, ChildProcess, Files, Fs, Groups, Handlebars, _callbacks, _deferTimeout, defaults, defer, disabled, echo, expandPath, generate, nop, reload, reloadNginx, server_name, server_port, setDisabled, setFile, setReload, setTemplate, sync, toConfig, verbose, warn, writeNginxFile;
({$, echo, warn, verbose} = require('../common'));
Fs = require('fs');
Files = require('../files');
({Groups} = require('./groups'));
Handlebars = require('handlebars');
ChildProcess = require('child_process');
({expandPath} = Files);
defaults = {
reload: reload = "service nginx reload",
server_name: server_name = null,
server_port: server_port = 80,
disabled: disabled = true,
template: Files.nginxTemplate = "%/nginx.template",
templateText: `upstream {{ name }} {
{{#each group}}
{{#if this.port}}
server 127.0.0.1:{{ this.port }} {{#unless this.started}}down{{/unless}};
{{/if}}
{{/each}}
}
server {
listen [::]:{{ public_port }};
server_name {{ public_name }};
location / {
proxy_pass http://{{ name }};
}
}
{{#if ssl_cert}}
server {
listen [::]:443;
server_name {{ public_name }};
ssl on;
ssl_certificate {{ ssl_cert }};
ssl_certificate_key {{ ssl_key }};
location / {
proxy_pass http://{{ name }};
}
}
{{/if}}`
};
setReload = function(r) {
return reload = r;
};
setTemplate = function(f) {
return Files.nginxTemplate = f;
};
setFile = function(f) {
return Files.nginxFile = f.replace(/^~/, process.env.HOME).replace(/^%/, Files.basePath);
};
setDisabled = function(d) {
return disabled = d;
};
generate = (t) => {
var buf;
buf = "";
if (t == null) {
return "no template";
}
Groups.forEach((group) => {
if ((group.public_port != null) && (group.public_name != null)) {
return buf += t({
group: group,
public_name: group.public_name,
public_port: group.public_port,
ssl_cert: group.ssl_cert,
ssl_key: group.ssl_key,
name: group.name
});
}
});
return buf;
};
nop = function() {};
writeNginxFile = (cb) => {
var inputFile, start;
cb || (cb = nop);
if (disabled) {
return cb('disabled', false);
}
echo(`Saving nginx file: ${expandPath(Files.nginxFile)}...`);
start = Date.now();
inputFile = expandPath(Files.nginxTemplate);
verbose("Reading nginx template...", inputFile);
Fs.readFile(inputFile, function(err, data) {
var outputFile, text;
if (err) {
warn("Failed to read nginx template:", inputFile, err);
return cb(err, false);
}
text = generate(Handlebars.compile(data.toString('utf8')));
outputFile = expandPath(Files.nginxFile);
verbose("Writing nginx file...", outputFile);
Fs.writeFile(outputFile, text, function(err) {
verbose(`writeNginxFile took ${Date.now() - start} ms`);
return cb(err, true);
});
return null;
});
return null;
};
toConfig = () => {
var _disabled, _file, _reload, _template, buf;
_reload = reload === defaults.reload ? "" : ` --reload-cmd '${reload}'`;
_file = Files.nginxFile === Files.makePath("nginx") ? "" : ` --file '${Files.nginxFile}'`;
_template = Files.nginxTemplate === defaults.template ? "" : ` --template '${Files.nginxTemplate}'`;
_disabled = disabled ? " --disable" : " --enable";
buf = `nginx${_disabled}${_reload}${_file}${_template}`;
Groups.forEach((group) => {
if ((group.public_name != null) || (group.public_port != null) || (group.ssl_cert != null) || (group.ssl_key != null)) {
return buf += `\nnginx --group ${group.name}` + (group.public_name ? ` --name ${group.public_name}` : "") + (group.public_port ? ` --port ${group.public_port}` : "") + (group.ssl_cert ? ` --ssl_cert ${group.ssl_cert}` : "") + (group.ssl_key ? ` --ssl_key ${group.ssl_key}` : "");
}
});
return buf;
};
_callbacks = [];
_deferTimeout = null;
// like a debounce, but we save all the callback that _dont_ get fired
defer = (ms, cb, f) => {
_callbacks.push(cb);
clearTimeout(_deferTimeout);
_deferTimeout = setTimeout((() => {
while (_callbacks.length > 1) {
_callbacks.pop()(null, false);
}
if (_callbacks.length > 0) {
return f(_callbacks.pop());
}
}), ms);
return null;
};
reloadNginx = (cb) => {
cb || (cb = nop);
if (disabled) {
return cb(null, false);
}
defer(500, cb, (_cb) => {
var lastReload, p;
lastReload = $.now;
echo("Reloading nginx with command:", reload);
p = ChildProcess.exec(reload, {
shell: true
});
p.stdout.on('data', function(data) {
return echo(`${reload} (stdout)`, data.toString("utf8"));
});
p.stderr.on('data', function(data) {
return echo(`${reload} (stderr)`, data.toString("utf8"));
});
return _cb(null, true);
});
return null;
};
sync = (cb) => {
cb || (cb = nop);
if (disabled) {
return cb('disabled', false);
}
return defer(500, cb, (_cb) => {
_cb || (_cb = nop);
return writeNginxFile((err, acted) => {
if (err) {
return _cb(err, false);
}
if (acted) {
return reloadNginx(_cb);
} else {
return _cb(null, false);
}
});
});
};
Object.assign(module.exports, {writeNginxFile, reloadNginx, setReload, setTemplate, setFile, setDisabled, toConfig, sync, defaults});
}).call(this);