added configurable '/systemd' endpoints
This commit is contained in:
parent
a32544fbff
commit
1579d8480f
7 changed files with 106 additions and 13 deletions
2
.nvmrc
2
.nvmrc
|
@ -1 +1 @@
|
|||
default
|
||||
16
|
1
.vscode/launch.json
vendored
1
.vscode/launch.json
vendored
|
@ -3,6 +3,7 @@
|
|||
"configurations": [
|
||||
{
|
||||
"type": "pwa-node",
|
||||
"runtimeVersion": "16",
|
||||
"request": "launch",
|
||||
"name": "api",
|
||||
"skipFiles": [
|
||||
|
|
|
@ -7,6 +7,9 @@
|
|||
"active": true,
|
||||
"lifetime": 0
|
||||
},
|
||||
"systemd": [
|
||||
"docker"
|
||||
],
|
||||
"log": {
|
||||
"level": "debug",
|
||||
"format": "DD.MM.YYYY HH:mm:ss:SS"
|
||||
|
|
12
libs/api.js
12
libs/api.js
|
@ -4,6 +4,7 @@ const constants = require('./constants.js');
|
|||
const modep = require('./modep.js');
|
||||
const osc = require('./osc.js');
|
||||
const info = require('./info.js');
|
||||
const systemd = require('./systemd.js');
|
||||
|
||||
const endpoints = new Map();
|
||||
|
||||
|
@ -69,8 +70,17 @@ async function setupEndpoints() {
|
|||
setEndpoint(
|
||||
constants.API_MIDI,
|
||||
undefined,
|
||||
{ method: osc.sendByRequest}
|
||||
{ method: osc.sendByRequest }
|
||||
)
|
||||
if (global.config.systemd !== undefined) {
|
||||
for (let index = 0; index < global.config.systemd.length; index++) {
|
||||
setEndpoint(
|
||||
constants.API_SYSTEMD + '/' + global.config.systemd[index],
|
||||
{ method: systemd.getServiceState },
|
||||
{ method: systemd.setServiceState }
|
||||
)
|
||||
}
|
||||
}
|
||||
logger.debug('setting up ' + endpoints.size + ' endpoints took ' + util.timeDiff(timestamp) + 'ms');
|
||||
}
|
||||
|
||||
|
|
|
@ -2,22 +2,45 @@ const logger = require('./logger.js');
|
|||
const util = require('./util.js');
|
||||
const { spawn } = require('child_process');
|
||||
|
||||
function execute(cmd, args) {
|
||||
return new Promise(function (resolve, reject) {
|
||||
var spawned = spawn(cmd, args);
|
||||
function execute(cmd, args, await) {
|
||||
return new Promise((resolve, reject) => {
|
||||
let result = '';
|
||||
let error = '';
|
||||
const spawned = spawn(cmd, args);
|
||||
spawned.timestamp = new Date();
|
||||
spawned.stdout.on('data', function (data) {
|
||||
logger.debug(data);
|
||||
spawned.on('spawn', () => {
|
||||
logger.info('spawned command \'' + cmd + '\' with args \'' + args + '\'');
|
||||
if (await !== true) {
|
||||
resolve();
|
||||
}
|
||||
});
|
||||
spawned.stderr.on('data', function (data) {
|
||||
logger.error(data);
|
||||
spawned.stdout.on('data', (data) => {
|
||||
result += data;
|
||||
});
|
||||
spawned.on('error', function (err) {
|
||||
spawned.stderr.on('data', (data) => {
|
||||
if (data.toString().toLowerCase().startsWith('warning')) {
|
||||
result += data;
|
||||
return;
|
||||
}
|
||||
error += data;
|
||||
});
|
||||
spawned.on('error', (err) => {
|
||||
reject('command \'' + cmd + '\' with args \'' + args + '\' encountered an error after ' + util.timeDiff(spawned.timestamp) + 'ms >>> ' + err);
|
||||
});
|
||||
spawned.on('exit', function (code) {
|
||||
logger.debug('command \'' + cmd + '\' with args \'' + args + '\' finished with exit code ' + code + ' after ' + util.timeDiff(spawned.timestamp) + 'ms');
|
||||
resolve();
|
||||
spawned.on('exit', (code) => {
|
||||
let msg = 'command \'' + cmd + '\' with args \'' + args + '\' finished with exit code ' + code + ' after ' + util.timeDiff(spawned.timestamp) + 'ms';
|
||||
if (error !== undefined && error.length > 0) {
|
||||
error = error.trim();
|
||||
msg += ' > error: ' + error;
|
||||
logger.error(error);
|
||||
return reject(error);
|
||||
}
|
||||
if (result !== undefined && result.length > 0) {
|
||||
result = result.trim();
|
||||
msg += ' > data: ' + result;
|
||||
}
|
||||
logger.info(msg);
|
||||
resolve(result);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
|
|
@ -8,6 +8,11 @@ const PEDALBOARDS = '/pedalboards';
|
|||
const PEDALS = '/pedals';
|
||||
const BYPASS = '/bypass';
|
||||
const MIDI = '/midi';
|
||||
const SYSTEMD = '/systemd';
|
||||
|
||||
exports.SYSTEMD_STATE_ACTIVE = 'active';
|
||||
exports.SYSTEMD_STATE_INACTIVE = 'inactive';
|
||||
exports.SYSTEMD_STATE_TOGGLE = 'toggle';
|
||||
|
||||
exports.VARIABLE_ID = VARIABLE_ID;
|
||||
|
||||
|
@ -27,6 +32,7 @@ exports.API_PEDAL_BY_ID = PEDALS + '/' + VARIABLE_ID;
|
|||
exports.API_BYPASS = BYPASS;
|
||||
exports.API_BYPASS_BY_ID = BYPASS + '/' + VARIABLE_ID;
|
||||
exports.API_MIDI = MIDI;
|
||||
exports.API_SYSTEMD = SYSTEMD;
|
||||
|
||||
exports.CACHE_INFO = "info";
|
||||
exports.CACHE_BANKS = "banks";
|
||||
|
|
50
libs/systemd.js
Normal file
50
libs/systemd.js
Normal file
|
@ -0,0 +1,50 @@
|
|||
const logger = require('./logger.js');
|
||||
const commands = require('./commands.js');
|
||||
const constants = require('./constants.js');
|
||||
const blinky = require('./blinky.js');
|
||||
|
||||
async function getServiceState(name) {
|
||||
if (name === undefined) {
|
||||
return;
|
||||
}
|
||||
logger.debug('checking service \'' + name + '\'...');
|
||||
const state = await commands.execute('systemctl', ['is-active', name], true);
|
||||
logger.debug('state of service \'' + name + '\' is \'' + state + '\'');
|
||||
return { service: name, state: state };
|
||||
}
|
||||
|
||||
async function setServiceState(name, args) {
|
||||
if (name === undefined || args === undefined) {
|
||||
return;
|
||||
}
|
||||
let state = args.get('state');
|
||||
if (state === undefined) {
|
||||
return;
|
||||
}
|
||||
if (state !== constants.SYSTEMD_STATE_ACTIVE && state !== constants.SYSTEMD_STATE_INACTIVE && state !== constants.SYSTEMD_STATE_TOGGLE) {
|
||||
const msg = 'can not set state of service \'' + name + '\' to unknown state \'' + state + '\'';
|
||||
logger.debug(msg);
|
||||
return { err: msg };
|
||||
}
|
||||
let service = await getServiceState(name);
|
||||
if (state !== constants.SYSTEMD_STATE_TOGGLE && service.state === state) {
|
||||
const msg = 'service \'' + name + '\' is already in state \'' + service.state + '\'';
|
||||
logger.debug(msg);
|
||||
return { msg: msg };
|
||||
}
|
||||
let command;
|
||||
if (service.state === constants.SYSTEMD_STATE_ACTIVE) {
|
||||
command = 'stop';
|
||||
state = constants.SYSTEMD_STATE_INACTIVE;
|
||||
} else if (service.state === constants.SYSTEMD_STATE_INACTIVE) {
|
||||
command = 'start';
|
||||
state = constants.SYSTEMD_STATE_ACTIVE;
|
||||
}
|
||||
logger.debug('setting state of service \'' + name + '\' to \'' + state + '\'...');
|
||||
return { service: name, state: state, result: await commands.execute('systemctl', [command, name], true)};
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
getServiceState,
|
||||
setServiceState
|
||||
}
|
Loading…
Reference in a new issue