filmout_manager/src/shell/index.ts

76 lines
2.2 KiB
TypeScript

import { spawn, ChildProcessWithoutNullStreams } from 'child_process';
import { createLog } from '../log';
import type { Logger } from 'winston';
import { EOL } from 'os';
export class Shell {
private child : ChildProcessWithoutNullStreams;
private log : Logger;
private bin : string;
private args : any[];
private opts : any = {};
private lines : string[] = [];
private stdio : Function = null;
private stderr : Function = null;
private after : Function = null;
private silent : boolean = false;
constructor (args : any[], env : any = null, stdio : Function = null, stderr : Function = null, after : Function = null, silent : boolean = false) {
const bin : string = args.shift();
if (env !== null) this.opts = { env };
this.bin = bin;
this.args = args;
this.stdio = stdio;
this.stderr = stderr;
this.silent = silent;
this.after = after;
if (!this.silent) this.log = createLog(bin);
}
public async execute () : Promise<number> {
return new Promise((resolve : Function, reject : Function) => {
this.child = spawn(this.bin, this.args);
if (!this.silent) this.log.info(`Shell: ${this.bin} ${this.args.join(' ')}`);
this.child.stdout.on('data', (data : string) => {
if (!this.silent) this.log.info(data.toString());
if (this.after !== null) this.lines.push(data);
if (this.stdio !== null) {
let lines : string[] = data.toString().split(EOL).filter( el => el.trim() !== '');
for (let line of lines) {
this.stdio(line);
}
}
});
this.child.stderr.on('data', (data : string) => {
if (!this.silent) this.log.warn(data.toString());
if (this.stderr !== null) {
this.stderr(data.toString());
}
});
this.child.on('close', (code : number) => {
if (this.after !== null) {
this.after(this.lines.join(EOL));
}
if (code === 0) {
if (!this.silent) this.log.info(`Complete: ${this.bin} ${this.args.join(' ')}`);
return resolve(code);
} else {
if (!this.silent) this.log.error(`Error executing: ${this.bin} ${this.args.join(' ')}`);
return reject(code);
}
});
});
}
public kill () {
if (!this.silent) this.log.warn(`Killing: ${this.bin} ${this.args.join(' ')}`);
//this.child.stdin.pause();
this.child.kill();
}
}
module.exports = { Shell };