From c6b3b8a4937c85c72f4adfe08ff06b940c962110 Mon Sep 17 00:00:00 2001 From: Jon Lamb Date: Fri, 26 Apr 2024 05:04:26 -0700 Subject: [PATCH] Check if modalityd is reachable on startup --- vscode/package-lock.json | 91 +++++++++++++++++++++++++++++++++++++++ vscode/package.json | 1 + vscode/src/main.ts | 10 ++++- vscode/src/modalityApi.ts | 14 ++++++ 4 files changed, 115 insertions(+), 1 deletion(-) diff --git a/vscode/package-lock.json b/vscode/package-lock.json index 63391f1..20adc87 100644 --- a/vscode/package-lock.json +++ b/vscode/package-lock.json @@ -13,6 +13,7 @@ "@viz-js/viz": "^3.0.1", "@vscode/codicons": "^0.0.32", "@vscode/webview-ui-toolkit": "^1.4.0", + "axios": "^1.6.8", "cytoscape": "^3.28.1", "cytoscape-context-menus": "^4.1.0", "cytoscape-cose-bilkent": "^4.1.0", @@ -1142,6 +1143,21 @@ "node": ">=8" } }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" + }, + "node_modules/axios": { + "version": "1.6.8", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.6.8.tgz", + "integrity": "sha512-v/ZHtJDU39mDpyBoFVkETcd/uNdxrWRrg3bKpOKzXFA6Bvqopts6ALSMU3y6ijYxbw2B+wPrIv46egTzJXCLGQ==", + "dependencies": { + "follow-redirects": "^1.15.6", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, "node_modules/azure-devops-node-api": { "version": "11.2.0", "resolved": "https://registry.npmjs.org/azure-devops-node-api/-/azure-devops-node-api-11.2.0.tgz", @@ -1488,6 +1504,17 @@ "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==", "dev": true }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/commander": { "version": "6.2.1", "resolved": "https://registry.npmjs.org/commander/-/commander-6.2.1.tgz", @@ -1686,6 +1713,14 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/detect-libc": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.0.2.tgz", @@ -2340,6 +2375,38 @@ "integrity": "sha512-X8cqMLLie7KsNUDSdzeN8FYK9rEt4Dt67OsG/DNGnYTSDBG4uFAJFBnUeiV+zCVAvwFy56IjM9sH51jVaEhNxw==", "dev": true }, + "node_modules/follow-redirects": { + "version": "1.15.6", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.6.tgz", + "integrity": "sha512-wWN62YITEaOpSK584EZXJafH1AGpO8RVgElfkuXbTOrPX4fIfOyEpW/CsiNd8JdYrAoOvafRTOEnvsO++qCqFA==", + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, + "node_modules/form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/formdata-polyfill": { "version": "4.0.10", "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", @@ -3177,6 +3244,25 @@ "node": ">=4" } }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/mimic-response": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", @@ -3781,6 +3867,11 @@ "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", "dev": true }, + "node_modules/proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" + }, "node_modules/pump": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", diff --git a/vscode/package.json b/vscode/package.json index 33525c3..07b402b 100644 --- a/vscode/package.json +++ b/vscode/package.json @@ -1029,6 +1029,7 @@ "@viz-js/viz": "^3.0.1", "@vscode/codicons": "^0.0.32", "@vscode/webview-ui-toolkit": "^1.4.0", + "axios": "^1.6.8", "cytoscape": "^3.28.1", "cytoscape-context-menus": "^4.1.0", "cytoscape-cose-bilkent": "^4.1.0", diff --git a/vscode/src/main.ts b/vscode/src/main.ts index d5ea802..53ebda1 100644 --- a/vscode/src/main.ts +++ b/vscode/src/main.ts @@ -31,12 +31,20 @@ let lspClient: LanguageClient; export async function activate(context: vscode.ExtensionContext) { log = vscode.window.createOutputChannel("Auxon"); + const apiUrl = await config.modalityUrl(); + const modalitydIsAlive = await api.isModalitydReachable(apiUrl.toString()); + if (!modalitydIsAlive) { + const msg = + `The Auxon Modality backend server cannot be reached at '${apiUrl}'. ` + + `If modalityd is not running locally, set the 'auxon.modalityUrl' configuration`; + throw new Error(msg); + } + // If this is a fresh install, prompt for new first user creation await user.handleNewUserCreation(); lspClient = await lsp.activateLspClient(context); - const apiUrl = await config.modalityUrl(); const allowInsecure = await config.allowInsecureHttps(); let token = await config.userAuthToken(); diff --git a/vscode/src/modalityApi.ts b/vscode/src/modalityApi.ts index dd8ed79..bfccc91 100644 --- a/vscode/src/modalityApi.ts +++ b/vscode/src/modalityApi.ts @@ -1,5 +1,6 @@ import * as gen from "./generated/src/modality-api"; import createClient from "openapi-fetch"; +import axios from "axios"; // See https://github.com/ajaishankar/openapi-typescript-fetch#server-side-usage import fetch, { Headers, Request, Response } from "node-fetch"; @@ -75,6 +76,19 @@ export type Experiment = gen.components["schemas"]["Experiment"]; type InternalClient = ReturnType>; +export async function isModalitydReachable(baseUrl: string): Promise { + if (baseUrl.endsWith("/")) { + baseUrl = baseUrl.slice(0, -1); + } + const url = baseUrl + "/v1/alive"; + try { + const _response = await axios.get(url); + } catch (_exception) { + return false; + } + return true; +} + export class Client { client: InternalClient;