From 0dbe556835cb7b4b36fefbb7a88ba593c9eb3962 Mon Sep 17 00:00:00 2001 From: Koushik Dutta Date: Sat, 16 Nov 2024 09:40:34 -0800 Subject: [PATCH] diagnostics: use a better defaults for detection plugin verification --- plugins/diagnostics/.vscode/settings.json | 2 +- plugins/diagnostics/package-lock.json | 38 +++++++++++------------ plugins/diagnostics/package.json | 2 +- plugins/diagnostics/src/main.ts | 29 ++++++++++++++--- 4 files changed, 46 insertions(+), 25 deletions(-) diff --git a/plugins/diagnostics/.vscode/settings.json b/plugins/diagnostics/.vscode/settings.json index a620593fa..6688adb73 100644 --- a/plugins/diagnostics/.vscode/settings.json +++ b/plugins/diagnostics/.vscode/settings.json @@ -1,4 +1,4 @@ { - "scrypted.debugHost": "scrypted-nvr", + "scrypted.debugHost": "koushik-winvm", } \ No newline at end of file diff --git a/plugins/diagnostics/package-lock.json b/plugins/diagnostics/package-lock.json index 22d24cda2..3b63a1a38 100644 --- a/plugins/diagnostics/package-lock.json +++ b/plugins/diagnostics/package-lock.json @@ -1,10 +1,12 @@ { "name": "@scrypted/diagnostics", + "version": "0.0.19", "lockfileVersion": 2, "requires": true, "packages": { "": { "name": "@scrypted/diagnostics", + "version": "0.0.19", "dependencies": { "@scrypted/common": "file:../../common", "@scrypted/sdk": "file:../../sdk", @@ -12,8 +14,7 @@ }, "devDependencies": { "@types/node": "^22.5.4" - }, - "version": "0.0.18" + } }, "../../common": { "name": "@scrypted/common", @@ -32,13 +33,13 @@ }, "../../sdk": { "name": "@scrypted/sdk", - "version": "0.3.62", + "version": "0.3.69", "license": "ISC", "dependencies": { - "@babel/preset-typescript": "^7.24.7", - "adm-zip": "^0.5.14", - "axios": "^1.7.3", - "babel-loader": "^9.1.3", + "@babel/preset-typescript": "^7.26.0", + "adm-zip": "^0.5.16", + "axios": "^1.7.7", + "babel-loader": "^9.2.1", "babel-plugin-const-enum": "^1.2.0", "ncp": "^2.0.0", "raw-loader": "^4.0.2", @@ -46,7 +47,7 @@ "tmp": "^0.2.3", "ts-loader": "^9.5.1", "typescript": "^5.5.4", - "webpack": "^5.93.0", + "webpack": "^5.95.0", "webpack-bundle-analyzer": "^4.10.2" }, "bin": { @@ -59,11 +60,11 @@ "scrypted-webpack": "bin/scrypted-webpack.js" }, "devDependencies": { - "@types/node": "^22.1.0", + "@types/node": "^22.8.1", "@types/stringify-object": "^4.0.5", "stringify-object": "^3.3.0", "ts-node": "^10.9.2", - "typedoc": "^0.26.5" + "typedoc": "^0.26.10" } }, "node_modules/@emnapi/runtime": { @@ -719,12 +720,12 @@ "@scrypted/sdk": { "version": "file:../../sdk", "requires": { - "@babel/preset-typescript": "^7.24.7", - "@types/node": "^22.1.0", + "@babel/preset-typescript": "^7.26.0", + "@types/node": "^22.8.1", "@types/stringify-object": "^4.0.5", - "adm-zip": "^0.5.14", - "axios": "^1.7.3", - "babel-loader": "^9.1.3", + "adm-zip": "^0.5.16", + "axios": "^1.7.7", + "babel-loader": "^9.2.1", "babel-plugin-const-enum": "^1.2.0", "ncp": "^2.0.0", "raw-loader": "^4.0.2", @@ -733,9 +734,9 @@ "tmp": "^0.2.3", "ts-loader": "^9.5.1", "ts-node": "^10.9.2", - "typedoc": "^0.26.5", + "typedoc": "^0.26.10", "typescript": "^5.5.4", - "webpack": "^5.93.0", + "webpack": "^5.95.0", "webpack-bundle-analyzer": "^4.10.2" } }, @@ -843,6 +844,5 @@ "integrity": "sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw==", "dev": true } - }, - "version": "0.0.18" + } } diff --git a/plugins/diagnostics/package.json b/plugins/diagnostics/package.json index 114c2ee03..d5f4ce510 100644 --- a/plugins/diagnostics/package.json +++ b/plugins/diagnostics/package.json @@ -1,6 +1,6 @@ { "name": "@scrypted/diagnostics", - "version": "0.0.18", + "version": "0.0.19", "scripts": { "scrypted-setup-project": "scrypted-setup-project", "prescrypted-setup-project": "scrypted-package-json", diff --git a/plugins/diagnostics/src/main.ts b/plugins/diagnostics/src/main.ts index 28241b770..1f7edbf4b 100644 --- a/plugins/diagnostics/src/main.ts +++ b/plugins/diagnostics/src/main.ts @@ -294,6 +294,8 @@ class DiagnosticsPlugin extends ScryptedDeviceBase implements Settings { const nvrPlugin = sdk.systemManager.getDeviceById('@scrypted/nvr'); const cloudPlugin = sdk.systemManager.getDeviceById('@scrypted/cloud'); + const hasCUDA = process.env.NVIDIA_VISIBLE_DEVICES && process.env.NVIDIA_DRIVER_CAPABILITIES; + const onnxPlugin = sdk.systemManager.getDeviceById('@scrypted/onnx'); const openvinoPlugin = sdk.systemManager.getDeviceById('@scrypted/openvino'); await this.validate(this.console, 'Scrypted Installation', async () => { @@ -367,10 +369,14 @@ class DiagnosticsPlugin extends ScryptedDeviceBase implements Settings { }); if (process.platform === 'linux' && nvrPlugin) { - // ensure /dev/dri/renderD128 is available + // ensure /dev/dri/renderD128 or /dev/dri/renderD129 is available await this.validate(this.console, 'GPU Passthrough', async () => { - if (!fs.existsSync('/dev/dri/renderD128')) - throw new Error('GPU device unvailable or not passed through to container.'); + if (!fs.existsSync('/dev/dri/renderD128') && !fs.existsSync('/dev/dri/renderD129')) + throw new Error('GPU device unvailable or not passed through to container. (/dev/dri/renderD128, /dev/dri/renderD129)'); + // also check /dev/kfd for AMD CPU + const amdCPU = os.cpus().find(c => c.model.includes('AMD')); + if (amdCPU && !fs.existsSync('/dev/kfd')) + throw new Error('GPU device unvailable or not passed through to container. (/dev/kfd)'); }); } @@ -406,7 +412,22 @@ class DiagnosticsPlugin extends ScryptedDeviceBase implements Settings { throw new Error('Invalid response received from short lived URL.'); }); - if (openvinoPlugin) { + if ((hasCUDA || process.platform === 'win32') && onnxPlugin) { + await this.validate(this.console, 'ONNX Plugin', async () => { + const settings = await onnxPlugin.getSettings(); + const executionDevice = settings.find(s => s.key === 'execution_device'); + if (executionDevice?.value?.toString().includes('CPU')) + this.warnStep(this.console, 'GPU device unvailable or not passed through to container.'); + + const zidane = await sdk.mediaManager.createMediaObjectFromUrl('https://docs.scrypted.app/img/scrypted-nvr/troubleshooting/zidane.jpg'); + const detected = await onnxPlugin.detectObjects(zidane); + const personFound = detected.detections!.find(d => d.className === 'person' && d.score > .9); + if (!personFound) + throw new Error('Person not detected in test image.'); + }); + } + + if (!hasCUDA && openvinoPlugin && (process.platform !== 'win32' || !onnxPlugin)) { await this.validate(this.console, 'OpenVINO Plugin', async () => { const settings = await openvinoPlugin.getSettings(); const availbleDevices = settings.find(s => s.key === 'available_devices');