From 83d3631ab00559b8a3e9518d4291aa4bb3fa7e04 Mon Sep 17 00:00:00 2001 From: esarver Date: Tue, 12 Nov 2024 08:09:50 -0500 Subject: [PATCH] Add Setting to Dump Output Queue When Connecting (#71) Sometimes developers may want TSP Toolkit to show the contents of the output queue of the instrument when connecting instead of the queue being cleared. This is especially helpful when connecting to an instrument after the terminal is lost or the instrument drops the connection. This PR also improves the notifications shown while connecting to keep the user informed of the progress of connecting to the instrument. --- CHANGELOG.md | 11 +- package-lock.json | 134 +++++++------- package.json | 20 +- src/communicationmanager.ts | 10 +- src/extension.ts | 8 +- src/logging.ts | 1 + src/resourceManager.ts | 352 ++++++++++++++++++++++-------------- 7 files changed, 313 insertions(+), 223 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index b59a942..4e5403e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -16,6 +16,14 @@ Check [Keep a Changelog](http://keepachangelog.com/) for recommendations on how Security -- in case of vulnerabilities. --> +## [1.1.0] + +### Added + +- Added `tsp.dumpQueueOnConnect` setting to dump the instrument output queue before + clearing it so it can be printed when opening the terminal +- Added progress indication to connection notification + ## [1.0.0] ### Added @@ -234,7 +242,8 @@ Check [Keep a Changelog](http://keepachangelog.com/) for recommendations on how - Feature to retrieve TSP-Link network details -[Unreleased]: https://github.com/tektronix/tsp-toolkit/compare/v1.0.0...HEAD +[Unreleased]: https://github.com/tektronix/tsp-toolkit/compare/v1.1.0...HEAD +[1.1.0]: https://github.com/tektronix/tsp-toolkit/releases/tag/v1.1.0 [1.0.0]: https://github.com/tektronix/tsp-toolkit/releases/tag/v1.0.0 [0.18.2]: https://github.com/tektronix/tsp-toolkit/releases/tag/v0.18.2 [0.18.1]: https://github.com/tektronix/tsp-toolkit/releases/tag/v0.18.1 diff --git a/package-lock.json b/package-lock.json index 0f30f53..f30dca9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "tsp-toolkit", - "version": "1.0.0", + "version": "1.1.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "tsp-toolkit", - "version": "1.0.0", + "version": "1.1.0", "license": "Apache-2.0", "dependencies": { "@tektronix/keithley_instrument_libraries": "0.18.2", @@ -49,9 +49,9 @@ "vscode": "^1.92.0" }, "optionalDependencies": { - "@tektronix/kic-cli-darwin-arm64": "0.18.4", - "@tektronix/kic-cli-linux-x64": "0.18.4", - "@tektronix/kic-cli-win32-x64": "0.18.4" + "@tektronix/kic-cli-darwin-arm64": "0.19.0-0", + "@tektronix/kic-cli-linux-x64": "0.19.0-0", + "@tektronix/kic-cli-win32-x64": "0.19.0-0" } }, "node_modules/@ampproject/remapping": { @@ -193,33 +193,33 @@ } }, "node_modules/@azure/msal-browser": { - "version": "3.26.1", - "resolved": "https://registry.npmjs.org/@azure/msal-browser/-/msal-browser-3.26.1.tgz", - "integrity": "sha512-y78sr9g61aCAH9fcLO1um+oHFXc1/5Ap88RIsUSuzkm0BHzFnN+PXGaQeuM1h5Qf5dTnWNOd6JqkskkMPAhh7Q==", + "version": "3.27.0", + "resolved": "https://registry.npmjs.org/@azure/msal-browser/-/msal-browser-3.27.0.tgz", + "integrity": "sha512-+b4ZKSD8+vslCtVRVetkegEhOFMLP3rxDWJY212ct+2r6jVg6OSQKc1Qz3kCoXo0FgwaXkb+76TMZfpHp8QtgA==", "dev": true, "dependencies": { - "@azure/msal-common": "14.15.0" + "@azure/msal-common": "14.16.0" }, "engines": { "node": ">=0.8.0" } }, "node_modules/@azure/msal-common": { - "version": "14.15.0", - "resolved": "https://registry.npmjs.org/@azure/msal-common/-/msal-common-14.15.0.tgz", - "integrity": "sha512-ImAQHxmpMneJ/4S8BRFhjt1MZ3bppmpRPYYNyzeQPeFN288YKbb8TmmISQEbtfkQ1BPASvYZU5doIZOPBAqENQ==", + "version": "14.16.0", + "resolved": "https://registry.npmjs.org/@azure/msal-common/-/msal-common-14.16.0.tgz", + "integrity": "sha512-1KOZj9IpcDSwpNiQNjt0jDYZpQvNZay7QAEi/5DLubay40iGYtLzya/jbjRPLyOTZhEKyL1MzPuw2HqBCjceYA==", "dev": true, "engines": { "node": ">=0.8.0" } }, "node_modules/@azure/msal-node": { - "version": "2.15.0", - "resolved": "https://registry.npmjs.org/@azure/msal-node/-/msal-node-2.15.0.tgz", - "integrity": "sha512-gVPW8YLz92ZeCibQH2QUw96odJoiM3k/ZPH3f2HxptozmH6+OnyyvKXo/Egg39HAM230akarQKHf0W74UHlh0Q==", + "version": "2.16.0", + "resolved": "https://registry.npmjs.org/@azure/msal-node/-/msal-node-2.16.0.tgz", + "integrity": "sha512-oww0oJTOOvPKTVXqVyxfcFVjExQKYEkKR5KM0cTG3jnzt6u/MRMx8XaK49L/bxV35r9sCHQFjNlEShad9qGSYA==", "dev": true, "dependencies": { - "@azure/msal-common": "14.15.0", + "@azure/msal-common": "14.16.0", "jsonwebtoken": "^9.0.0", "uuid": "^8.3.0" }, @@ -228,9 +228,9 @@ } }, "node_modules/@babel/code-frame": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.26.0.tgz", - "integrity": "sha512-INCKxTtbXtcNbUZ3YXutwMpEleqttcswhAdee7dhuoVrD2cnuc3PqtERBtxkX5nziX9vnBL8WXmSGwv8CuPV6g==", + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.26.2.tgz", + "integrity": "sha512-RJlIHRueQgwWitWgF8OdFYGZX328Ax5BCemNGlqHfplnRT9ESi8JkFlvaVYbS+UubVY6dpv87Fs2u5M29iNFVQ==", "dev": true, "dependencies": { "@babel/helper-validator-identifier": "^7.25.9", @@ -242,9 +242,9 @@ } }, "node_modules/@babel/compat-data": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.0.tgz", - "integrity": "sha512-qETICbZSLe7uXv9VE8T/RWOdIE5qqyTucOt4zLYMafj2MRO271VGgLd4RACJMeBO37UPWhXiKMBk7YlJ0fOzQA==", + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.2.tgz", + "integrity": "sha512-Z0WgzSEa+aUcdiJuCIqgujCshpMWgUpgOxXotrYPSA53hA3qopNaqcJpyr0hVb1FeWdnqFA35/fUtXgBK8srQg==", "dev": true, "engines": { "node": ">=6.9.0" @@ -296,12 +296,12 @@ } }, "node_modules/@babel/generator": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.0.tgz", - "integrity": "sha512-/AIkAmInnWwgEAJGQr9vY0c66Mj6kjkE2ZPB1PurTRaRAh3U+J45sAQMjQDJdh4WbR3l0x5xkimXBKyBXXAu2w==", + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.2.tgz", + "integrity": "sha512-zevQbhbau95nkoxSq3f/DC/SC+EEOUZd3DYqfSkMhY2/wfSeaHV1Ew4vk8e+x8lja31IbyuUa2uQ3JONqKbysw==", "dev": true, "dependencies": { - "@babel/parser": "^7.26.0", + "@babel/parser": "^7.26.2", "@babel/types": "^7.26.0", "@jridgewell/gen-mapping": "^0.3.5", "@jridgewell/trace-mapping": "^0.3.25", @@ -422,9 +422,9 @@ } }, "node_modules/@babel/parser": { - "version": "7.26.1", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.26.1.tgz", - "integrity": "sha512-reoQYNiAJreZNsJzyrDNzFQ+IQ5JFiIzAHJg9bn94S3l+4++J7RsIhNMoB+lgP/9tpmiAQqspv+xfdxTSzREOw==", + "version": "7.26.2", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.26.2.tgz", + "integrity": "sha512-DWMCZH9WA4Maitz2q21SRKHo9QXZxkDsbNZoVD62gusNtNBBqDg9i7uOhASfTfIGNzW+O+r7+jAlM8dwphcJKQ==", "dev": true, "dependencies": { "@babel/types": "^7.26.0" @@ -944,9 +944,9 @@ } }, "node_modules/@tektronix/kic-cli-darwin-arm64": { - "version": "0.18.4", - "resolved": "https://npm.pkg.github.com/download/@tektronix/kic-cli-darwin-arm64/0.18.4/bec330cd00d27dd7c5975d1e455a6b0d6b794d2c", - "integrity": "sha512-CnSbHr7Qc0Skyd7vkX+/bfcGh74LqXUhU7BbU0JGGDfkkyjroWzb47Dd3OYWdPQXdKozkvwjZkdUvrxMmVysNw==", + "version": "0.19.0-0", + "resolved": "https://npm.pkg.github.com/download/@tektronix/kic-cli-darwin-arm64/0.19.0-0/bcb670613090cf572d34eaed7adb00064d86daaa", + "integrity": "sha512-rNTGrLJ3UkPp3aEaLiFNeylOVwbbsgTNovsDjqaroI2zcTEr6QYH9De3CBkDR470FMhkwrLmB9FauwXdssYr5g==", "cpu": [ "arm64" ], @@ -962,9 +962,9 @@ } }, "node_modules/@tektronix/kic-cli-linux-x64": { - "version": "0.18.4", - "resolved": "https://npm.pkg.github.com/download/@tektronix/kic-cli-linux-x64/0.18.4/b3a387b7f656f2bdc10bce519640c38c352754cc", - "integrity": "sha512-x57ujdwyUJWZVQdji2YYmyFHFjQpSzh/xFBwdan2D5Z0LkAVhcGePDT2AB3rQG3hgcRgHqwh3EVv4VmFZhdyZA==", + "version": "0.19.0-0", + "resolved": "https://npm.pkg.github.com/download/@tektronix/kic-cli-linux-x64/0.19.0-0/64257f6a1300e37b03ba6568bbdce07cb40cf745", + "integrity": "sha512-+AEqIp7n4OV/DgwMTCyGSPmgHn5Q4SOEdboCZgS4WWPOpvL7//F1DDrxdcHdMnokPKWKuBOBtcrDQaN5veleXg==", "cpu": [ "x64" ], @@ -980,9 +980,9 @@ } }, "node_modules/@tektronix/kic-cli-win32-x64": { - "version": "0.18.4", - "resolved": "https://npm.pkg.github.com/download/@tektronix/kic-cli-win32-x64/0.18.4/fdcba619e937da84e75be3b530bd0d89742d3f54", - "integrity": "sha512-ASoSNLW/sCfCWF7OjQKOvMeR1Hur0YCQ6XRs6F7g/bBEkCdEQ2hg7Qu4YgAh7G9y6jr02qAQ6aSOKl6W2/EE9g==", + "version": "0.19.0-0", + "resolved": "https://npm.pkg.github.com/download/@tektronix/kic-cli-win32-x64/0.19.0-0/3501ad9222a40e046a28561b99d11b958258be0d", + "integrity": "sha512-LQDQYcikajhS6yINANLDnjBnSJZjQqWIcYBQHIHRjfDb1XEev/1qfABr13J1Ps+fvAcBJh45F0t47qXJk6kYCg==", "cpu": [ "x64" ], @@ -2020,9 +2020,9 @@ } }, "node_modules/caniuse-lite": { - "version": "1.0.30001673", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001673.tgz", - "integrity": "sha512-WTrjUCSMp3LYX0nE12ECkV0a+e6LC85E0Auz75555/qr78Oc8YWhEPNfDd6SHdtlCMSzqtuXY0uyEMNRcsKpKw==", + "version": "1.0.30001680", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001680.tgz", + "integrity": "sha512-rPQy70G6AGUMnbwS1z6Xg+RkHYPAi18ihs47GH0jcxIG7wArmPgY3XbS2sRdBbxJljp3thdT8BIqv9ccCypiPA==", "dev": true, "funding": [ { @@ -2343,9 +2343,9 @@ "dev": true }, "node_modules/cross-spawn": { - "version": "7.0.3", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", - "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", + "version": "7.0.5", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.5.tgz", + "integrity": "sha512-ZVJrKKYunU38/76t0RMOulHOnUcbU9GbpWKAOZ0mhjr7CX6FVrH+4FrAapSOekrgFQ3f/8gwMEuIft0aKq6Hug==", "dev": true, "dependencies": { "path-key": "^3.1.0", @@ -2688,9 +2688,9 @@ } }, "node_modules/electron-to-chromium": { - "version": "1.5.47", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.47.tgz", - "integrity": "sha512-zS5Yer0MOYw4rtK2iq43cJagHZ8sXN0jDHDKzB+86gSBSAI4v07S97mcq+Gs2vclAxSh1j7vOAHxSVgduiiuVQ==", + "version": "1.5.56", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.56.tgz", + "integrity": "sha512-7lXb9dAvimCFdvUMTyucD4mnIndt/xhRKFAlky0CyFogdnNmdPQNoHI23msF/2V4mpTxMzgMdjK4+YRlFlRQZw==", "dev": true }, "node_modules/emoji-regex": { @@ -3178,9 +3178,9 @@ } }, "node_modules/eslint-plugin-jsdoc/node_modules/eslint-visitor-keys": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.1.0.tgz", - "integrity": "sha512-Q7lok0mqMUSf5a/AdAZkA5a/gHcO6snwQClVNNvFKCAVlxXucdU8pKydU5ZVZjBx5xr37vGbFFWtLQYreLzrZg==", + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.0.tgz", + "integrity": "sha512-UyLnSehNt62FFhSwjZlHmeokpRK59rcz29j+F1/aDgbkbRTk7wIc9XzdoasMUbRNKDM0qQt/+BJ4BrpFeABemw==", "dev": true, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3190,14 +3190,14 @@ } }, "node_modules/eslint-plugin-jsdoc/node_modules/espree": { - "version": "10.2.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-10.2.0.tgz", - "integrity": "sha512-upbkBJbckcCNBDBDXEbuhjbP68n+scUd3k/U2EkyM9nw+I/jPiL4cLF/Al06CF96wRltFda16sxDFrxsI1v0/g==", + "version": "10.3.0", + "resolved": "https://registry.npmjs.org/espree/-/espree-10.3.0.tgz", + "integrity": "sha512-0QYC8b24HWY8zjRnDTL6RiHfDbAWn63qb4LMj1Z4b076A4une81+z03Kg7l7mn/48PUTqoLptSXez8oknU8Clg==", "dev": true, "dependencies": { - "acorn": "^8.12.0", + "acorn": "^8.14.0", "acorn-jsx": "^5.3.2", - "eslint-visitor-keys": "^4.1.0" + "eslint-visitor-keys": "^4.2.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -5969,9 +5969,9 @@ } }, "node_modules/object-inspect": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.2.tgz", - "integrity": "sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==", + "version": "1.13.3", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.3.tgz", + "integrity": "sha512-kDCGIbxkDSXE3euJZZXzc6to7fCrKHNI/hSRQnRuQ+BWjFNzZwiFF8fj/6o2t2G9/jTj8PSIYTfCLelLZEeRpA==", "dev": true, "engines": { "node": ">= 0.4" @@ -6332,9 +6332,9 @@ } }, "node_modules/path-scurry/node_modules/lru-cache": { - "version": "11.0.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.0.1.tgz", - "integrity": "sha512-CgeuL5uom6j/ZVrg7G/+1IXqRY8JXX4Hghfy5YE0EhoYQWvndP1kufu58cmZLNIDKnRhZrXfdS9urVWx98AipQ==", + "version": "11.0.2", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.0.2.tgz", + "integrity": "sha512-123qHRfJBmo2jXDbo/a5YOQrJoHF/GNQTLzQ5+IdK5pWpceK17yRc6ozlWd25FxvGKQbIUs91fDFkXmDHTKcyA==", "dev": true, "engines": { "node": "20 || >=22" @@ -7694,9 +7694,9 @@ } }, "node_modules/ts-api-utils": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.3.0.tgz", - "integrity": "sha512-UQMIo7pb8WRomKR1/+MFVLTroIvDVtMX3K6OUir8ynLyzB8Jeriont2bTAtmNPa1ekAgN7YPDyf6V+ygrdU+eQ==", + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.4.0.tgz", + "integrity": "sha512-032cPxaEKwM+GT3vA5JXNzIaizx388rhsSW79vGRNGXfRRAdEAn2mvk36PvK5HnOchyWZ7afLEXqYCvPCrzuzQ==", "dev": true, "engines": { "node": ">=16" @@ -7791,9 +7791,9 @@ } }, "node_modules/tslib": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.0.tgz", - "integrity": "sha512-jWVzBLplnCmoaTr13V9dYbiQ99wvZRd0vNWaDRg+aVYRcjDF3nDksxFDE/+fkXnKhpnUUkmx5pK/v8mCtLVqZA==", + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", + "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", "dev": true }, "node_modules/tunnel": { diff --git a/package.json b/package.json index 22fef74..ea7ee6b 100644 --- a/package.json +++ b/package.json @@ -3,7 +3,7 @@ "publisher": "Tektronix", "displayName": "Keithley TSP Toolkit", "description": "VSCode extension for Keithley Instruments' Test Script Processor", - "version": "1.0.0", + "version": "1.1.0", "icon": "./resources/TSP_Toolkit_128x128.png", "galleryBanner": { "color": "#EEEEEE", @@ -248,17 +248,17 @@ ], "configuration": { "type": "object", - "title": "TSP Configuration", + "title": "TSP Toolkit", "properties": { - "tsp.errorLimit": { - "type": "number", - "default": 3, - "description": "Maximum number of consecutive errors to print in the terminal" - }, "tsp.savedInstruments": { "type": "array", "default": [], "description": "A list of saved instrument serial numbers" + }, + "tsp.dumpQueueOnConnect": { + "type": "boolean", + "default": false, + "description": "If `true`, collect the contents of the instrument output queue and print it to the terminal when connecting." } } }, @@ -489,9 +489,9 @@ "xml-js": "1.6.11" }, "optionalDependencies": { - "@tektronix/kic-cli-linux-x64": "0.18.4", - "@tektronix/kic-cli-win32-x64": "0.18.4", - "@tektronix/kic-cli-darwin-arm64": "0.18.4" + "@tektronix/kic-cli-linux-x64": "0.19.0-0", + "@tektronix/kic-cli-win32-x64": "0.19.0-0", + "@tektronix/kic-cli-darwin-arm64": "0.19.0-0" }, "extensionDependencies": [ "sumneko.lua" diff --git a/src/communicationmanager.ts b/src/communicationmanager.ts index 3cb798f..c71ff36 100644 --- a/src/communicationmanager.ts +++ b/src/communicationmanager.ts @@ -195,12 +195,12 @@ export class CommunicationManager { * @returns A tuple where the first element (string) is the *idn? info * and the second element (string | undefined) is system generated unique connection name if term_name is empty */ - public createTerminal( + public async createTerminal( term_name: string, connType: IoType, address: string, filePath?: string, - ): [info: string, verified_name?: string] { + ): Promise<[info: string, verified_name?: string]> { const LOGLOC: SourceLocation = { file: "extension.ts", func: `CommunicationManager.createTerminal("${term_name}", "${connType.toString()}", "${address}", "${filePath ?? ""}")`, @@ -217,7 +217,7 @@ export class CommunicationManager { if (parts == null) return ["", undefined] const ip_addr = parts[2] const ip = ip_addr.split(":")[0] //take only IPv4 address, don't include socket. - res = this._kicProcessMgr.createKicCell( + res = await this._kicProcessMgr.createKicCell( term_name, ip, "lan", @@ -234,7 +234,7 @@ export class CommunicationManager { if (string_split.length > 1) { unique_string = string_split[1] } - res = this._kicProcessMgr.createKicCell( + res = await this._kicProcessMgr.createKicCell( term_name, unique_string, "usb", @@ -251,7 +251,7 @@ export class CommunicationManager { if (string_split.length > 1) { unique_string = string_split[1] } - res = this._kicProcessMgr.createKicCell( + res = await this._kicProcessMgr.createKicCell( term_name, unique_string, "visa", diff --git a/src/extension.ts b/src/extension.ts index 9c419a2..0fb1592 100644 --- a/src/extension.ts +++ b/src/extension.ts @@ -62,7 +62,7 @@ export async function createTerminal( Log.debug("Connection type was determined to be LAN", LOGLOC) //LAN Log.trace("Creating terminal", LOGLOC) - res = _activeConnectionManager?.createTerminal( + res = await _activeConnectionManager?.createTerminal( name, IoType.Lan, connection_string, @@ -102,7 +102,7 @@ export async function createTerminal( } else { Log.debug("Connection type was determined to be VISA", LOGLOC) //VISA - res = _activeConnectionManager?.createTerminal( + res = await _activeConnectionManager?.createTerminal( name, IoType.Visa, connection_string, @@ -624,9 +624,9 @@ const base_api = { } }, - restartConnAfterDbg(instr: ConnectionDetails) { + async restartConnAfterDbg(instr: ConnectionDetails) { if (instr != undefined) { - _kicProcessMgr.createKicCell( + await _kicProcessMgr.createKicCell( instr.Name, instr.ConnAddr, instr.ConnType, diff --git a/src/logging.ts b/src/logging.ts index cee3478..d3e7162 100644 --- a/src/logging.ts +++ b/src/logging.ts @@ -145,6 +145,7 @@ export class Log { const content = `${timestamp.toISOString()} [${logLevelToString(level).padEnd(LOGLEVEL_PAD, " ")}] ${toString(location)}${msg}\n` try { appendFileSync(this.file, content) + console.log(content) } catch (err) { console.error(err) } diff --git a/src/resourceManager.ts b/src/resourceManager.ts index 6159058..0cf619b 100644 --- a/src/resourceManager.ts +++ b/src/resourceManager.ts @@ -1,6 +1,8 @@ -import * as child from "child_process" -import { join } from "path" -import { EventEmitter } from "events" +import { mkdtempSync } from "node:fs" +import { join } from "node:path" +import { tmpdir } from "node:os" +import * as child from "node:child_process" +import { EventEmitter } from "node:events" import * as vscode from "vscode" import { EXECUTABLE } from "./kic-cli" import { LOG_DIR } from "./utility" @@ -216,20 +218,20 @@ export class KicProcessMgr { * @param maxerr - maximum error * @param filePath - file path of tsp file to be executed on the instrument */ - public createKicCell( + public async createKicCell( name: string, unique_id: string, connType: string, maxerr?: number, filePath?: string, - ): [info: string, verified_name?: string] { + ): Promise<[info: string, verified_name?: string]> { const LOGLOC: SourceLocation = { file: "resourceManager.ts", func: `KicProcessMgr.createKicCell("${name}", "${unique_id}", "${connType}", "${maxerr ?? ""}", "${filePath ?? ""}")`, } Log.trace("Creating Kic Cell", LOGLOC) const newCell = new KicCell() - const [info, verified_name] = newCell.initialiseComponents( + const [info, verified_name] = await newCell.initialiseComponents( name, unique_id, connType, @@ -243,14 +245,23 @@ export class KicProcessMgr { return [info, verified_name] } - public restartConnectionAfterDebug() { + public async restartConnectionAfterDebug() { if (this._reconnectInstrDetails != undefined) { - this.createKicCell( - this._reconnectInstrDetails.Name, - this._reconnectInstrDetails.ConnAddr, - this._reconnectInstrDetails.ConnType, - this._reconnectInstrDetails.Maxerr, - ) + try { + await this.createKicCell( + this._reconnectInstrDetails.Name, + this._reconnectInstrDetails.ConnAddr, + this._reconnectInstrDetails.ConnType, + this._reconnectInstrDetails.Maxerr, + ) + } catch (error) { + const details = `Unable to reconnect after debugging: ${error?.toString()}` + Log.error(details, { + file: "resourceManager.ts", + func: "restartConnectionAfterDebug", + }) + console.error(details) + } } } @@ -289,148 +300,217 @@ export class KicCell extends EventEmitter { /** * Used to create the components that establish communication with the instrument * */ - public initialiseComponents( + public async initialiseComponents( name: string, unique_id: string, connType: string, maxerr?: number, filePath?: string, - ): [info: string, verified_name?: string] { + ): Promise<[info: string, verified_name?: string]> { //#ToDo: need to verify if maxerr is required const LOGLOC: SourceLocation = { file: "resourceManager.ts", func: `KicCell.initialiseComponents("${name}", "${unique_id}", "${connType}", "${maxerr ?? ""}", "${filePath ?? ""}")`, } - Log.trace("Initializing components", LOGLOC) - this._uniqueID = unique_id - let info = "" - let verified_name: string | undefined = undefined - this._connDetails = new ConnectionDetails( - name, - unique_id, - connType, - maxerr, - ) - - Log.trace("Getting instrument information", LOGLOC) - const info_proc = child.spawnSync( - EXECUTABLE, - [ - "--log-file", - join( - LOG_DIR, - `${new Date().toISOString().substring(0, 10)}-kic.log`, - ), - "info", - connType, - "--json", - unique_id, - ], + return await vscode.window.withProgress( { - env: { CLICOLOR: "1", CLICOLOR_FORCE: "1" }, + cancellable: false, + location: vscode.ProgressLocation.Notification, + title: "Connecting to instrument", }, - ) - const exit_code = info_proc.status - - info = info_proc.stdout.toString() - - Log.trace( - `Info process exited with code: ${exit_code}, information: ${info.trim()}`, - LOGLOC, - ) - - if (info == "") return [info] - - const _info = JSON.parse(info) - void vscode.window.showInformationMessage( - unique_id + - ": Found instrument model " + - _info.model + - " with S/N: " + - _info.serial_number, - ) + (progress) => { + Log.trace("Initializing components", LOGLOC) + this._uniqueID = unique_id + let info = "" + let verified_name: string | undefined = undefined + this._connDetails = new ConnectionDetails( + name, + unique_id, + connType, + maxerr, + ) + + //TODO Get tsp.dumpQueueOnConnect setting + let dump_path: string | undefined = undefined + if ( + vscode.workspace + .getConfiguration("tsp") + .get("dumpQueueOnConnect") + ) { + progress.report({ + increment: 0, + message: "Dumping data from instrument output queue", + }) + Log.info( + "Dumping data from instrument output queue", + LOGLOC, + ) + const dump_dir = mkdtempSync(join(tmpdir(), "tsp-toolkit-")) + dump_path = join(dump_dir, "dump-output") + + Log.trace(`Dumping data to ${dump_path}`, LOGLOC) + + const dump_proc = child.spawnSync(EXECUTABLE, [ + "--log-file", + join( + LOG_DIR, + `${new Date().toISOString().substring(0, 10)}-kic.log`, + ), + "dump", + connType, + unique_id, + "--output", + dump_path, + ]) + Log.trace( + `Dump process exited with code: ${dump_proc.status}}`, + LOGLOC, + ) + } - if (name == "") { - verified_name = FriendlyNameMgr.generateUniqueName( - connType, - _info.model + "#" + _info.serial_number, - ) - name = verified_name - this._connDetails.Name = name - Log.trace(`Set name to "${name}"`, LOGLOC) - } + progress.report({ + increment: 50, + message: "Getting instrument information", + }) + Log.trace("Getting instrument information", LOGLOC) + const info_proc = child.spawnSync( + EXECUTABLE, + [ + "--log-file", + join( + LOG_DIR, + `${new Date().toISOString().substring(0, 10)}-kic.log`, + ), + "info", + connType, + "--json", + unique_id, + ], + { + env: { CLICOLOR: "1", CLICOLOR_FORCE: "1" }, + }, + ) + const exit_code = info_proc.status + + info = info_proc.stdout.toString() + + Log.trace( + `Info process exited with code: ${exit_code}, information: ${info.trim()}`, + LOGLOC, + ) + + if (info == "") return new Promise((resolve) => resolve([info])) + + const _info = JSON.parse(info) + // void vscode.window.showInformationMessage( + // unique_id + + // ": Found instrument model " + + // _info.model + + // " with S/N: " + + // _info.serial_number, + // ) + + if (name == "") { + verified_name = FriendlyNameMgr.generateUniqueName( + connType, + _info.model + "#" + _info.serial_number, + ) + name = verified_name + this._connDetails.Name = name + Log.trace(`Set name to "${name}"`, LOGLOC) + } - Log.trace("Starting VSCode Terminal", LOGLOC) - this._term = vscode.window.createTerminal({ - name: name, - shellPath: EXECUTABLE, - shellArgs: [ - "--log-file", - join( - LOG_DIR, - `${new Date().toISOString().substring(0, 10)}-kic.log`, - ), - "connect", - connType, - unique_id, - ], - iconPath: { - light: vscode.Uri.file( + const terminal_args = [ + "--log-file", join( - __dirname, - "..", - "resources", - "light", - "tsp-terminal-icon.svg", + LOG_DIR, + `${new Date().toISOString().substring(0, 10)}-kic.log`, ), - ), - dark: vscode.Uri.file( - join( - __dirname, - "..", - "resources", - "dark", - "tsp-terminal-icon.svg", - ), - ), - }, - }) - - vscode.window.onDidCloseTerminal((t) => { - Log.info("Terminal closed", LOGLOC) - if ( - t.creationOptions.iconPath !== undefined && - // eslint-disable-next-line @typescript-eslint/no-base-to-string - t.creationOptions.iconPath - .toString() - .search("tsp-terminal-icon") && - t.exitStatus !== undefined && - t.exitStatus.reason !== vscode.TerminalExitReason.Process - ) { - setTimeout(() => { - Log.trace("Resetting closed instrument", LOGLOC) - child.spawnSync(EXECUTABLE, [ - "-v", - "reset", - connType, - unique_id, - ]) - }, 500) - } - }) + "connect", + connType, + unique_id, + ] + + if (dump_path) { + Log.trace(`Showing dump content from ${dump_path}`, LOGLOC) + terminal_args.push("--dump-output", dump_path) + } - this.terminalPid = this._term?.processId + progress.report({ + increment: 10, + message: `Connecting to instrument with model ${_info.model} and S/N ${_info.serial_number}`, + }) + + Log.trace("Starting VSCode Terminal", LOGLOC) + this._term = vscode.window.createTerminal({ + name: name, + shellPath: EXECUTABLE, + shellArgs: terminal_args, + iconPath: { + light: vscode.Uri.file( + join( + __dirname, + "..", + "resources", + "light", + "tsp-terminal-icon.svg", + ), + ), + dark: vscode.Uri.file( + join( + __dirname, + "..", + "resources", + "dark", + "tsp-terminal-icon.svg", + ), + ), + }, + }) + + vscode.window.onDidCloseTerminal((t) => { + Log.info("Terminal closed", LOGLOC) + if ( + t.creationOptions.iconPath !== undefined && + // eslint-disable-next-line @typescript-eslint/no-base-to-string + t.creationOptions.iconPath + .toString() + .search("tsp-terminal-icon") && + t.exitStatus !== undefined && + t.exitStatus.reason !== + vscode.TerminalExitReason.Process + ) { + setTimeout(() => { + Log.trace("Resetting closed instrument", LOGLOC) + child.spawnSync(EXECUTABLE, [ + "-v", + "reset", + connType, + unique_id, + ]) + }, 500) + } + }) + + this.terminalPid = this._term?.processId + + if (this._term != undefined) { + this._term.show() + if (filePath != undefined) { + this._term.sendText(filePath) + } + } - if (this._term != undefined) { - this._term.show() - if (filePath != undefined) { - this._term.sendText(filePath) - } - } + console.log(info) + Log.trace(`Connected to ${info.trim()}`, LOGLOC) - console.log(info) - Log.trace(`Connected to ${info.trim()}`, LOGLOC) - return [info, verified_name] + progress.report({ + increment: 40, + message: `Connected to instrument with model ${_info.model} and S/N ${_info.serial_number}`, + }) + return new Promise((resolve) => resolve([info, verified_name])) + }, + ) } public async getTerminalState(): Promise {