@camstack/addon-pipeline 1.2.615 → 1.2.617
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/THIRD_PARTY_MODELS.md +2 -2
- package/dist/audio-analyzer/index.js +3 -3
- package/dist/audio-analyzer/index.mjs +3 -3
- package/dist/{custom-model-catalog-BmJXsT0k.mjs → custom-model-catalog-BT8HKaes.mjs} +3 -3
- package/dist/{custom-model-catalog-DFuM_m3D.js → custom-model-catalog-Yu1sxc4A.js} +3 -3
- package/dist/detection-pipeline/index.js +114 -6
- package/dist/detection-pipeline/index.mjs +114 -6
- package/dist/{dist-B_1t8oSg.js → dist-CGDR6bSg.js} +114 -67
- package/dist/{dist-CfOv146z.mjs → dist-OImyOnr3.mjs} +114 -67
- package/dist/{model-catalogs-Dnj7Cr3q.mjs → model-catalogs-Cj101H8x.mjs} +14 -4
- package/dist/{model-catalogs-Dr-_ANpG.js → model-catalogs-DV562sqJ.js} +14 -4
- package/dist/motion-wasm/index.js +1 -1
- package/dist/motion-wasm/index.mjs +1 -1
- package/dist/{node-D82_5p1M.js → node-CSFdbFlw.js} +1 -1
- package/dist/{node-tn9-iwDj.mjs → node-DciF_ZRl.mjs} +1 -1
- package/dist/pipeline-runner/index.js +3 -3
- package/dist/pipeline-runner/index.mjs +3 -3
- package/dist/{process-memory-BlkUi_7x.js → process-memory-CJEkTpRM.js} +1 -1
- package/dist/{process-memory-CD5f3ehN.mjs → process-memory-DjIov9TF.mjs} +1 -1
- package/dist/recorder/index.js +80 -5
- package/dist/recorder/index.mjs +80 -5
- package/dist/{segment-demux-js-Cx61fdp7.mjs → segment-demux-js-B5PU-E-G.mjs} +1 -1
- package/dist/{segment-demux-js-uWcwFqRL.js → segment-demux-js-BsqG99U7.js} +1 -1
- package/dist/stream-broker/_stub.js +2 -2
- package/dist/stream-broker/{_virtual_mf-localSharedImportMap___mfe_internal__addon_stream_broker_widgets-dldjR7yB.mjs → _virtual_mf-localSharedImportMap___mfe_internal__addon_stream_broker_widgets-BVGTBmAI.mjs} +3 -3
- package/dist/stream-broker/_virtual_mf___mfe_internal__addon_stream_broker_widgets__loadShare___mf_0_camstack_mf_1_types__loadShare__.js-BubwMH51.mjs +26 -0
- package/dist/stream-broker/{_virtual_mf___mfe_internal__addon_stream_broker_widgets__loadShare___mf_0_camstack_mf_1_ui_mf_2_library__loadShare__.js-BvJiBUdN.mjs → _virtual_mf___mfe_internal__addon_stream_broker_widgets__loadShare___mf_0_camstack_mf_1_ui_mf_2_library__loadShare__.js-TnEvW5tZ.mjs} +1 -1
- package/dist/stream-broker/demux-worker-child.js +1 -1
- package/dist/stream-broker/demux-worker-child.mjs +1 -1
- package/dist/stream-broker/{hostInit-Bo0bh2FZ.mjs → hostInit-CMCfVKgd.mjs} +3 -3
- package/dist/stream-broker/index.js +38 -5
- package/dist/stream-broker/index.mjs +38 -5
- package/dist/stream-broker/remoteEntry.js +1 -1
- package/package.json +1 -1
- package/python/inference_pool.py +33 -0
- package/python/openvino_compile_probe.py +245 -0
- package/python/test_openvino_compile_probe.py +298 -0
- package/dist/stream-broker/_virtual_mf___mfe_internal__addon_stream_broker_widgets__loadShare___mf_0_camstack_mf_1_types__loadShare__.js-D4kDfIKO.mjs +0 -26
package/THIRD_PARTY_MODELS.md
CHANGED
|
@@ -123,8 +123,8 @@ entry kept resolvable for a saved selection but no longer offered.
|
|
|
123
123
|
| --- | --- | --- | --- | --- | --- |
|
|
124
124
|
| `yolo26n-seg`, `yolo26s-seg`, `yolo26m-seg` | [Ultralytics](https://github.com/ultralytics/ultralytics) | AGPL-3.0 / AGPL-3.0 (`AGPL-3.0.txt`) | COCO 2017: annotations CC-BY-4.0; images under their Flickr owners' terms | exported to ONNX, OpenVINO IR and CoreML | mirror `segmentation/yolo26-seg` |
|
|
125
125
|
| `yolo26n` (default), `yolo26s`, `yolo26m`, `yolo26l`, `yolo26x` (hidden), `yolo26n-fp16` (hidden), `yolo26n-int8`, `yolo26s-fp16` (hidden), `yolo26s-int8`, `yolo26m-fp16` (hidden), `yolo26m-int8`, `yolo26l-fp16` (hidden), `yolo26l-int8`, `yolo26n-320`, `yolo26n-320-int8`, `yolo26n-256`, `yolo26n-256-int8`, `yolo26s-320`, `yolo26s-320-int8`, `yolo26s-256`, `yolo26s-256-int8`, `yolo26m-320`, `yolo26m-320-int8`, `yolo26m-256`, `yolo26m-256-int8`, `yolo26l-320`, `yolo26l-320-int8`, `yolo26l-256`, `yolo26l-256-int8`, `yolo26x-fp16` (hidden), `yolo26x-int8` (hidden) | [Ultralytics](https://github.com/ultralytics/ultralytics) | AGPL-3.0 / AGPL-3.0 (`AGPL-3.0.txt`) | COCO 2017: annotations CC-BY-4.0; images under their Flickr owners' terms | exported to ONNX, OpenVINO IR and CoreML (scripts/build-camstack-models.py); OpenVINO FP16 export; exported to OpenVINO IR, then OpenVINO NNCF INT8 post-training quantisation; re-exported at 320×320 to ONNX, OpenVINO IR and CoreML; re-exported at 320×320 to OpenVINO IR; OpenVINO NNCF INT8 post-training quantisation; re-exported at 256×256 to ONNX, OpenVINO IR and CoreML; re-exported at 256×256 to OpenVINO IR; OpenVINO NNCF INT8 post-training quantisation | mirror `objectDetection/yolo26` |
|
|
126
|
-
| `ssd-mobilenet-v2-coco-edgetpu`
|
|
127
|
-
| `yolov9s-320-edgetpu
|
|
126
|
+
| `ssd-mobilenet-v2-coco-edgetpu` | [Google Coral test_data](https://github.com/google-coral/test_data) | Apache-2.0 / Apache-2.0 (`Apache-2.0.txt`) | COCO 2017: annotations CC-BY-4.0; images under their Flickr owners' terms | none | https://github.com/google-coral/test_data |
|
|
127
|
+
| `yolov9s-320-edgetpu` (default), `yolov9s-512-edgetpu` | [YOLOv9-s EdgeTPU (Dan Brown)](https://github.com/dbro/frigate-detector-edgetpu-yolo9) | GPL-3.0 / GPL-3.0 (`GPL-3.0.txt`) | COCO 2017: annotations CC-BY-4.0; images under their Flickr owners' terms | none: the publisher release files are mirrored byte-identical | mirror `objectDetection/yolov9` |
|
|
128
128
|
| `yolov9t-320`, `yolov9t-320-int8`, `yolov9t-640`, `yolov9t-640-int8`, `yolov9s-320`, `yolov9s-320-int8`, `yolov9s-640`, `yolov9s-640-int8`, `yolov9m-320`, `yolov9m-320-int8`, `yolov9m-640`, `yolov9m-640-int8`, `yolov9c-320`, `yolov9c-320-int8`, `yolov9c-640`, `yolov9c-640-int8` | [Ultralytics](https://github.com/ultralytics/ultralytics) | AGPL-3.0 / AGPL-3.0 (`AGPL-3.0.txt`) | COCO 2017: annotations CC-BY-4.0; images under their Flickr owners' terms | exported at 320×320 to ONNX, OpenVINO IR FP16 and CoreML; exported at 320×320 to OpenVINO IR; OpenVINO NNCF INT8 post-training quantisation; exported at 640×640 to ONNX, OpenVINO IR FP16 and CoreML; exported at 640×640 to OpenVINO IR; OpenVINO NNCF INT8 post-training quantisation | mirror `objectDetection/yolov9` |
|
|
129
129
|
|
|
130
130
|
### Package detection
|
|
@@ -3,9 +3,9 @@ Object.defineProperties(exports, {
|
|
|
3
3
|
[Symbol.toStringTag]: { value: "Module" }
|
|
4
4
|
});
|
|
5
5
|
const require_chunk = require("../chunk-emK7D4bc.js");
|
|
6
|
-
const require_dist = require("../dist-
|
|
7
|
-
const require_model_catalogs = require("../model-catalogs-
|
|
8
|
-
const require_process_memory = require("../process-memory-
|
|
6
|
+
const require_dist = require("../dist-CGDR6bSg.js");
|
|
7
|
+
const require_model_catalogs = require("../model-catalogs-DV562sqJ.js");
|
|
8
|
+
const require_process_memory = require("../process-memory-CJEkTpRM.js");
|
|
9
9
|
let node_fs = require("node:fs");
|
|
10
10
|
node_fs = require_chunk.__toESM(node_fs);
|
|
11
11
|
let node_path = require("node:path");
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { n as __require } from "../chunk-DnnnRqeS.mjs";
|
|
2
|
-
import { $ as audioAnalyzerCapability, F as PoolMemoryWatchdog, Kn as hydrateSchema, Mn as errMsg, Pn as BaseAddon, Q as audioAnalysisCapability, Qn as nodePin, Rt as mapAudioLabelToMacro, Wn as expandAudioChunkToF32le, h as DEFAULT_AUDIO_ANALYZER_CONFIG, hr as EventCategory, ln as resolvePoolMemoryPolicy, r as AUDIO_BACKEND_CHOICES, zn as audioChunkBytesPerSample } from "../dist-
|
|
3
|
-
import { n as AUDIO_CLASSIFIER_MODELS } from "../model-catalogs-
|
|
4
|
-
import { n as pickNodePlatformArch, t as readProcessMemory } from "../process-memory-
|
|
2
|
+
import { $ as audioAnalyzerCapability, F as PoolMemoryWatchdog, Kn as hydrateSchema, Mn as errMsg, Pn as BaseAddon, Q as audioAnalysisCapability, Qn as nodePin, Rt as mapAudioLabelToMacro, Wn as expandAudioChunkToF32le, h as DEFAULT_AUDIO_ANALYZER_CONFIG, hr as EventCategory, ln as resolvePoolMemoryPolicy, r as AUDIO_BACKEND_CHOICES, zn as audioChunkBytesPerSample } from "../dist-OImyOnr3.mjs";
|
|
3
|
+
import { n as AUDIO_CLASSIFIER_MODELS } from "../model-catalogs-Cj101H8x.mjs";
|
|
4
|
+
import { n as pickNodePlatformArch, t as readProcessMemory } from "../process-memory-DjIov9TF.mjs";
|
|
5
5
|
import * as fs from "node:fs";
|
|
6
6
|
import * as path$1 from "node:path";
|
|
7
7
|
import { ensureModel } from "@camstack/system/addon-utils";
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { Mt as inferModelProvider, b as DEVICE_BACKEND_TO_FORMAT, et as audioKindId, f as COCO_80_LABELS, hn as stepModelRunsOnFormat, i as AUDIO_MACRO_LABELS, k as LABEL_SUPPLY_VOCABULARIES, p as COCO_TO_MACRO } from "./dist-
|
|
2
|
-
import { a as FACE_DETECTION_MODELS, c as OBJECT_DETECTION_MODELS, d as PLATE_OCR_MODELS, f as SEGMENTATION_REFINER_MODELS, i as CLIP_EMBEDDING_MODELS, l as PACKAGE_DETECTION_MODELS, n as AUDIO_CLASSIFIER_MODELS, o as FACE_EMBEDDING_MODELS, p as VEHICLE_CLASSIFIER_MODELS, r as BIRD_CLASSIFIER_MODELS, s as INSTANCE_SEGMENTATION_MODELS, t as ANIMAL_CLASSIFIER_MODELS, u as PLATE_DETECTION_MODELS } from "./model-catalogs-
|
|
1
|
+
import { Mt as inferModelProvider, b as DEVICE_BACKEND_TO_FORMAT, et as audioKindId, f as COCO_80_LABELS, hn as stepModelRunsOnFormat, i as AUDIO_MACRO_LABELS, k as LABEL_SUPPLY_VOCABULARIES, p as COCO_TO_MACRO } from "./dist-OImyOnr3.mjs";
|
|
2
|
+
import { a as FACE_DETECTION_MODELS, c as OBJECT_DETECTION_MODELS, d as PLATE_OCR_MODELS, f as SEGMENTATION_REFINER_MODELS, i as CLIP_EMBEDDING_MODELS, l as PACKAGE_DETECTION_MODELS, n as AUDIO_CLASSIFIER_MODELS, o as FACE_EMBEDDING_MODELS, p as VEHICLE_CLASSIFIER_MODELS, r as BIRD_CLASSIFIER_MODELS, s as INSTANCE_SEGMENTATION_MODELS, t as ANIMAL_CLASSIFIER_MODELS, u as PLATE_DETECTION_MODELS } from "./model-catalogs-Cj101H8x.mjs";
|
|
3
3
|
import { t as isWorkerReply } from "./worker-protocol-D_NzPcnh.mjs";
|
|
4
4
|
import { randomUUID } from "node:crypto";
|
|
5
5
|
//#region src/detection-pipeline/registry/effective-confidence.ts
|
|
@@ -99,7 +99,7 @@ var ObjectDetectionStep = class {
|
|
|
99
99
|
labelTier: 1,
|
|
100
100
|
models: [...OBJECT_DETECTION_MODELS],
|
|
101
101
|
defaultModelId: "yolo26n",
|
|
102
|
-
defaultModelIdByFormat: { tflite: "
|
|
102
|
+
defaultModelIdByFormat: { tflite: "yolov9s-320-edgetpu" },
|
|
103
103
|
defaultConfidence: .5,
|
|
104
104
|
labels: COCO_80_LABELS.map((l) => l.id),
|
|
105
105
|
classMap: COCO_TO_MACRO
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
const require_dist = require("./dist-
|
|
2
|
-
const require_model_catalogs = require("./model-catalogs-
|
|
1
|
+
const require_dist = require("./dist-CGDR6bSg.js");
|
|
2
|
+
const require_model_catalogs = require("./model-catalogs-DV562sqJ.js");
|
|
3
3
|
const require_worker_protocol = require("./worker-protocol-C-G8qmye.js");
|
|
4
4
|
let node_crypto = require("node:crypto");
|
|
5
5
|
//#region src/detection-pipeline/registry/effective-confidence.ts
|
|
@@ -99,7 +99,7 @@ var ObjectDetectionStep = class {
|
|
|
99
99
|
labelTier: 1,
|
|
100
100
|
models: [...require_model_catalogs.OBJECT_DETECTION_MODELS],
|
|
101
101
|
defaultModelId: "yolo26n",
|
|
102
|
-
defaultModelIdByFormat: { tflite: "
|
|
102
|
+
defaultModelIdByFormat: { tflite: "yolov9s-320-edgetpu" },
|
|
103
103
|
defaultConfidence: .5,
|
|
104
104
|
labels: require_dist.COCO_80_LABELS.map((l) => l.id),
|
|
105
105
|
classMap: require_dist.COCO_TO_MACRO
|
|
@@ -3,11 +3,11 @@ Object.defineProperties(exports, {
|
|
|
3
3
|
[Symbol.toStringTag]: { value: "Module" }
|
|
4
4
|
});
|
|
5
5
|
const require_chunk = require("../chunk-emK7D4bc.js");
|
|
6
|
-
const require_dist = require("../dist-
|
|
7
|
-
const require_node = require("../node-
|
|
8
|
-
const require_custom_model_catalog = require("../custom-model-catalog-
|
|
6
|
+
const require_dist = require("../dist-CGDR6bSg.js");
|
|
7
|
+
const require_node = require("../node-CSFdbFlw.js");
|
|
8
|
+
const require_custom_model_catalog = require("../custom-model-catalog-Yu1sxc4A.js");
|
|
9
9
|
const require_lazy_sharp = require("../lazy-sharp-BuwKlQLR.js");
|
|
10
|
-
const require_process_memory = require("../process-memory-
|
|
10
|
+
const require_process_memory = require("../process-memory-CJEkTpRM.js");
|
|
11
11
|
let node_os = require("node:os");
|
|
12
12
|
node_os = require_chunk.__toESM(node_os);
|
|
13
13
|
let node_fs = require("node:fs");
|
|
@@ -4164,6 +4164,72 @@ var IdlePoolReaper = class {
|
|
|
4164
4164
|
}
|
|
4165
4165
|
}
|
|
4166
4166
|
};
|
|
4167
|
+
/** The key a benchmark's model loads are tracked under, apart from the live device's. */
|
|
4168
|
+
var BENCHMARK_KEY_PREFIX = "bench:";
|
|
4169
|
+
function benchmarkKeyOf(deviceKey) {
|
|
4170
|
+
return `${BENCHMARK_KEY_PREFIX}${deviceKey}`;
|
|
4171
|
+
}
|
|
4172
|
+
/** True for the one-shot UI benchmark call — see the file header for why the shape is enough. */
|
|
4173
|
+
function isBenchmarkRun(input) {
|
|
4174
|
+
return input.frame === void 0 && input.frameRef === void 0 && input.deviceId === void 0 && input.replay !== true;
|
|
4175
|
+
}
|
|
4176
|
+
var BenchmarkPools = class {
|
|
4177
|
+
options;
|
|
4178
|
+
pools = /* @__PURE__ */ new Map();
|
|
4179
|
+
inflight = /* @__PURE__ */ new Map();
|
|
4180
|
+
reaper;
|
|
4181
|
+
constructor(options) {
|
|
4182
|
+
this.options = options;
|
|
4183
|
+
this.reaper = new IdlePoolReaper({
|
|
4184
|
+
ttlMs: options.ttlMs ?? 3e5,
|
|
4185
|
+
dispose: (key) => this.disposeOne(key),
|
|
4186
|
+
onError: (key, err) => options.onDisposeError?.(key, err)
|
|
4187
|
+
});
|
|
4188
|
+
}
|
|
4189
|
+
/** The benchmark pool for `deviceKey`: warm if one is up, otherwise built (single-flight). */
|
|
4190
|
+
async acquire(deviceKey, engine) {
|
|
4191
|
+
const existing = this.pools.get(deviceKey);
|
|
4192
|
+
if (existing) {
|
|
4193
|
+
if (existing.isReady()) {
|
|
4194
|
+
this.reaper.touch(deviceKey);
|
|
4195
|
+
return existing;
|
|
4196
|
+
}
|
|
4197
|
+
this.pools.delete(deviceKey);
|
|
4198
|
+
this.reaper.cancel(deviceKey);
|
|
4199
|
+
await existing.dispose().catch(() => void 0);
|
|
4200
|
+
}
|
|
4201
|
+
const pending = this.inflight.get(deviceKey);
|
|
4202
|
+
if (pending) return pending;
|
|
4203
|
+
const creation = (async () => {
|
|
4204
|
+
const pool = await this.options.create(deviceKey, engine);
|
|
4205
|
+
this.pools.set(deviceKey, pool);
|
|
4206
|
+
this.reaper.touch(deviceKey);
|
|
4207
|
+
return pool;
|
|
4208
|
+
})();
|
|
4209
|
+
this.inflight.set(deviceKey, creation);
|
|
4210
|
+
try {
|
|
4211
|
+
return await creation;
|
|
4212
|
+
} finally {
|
|
4213
|
+
this.inflight.delete(deviceKey);
|
|
4214
|
+
}
|
|
4215
|
+
}
|
|
4216
|
+
/** The device keys that currently hold a benchmark pool. */
|
|
4217
|
+
deviceKeys() {
|
|
4218
|
+
return [...this.pools.keys()];
|
|
4219
|
+
}
|
|
4220
|
+
async disposeAll() {
|
|
4221
|
+
this.reaper.disposeAll();
|
|
4222
|
+
const pools = [...this.pools.values()];
|
|
4223
|
+
this.pools.clear();
|
|
4224
|
+
await Promise.all(pools.map((p) => p.dispose().catch(() => void 0)));
|
|
4225
|
+
}
|
|
4226
|
+
async disposeOne(deviceKey) {
|
|
4227
|
+
const pool = this.pools.get(deviceKey);
|
|
4228
|
+
if (!pool) return;
|
|
4229
|
+
this.pools.delete(deviceKey);
|
|
4230
|
+
await pool.dispose();
|
|
4231
|
+
}
|
|
4232
|
+
};
|
|
4167
4233
|
//#endregion
|
|
4168
4234
|
//#region src/detection-pipeline/engine/inference-device-liveness.ts
|
|
4169
4235
|
/**
|
|
@@ -8266,6 +8332,18 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
8266
8332
|
executorOptions;
|
|
8267
8333
|
engineFactory = null;
|
|
8268
8334
|
/**
|
|
8335
|
+
* The pools a benchmark call loads its models into (D910): one separate
|
|
8336
|
+
* worker per device, never `factoriesByDevice` and never the node-default
|
|
8337
|
+
* pool, so a compile that kills its worker cannot take live detection down.
|
|
8338
|
+
*/
|
|
8339
|
+
benchmarkPools = new BenchmarkPools({
|
|
8340
|
+
create: (deviceKey, engine) => this.createBenchmarkFactory(deviceKey, engine),
|
|
8341
|
+
onDisposeError: (deviceKey, err) => this.log.warn("Idle benchmark pool dispose failed", { meta: {
|
|
8342
|
+
deviceKey,
|
|
8343
|
+
error: err instanceof Error ? err.message : String(err)
|
|
8344
|
+
} })
|
|
8345
|
+
});
|
|
8346
|
+
/**
|
|
8269
8347
|
* Per-device engine factories (Phase 2 multi-device), keyed by deviceKey
|
|
8270
8348
|
* (`<backend>:<device>`, e.g. `openvino:npu`, `edgetpu:usb`). Each is its own
|
|
8271
8349
|
* inference pool, warm CONCURRENTLY — so the node runs detection on NPU + iGPU
|
|
@@ -9712,12 +9790,13 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
9712
9790
|
});
|
|
9713
9791
|
this.executor = executor;
|
|
9714
9792
|
const dispatchEngine = dispatchDeviceKey ? require_custom_model_catalog.resolveDeviceEngine(dispatchDeviceKey) : runEngine;
|
|
9715
|
-
const
|
|
9793
|
+
const benchmark = isBenchmarkRun(input);
|
|
9794
|
+
const dispatchFactory = benchmark ? await this.benchmarkPools.acquire(require_custom_model_catalog.deviceKeyOf(dispatchEngine), dispatchEngine) : dispatchDeviceKey ? await this.resolveDeviceFactory(dispatchDeviceKey) : this.engineFactory;
|
|
9716
9795
|
const needed = enabledSteps.filter((s) => dispatchFactory.needsPoolUpdate(s));
|
|
9717
9796
|
let runSteps = benchmarkSteps;
|
|
9718
9797
|
const loadPolicy = dispatchLoadPolicyOf(input);
|
|
9719
9798
|
if (needed.length > 0) {
|
|
9720
|
-
const dispatchDeviceKeyLabel = require_custom_model_catalog.deviceKeyOf(dispatchEngine);
|
|
9799
|
+
const dispatchDeviceKeyLabel = benchmark ? benchmarkKeyOf(require_custom_model_catalog.deviceKeyOf(dispatchEngine)) : require_custom_model_catalog.deviceKeyOf(dispatchEngine);
|
|
9721
9800
|
const toIssue = needed.filter((s) => this.loadGovernor.check(dispatchFactory, dispatchDeviceKeyLabel, [stepModelKey(s)]).kind === "go");
|
|
9722
9801
|
if (toIssue.length > 0) this.log.info("Benchmark: models to load", { meta: {
|
|
9723
9802
|
count: toIssue.length,
|
|
@@ -10583,6 +10662,7 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
10583
10662
|
this.engineFactory = null;
|
|
10584
10663
|
this.executor = null;
|
|
10585
10664
|
}
|
|
10665
|
+
await this.benchmarkPools.disposeAll();
|
|
10586
10666
|
this.deviceReaper.disposeAll();
|
|
10587
10667
|
const deviceFactories = Array.from(this.factoriesByDevice.values());
|
|
10588
10668
|
this.factoriesByDevice.clear();
|
|
@@ -10919,6 +10999,34 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
10919
10999
|
} });
|
|
10920
11000
|
return { rearmed };
|
|
10921
11001
|
}
|
|
11002
|
+
/**
|
|
11003
|
+
* Build the pool a benchmark loads into: a fresh worker for the engine of
|
|
11004
|
+
* `deviceKey`, outside the live pools' liveness budget and late-compile
|
|
11005
|
+
* bookkeeping (a benchmark's failure is a verdict about the benchmark).
|
|
11006
|
+
*/
|
|
11007
|
+
async createBenchmarkFactory(deviceKey, engine) {
|
|
11008
|
+
await this.ensureBackendDeps(engine);
|
|
11009
|
+
const factory = new EngineFactory({
|
|
11010
|
+
engine,
|
|
11011
|
+
modelsDir: this.modelsDir,
|
|
11012
|
+
logger: this.log.child(`bench:${deviceKey}`),
|
|
11013
|
+
pythonPath: this.executorOptions.pythonPath ?? "",
|
|
11014
|
+
provisioning: this.executorOptions.provisioning,
|
|
11015
|
+
resolveCustomModel: this.customModelResolver
|
|
11016
|
+
});
|
|
11017
|
+
try {
|
|
11018
|
+
await factory.initialize([]);
|
|
11019
|
+
} catch (err) {
|
|
11020
|
+
await factory.dispose().catch(() => void 0);
|
|
11021
|
+
this.log.error("Benchmark pool failed to initialize", { meta: {
|
|
11022
|
+
deviceKey,
|
|
11023
|
+
error: require_dist.errMsg(err)
|
|
11024
|
+
} });
|
|
11025
|
+
throw err;
|
|
11026
|
+
}
|
|
11027
|
+
this.log.info("Benchmark pool started — its loads stay out of the live pool", { meta: { deviceKey } });
|
|
11028
|
+
return factory;
|
|
11029
|
+
}
|
|
10922
11030
|
async resolveDeviceFactory(deviceKey) {
|
|
10923
11031
|
const engine = require_custom_model_catalog.resolveDeviceEngine(deviceKey);
|
|
10924
11032
|
if (enginesEqual(engine, this.currentEngine)) {
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { n as __require } from "../chunk-DnnnRqeS.mjs";
|
|
2
|
-
import { Bn as createEvent, Ct as evaluateZoneRules, F as PoolMemoryWatchdog, Gn as hfModelUrl, It as loadContributionCapability, Jt as pickClusterStepSettings, Kn as hydrateSchema, Kt as overlayClusterStepSettings, Mn as errMsg$1, O as LABEL_SUPPLY_MACRO, Pn as BaseAddon, Pt as linkedLabelStepId, Qn as nodePin, St as enumerateInferenceDevices, Wt as modelBindingKey, X as applyModelBoundSettings, Zt as pipelineExecutorCapability, _t as detectionPipelineCapability, bn as supportedRuntimes$1, ct as containingParentIndex, d as CLUSTER_MODEL_SCOPED_STEPS, fn as rootSuppliesOf, ft as defaultDeviceFor$1, g as DEFAULT_CLUSTER_STEP_SETTINGS, hn as stepModelRunsOnFormat, hr as EventCategory, in as resolveClusterStepModelId, ir as array, ln as resolvePoolMemoryPolicy, mr as union, n as APPLE_SA_TO_MACRO, pn as runtimeDevices$1, pr as string, q as YAMNET_TO_MACRO, st as collectModelBoundKeys, tr as sleep, ur as object, yt as edgetpuDelegateDevice } from "../dist-
|
|
3
|
-
import { c as readProcessCost } from "../node-
|
|
4
|
-
import { C as resolveModelDefaultConfidence, S as landmarkPrecisionVerdict, _ as ALL_STEPS, b as getStepDefinition, f as localFrameRegistry, g as ALL_PIPELINE_STEPS, l as resolveDefaultDetectionModel, n as mergeCustomModels, o as deviceKeyOf, r as buildSubtreeCanRun, s as resolveDeviceEngine, t as CustomModelCatalog, u as macroGateVerdict, v as getDefaultModelForFormat, x as resolveModelForFormat, y as getStep } from "../custom-model-catalog-
|
|
2
|
+
import { Bn as createEvent, Ct as evaluateZoneRules, F as PoolMemoryWatchdog, Gn as hfModelUrl, It as loadContributionCapability, Jt as pickClusterStepSettings, Kn as hydrateSchema, Kt as overlayClusterStepSettings, Mn as errMsg$1, O as LABEL_SUPPLY_MACRO, Pn as BaseAddon, Pt as linkedLabelStepId, Qn as nodePin, St as enumerateInferenceDevices, Wt as modelBindingKey, X as applyModelBoundSettings, Zt as pipelineExecutorCapability, _t as detectionPipelineCapability, bn as supportedRuntimes$1, ct as containingParentIndex, d as CLUSTER_MODEL_SCOPED_STEPS, fn as rootSuppliesOf, ft as defaultDeviceFor$1, g as DEFAULT_CLUSTER_STEP_SETTINGS, hn as stepModelRunsOnFormat, hr as EventCategory, in as resolveClusterStepModelId, ir as array, ln as resolvePoolMemoryPolicy, mr as union, n as APPLE_SA_TO_MACRO, pn as runtimeDevices$1, pr as string, q as YAMNET_TO_MACRO, st as collectModelBoundKeys, tr as sleep, ur as object, yt as edgetpuDelegateDevice } from "../dist-OImyOnr3.mjs";
|
|
3
|
+
import { c as readProcessCost } from "../node-DciF_ZRl.mjs";
|
|
4
|
+
import { C as resolveModelDefaultConfidence, S as landmarkPrecisionVerdict, _ as ALL_STEPS, b as getStepDefinition, f as localFrameRegistry, g as ALL_PIPELINE_STEPS, l as resolveDefaultDetectionModel, n as mergeCustomModels, o as deviceKeyOf, r as buildSubtreeCanRun, s as resolveDeviceEngine, t as CustomModelCatalog, u as macroGateVerdict, v as getDefaultModelForFormat, x as resolveModelForFormat, y as getStep } from "../custom-model-catalog-BT8HKaes.mjs";
|
|
5
5
|
import { t as getSharp } from "../lazy-sharp-DXsqwpph.mjs";
|
|
6
|
-
import { n as pickNodePlatformArch, t as readProcessMemory } from "../process-memory-
|
|
6
|
+
import { n as pickNodePlatformArch, t as readProcessMemory } from "../process-memory-DjIov9TF.mjs";
|
|
7
7
|
import * as os$1 from "node:os";
|
|
8
8
|
import * as fs from "node:fs";
|
|
9
9
|
import * as path$1 from "node:path";
|
|
@@ -4157,6 +4157,72 @@ var IdlePoolReaper = class {
|
|
|
4157
4157
|
}
|
|
4158
4158
|
}
|
|
4159
4159
|
};
|
|
4160
|
+
/** The key a benchmark's model loads are tracked under, apart from the live device's. */
|
|
4161
|
+
var BENCHMARK_KEY_PREFIX = "bench:";
|
|
4162
|
+
function benchmarkKeyOf(deviceKey) {
|
|
4163
|
+
return `${BENCHMARK_KEY_PREFIX}${deviceKey}`;
|
|
4164
|
+
}
|
|
4165
|
+
/** True for the one-shot UI benchmark call — see the file header for why the shape is enough. */
|
|
4166
|
+
function isBenchmarkRun(input) {
|
|
4167
|
+
return input.frame === void 0 && input.frameRef === void 0 && input.deviceId === void 0 && input.replay !== true;
|
|
4168
|
+
}
|
|
4169
|
+
var BenchmarkPools = class {
|
|
4170
|
+
options;
|
|
4171
|
+
pools = /* @__PURE__ */ new Map();
|
|
4172
|
+
inflight = /* @__PURE__ */ new Map();
|
|
4173
|
+
reaper;
|
|
4174
|
+
constructor(options) {
|
|
4175
|
+
this.options = options;
|
|
4176
|
+
this.reaper = new IdlePoolReaper({
|
|
4177
|
+
ttlMs: options.ttlMs ?? 3e5,
|
|
4178
|
+
dispose: (key) => this.disposeOne(key),
|
|
4179
|
+
onError: (key, err) => options.onDisposeError?.(key, err)
|
|
4180
|
+
});
|
|
4181
|
+
}
|
|
4182
|
+
/** The benchmark pool for `deviceKey`: warm if one is up, otherwise built (single-flight). */
|
|
4183
|
+
async acquire(deviceKey, engine) {
|
|
4184
|
+
const existing = this.pools.get(deviceKey);
|
|
4185
|
+
if (existing) {
|
|
4186
|
+
if (existing.isReady()) {
|
|
4187
|
+
this.reaper.touch(deviceKey);
|
|
4188
|
+
return existing;
|
|
4189
|
+
}
|
|
4190
|
+
this.pools.delete(deviceKey);
|
|
4191
|
+
this.reaper.cancel(deviceKey);
|
|
4192
|
+
await existing.dispose().catch(() => void 0);
|
|
4193
|
+
}
|
|
4194
|
+
const pending = this.inflight.get(deviceKey);
|
|
4195
|
+
if (pending) return pending;
|
|
4196
|
+
const creation = (async () => {
|
|
4197
|
+
const pool = await this.options.create(deviceKey, engine);
|
|
4198
|
+
this.pools.set(deviceKey, pool);
|
|
4199
|
+
this.reaper.touch(deviceKey);
|
|
4200
|
+
return pool;
|
|
4201
|
+
})();
|
|
4202
|
+
this.inflight.set(deviceKey, creation);
|
|
4203
|
+
try {
|
|
4204
|
+
return await creation;
|
|
4205
|
+
} finally {
|
|
4206
|
+
this.inflight.delete(deviceKey);
|
|
4207
|
+
}
|
|
4208
|
+
}
|
|
4209
|
+
/** The device keys that currently hold a benchmark pool. */
|
|
4210
|
+
deviceKeys() {
|
|
4211
|
+
return [...this.pools.keys()];
|
|
4212
|
+
}
|
|
4213
|
+
async disposeAll() {
|
|
4214
|
+
this.reaper.disposeAll();
|
|
4215
|
+
const pools = [...this.pools.values()];
|
|
4216
|
+
this.pools.clear();
|
|
4217
|
+
await Promise.all(pools.map((p) => p.dispose().catch(() => void 0)));
|
|
4218
|
+
}
|
|
4219
|
+
async disposeOne(deviceKey) {
|
|
4220
|
+
const pool = this.pools.get(deviceKey);
|
|
4221
|
+
if (!pool) return;
|
|
4222
|
+
this.pools.delete(deviceKey);
|
|
4223
|
+
await pool.dispose();
|
|
4224
|
+
}
|
|
4225
|
+
};
|
|
4160
4226
|
//#endregion
|
|
4161
4227
|
//#region src/detection-pipeline/engine/inference-device-liveness.ts
|
|
4162
4228
|
/**
|
|
@@ -8259,6 +8325,18 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
8259
8325
|
executorOptions;
|
|
8260
8326
|
engineFactory = null;
|
|
8261
8327
|
/**
|
|
8328
|
+
* The pools a benchmark call loads its models into (D910): one separate
|
|
8329
|
+
* worker per device, never `factoriesByDevice` and never the node-default
|
|
8330
|
+
* pool, so a compile that kills its worker cannot take live detection down.
|
|
8331
|
+
*/
|
|
8332
|
+
benchmarkPools = new BenchmarkPools({
|
|
8333
|
+
create: (deviceKey, engine) => this.createBenchmarkFactory(deviceKey, engine),
|
|
8334
|
+
onDisposeError: (deviceKey, err) => this.log.warn("Idle benchmark pool dispose failed", { meta: {
|
|
8335
|
+
deviceKey,
|
|
8336
|
+
error: err instanceof Error ? err.message : String(err)
|
|
8337
|
+
} })
|
|
8338
|
+
});
|
|
8339
|
+
/**
|
|
8262
8340
|
* Per-device engine factories (Phase 2 multi-device), keyed by deviceKey
|
|
8263
8341
|
* (`<backend>:<device>`, e.g. `openvino:npu`, `edgetpu:usb`). Each is its own
|
|
8264
8342
|
* inference pool, warm CONCURRENTLY — so the node runs detection on NPU + iGPU
|
|
@@ -9705,12 +9783,13 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
9705
9783
|
});
|
|
9706
9784
|
this.executor = executor;
|
|
9707
9785
|
const dispatchEngine = dispatchDeviceKey ? resolveDeviceEngine(dispatchDeviceKey) : runEngine;
|
|
9708
|
-
const
|
|
9786
|
+
const benchmark = isBenchmarkRun(input);
|
|
9787
|
+
const dispatchFactory = benchmark ? await this.benchmarkPools.acquire(deviceKeyOf(dispatchEngine), dispatchEngine) : dispatchDeviceKey ? await this.resolveDeviceFactory(dispatchDeviceKey) : this.engineFactory;
|
|
9709
9788
|
const needed = enabledSteps.filter((s) => dispatchFactory.needsPoolUpdate(s));
|
|
9710
9789
|
let runSteps = benchmarkSteps;
|
|
9711
9790
|
const loadPolicy = dispatchLoadPolicyOf(input);
|
|
9712
9791
|
if (needed.length > 0) {
|
|
9713
|
-
const dispatchDeviceKeyLabel = deviceKeyOf(dispatchEngine);
|
|
9792
|
+
const dispatchDeviceKeyLabel = benchmark ? benchmarkKeyOf(deviceKeyOf(dispatchEngine)) : deviceKeyOf(dispatchEngine);
|
|
9714
9793
|
const toIssue = needed.filter((s) => this.loadGovernor.check(dispatchFactory, dispatchDeviceKeyLabel, [stepModelKey(s)]).kind === "go");
|
|
9715
9794
|
if (toIssue.length > 0) this.log.info("Benchmark: models to load", { meta: {
|
|
9716
9795
|
count: toIssue.length,
|
|
@@ -10576,6 +10655,7 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
10576
10655
|
this.engineFactory = null;
|
|
10577
10656
|
this.executor = null;
|
|
10578
10657
|
}
|
|
10658
|
+
await this.benchmarkPools.disposeAll();
|
|
10579
10659
|
this.deviceReaper.disposeAll();
|
|
10580
10660
|
const deviceFactories = Array.from(this.factoriesByDevice.values());
|
|
10581
10661
|
this.factoriesByDevice.clear();
|
|
@@ -10912,6 +10992,34 @@ var DetectionPipelineProvider = class DetectionPipelineProvider {
|
|
|
10912
10992
|
} });
|
|
10913
10993
|
return { rearmed };
|
|
10914
10994
|
}
|
|
10995
|
+
/**
|
|
10996
|
+
* Build the pool a benchmark loads into: a fresh worker for the engine of
|
|
10997
|
+
* `deviceKey`, outside the live pools' liveness budget and late-compile
|
|
10998
|
+
* bookkeeping (a benchmark's failure is a verdict about the benchmark).
|
|
10999
|
+
*/
|
|
11000
|
+
async createBenchmarkFactory(deviceKey, engine) {
|
|
11001
|
+
await this.ensureBackendDeps(engine);
|
|
11002
|
+
const factory = new EngineFactory({
|
|
11003
|
+
engine,
|
|
11004
|
+
modelsDir: this.modelsDir,
|
|
11005
|
+
logger: this.log.child(`bench:${deviceKey}`),
|
|
11006
|
+
pythonPath: this.executorOptions.pythonPath ?? "",
|
|
11007
|
+
provisioning: this.executorOptions.provisioning,
|
|
11008
|
+
resolveCustomModel: this.customModelResolver
|
|
11009
|
+
});
|
|
11010
|
+
try {
|
|
11011
|
+
await factory.initialize([]);
|
|
11012
|
+
} catch (err) {
|
|
11013
|
+
await factory.dispose().catch(() => void 0);
|
|
11014
|
+
this.log.error("Benchmark pool failed to initialize", { meta: {
|
|
11015
|
+
deviceKey,
|
|
11016
|
+
error: errMsg$1(err)
|
|
11017
|
+
} });
|
|
11018
|
+
throw err;
|
|
11019
|
+
}
|
|
11020
|
+
this.log.info("Benchmark pool started — its loads stay out of the live pool", { meta: { deviceKey } });
|
|
11021
|
+
return factory;
|
|
11022
|
+
}
|
|
10915
11023
|
async resolveDeviceFactory(deviceKey) {
|
|
10916
11024
|
const engine = resolveDeviceEngine(deviceKey);
|
|
10917
11025
|
if (enginesEqual(engine, this.currentEngine)) {
|