From 9393081e583390883c40e1f228f562647ee08dc7 Mon Sep 17 00:00:00 2001 From: rodrigorodriguez Date: Mon, 14 Nov 2022 16:09:05 -0300 Subject: [PATCH] new(all): Alpha Word Debugger for 3.0. --- package-lock.json | 14 ------ .../basic.gblib/services/DebuggerService.ts | 47 +++++++++++-------- .../basic.gblib/services/vm2-process/index.ts | 22 ++++++--- 3 files changed, 43 insertions(+), 40 deletions(-) diff --git a/package-lock.json b/package-lock.json index 83e5c301..7d41a0d2 100644 --- a/package-lock.json +++ b/package-lock.json @@ -43,7 +43,6 @@ "botframework-connector": "4.11.0", "botlib": "1.10.9", "c3-chart-maker": "^0.2.8", - "cd": "^0.3.3", "chrome-remote-interface": "^0.31.3", "cli-progress": "^3.11.2", "cli-spinner": "0.2.10", @@ -8645,14 +8644,6 @@ "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", "integrity": "sha512-4tYFyifaFfGacoiObjJegolkwSU4xQNGbVgUiNYVUxbQ2x2lUsFvY4hVgVzGiIe6WLOPqycWXA40l+PWsxthUw==" }, - "node_modules/cd": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/cd/-/cd-0.3.3.tgz", - "integrity": "sha512-X2y0Ssu48ucdkrNgCdg6k3EZWjWVy/dsEywUUTeZEIW31f3bQfq65Svm+TzU1Hz+qqhdmyCdjGhUvRsSKHl/mw==", - "engines": { - "node": "*" - } - }, "node_modules/center-align": { "version": "0.1.3", "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", @@ -41049,11 +41040,6 @@ "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", "integrity": "sha512-4tYFyifaFfGacoiObjJegolkwSU4xQNGbVgUiNYVUxbQ2x2lUsFvY4hVgVzGiIe6WLOPqycWXA40l+PWsxthUw==" }, - "cd": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/cd/-/cd-0.3.3.tgz", - "integrity": "sha512-X2y0Ssu48ucdkrNgCdg6k3EZWjWVy/dsEywUUTeZEIW31f3bQfq65Svm+TzU1Hz+qqhdmyCdjGhUvRsSKHl/mw==" - }, "center-align": { "version": "0.1.3", "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", diff --git a/packages/basic.gblib/services/DebuggerService.ts b/packages/basic.gblib/services/DebuggerService.ts index 7c645a4b..99310be5 100644 --- a/packages/basic.gblib/services/DebuggerService.ts +++ b/packages/basic.gblib/services/DebuggerService.ts @@ -32,21 +32,13 @@ 'use strict'; -import { GBError, GBLog, GBMinInstance } from 'botlib'; +import { GBLog, GBMinInstance } from 'botlib'; import { GBServer } from '../../../src/app'; -import { GBAdminService } from '../../admin.gbapp/services/GBAdminService'; import { GuaribasUser } from '../../security.gbapp/models'; import { DialogKeywords } from './DialogKeywords'; -import { GBDeployer } from '../../core.gbapp/services/GBDeployer'; const Swagger = require('swagger-client'); const fs = require('fs'); -import { CollectionUtil } from 'pragmatismo-io-framework'; -import * as request from 'request-promise-native'; - -const urlJoin = require('url-join'); -const Path = require('path'); -const Fs = require('fs'); -const url = require('url'); +const { spawn } = require('child_process'); /** * Web Automation services of conversation to be called by BASIC. @@ -83,6 +75,7 @@ export class DebuggerService { debugWeb: boolean; lastDebugWeb: Date; + /** * SYSTEM account maxLines,when used with impersonated contexts (eg. running in SET SCHEDULE). */ @@ -198,16 +191,17 @@ export class DebuggerService { GBServer.globals.debuggers[botId].state = 0; GBServer.globals.debuggers[botId].breaks = []; GBServer.globals.debuggers[botId].stateInfo = "Stopped"; + GBServer.globals.debuggers[botId].childProcess = null; } private client; - public async breakpoint({ botId, botApiKey, line }) { + public async breakpoint({ botId, line }) { GBLog.info(`BASIC: Enabled breakpoint for ${botId} on ${line}.`); GBServer.globals.debuggers[botId].breaks.push(Number.parseInt(line)); } - public async resume({ botId, botApiKey, force }) { + public async resume({ botId }) { if (GBServer.globals.debuggers[botId].state === 2) { const client = GBServer.globals.debuggers[botId].client; await client.Debugger.resume(); @@ -220,15 +214,20 @@ export class DebuggerService { } } - public async stop({ botId, botApiKey, force }) { + public async stop({ botId }) { GBServer.globals.debuggers[botId].state = 0; GBServer.globals.debuggers[botId].stateInfo = "Stopped"; - const client = GBServer.globals.debuggers[botId].client; - await client.Debugger.close(); + + const kill = ref => { + spawn('sh', ['-c', `pkill -9 -f ${ref}`]); + }; + + kill(GBServer.globals.debuggers[botId].childProcess); + return {status: 'OK'}; } - public async step({ botId, botApiKey }) { + public async step({ botId }) { if (GBServer.globals.debuggers[botId].state === 2) { GBServer.globals.debuggers[botId].stateInfo = "Break"; const client = GBServer.globals.debuggers[botId].client; @@ -240,7 +239,7 @@ export class DebuggerService { } } - public async context({ botId, botApiKey, force }) { + public async context({ botId }) { const conversationId = this.conversationsMap[botId]; let messages = []; if (this.client) { @@ -273,14 +272,24 @@ export class DebuggerService { }; } - public async debug({ botId, botApiKey, scriptName }) { + public async getRunning({ botId, botApiKey, scriptName }) { let error; + botId = botId[0]; // TODO: Handle call in POST. + if (!GBServer.globals.debuggers[botId]) + { + GBServer.globals.debuggers[botId]= {}; + } + + if (!scriptName){ + scriptName = 'start'; + } + if (GBServer.globals.debuggers[botId].state === 1) { error = `Cannot DEBUG an already running process. ${botId}`; return {error: error}; } else if (GBServer.globals.debuggers[botId].state === 2) { GBLog.info(`BASIC: Releasing execution ${botId} in DEBUG mode.`); - await this.resume({ botId, botApiKey, force: false }); + await this.resume({ botId}); return {status: 'OK'}; } else { GBLog.info(`BASIC: Running ${botId} in DEBUG mode.`); diff --git a/packages/basic.gblib/services/vm2-process/index.ts b/packages/basic.gblib/services/vm2-process/index.ts index 53e58f61..b6da43c3 100644 --- a/packages/basic.gblib/services/vm2-process/index.ts +++ b/packages/basic.gblib/services/vm2-process/index.ts @@ -63,6 +63,7 @@ const createVm2Pool = ({ min, max, ...limits }) => { { cwd: limits.cwd, shell: false } ); + childProcess.stdout.on('data', data => { childProcess.socket = childProcess.socket || data.toString().trim(); }); @@ -75,18 +76,22 @@ const createVm2Pool = ({ min, max, ...limits }) => { GBServer.globals.debuggers[limits.botId].state = 0; GBServer.globals.debuggers[limits.botId].stateInfo = stderrCache; } - if (stderrCache.includes('FATAL ERROR: Reached heap limit Allocation failed - JavaScript heap out of memory')) { + else if (stderrCache.includes('FATAL ERROR: Reached heap limit Allocation failed - JavaScript heap out of memory')) { limitError = 'code execution exceeed allowed memory'; kill(process); GBServer.globals.debuggers[limits.botId].state = 0; - GBServer.globals.debuggers[limits.botId].stateInfo = "Fail"; + GBServer.globals.debuggers[limits.botId].stateInfo = 'Fail'; } + else if (stderrCache.includes('Debugger attached.')) { + GBLog.info(`BASIC: General Bots Debugger attached to Node .gbdialog process for ${limits.botId}.`); + } }); let socket = null; await waitUntil(() => childProcess.socket); - socket = net.createConnection(childProcess.socket); - socket.write(JSON.stringify({ code, scope }) + '\n'); + + GBServer.globals.debuggers[limits.botId].childProcess = ref; + // Only attach if called by debugger/run. @@ -124,7 +129,7 @@ const createVm2Pool = ({ min, max, ...limits }) => { GBLog.info(`BASIC: Break at line ${frame.location.lineNumber + 1}`); // (zero-based) GBServer.globals.debuggers[limits.botId].state = 2; - GBServer.globals.debuggers[limits.botId].stateInfo = "Break"; + GBServer.globals.debuggers[limits.botId].stateInfo = 'Break'; } else { GBLog.verbose(`BASIC: Configuring breakpoints if any for ${limits.botId}...`); // Waits for debugger and setup breakpoints. @@ -149,19 +154,20 @@ const createVm2Pool = ({ min, max, ...limits }) => { await client.Runtime.runIfWaitingForDebugger(); await client.Debugger.enable(); await client.Runtime.enable(); + resolve(1); } catch (err) { GBLog.error(err); kill(childProcess); GBServer.globals.debuggers[limits.botId].state = 0; - GBServer.globals.debuggers[limits.botId].stateInfo = "Stopped"; + GBServer.globals.debuggers[limits.botId].stateInfo = 'Stopped'; } }).on('error', err => { console.error(err); kill(childProcess); GBServer.globals.debuggers[limits.botId].state = 0; - GBServer.globals.debuggers[limits.botId].stateInfo = "Stopped"; + GBServer.globals.debuggers[limits.botId].stateInfo = 'Stopped'; reject(err); }); }); @@ -169,6 +175,8 @@ const createVm2Pool = ({ min, max, ...limits }) => { await debug(); } + socket = net.createConnection(childProcess.socket); + socket.write(JSON.stringify({ code, scope }) + '\n'); const timer = setTimeout(() => { limitError = 'code execution took too long and was killed';