Skip to content

Commit

Permalink
fixing maxBuffer abort
Browse files Browse the repository at this point in the history
  • Loading branch information
ansibleguy76 committed Jan 19, 2025
1 parent 755f4f9 commit 0f9ba99
Show file tree
Hide file tree
Showing 4 changed files with 36 additions and 11 deletions.
8 changes: 8 additions & 0 deletions docs/_data/help.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -240,6 +240,14 @@
description: |
This is not a single variable but rather an infinite amount of variables. You can set as many as you want. The dynamic part is the name of the lib data. For example `YTT_LIB_DATA_MYLIB=values.yml` results in the contents of `values.yml` to be used by ytt in the `mylib` library.
version: 5.0.8
- name: PROCESS_MAX_BUFFER
type: number
allowed: a valid number
short: Maximum buffer size
default: 1024 * 1024
description: |
The maximum buffer size for the process execution. If you have large output, you might want to increase this value.
version: 5.0.8
- name: LOG_LEVEL
type: string
choices:
Expand Down
1 change: 1 addition & 0 deletions server/config/app.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ var app_config = {
enableBypass: (process.env.ENABLE_BYPASS ?? 0)==1,
enableDbQueryLogging: (process.env.ENABLE_DB_QUERY_LOGGING ?? 0)==1,
enableFormsYamlInDatabase: (process.env.ENABLE_FORMS_YAML_IN_DATABASE ?? 0)==1,
processMaxBuffer: process.env.PROCESS_MAX_BUFFER || (1024 * 1024),
adminUsername: process.env.ADMIN_USERNAME || "admin",
adminPassword: process.env.ADMIN_PASSWORD || "AnsibleForms!123"
};
Expand Down
6 changes: 3 additions & 3 deletions server/src/controllers/job.controller.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,9 @@ exports.abortJob = function(req, res) {
res.json(new RestResult("error","You must provide a jobid","",""));
return false
}
Job.abort(jobid)
.then((job)=>{res.json(new RestResult("success","job aborted",null,""))})
.catch((err)=>{res.json(new RestResult("error","failed to abort job",null,err.toString()))})
Job.abort(jobid)
.then((job)=>{res.json(new RestResult("success","job aborted",null,""))})
.catch((err)=>{res.json(new RestResult("error","failed to abort job",null,err.toString()))})
};
exports.getJob = function(req, res) {
var user = req.user.user
Expand Down
32 changes: 24 additions & 8 deletions server/src/models/job.model.js
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ Exec.executeCommand = (cmd,jobid,counter) => {
var hiddenExtravarsFileName = cmd.hiddenExtravarsFileName
var keepExtravars = cmd.keepExtravars
var task = cmd.task
const ac = new AbortController()

// execute the procces
return new Promise((resolve,reject)=>{
Expand All @@ -69,7 +70,13 @@ Exec.executeCommand = (cmd,jobid,counter) => {
logger.warning("No filename was given")
}

var child = exec(command,{cwd:directory,encoding: "UTF-8"});
// adding abort signal
var child = exec(command,{cwd:directory,signal:ac.signal,maxBuffer:appConfig.processMaxBuffer,encoding: "UTF-8"});

// capture the abort event, logging only
ac.signal.addEventListener('abort', (event) => {
logger.warning("Operator aborted the process")
}, { once: true });

// add output eventlistener to the process to save output
child.stdout.on('data',function(data){
Expand All @@ -78,8 +85,8 @@ Exec.executeCommand = (cmd,jobid,counter) => {
.then((status)=>{
// if abort request found ; kill the process
if(status=="abort"){
logger.warning("Abort is requested, killing child")
process.kill(child.pid,"SIGTERM");
logger.warning("Abort is requested, aborting child")
ac.abort("Aborted by operator")
}
})
.catch((error)=>{logger.error("Failed to create output : ", error)})
Expand All @@ -91,18 +98,27 @@ Exec.executeCommand = (cmd,jobid,counter) => {
.then((status)=>{
// if abort request found ; kill the process
if(status=="abort"){
logger.warning("Abort is requested, killing child")
process.kill(child.pid,"SIGTERM");
logger.warning("Abort is requested, aborting child")
ac.abort("Aborted by operator")
}
})
.catch((error)=>{logger.error("Failed to create output: ", error)})
})



// add exit eventlistener to the process to handle status update
child.on('exit',function(data){
child.on('exit',async function(data){
// if the exit was an actual request ; set aborted
if(child.signalCode=='SIGTERM'){
Job.endJobStatus(jobid,++counter,"stderr","aborted",`${task} was aborted by operator`)
reject(`${task} was aborted by operator`)
const statusResult = await mysql.do("SELECT status FROM AnsibleForms.`jobs` WHERE id=?;", [jobid])
if(statusResult[0].status=="abort"){
Job.endJobStatus(jobid,++counter,"stderr","aborted",`${task} was aborted by the operator`)
reject(`${task} was aborted by the operator`)
}else{
Job.endJobStatus(jobid,++counter,"stderr","failed",`${task} was aborted by the main process. Likely some buffer or memory error occured. Also check the maxBuffer option.`)
reject(`${task} was aborted by the main process`)
}
}else{ // if the exit was natural; set the jobstatus (either success or failed)
if(data!=0){
jobstatus="failed"
Expand Down

0 comments on commit 0f9ba99

Please sign in to comment.