crontab-ui/app.js

280 lines
7.1 KiB
JavaScript
Raw Normal View History

2016-12-03 15:39:12 +00:00
/*jshint esversion: 6*/
2015-06-11 17:17:06 +00:00
var express = require('express');
var app = express();
2015-06-11 19:21:59 +00:00
var crontab = require("./crontab");
2015-06-13 02:53:13 +00:00
var restore = require("./restore");
2016-08-05 17:47:49 +00:00
var moment = require('moment');
var basicAuth = require('express-basic-auth');
2015-06-11 19:21:59 +00:00
2015-06-13 20:38:20 +00:00
var path = require('path');
var mime = require('mime-types');
2015-06-13 20:38:20 +00:00
var fs = require('fs');
var busboy = require('connect-busboy'); // for file upload
2020-09-22 07:57:38 +00:00
// base url
var base_url = require("./routes").base_url
app.locals.baseURL = base_url
// basic auth
var BASIC_AUTH_USER = process.env.BASIC_AUTH_USER;
var BASIC_AUTH_PWD = process.env.BASIC_AUTH_PWD;
if (BASIC_AUTH_USER && BASIC_AUTH_PWD) {
app.use(function(req, res, next) {
res.setHeader('WWW-Authenticate', 'Basic realm="Restricted Area"')
next();
});
app.use(basicAuth({
users: {
[BASIC_AUTH_USER]: BASIC_AUTH_PWD
}
}))
}
2015-06-11 19:21:59 +00:00
// include the routes
var routes = require("./routes").routes;
var routes_relative = require("./routes").relative
2015-06-11 17:17:06 +00:00
// set the view engine to ejs
app.set('view engine', 'ejs');
2016-08-05 18:17:28 +00:00
var bodyParser = require('body-parser');
2016-12-03 15:39:12 +00:00
app.use(bodyParser.json()); // to support JSON-encoded bodies
2015-06-12 10:17:26 +00:00
app.use(bodyParser.urlencoded({ // to support URL-encoded bodies
extended: true
2016-02-14 03:46:27 +00:00
}));
2016-08-05 18:17:28 +00:00
app.use(busboy()); // to support file uploads
2015-06-12 10:17:26 +00:00
2015-06-11 17:17:06 +00:00
// include all folders
2020-09-22 07:57:38 +00:00
app.use(base_url, express.static(__dirname + '/public'));
app.use(base_url, express.static(__dirname + '/public/css'));
app.use(base_url, express.static(__dirname + '/public/js'));
app.use(base_url, express.static(__dirname + '/config'));
2015-06-15 07:39:43 +00:00
app.set('views', __dirname + '/views');
2015-06-11 19:21:59 +00:00
2017-03-08 07:28:13 +00:00
// set host to 127.0.0.1 or the value set by environment var HOST
app.set('host', (process.env.HOST || '127.0.0.1'));
2016-12-03 15:39:12 +00:00
// set port to 8000 or the value set by environment var PORT
2015-06-11 17:17:06 +00:00
app.set('port', (process.env.PORT || 8000));
2016-12-03 15:39:12 +00:00
// root page handler
2015-06-11 19:21:59 +00:00
app.get(routes.root, function(req, res) {
2016-12-03 15:39:12 +00:00
// reload the database before rendering
2016-08-04 21:49:22 +00:00
crontab.reload_db();
2016-12-03 15:39:12 +00:00
// send all the required parameters
2015-06-11 19:21:59 +00:00
crontab.crontabs( function(docs){
res.render('index', {
routes : JSON.stringify(routes_relative),
2015-06-12 19:19:46 +00:00
crontabs : JSON.stringify(docs),
2015-12-16 10:04:44 +00:00
backups : crontab.get_backup_names(),
2016-08-05 17:47:49 +00:00
env : crontab.get_env(),
moment: moment
2015-06-11 19:21:59 +00:00
});
});
2016-08-05 18:17:28 +00:00
});
2015-06-11 19:21:59 +00:00
2016-12-03 15:39:12 +00:00
/*
Handle to save crontab to database
If it is a new job @param _id is set to -1
@param name, command, schedule, logging has to be sent with _id (if exists)
*/
2015-06-12 10:17:26 +00:00
app.post(routes.save, function(req, res) {
// new job
if(req.body._id == -1){
2016-12-14 04:18:15 +00:00
crontab.create_new(req.body.name, req.body.command, req.body.schedule, req.body.logging, req.body.mailing);
2015-06-12 10:17:26 +00:00
}
// edit job
else{
crontab.update(req.body);
}
res.end();
2016-08-05 18:17:28 +00:00
});
2015-06-11 17:17:06 +00:00
2016-12-03 15:39:12 +00:00
// set stop to job
2015-06-12 19:19:46 +00:00
app.post(routes.stop, function(req, res) {
crontab.status(req.body._id, true);
res.end();
2016-08-05 18:17:28 +00:00
});
2015-06-12 19:19:46 +00:00
2016-12-03 15:39:12 +00:00
// set start to job
2015-06-12 19:19:46 +00:00
app.post(routes.start, function(req, res) {
crontab.status(req.body._id, false);
res.end();
2016-08-05 18:17:28 +00:00
});
2015-06-12 19:19:46 +00:00
2016-12-03 15:39:12 +00:00
// remove a job
2015-06-12 19:19:46 +00:00
app.post(routes.remove, function(req, res) {
crontab.remove(req.body._id);
res.end();
2016-08-05 18:17:28 +00:00
});
2016-12-03 15:39:12 +00:00
2018-05-07 10:40:41 +00:00
// run a job
app.post(routes.run, function(req, res) {
crontab.runjob(req.body._id);
res.end();
});
2016-12-03 15:39:12 +00:00
// set crontab. Needs env_vars to be passed
app.get(routes.crontab, function(req, res, next) {
crontab.set_crontab(req.query.env_vars, function(err) {
if (err) next(err);
else res.end();
});
2016-08-05 18:17:28 +00:00
});
2015-06-12 19:19:46 +00:00
2016-12-03 15:39:12 +00:00
// backup crontab db
2015-06-12 19:19:46 +00:00
app.get(routes.backup, function(req, res) {
crontab.backup();
res.end();
2016-08-05 18:17:28 +00:00
});
2015-06-13 02:53:13 +00:00
2016-12-03 15:39:12 +00:00
// This renders the restore page similar to backup page
2015-06-13 02:53:13 +00:00
app.get(routes.restore, function(req, res) {
// get all the crontabs
restore.crontabs(req.query.db, function(docs){
res.render('restore', {
routes : JSON.stringify(routes_relative),
2015-06-13 02:53:13 +00:00
crontabs : JSON.stringify(docs),
backups : crontab.get_backup_names(),
db: req.query.db
});
});
2016-08-05 18:17:28 +00:00
});
2015-06-13 02:53:13 +00:00
2016-12-03 15:39:12 +00:00
// delete backup db
2015-06-13 02:53:13 +00:00
app.get(routes.delete_backup, function(req, res) {
restore.delete(req.query.db);
res.end();
2016-08-05 18:17:28 +00:00
});
2015-06-13 02:53:13 +00:00
2016-12-03 15:39:12 +00:00
// restore from backup db
2015-06-13 02:53:13 +00:00
app.get(routes.restore_backup, function(req, res) {
crontab.restore(req.query.db);
res.end();
2016-08-05 18:17:28 +00:00
});
2015-06-13 02:53:13 +00:00
2016-12-03 15:39:12 +00:00
// export current crontab db so that user can download it
2015-06-13 20:38:20 +00:00
app.get(routes.export, function(req, res) {
2020-06-09 13:38:22 +00:00
var file = crontab.crontab_db_file;
2015-06-13 20:38:20 +00:00
var filename = path.basename(file);
var mimetype = mime.lookup(file);
res.setHeader('Content-disposition', 'attachment; filename=' + filename);
res.setHeader('Content-type', mimetype);
var filestream = fs.createReadStream(file);
filestream.pipe(res);
2016-08-05 18:17:28 +00:00
});
2015-06-13 20:38:20 +00:00
2016-12-03 15:39:12 +00:00
// import from exported crontab db
2015-06-13 20:38:20 +00:00
app.post(routes.import, function(req, res) {
var fstream;
req.pipe(req.busboy);
req.busboy.on('file', function (fieldname, file, filename) {
2020-06-09 13:38:22 +00:00
fstream = fs.createWriteStream(crontab.crontab_db_file);
2015-06-13 20:38:20 +00:00
file.pipe(fstream);
fstream.on('close', function () {
crontab.reload_db();
res.redirect(routes.root);
});
});
2016-08-05 18:17:28 +00:00
});
2015-06-13 20:38:20 +00:00
2016-12-03 15:39:12 +00:00
// import from current ACTUALL crontab
2015-06-13 20:38:20 +00:00
app.get(routes.import_crontab, function(req, res) {
2016-08-05 18:17:28 +00:00
crontab.import_crontab();
2015-06-13 20:38:20 +00:00
res.end();
2016-08-05 18:17:28 +00:00
});
2015-06-13 20:38:20 +00:00
2019-11-27 05:55:45 +00:00
function sendLog(path, req, res) {
if (fs.existsSync(path))
res.sendFile(path);
2015-12-16 11:00:33 +00:00
else
res.end("No errors logged yet");
2019-11-27 05:55:45 +00:00
}
// get the log file a given job. id passed as query param
app.get(routes.logger, function(req, res) {
let _file = crontab.log_folder + "/" + req.query.id + ".log";
sendLog(_file, req, res);
});
// get the log file a given job. id passed as query param
app.get(routes.stdout, function(req, res) {
let _file = crontab.log_folder + "/" + req.query.id + ".stdout.log";
sendLog(_file, req, res);
2016-08-05 18:17:28 +00:00
});
2015-12-16 10:04:44 +00:00
// error handler
app.use(function(err, req, res, next) {
var data = {};
var statusCode = err.statusCode || 500;
data.message = err.message || 'Internal Server Error';
if (process.env.NODE_ENV === 'development' && err.stack) {
2016-12-03 15:39:12 +00:00
data.stack = err.stack;
}
if (statusCode >= 500) {
console.error(err);
}
res.status(statusCode).json(data);
});
process.on('SIGINT', function() {
console.log("Exiting crontab-ui");
process.exit();
})
process.on('SIGTERM', function() {
console.log("Exiting crontab-ui");
process.exit();
})
2017-03-08 07:28:13 +00:00
app.listen(app.get('port'), app.get('host'), function() {
console.log("Node version:", process.versions.node);
2020-06-09 15:42:42 +00:00
fs.access(crontab.db_folder, fs.W_OK, function(err) {
if(err){
2020-06-09 15:42:42 +00:00
console.error("Write access to", crontab.db_folder, "DENIED.");
process.exit(1);
}
});
2016-12-03 15:39:12 +00:00
// If --autosave is used then we will also save whatever is in the db automatically without having to mention it explictly
// we do this by watching log file and setting a on change hook to it
if (process.argv.includes("--autosave")){
crontab.autosave_crontab(()=>{});
2020-06-09 13:38:22 +00:00
fs.watchFile(crontab.crontab_db_file, () => {
2016-12-03 15:39:12 +00:00
crontab.autosave_crontab(()=>{
console.log("Attempted to autosave crontab");
});
});
2016-12-16 16:24:38 +00:00
}
if (process.argv.includes("--reset")){
console.log("Resetting crontab-ui");
2020-06-09 13:38:22 +00:00
var crontabdb = crontab.crontab_db_file;
var envdb = crontab.env_file;
2016-12-16 16:24:38 +00:00
console.log("Deleting " + crontabdb);
try{
fs.unlinkSync(crontabdb);
} catch (e) {
console.log("Unable to delete " + crontabdb);
}
console.log("Deleting " + envdb);
try{
fs.unlinkSync(envdb);
} catch (e) {
console.log("Unable to delete " + envdb);
}
crontab.reload_db();
2016-12-03 15:39:12 +00:00
}
2020-09-22 07:57:38 +00:00
console.log("Crontab UI is running at http://" + app.get('host') + ":" + app.get('port') + base_url);
2016-08-05 18:17:28 +00:00
});