hackernews2nntp
Version:
Post Hacker News Stories & Comments to an NNTP Server
199 lines (178 loc) • 5.56 kB
JavaScript
// Generated by CoffeeScript 1.8.0
(function() {
var Message, conf, dispatcher, errx, ext_deps, ext_deps_check, log, mbox, message_create, meta, path, program, readline, shellquote, spawn, warnx, which, wrap_mail;
readline = require('readline');
path = require('path');
spawn = require('child_process').spawn;
program = require('commander');
shellquote = require('shell-quote');
which = require('which');
meta = require('../package.json');
Message = require('./message');
mbox = require('./mbox');
conf = {
verbose: false,
format: 'rnews',
cmd: ['sudo', 'rnews', '-N'],
destination: 'printer',
ext_deps: [],
template_dir: null
};
warnx = function(msg) {
return console.error("" + (path.basename(process.argv[1])) + " warning: " + msg);
};
errx = function(msg) {
console.error("" + (path.basename(process.argv[1])) + " error: " + msg);
return process.exit(1);
};
log = function(msg) {
if (conf.verbose) {
return console.error("" + (path.basename(process.argv[1])) + ": " + msg);
}
};
dispatcher = {
printer: function(id, mail) {
log("" + id + ": writing");
return process.stdout.write("" + mail + "\n");
},
fork: function(id, mail) {
var cmd, stderr, text;
text = '';
stderr = '';
log("" + id + ": writing to `" + (conf.cmd.join(' ')) + "`");
cmd = spawn(conf.cmd[0], conf.cmd.slice(1));
cmd.on('error', function(err) {
return warnx("" + id + ": cmd failed: " + err.message);
});
cmd.stdout.on('data', function(data) {
return text += data;
});
cmd.stderr.on('data', function(data) {
return stderr += data;
});
cmd.on('close', function(code) {
return log("" + id + ": cmd exit code: " + code);
});
cmd.stdin.write("" + mail + "\n");
return cmd.stdin.end();
}
};
wrap_mail = function(message) {
var sendoff;
if (!message) {
return;
}
sendoff = dispatcher[conf.destination];
return message.render().then(function(mail) {
if (conf.format === 'rnews') {
return sendoff(message.json_data.id, "#! rnews " + (Buffer.byteLength(mail) + 1) + "\n" + mail);
} else if (conf.format === 'mbox') {
return sendoff(message.json_data.id, "" + (mbox.prefix(message.json_data)) + "\n" + (mbox.escape(mail)));
} else {
return sendoff(message.json_data.id, mail);
}
}).done();
};
message_create = function(json, parts) {
var err, message;
if (parts == null) {
parts = [];
}
try {
message = new Message(json, parts);
message.opt.alt_dir = conf.template_dir;
} catch (_error) {
err = _error;
if (err.message.match(/invalid json input/)) {
warnx("json validation failed");
return null;
} else {
throw err;
}
}
return message;
};
ext_deps = function() {
return ['w3m', conf.cmd[0]];
};
ext_deps_check = function() {
var e, idx, _i, _len, _ref, _results;
_ref = ext_deps();
_results = [];
for (_i = 0, _len = _ref.length; _i < _len; _i++) {
idx = _ref[_i];
try {
_results.push(which.sync(idx));
} catch (_error) {
e = _error;
_results.push(errx("" + idx + " not found in PATH"));
}
}
return _results;
};
exports.main = function() {
var poll, poll_read, pollopts, rl;
program.version(meta.version).option('-v, --verbose', 'Print debug info to stderr').option('--fork', "Don't print the result to stdout, but feed an external program w/ input").option('--cmd <string>', "Custom external command instead of `" + (conf.cmd.join(' ')) + "`").option('-f, --format <format>', 'Convert to rnews (default), mbox or plain').option('--template-dir <name>', 'A directory w/ custom templates').parse(process.argv);
if (program.verbose) {
conf.verbose = program.verbose;
}
if (program.fork) {
conf.destination = 'fork';
}
if (program.format) {
conf.format = program.format;
}
if (program.cmd) {
conf.cmd = shellquote.parse(program.cmd);
}
if (program.templateDir) {
conf.template_dir = program.templateDir;
}
ext_deps_check();
rl = readline.createInterface({
input: process.stdin,
output: process.stdout,
terminal: false
});
poll = null;
poll_read = 0;
pollopts = [];
rl.on('line', function(line) {
var err, json, message, _ref;
try {
json = JSON.parse(line);
} catch (_error) {
err = _error;
warnx("line not parsed: " + err.message);
return;
}
if (!poll && json.type === 'poll') {
poll = json;
if (((_ref = json.parts) != null ? _ref.length : void 0) < 1) {
warnx("invalid poll w/ id=" + json.id);
poll = null;
return;
}
return poll_read = json.parts.length;
} else if (poll) {
--poll_read;
pollopts.push(json);
if (poll_read === 0) {
message = message_create(poll, pollopts);
wrap_mail(message);
poll = null;
return pollopts = [];
}
} else {
message = message_create(json);
return wrap_mail(message);
}
});
return process.stdout.on('error', function(err) {
if (err.code === "EPIPE") {
warnx("program you pipe in stopped reading input");
}
return errx(err);
});
};
}).call(this);