@camstack/types 1.2.327 → 1.2.329

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.
Files changed (72) hide show
  1. package/dist/addon/base-addon.d.ts +58 -0
  2. package/dist/addon/secret-aware-context.d.ts +27 -0
  3. package/dist/addon/secret-paths.d.ts +48 -0
  4. package/dist/addon/secret-settings-view.d.ts +80 -0
  5. package/dist/addon.d.ts +1 -0
  6. package/dist/addon.js +52 -4
  7. package/dist/addon.mjs +27 -5
  8. package/dist/capabilities/addons.cap.d.ts +4 -4
  9. package/dist/capabilities/alarm-panel.cap.d.ts +8 -8
  10. package/dist/capabilities/alerts.cap.d.ts +5 -5
  11. package/dist/capabilities/control.cap.d.ts +11 -11
  12. package/dist/capabilities/day-night.cap.d.ts +16 -16
  13. package/dist/capabilities/device-manager.cap.d.ts +2 -0
  14. package/dist/capabilities/enum-sensor.cap.d.ts +4 -4
  15. package/dist/capabilities/index.d.ts +6 -2
  16. package/dist/capabilities/integrations.cap.d.ts +6 -3
  17. package/dist/capabilities/keychain-admin.cap.d.ts +312 -0
  18. package/dist/capabilities/keychain.cap.d.ts +180 -0
  19. package/dist/capabilities/lawn-mower-control.cap.d.ts +4 -4
  20. package/dist/capabilities/log-channels.cap.d.ts +1 -1
  21. package/dist/capabilities/log-destination.cap.d.ts +5 -5
  22. package/dist/capabilities/notification-rules.cap.d.ts +118 -118
  23. package/dist/capabilities/osd-manager.cap.d.ts +11 -11
  24. package/dist/capabilities/osd.cap.d.ts +5 -5
  25. package/dist/capabilities/pipeline-analytics.cap.d.ts +1291 -118
  26. package/dist/capabilities/pipeline-orchestrator.cap.d.ts +384 -0
  27. package/dist/capabilities/pipeline-runner.cap.d.ts +145 -2
  28. package/dist/capabilities/storage.cap.d.ts +1 -1
  29. package/dist/capabilities/system.cap.d.ts +16 -16
  30. package/dist/capabilities/webrtc-session.cap.d.ts +3 -3
  31. package/dist/client.js +37 -1
  32. package/dist/client.mjs +37 -1
  33. package/dist/device/device-context.d.ts +11 -1
  34. package/dist/device/index.d.ts +1 -1
  35. package/dist/enums/event-category.d.ts +7 -0
  36. package/dist/enums.js +1 -1
  37. package/dist/enums.mjs +1 -1
  38. package/dist/{event-category-CtBAl88K.js → event-category-CHduMGvg.js} +7 -0
  39. package/dist/{event-category-B_0XEcLF.mjs → event-category-DaIZi00R.mjs} +7 -0
  40. package/dist/generated/addon-api.d.ts +289 -0
  41. package/dist/generated/cap-input-defaults.d.ts +1 -1
  42. package/dist/generated/capability-router-map.d.ts +8 -2
  43. package/dist/generated/method-access-map.d.ts +1 -1
  44. package/dist/generated/method-device-selectors.d.ts +1 -1
  45. package/dist/generated/system-proxy.d.ts +4 -2
  46. package/dist/health/wiring-health.d.ts +8 -8
  47. package/dist/index.d.ts +6 -2
  48. package/dist/index.js +1881 -101
  49. package/dist/index.mjs +1766 -98
  50. package/dist/interfaces/addon.d.ts +25 -0
  51. package/dist/interfaces/config-ui-secrets.d.ts +12 -0
  52. package/dist/interfaces/config-ui.d.ts +29 -1
  53. package/dist/interfaces/event-bus.d.ts +11 -0
  54. package/dist/interfaces/pipeline-runner-capability.d.ts +18 -0
  55. package/dist/keychain/index.d.ts +5 -0
  56. package/dist/keychain/known-secrets.d.ts +31 -0
  57. package/dist/keychain/resolve-secret-views.d.ts +2 -0
  58. package/dist/keychain/secret-marker.d.ts +52 -0
  59. package/dist/keychain/secret-ref.d.ts +62 -0
  60. package/dist/keychain/secrets-access.d.ts +77 -0
  61. package/dist/logging/log-channel.d.ts +2 -2
  62. package/dist/pipeline/auto-tune/plan-schemas.d.ts +123 -0
  63. package/dist/pipeline/auto-tune/recommend.d.ts +26 -1
  64. package/dist/pipeline/load-balancing/schemas.d.ts +8 -7
  65. package/dist/pipeline/node-benchmark/benchmark-mode.d.ts +57 -0
  66. package/dist/pipeline/node-benchmark/index.d.ts +9 -0
  67. package/dist/pipeline/node-benchmark/results.d.ts +52 -0
  68. package/dist/pipeline/node-benchmark/schemas.d.ts +848 -0
  69. package/dist/pipeline/node-benchmark/step-tree.d.ts +23 -0
  70. package/dist/{sleep-az1qiFzK.js → sleep-ClNXPpWR.js} +1580 -121
  71. package/dist/{sleep-B0JG7-_F.mjs → sleep-DujUvOcb.mjs} +1340 -121
  72. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_sleep = require("./sleep-az1qiFzK.js");
3
- const require_event_category = require("./event-category-CtBAl88K.js");
2
+ const require_sleep = require("./sleep-ClNXPpWR.js");
3
+ const require_event_category = require("./event-category-CHduMGvg.js");
4
4
  const require_composition = require("./composition-BLWAivB2.js");
5
5
  const require_err_msg = require("./err-msg-Dx2Kor0g.js");
6
6
  const require_enums = require("./enums.js");
@@ -1632,69 +1632,6 @@ function composeSwitchedOff(input) {
1632
1632
  };
1633
1633
  }
1634
1634
  //#endregion
1635
- //#region src/interfaces/config-ui-secrets.ts
1636
- /**
1637
- * The value a redacted secret is replaced with on every read surface.
1638
- *
1639
- * It is also the WRITE-BACK token: an `upsertLocation` that sends this value
1640
- * back for a key means "keep what is stored", which is what lets an operator
1641
- * rename a location without retyping its password. A literal an operator could
1642
- * plausibly choose as a real password would turn that convenience into a way
1643
- * to lock yourself out, hence the sentinel shape.
1644
- */
1645
- var REDACTED_SECRET = "__camstack_redacted__";
1646
- /** Is this field's stored value a credential? */
1647
- function isSecretConfigField(field) {
1648
- if (field.type === "password") return true;
1649
- return "secret" in field && field.secret === true;
1650
- }
1651
- /**
1652
- * Every config key in `schema` whose value is a secret, including keys nested
1653
- * inside `group` / `sub-tabs` containers.
1654
- */
1655
- function collectSecretConfigKeys(schema) {
1656
- const keys = /* @__PURE__ */ new Set();
1657
- for (const section of sectionsOf(schema)) for (const field of fieldsOf(section)) walkField(field, keys);
1658
- return keys;
1659
- }
1660
- /**
1661
- * True when the value is a readable schema declaring at least one field of any
1662
- * kind. Lets a caller tell "this provider has no secrets" from "this provider's
1663
- * schema could not be read", which are the same empty set otherwise.
1664
- */
1665
- function schemaDeclaresAnyField(schema) {
1666
- for (const section of sectionsOf(schema)) if (fieldsOf(section).length > 0) return true;
1667
- return false;
1668
- }
1669
- function isRecord$3(value) {
1670
- return typeof value === "object" && value !== null && !Array.isArray(value);
1671
- }
1672
- function sectionsOf(schema) {
1673
- if (!isRecord$3(schema)) return [];
1674
- const sections = schema["sections"];
1675
- return Array.isArray(sections) ? sections : [];
1676
- }
1677
- function fieldsOf(node) {
1678
- if (!isRecord$3(node)) return [];
1679
- const fields = node["fields"];
1680
- return Array.isArray(fields) ? fields : [];
1681
- }
1682
- function walkField(field, out) {
1683
- if (!isRecord$3(field)) return;
1684
- const type = field["type"];
1685
- const key = field["key"];
1686
- if ((type === "password" || field["secret"] === true) && typeof key === "string" && key.length > 0) out.add(key);
1687
- if (type === "group") {
1688
- for (const child of fieldsOf(field)) walkField(child, out);
1689
- return;
1690
- }
1691
- if (type === "sub-tabs") {
1692
- const tabs = field["tabs"];
1693
- if (!Array.isArray(tabs)) return;
1694
- for (const tab of tabs) for (const child of fieldsOf(tab)) walkField(child, out);
1695
- }
1696
- }
1697
- //#endregion
1698
1635
  //#region src/interfaces/birth-decision-ledger.ts
1699
1636
  /**
1700
1637
  * Birth-decision ledger — one durable row per track-birth VERDICT (D409).
@@ -12591,6 +12528,277 @@ id: zod.z.union([zod.z.string(), zod.z.number()]) }), {
12591
12528
  }
12592
12529
  };
12593
12530
  //#endregion
12531
+ //#region src/capabilities/keychain.cap.ts
12532
+ /**
12533
+ * `keychain` — the hub's encrypted store of secret values (D787).
12534
+ *
12535
+ * Settings blobs never hold a secret: they hold a marker
12536
+ * `{"$secret":"secret://<owner>/<scope>/<fieldPath>","v":1}` and the value
12537
+ * lives here, AES-256-GCM under a data key that a master key wraps. This cap
12538
+ * is the OWNER's door to its own values: every method is owner-checked
12539
+ * against the CALLER, never against anything the caller claims.
12540
+ *
12541
+ * Who the caller is: the transport stamps `callerAddonId` into the args of a
12542
+ * call that crossed a process (the parent `LocalChildRegistry` from the UDS
12543
+ * connection, the agent from its child's connection carried in
12544
+ * `$hub-cap-fwd`'s envelope). A stamp always overwrites; a wire call with no
12545
+ * stamp has its claim stripped. Only a hub in-process caller may state its own
12546
+ * identity — `ctx.secrets` does that with the addon id closed over. This is
12547
+ * identity against BUGS and misrouting, not against a malicious addon (every
12548
+ * runner is the same OS user): see the threat model in
12549
+ * `docs/design/2026-10-08-secrets-keychain.md`.
12550
+ *
12551
+ * `callerAddonId` is deliberately NOT in any input schema: the tRPC router
12552
+ * parses the input, so a session can never supply it, and the internal mount
12553
+ * floors every method to admin anyway (D240).
12554
+ *
12555
+ * Internal: addons reach it through `ctx.secrets`, never directly.
12556
+ */
12557
+ /** Why a value cannot be served right now. Never folded into "missing". */
12558
+ var KeychainUnavailableReasonSchema = zod.z.enum([
12559
+ "key-missing",
12560
+ "wrong-key",
12561
+ "key-file-unreadable",
12562
+ "store-unavailable",
12563
+ "not-initialized",
12564
+ "decrypt-failed"
12565
+ ]);
12566
+ var KeychainStateSchema = zod.z.discriminatedUnion("state", [zod.z.object({ state: zod.z.literal("ready") }), zod.z.object({
12567
+ state: zod.z.literal("locked"),
12568
+ reason: KeychainUnavailableReasonSchema
12569
+ })]);
12570
+ var KeychainResolveEntrySchema = zod.z.discriminatedUnion("kind", [
12571
+ zod.z.object({
12572
+ kind: zod.z.literal("value"),
12573
+ value: zod.z.string(),
12574
+ version: zod.z.number().int()
12575
+ }),
12576
+ zod.z.object({ kind: zod.z.literal("missing") }),
12577
+ zod.z.object({
12578
+ kind: zod.z.literal("unavailable"),
12579
+ reason: KeychainUnavailableReasonSchema
12580
+ }),
12581
+ zod.z.object({ kind: zod.z.literal("forbidden") })
12582
+ ]);
12583
+ var KeychainResolveResultSchema = zod.z.record(zod.z.string(), KeychainResolveEntrySchema);
12584
+ /** Metadata of one stored value — never the value. */
12585
+ var KeychainSecretMetaSchema = zod.z.object({
12586
+ ref: zod.z.string(),
12587
+ owner: zod.z.string(),
12588
+ /** Formatted scope (`global`, `node/<id>`, `device/<id>`, …). */
12589
+ scope: zod.z.string(),
12590
+ fieldPath: zod.z.string(),
12591
+ version: zod.z.number().int(),
12592
+ createdAt: zod.z.number(),
12593
+ updatedAt: zod.z.number(),
12594
+ /** `addon:<id>` | `user:<id>` | `system`. */
12595
+ updatedBy: zod.z.string(),
12596
+ /** Coarse — written at most once an hour per ref. `null` = never read. */
12597
+ lastReadAt: zod.z.number().nullable()
12598
+ });
12599
+ /** A batch bound: one `resolveConfig` resolves every marker of one blob at once. */
12600
+ var KEYCHAIN_MAX_REFS_PER_CALL = 512;
12601
+ var RefListSchema = zod.z.array(zod.z.string().min(1)).max(512);
12602
+ var keychainCapability = {
12603
+ name: "keychain",
12604
+ scope: "system",
12605
+ mode: "singleton",
12606
+ internal: true,
12607
+ methods: {
12608
+ /** Store (or replace) the caller's value at `ref`. Refused while locked. */
12609
+ put: require_sleep.method(zod.z.object({
12610
+ ref: zod.z.string().min(1),
12611
+ value: zod.z.string().min(1)
12612
+ }), zod.z.object({
12613
+ ref: zod.z.string(),
12614
+ version: zod.z.number().int()
12615
+ }), {
12616
+ kind: "mutation",
12617
+ auth: "admin"
12618
+ }),
12619
+ /**
12620
+ * Resolve the caller's refs in one round-trip. A locked keychain answers
12621
+ * `unavailable` per ref — never `missing`, never an empty value.
12622
+ */
12623
+ resolve: require_sleep.method(zod.z.object({ refs: RefListSchema }), KeychainResolveResultSchema, { auth: "admin" }),
12624
+ /** Remove the caller's refs. Unknown refs are ignored. */
12625
+ delete: require_sleep.method(zod.z.object({ refs: RefListSchema }), zod.z.object({ deleted: zod.z.number().int() }), {
12626
+ kind: "mutation",
12627
+ auth: "admin"
12628
+ }),
12629
+ /** The caller's own refs, metadata only. */
12630
+ listMeta: require_sleep.method(zod.z.object({}), zod.z.array(KeychainSecretMetaSchema).readonly(), { auth: "admin" }),
12631
+ /** Whether values can be served — the save path refuses a write while locked. */
12632
+ getState: require_sleep.method(zod.z.object({}), KeychainStateSchema, { auth: "admin" })
12633
+ }
12634
+ };
12635
+ //#endregion
12636
+ //#region src/capabilities/keychain-admin.cap.ts
12637
+ /**
12638
+ * `keychain-admin` — the operator's view of the keychain (System → Secrets).
12639
+ *
12640
+ * Every method is `admin`. Two methods hand out material, each audited and
12641
+ * each named for exactly that: {@link keychainAdminCapability.methods.reveal}
12642
+ * (one value, shown briefly by the UI) and `downloadRecoveryKey` (the master
12643
+ * key itself, so the operator can keep a copy off the hub). Nothing else
12644
+ * returns a value.
12645
+ *
12646
+ * The master key's LOCATION is configuration, never an env var (D788):
12647
+ * `keychain.keyFile` in `config.yaml`, the OS keychain on a desktop hub, else
12648
+ * `<dataDir>/.keychain/master.key` — which sits beside the database in every
12649
+ * whole-volume backup, and the status says so.
12650
+ */
12651
+ /** Where the master key in use came from. */
12652
+ var KeychainKeySourceKindSchema = zod.z.enum([
12653
+ "config-file",
12654
+ "previous-config-file",
12655
+ "platform",
12656
+ "default-file"
12657
+ ]);
12658
+ var KeychainKeySourceSchema = zod.z.object({
12659
+ kind: KeychainKeySourceKindSchema,
12660
+ /** File sources only — a path is not a secret. */
12661
+ path: zod.z.string().optional(),
12662
+ /**
12663
+ * True when a whole-volume backup of the data directory carries this key
12664
+ * next to the database it protects (the default file). The page warns.
12665
+ */
12666
+ sharesBackupWithDatabase: zod.z.boolean()
12667
+ });
12668
+ var KeychainStatusSchema = zod.z.object({
12669
+ keychain: KeychainStateSchema,
12670
+ /** The source of the master key in use; `null` while locked. */
12671
+ keySource: KeychainKeySourceSchema.nullable(),
12672
+ /** The source configured to be primary — differs from `keySource` while a rotation is pending. */
12673
+ configuredSource: KeychainKeySourceSchema,
12674
+ /** Short fingerprint of the master key in use (`HMAC(KEK, label)`, 16 hex). */
12675
+ fingerprint: zod.z.string().nullable(),
12676
+ activeKeyId: zod.z.string().nullable(),
12677
+ /**
12678
+ * The keychain unlocked with a NON-primary source: the configured primary
12679
+ * key is not the one that wraps the data key yet. `rotateMasterKey` moves it.
12680
+ */
12681
+ rotationPending: zod.z.boolean(),
12682
+ /** Wrapped copies of the data key under a previous master key, kept until purged. */
12683
+ retiredWraps: zod.z.number().int(),
12684
+ recoveryKeyDownloadedAt: zod.z.number().nullable(),
12685
+ secretCount: zod.z.number().int()
12686
+ });
12687
+ /**
12688
+ * Whether a stored value is still pointed at by its owner's settings.
12689
+ * `unknown` is a first-class answer: a scope whose blob could not be read is
12690
+ * never reported as an orphan (and never deleted as one).
12691
+ */
12692
+ var KeychainSecretUsageSchema = zod.z.enum([
12693
+ "in-use",
12694
+ "orphan",
12695
+ "unknown"
12696
+ ]);
12697
+ var KeychainAdminSecretSchema = KeychainSecretMetaSchema.extend({ usage: KeychainSecretUsageSchema });
12698
+ var KeychainAuditActionSchema = zod.z.enum([
12699
+ "put",
12700
+ "delete",
12701
+ "reveal",
12702
+ "rotate-master-key",
12703
+ "purge-retired-keys",
12704
+ "download-recovery-key",
12705
+ "delete-orphans",
12706
+ "reset",
12707
+ "initialize"
12708
+ ]);
12709
+ var KeychainAuditEntrySchema = zod.z.object({
12710
+ id: zod.z.string(),
12711
+ at: zod.z.number(),
12712
+ action: KeychainAuditActionSchema,
12713
+ /** `addon:<id>` | `user:<id>` | `system`. */
12714
+ actor: zod.z.string(),
12715
+ ref: zod.z.string().nullable(),
12716
+ detail: zod.z.string().nullable()
12717
+ });
12718
+ var KEYCHAIN_RESET_CONFIRMATION = "RESET KEYCHAIN";
12719
+ var keychainAdminCapability = {
12720
+ name: "keychain-admin",
12721
+ scope: "system",
12722
+ mode: "singleton",
12723
+ methods: {
12724
+ status: require_sleep.method(zod.z.object({}), KeychainStatusSchema, { auth: "admin" }),
12725
+ listSecrets: require_sleep.method(zod.z.object({}), zod.z.array(KeychainAdminSecretSchema).readonly(), { auth: "admin" }),
12726
+ listAudit: require_sleep.method(zod.z.object({ limit: zod.z.number().int().min(1).max(500).optional() }), zod.z.array(KeychainAuditEntrySchema).readonly(), { auth: "admin" }),
12727
+ /**
12728
+ * Show one value to the operator. Audited. The UI hides it again after a
12729
+ * few seconds; nothing caches it.
12730
+ */
12731
+ reveal: require_sleep.method(zod.z.object({ ref: zod.z.string().min(1) }), zod.z.object({
12732
+ value: zod.z.string(),
12733
+ version: zod.z.number().int()
12734
+ }), {
12735
+ kind: "mutation",
12736
+ auth: "admin",
12737
+ caller: "required"
12738
+ }),
12739
+ /** Delete refs no owner points at any more. Re-checked here; `unknown` is kept. */
12740
+ deleteOrphans: require_sleep.method(zod.z.object({ refs: zod.z.array(zod.z.string().min(1)).max(1e3) }), zod.z.object({
12741
+ deleted: zod.z.array(zod.z.string()).readonly(),
12742
+ kept: zod.z.array(zod.z.object({
12743
+ ref: zod.z.string(),
12744
+ usage: KeychainSecretUsageSchema
12745
+ })).readonly()
12746
+ }), {
12747
+ kind: "mutation",
12748
+ auth: "admin",
12749
+ caller: "required"
12750
+ }),
12751
+ /**
12752
+ * Wrap the data key under the configured primary master key.
12753
+ *
12754
+ * Pending rotation (the keychain unlocked with a previous source): re-wrap
12755
+ * under the primary. Otherwise, with the default file as primary: generate
12756
+ * a new master key, write it there, re-wrap. A file or OS-keychain primary
12757
+ * that is already in use cannot be replaced from here — put the new key at
12758
+ * the source, keep the old one as `keychain.previousKeyFile`, restart, and
12759
+ * rotate. No value is re-encrypted either way; the previous wrap is kept
12760
+ * (retired) until purged.
12761
+ */
12762
+ rotateMasterKey: require_sleep.method(zod.z.object({}), zod.z.object({
12763
+ fingerprint: zod.z.string(),
12764
+ keySource: KeychainKeySourceSchema
12765
+ }), {
12766
+ kind: "mutation",
12767
+ auth: "admin",
12768
+ caller: "required"
12769
+ }),
12770
+ purgeRetiredKeys: require_sleep.method(zod.z.object({}), zod.z.object({ purged: zod.z.number().int() }), {
12771
+ kind: "mutation",
12772
+ auth: "admin",
12773
+ caller: "required"
12774
+ }),
12775
+ /** The master key, base64. Audited; marks the recovery copy as taken. */
12776
+ downloadRecoveryKey: require_sleep.method(zod.z.object({}), zod.z.object({
12777
+ key: zod.z.string(),
12778
+ fingerprint: zod.z.string(),
12779
+ keySource: KeychainKeySourceSchema
12780
+ }), {
12781
+ kind: "mutation",
12782
+ auth: "admin",
12783
+ caller: "required"
12784
+ }),
12785
+ /**
12786
+ * Lost-key recovery: archive every stored value into a
12787
+ * `keychain:secrets-orphaned-<ts>` table and start over with a new data
12788
+ * key. Every secret field then reads "not set". Requires the typed
12789
+ * confirmation {@link KEYCHAIN_RESET_CONFIRMATION}.
12790
+ */
12791
+ resetKeychain: require_sleep.method(zod.z.object({ confirm: zod.z.literal(KEYCHAIN_RESET_CONFIRMATION) }), zod.z.object({
12792
+ archivedCollection: zod.z.string().nullable(),
12793
+ archived: zod.z.number().int()
12794
+ }), {
12795
+ kind: "mutation",
12796
+ auth: "admin",
12797
+ caller: "required"
12798
+ })
12799
+ }
12800
+ };
12801
+ //#endregion
12594
12802
  //#region src/capabilities/decoder.cap.ts
12595
12803
  /**
12596
12804
  * Stable UI option list for the `hwaccel` setting. Decoder addons
@@ -14319,7 +14527,11 @@ var DeviceRegisterPayloadSchema = zod.z.object({
14319
14527
  var DeviceRemovePayloadSchema = zod.z.object({ deviceId: zod.z.number() });
14320
14528
  var DevicePersistConfigPayloadSchema = zod.z.object({
14321
14529
  deviceId: zod.z.number(),
14322
- data: zod.z.record(zod.z.string(), zod.z.unknown())
14530
+ data: zod.z.record(zod.z.string(), zod.z.unknown()),
14531
+ /** The paths the device's schema declares secret (D783), when the caller
14532
+ * knows them — those values are kept in the keychain, not the blob (D787).
14533
+ * Absent: the paths the device last reported at `registerDevice` apply. */
14534
+ secretConfigPaths: zod.z.array(zod.z.string()).optional()
14323
14535
  });
14324
14536
  /** What a migration actually did, per switch. `unreachable` is a first-class
14325
14537
  * answer: a camera that could not be asked is not a camera that was silenced. */
@@ -24706,8 +24918,23 @@ var RetrainMacroClassSchema = zod.z.enum([
24706
24918
  ]);
24707
24919
  /** A subject to learn, or a phantom to unlearn (taught by OMISSION). */
24708
24920
  var RetrainAnnotationKindSchema = zod.z.enum(["subject", "model_error"]);
24709
- /** Did a human draw this box, or did the assist propose it? */
24710
- var RetrainAnnotationSourceSchema = zod.z.enum(["operator", "assist"]);
24921
+ /**
24922
+ * Where a box came from. A machine-sourced box is a DRAFT on the page until
24923
+ * the operator confirms it; once saved it keeps its source as provenance.
24924
+ *
24925
+ * - `operator` — drawn by hand.
24926
+ * - `assist` — proposed by a detector run on the copy (the camera's own
24927
+ * model, or a larger teacher model).
24928
+ * - `pipeline` — the box the live pipeline actually drew on that frame, read
24929
+ * back from the track store (never a re-run).
24930
+ * - `llm` — proposed by a vision-capable LLM profile.
24931
+ */
24932
+ var RetrainAnnotationSourceSchema = zod.z.enum([
24933
+ "operator",
24934
+ "assist",
24935
+ "pipeline",
24936
+ "llm"
24937
+ ]);
24711
24938
  /** Normalised `[0,1]` rectangle against the FULL frame — the canonical form. */
24712
24939
  var RetrainBboxSchema = zod.z.object({
24713
24940
  x: zod.z.number(),
@@ -24725,7 +24952,8 @@ var RetrainBboxSchema = zod.z.object({
24725
24952
  */
24726
24953
  var RetrainAnnotationSchema = zod.z.object({
24727
24954
  id: zod.z.string(),
24728
- trackId: zod.z.string(),
24955
+ /** The frame's track. Absent on a recording still, which has none. */
24956
+ trackId: zod.z.string().optional(),
24729
24957
  deviceId: zod.z.number(),
24730
24958
  /** The COPY in retrain storage — never the source track's media key. */
24731
24959
  mediaKey: zod.z.string(),
@@ -24774,13 +25002,47 @@ var RetrainFrameCandidateSchema = zod.z.object({
24774
25002
  * fail, whatever became of the original. */
24775
25003
  copied: zod.z.boolean()
24776
25004
  });
25005
+ /**
25006
+ * One box the live pipeline drew on a copied frame — what a correction starts
25007
+ * from. Derived when the frame is listed, from the track store: the subject
25008
+ * box recorded on the source media row when there is one, else the track
25009
+ * position nearest the frame's capture time. Never stored as an annotation
25010
+ * until the operator confirms it.
25011
+ */
25012
+ var RetrainPipelineBoxSchema = zod.z.object({
25013
+ /** Normalised `[0,1]` against the full frame. */
25014
+ bbox: RetrainBboxSchema,
25015
+ macroClass: RetrainMacroClassSchema,
25016
+ label: zod.z.string().optional(),
25017
+ subLabel: zod.z.string().optional(),
25018
+ /** The detection score of the position used, when it was recorded. */
25019
+ score: zod.z.number().optional(),
25020
+ /** The root model that produced the track, when it was recorded. */
25021
+ modelId: zod.z.string().optional(),
25022
+ trackId: zod.z.string(),
25023
+ /** `subject-box`: recorded on this very frame. `position`: the track's
25024
+ * position nearest the capture time, `deltaMs` away. */
25025
+ basis: zod.z.enum(["subject-box", "position"]),
25026
+ deltaMs: zod.z.number()
25027
+ });
25028
+ /**
25029
+ * Where a retrain frame came from: a TRACK's stored media (copy-on-select),
25030
+ * or the RECORDING at an instant — the frame a model saw nothing in has no
25031
+ * track at all.
25032
+ */
25033
+ var RetrainFrameOriginSchema = zod.z.enum(["track", "recording"]);
24777
25034
  /** A frame the dataset OWNS: bytes copied at selection time. */
24778
25035
  var RetrainFrameSchema = zod.z.object({
24779
25036
  frameId: zod.z.string(),
24780
25037
  deviceId: zod.z.number(),
24781
- trackId: zod.z.string(),
24782
- /** Provenance only. It may already point at nothing — that is expected. */
24783
- sourceMediaId: zod.z.number().int(),
25038
+ origin: RetrainFrameOriginSchema,
25039
+ /** The track it was copied from. Absent on a recording still. */
25040
+ trackId: zod.z.string().optional(),
25041
+ /** Provenance only. It may already point at nothing — that is expected.
25042
+ * Absent on a recording still. */
25043
+ sourceMediaId: zod.z.number().int().optional(),
25044
+ /** A recording still: the playhead instant it was taken at. */
25045
+ epochMs: zod.z.number().optional(),
24784
25046
  sourceKind: MediaFileKindEnum,
24785
25047
  sizeBytes: zod.z.number().int(),
24786
25048
  width: zod.z.number().int(),
@@ -24791,7 +25053,12 @@ var RetrainFrameSchema = zod.z.object({
24791
25053
  /** The operator's "every subject in this frame is boxed". Detector
24792
25054
  * evaluation keeps only complete frames: an unboxed subject would count as
24793
25055
  * a false positive. */
24794
- complete: zod.z.boolean()
25056
+ complete: zod.z.boolean(),
25057
+ /** The boxes the pipeline drew on this frame. Present on list answers;
25058
+ * empty when nothing the track store holds can be placed on it. */
25059
+ pipelineBoxes: zod.z.array(RetrainPipelineBoxSchema).readonly().optional(),
25060
+ /** The named collections this frame belongs to. Present on list answers. */
25061
+ collectionIds: zod.z.array(zod.z.string()).readonly().optional()
24795
25062
  });
24796
25063
  /** Why a copy-on-select could not be honoured — named, never a silent skip. */
24797
25064
  var RetrainCopyRefusalSchema = zod.z.enum([
@@ -24822,6 +25089,11 @@ var RetrainFrameListSchema = zod.z.object({
24822
25089
  var RetrainExportFilterSchema = zod.z.object({
24823
25090
  deviceIds: zod.z.array(zod.z.number()).optional(),
24824
25091
  frameIds: zod.z.array(zod.z.string()).max(2e4).optional(),
25092
+ /** Only frames in at least one of these named collections. */
25093
+ collectionIds: zod.z.array(zod.z.string()).max(200).optional(),
25094
+ /** Exactly the frames of this dataset version (and its completeOnly). An
25095
+ * unknown id selects nothing. */
25096
+ datasetVersionId: zod.z.string().optional(),
24825
25097
  batchId: zod.z.string().optional(),
24826
25098
  /** Only frames the operator marked complete (all subjects boxed). */
24827
25099
  completeOnly: zod.z.boolean().optional()
@@ -24886,6 +25158,170 @@ var RetrainAssistResultSchema = zod.z.discriminatedUnion("kind", [zod.z.object({
24886
25158
  reason: zod.z.string(),
24887
25159
  detail: zod.z.string().optional()
24888
25160
  })]);
25161
+ /** A named set over the retrain corpus — membership only, it owns no pixels. */
25162
+ var RetrainCollectionSchema = zod.z.object({
25163
+ id: zod.z.string(),
25164
+ name: zod.z.string(),
25165
+ createdAt: zod.z.number(),
25166
+ frameCount: zod.z.number().int()
25167
+ });
25168
+ var RetrainCollectionCreateResultSchema = zod.z.discriminatedUnion("kind", [zod.z.object({
25169
+ kind: zod.z.literal("created"),
25170
+ collection: RetrainCollectionSchema
25171
+ }), zod.z.object({
25172
+ kind: zod.z.literal("refused"),
25173
+ reason: zod.z.enum(["empty-name", "duplicate-name"])
25174
+ })]);
25175
+ var RetrainCollectionRenameResultSchema = zod.z.discriminatedUnion("kind", [zod.z.object({
25176
+ kind: zod.z.literal("renamed"),
25177
+ collection: RetrainCollectionSchema
25178
+ }), zod.z.object({
25179
+ kind: zod.z.literal("refused"),
25180
+ reason: zod.z.enum([
25181
+ "empty-name",
25182
+ "duplicate-name",
25183
+ "unknown-collection"
25184
+ ])
25185
+ })]);
25186
+ /**
25187
+ * The outcome of adding the frame at a recording instant. Every refusal is
25188
+ * named: `still-unavailable` (not recording, a gap, or an undecodable frame —
25189
+ * `detail` says which), `still-busy` (the recorder is at its decode bound; try
25190
+ * again), `unreadable-image`, `write-failed`, `unknown-collection`.
25191
+ */
25192
+ var AddRetrainFrameFromRecordingResultSchema = zod.z.discriminatedUnion("kind", [zod.z.object({
25193
+ kind: zod.z.literal("added"),
25194
+ collectionId: zod.z.string(),
25195
+ frame: RetrainFrameSchema,
25196
+ /** The moment was already in the dataset; nothing was decoded. */
25197
+ reused: zod.z.boolean()
25198
+ }), zod.z.object({
25199
+ kind: zod.z.literal("refused"),
25200
+ reason: zod.z.enum([
25201
+ "unknown-collection",
25202
+ "still-unavailable",
25203
+ "still-busy",
25204
+ "unreadable-image",
25205
+ "write-failed"
25206
+ ]),
25207
+ detail: zod.z.string().optional()
25208
+ })]);
25209
+ /** A vision LLM profile the AI assist may use, and where it sends the frame. */
25210
+ var RetrainAssistProfileSchema = zod.z.object({
25211
+ id: zod.z.string(),
25212
+ name: zod.z.string(),
25213
+ model: zod.z.string(),
25214
+ kind: zod.z.string(),
25215
+ /** `true` when the frame would leave the house (a cloud vendor, or an
25216
+ * endpoint that is not on the local network). The page confirms each such
25217
+ * run, and the provider refuses one without `allowCloud`. */
25218
+ leavesHouse: zod.z.boolean()
25219
+ });
25220
+ /** A box the AI assist proposed: a draft, plus the model's own reason. */
25221
+ var RetrainLlmProposalSchema = RetrainAnnotationDraftSchema.extend({ reason: zod.z.string() });
25222
+ /** What the AI assist said about a box that was already on the canvas. */
25223
+ var RetrainLlmReviewSchema = zod.z.object({
25224
+ /** The `ref` the page sent the box under. */
25225
+ ref: zod.z.string(),
25226
+ verdict: zod.z.enum([
25227
+ "confirmed",
25228
+ "wrong-class",
25229
+ "not-an-object",
25230
+ "uncertain"
25231
+ ]),
25232
+ suggestedClass: RetrainMacroClassSchema.optional(),
25233
+ reason: zod.z.string()
25234
+ });
25235
+ /**
25236
+ * The AI assist's answer. `proposed` carries drafts (`source: 'llm'`, the
25237
+ * model and its confidence) and reviews; items the model got wrong (a box off
25238
+ * the frame, an unasked class, an unknown ref) are dropped and counted in
25239
+ * `rejected`. A whole answer that is not the schema is `malformed-answer`.
25240
+ */
25241
+ var RetrainLlmAssistResultSchema = zod.z.discriminatedUnion("kind", [zod.z.object({
25242
+ kind: zod.z.literal("proposed"),
25243
+ profileId: zod.z.string(),
25244
+ model: zod.z.string(),
25245
+ /** The frame was sent outside the house for this answer. */
25246
+ leftHouse: zod.z.boolean(),
25247
+ proposals: zod.z.array(RetrainLlmProposalSchema).readonly(),
25248
+ reviews: zod.z.array(RetrainLlmReviewSchema).readonly(),
25249
+ rejected: zod.z.number().int()
25250
+ }), zod.z.object({
25251
+ kind: zod.z.literal("refused"),
25252
+ reason: zod.z.enum([
25253
+ "unknown-frame",
25254
+ "unreadable-frame",
25255
+ "unknown-profile",
25256
+ "profile-disabled",
25257
+ "no-vision",
25258
+ "cloud-not-confirmed",
25259
+ "llm-error",
25260
+ "malformed-answer"
25261
+ ]),
25262
+ detail: zod.z.string().optional()
25263
+ })]);
25264
+ /** What a dataset version is cut from. Every field narrows. */
25265
+ var RetrainDatasetSelectionSchema = zod.z.object({
25266
+ deviceIds: zod.z.array(zod.z.number()).readonly().optional(),
25267
+ collectionIds: zod.z.array(zod.z.string()).max(200).readonly().optional(),
25268
+ frameIds: zod.z.array(zod.z.string()).max(2e4).readonly().optional()
25269
+ });
25270
+ /** The counts a dataset is judged by. */
25271
+ var RetrainDatasetStatsSchema = zod.z.object({
25272
+ frames: zod.z.number().int(),
25273
+ completeFrames: zod.z.number().int(),
25274
+ /** `completeFrames / frames`, 0..1. */
25275
+ completeness: zod.z.number(),
25276
+ /** Boxes to learn (model errors excluded). */
25277
+ subjects: zod.z.number().int(),
25278
+ modelErrors: zod.z.number().int(),
25279
+ /** Complete frames with no subject. */
25280
+ hardNegatives: zod.z.number().int(),
25281
+ /** Subjects per class × camera × day/night. */
25282
+ cells: zod.z.array(zod.z.object({
25283
+ macroClass: zod.z.string(),
25284
+ deviceId: zod.z.number(),
25285
+ lighting: zod.z.enum([
25286
+ "day",
25287
+ "night",
25288
+ "unknown"
25289
+ ]),
25290
+ subjects: zod.z.number().int(),
25291
+ frames: zod.z.number().int()
25292
+ })).readonly(),
25293
+ cameras: zod.z.array(zod.z.object({
25294
+ deviceId: zod.z.number(),
25295
+ frames: zod.z.number().int(),
25296
+ completeFrames: zod.z.number().int()
25297
+ })).readonly()
25298
+ });
25299
+ /** An immutable dataset version, without its frame list. */
25300
+ var RetrainDatasetVersionSchema = zod.z.object({
25301
+ id: zod.z.string(),
25302
+ name: zod.z.string(),
25303
+ createdAt: zod.z.number(),
25304
+ selection: RetrainDatasetSelectionSchema,
25305
+ layout: RetrainExportLayoutSchema,
25306
+ completeOnly: zod.z.boolean(),
25307
+ frameCount: zod.z.number().int(),
25308
+ /** sha256 of what the frames taught when the version was frozen. */
25309
+ annotationHash: zod.z.string(),
25310
+ /** The export manifest schema the version was cut under. */
25311
+ manifestSchema: zod.z.string(),
25312
+ stats: RetrainDatasetStatsSchema
25313
+ });
25314
+ var CreateRetrainDatasetVersionResultSchema = zod.z.discriminatedUnion("kind", [zod.z.object({
25315
+ kind: zod.z.literal("created"),
25316
+ version: RetrainDatasetVersionSchema
25317
+ }), zod.z.object({
25318
+ kind: zod.z.literal("refused"),
25319
+ reason: zod.z.enum([
25320
+ "empty-name",
25321
+ "duplicate-name",
25322
+ "no-frames"
25323
+ ])
25324
+ })]);
24889
25325
  /** The outcome of a lifecycle move owned by the retrain page. */
24890
25326
  var RetrainTransitionResultSchema = zod.z.object({
24891
25327
  trackId: zod.z.string(),
@@ -26121,7 +26557,7 @@ var pipelineAnalyticsCapability = {
26121
26557
  * a frame leaves the dataset before export. */
26122
26558
  deselectRetrainFrame: require_sleep.method(zod.z.object({
26123
26559
  deviceId: zod.z.number(),
26124
- trackId: zod.z.string(),
26560
+ trackId: zod.z.string().optional(),
26125
26561
  frameId: zod.z.string()
26126
26562
  }), zod.z.object({
26127
26563
  removed: zod.z.boolean(),
@@ -26164,7 +26600,8 @@ var pipelineAnalyticsCapability = {
26164
26600
  */
26165
26601
  proposeRetrainAnnotations: require_sleep.method(zod.z.object({
26166
26602
  deviceId: zod.z.number(),
26167
- trackId: zod.z.string(),
26603
+ /** The frame's track, when it has one — checked against the frame. */
26604
+ trackId: zod.z.string().optional(),
26168
26605
  frameId: zod.z.string(),
26169
26606
  subject: RetrainAssistSubjectSchema,
26170
26607
  /** Which node runs it. Absent ⇒ wherever an unowned call lands. */
@@ -26173,8 +26610,12 @@ var pipelineAnalyticsCapability = {
26173
26610
  kind: "mutation",
26174
26611
  auth: "admin"
26175
26612
  }),
26176
- /** Every annotation on a track, oldest first. */
26177
- listRetrainAnnotations: require_sleep.method(zod.z.object({ trackId: zod.z.string() }), zod.z.array(RetrainAnnotationSchema).readonly(), {
26613
+ /** Every annotation on a track, or on named frames (a recording still has
26614
+ * no track), oldest first. One of the two is required. */
26615
+ listRetrainAnnotations: require_sleep.method(zod.z.object({
26616
+ trackId: zod.z.string().optional(),
26617
+ frameIds: zod.z.array(zod.z.string()).max(2e3).optional()
26618
+ }), zod.z.array(RetrainAnnotationSchema).readonly(), {
26178
26619
  kind: "query",
26179
26620
  auth: "admin"
26180
26621
  }),
@@ -26193,7 +26634,8 @@ var pipelineAnalyticsCapability = {
26193
26634
  */
26194
26635
  saveRetrainAnnotations: require_sleep.method(zod.z.object({
26195
26636
  deviceId: zod.z.number(),
26196
- trackId: zod.z.string(),
26637
+ /** The frame's track, when it has one — checked against the frame. */
26638
+ trackId: zod.z.string().optional(),
26197
26639
  frameId: zod.z.string(),
26198
26640
  annotations: zod.z.array(RetrainAnnotationDraftSchema)
26199
26641
  }), zod.z.array(RetrainAnnotationSchema).readonly(), {
@@ -26256,7 +26698,7 @@ var pipelineAnalyticsCapability = {
26256
26698
  */
26257
26699
  setRetrainFrameComplete: require_sleep.method(zod.z.object({
26258
26700
  deviceId: zod.z.number(),
26259
- trackId: zod.z.string(),
26701
+ trackId: zod.z.string().optional(),
26260
26702
  frameId: zod.z.string(),
26261
26703
  complete: zod.z.boolean()
26262
26704
  }), RetrainFrameSchema, {
@@ -26279,6 +26721,162 @@ var pipelineAnalyticsCapability = {
26279
26721
  auth: "admin",
26280
26722
  timeoutMs: 60 * 6e4
26281
26723
  }),
26724
+ /** The counts a selection would freeze — class × camera × day/night,
26725
+ * completeness — without freezing anything. Index reads only. */
26726
+ previewRetrainDataset: require_sleep.method(zod.z.object({
26727
+ selection: RetrainDatasetSelectionSchema,
26728
+ completeOnly: zod.z.boolean().optional()
26729
+ }), RetrainDatasetStatsSchema, {
26730
+ kind: "query",
26731
+ auth: "admin"
26732
+ }),
26733
+ /**
26734
+ * Freeze a dataset version: the frames the selection yields (the same plan
26735
+ * the annotated export builds), the hash of what they teach, the export
26736
+ * parameters and the counts. Immutable — a different selection is a new
26737
+ * version. Export it with `getRetrainExportUrl({ datasetVersionId })`.
26738
+ */
26739
+ createRetrainDatasetVersion: require_sleep.method(zod.z.object({
26740
+ name: zod.z.string().max(120),
26741
+ selection: RetrainDatasetSelectionSchema,
26742
+ layout: RetrainExportLayoutSchema,
26743
+ completeOnly: zod.z.boolean()
26744
+ }), CreateRetrainDatasetVersionResultSchema, {
26745
+ kind: "mutation",
26746
+ auth: "admin",
26747
+ timeoutMs: 12e4
26748
+ }),
26749
+ /** Every dataset version, newest first. */
26750
+ listRetrainDatasetVersions: require_sleep.method(zod.z.object({}), zod.z.array(RetrainDatasetVersionSchema).readonly(), {
26751
+ kind: "query",
26752
+ auth: "admin"
26753
+ }),
26754
+ /** Delete a version. Its frames stay in the dataset. */
26755
+ deleteRetrainDatasetVersion: require_sleep.method(zod.z.object({ id: zod.z.string() }), zod.z.object({ deleted: zod.z.boolean() }), {
26756
+ kind: "mutation",
26757
+ auth: "admin"
26758
+ }),
26759
+ /** Does the corpus still teach what the version froze? `missingFrames`
26760
+ * counts frames that left the dataset (or lost every box and tick). */
26761
+ verifyRetrainDatasetVersion: require_sleep.method(zod.z.object({ id: zod.z.string() }), zod.z.object({
26762
+ found: zod.z.boolean(),
26763
+ annotationHash: zod.z.string(),
26764
+ matches: zod.z.boolean(),
26765
+ missingFrames: zod.z.number().int()
26766
+ }), {
26767
+ kind: "query",
26768
+ auth: "admin",
26769
+ timeoutMs: 12e4
26770
+ }),
26771
+ /** The enabled, vision-capable LLM profiles, each saying whether a frame
26772
+ * sent to it leaves the house. */
26773
+ listRetrainAssistProfiles: require_sleep.method(zod.z.object({}), zod.z.array(RetrainAssistProfileSchema).readonly(), {
26774
+ kind: "query",
26775
+ auth: "admin"
26776
+ }),
26777
+ /**
26778
+ * Ask a vision LLM (the `llm` capability) about ONE copied frame: list the
26779
+ * objects of `classes` with boxes, and review the boxes already on the
26780
+ * canvas (sent by `ref`). Answers drafts (`source: 'llm'`) and reviews —
26781
+ * nothing is stored, nothing is accepted. A profile that sends the frame
26782
+ * outside the house is refused unless `allowCloud` says the operator
26783
+ * confirmed this run.
26784
+ */
26785
+ proposeRetrainAnnotationsWithLlm: require_sleep.method(zod.z.object({
26786
+ deviceId: zod.z.number(),
26787
+ trackId: zod.z.string().optional(),
26788
+ frameId: zod.z.string(),
26789
+ profileId: zod.z.string(),
26790
+ classes: zod.z.array(RetrainMacroClassSchema).min(1),
26791
+ boxes: zod.z.array(zod.z.object({
26792
+ ref: zod.z.string(),
26793
+ bbox: RetrainBboxSchema,
26794
+ macroClass: RetrainMacroClassSchema,
26795
+ label: zod.z.string().optional()
26796
+ })).max(50),
26797
+ allowCloud: zod.z.boolean()
26798
+ }), RetrainLlmAssistResultSchema, {
26799
+ kind: "mutation",
26800
+ auth: "admin",
26801
+ timeoutMs: 18e4
26802
+ }),
26803
+ /**
26804
+ * Create a named collection — a set over the retrain corpus ("packages
26805
+ * porch night"). Names are unique case-insensitively and never empty;
26806
+ * both refusals are named.
26807
+ */
26808
+ createRetrainCollection: require_sleep.method(zod.z.object({ name: zod.z.string().max(120) }), RetrainCollectionCreateResultSchema, {
26809
+ kind: "mutation",
26810
+ auth: "admin"
26811
+ }),
26812
+ /** Every collection, newest first, with its frame count. */
26813
+ listRetrainCollections: require_sleep.method(zod.z.object({}), zod.z.array(RetrainCollectionSchema).readonly(), {
26814
+ kind: "query",
26815
+ auth: "admin"
26816
+ }),
26817
+ renameRetrainCollection: require_sleep.method(zod.z.object({
26818
+ id: zod.z.string(),
26819
+ name: zod.z.string().max(120)
26820
+ }), RetrainCollectionRenameResultSchema, {
26821
+ kind: "mutation",
26822
+ auth: "admin"
26823
+ }),
26824
+ /**
26825
+ * Delete a collection. Its recording stills that no other collection
26826
+ * holds are deleted with their annotations (nothing else reaches them);
26827
+ * frames copied from tracks always stay in the dataset.
26828
+ */
26829
+ deleteRetrainCollection: require_sleep.method(zod.z.object({ id: zod.z.string() }), zod.z.object({
26830
+ deleted: zod.z.boolean(),
26831
+ removedFrames: zod.z.number().int()
26832
+ }), {
26833
+ kind: "mutation",
26834
+ auth: "admin"
26835
+ }),
26836
+ /**
26837
+ * Add the frame at a recording instant to a collection — the frame the
26838
+ * model may have seen NOTHING in. The recorder re-decodes the native
26839
+ * frame at `epochMs`; the dataset copies it (trackless, durable). The same
26840
+ * moment twice is one copy. Every refusal is named.
26841
+ */
26842
+ addRetrainFrameFromRecording: require_sleep.method(zod.z.object({
26843
+ collectionId: zod.z.string(),
26844
+ deviceId: zod.z.number(),
26845
+ epochMs: zod.z.number()
26846
+ }), AddRetrainFrameFromRecordingResultSchema, {
26847
+ kind: "mutation",
26848
+ auth: "admin",
26849
+ timeoutMs: 6e4
26850
+ }),
26851
+ /** Add frames already in the dataset to a collection. */
26852
+ addRetrainFramesToCollection: require_sleep.method(zod.z.object({
26853
+ collectionId: zod.z.string(),
26854
+ frameIds: zod.z.array(zod.z.string()).min(1).max(500)
26855
+ }), zod.z.object({
26856
+ added: zod.z.number().int(),
26857
+ alreadyMember: zod.z.number().int(),
26858
+ unknownFrameIds: zod.z.array(zod.z.string()).readonly()
26859
+ }), {
26860
+ kind: "mutation",
26861
+ auth: "admin"
26862
+ }),
26863
+ /** Remove a frame from a collection. A recording still left in no
26864
+ * collection is deleted with its annotations (`deletedFrame`). */
26865
+ removeRetrainFrameFromCollection: require_sleep.method(zod.z.object({
26866
+ collectionId: zod.z.string(),
26867
+ frameId: zod.z.string()
26868
+ }), zod.z.object({
26869
+ removed: zod.z.boolean(),
26870
+ deletedFrame: zod.z.boolean()
26871
+ }), {
26872
+ kind: "mutation",
26873
+ auth: "admin"
26874
+ }),
26875
+ /** The frames of a collection, with their pipeline boxes. */
26876
+ listRetrainCollectionFrames: require_sleep.method(zod.z.object({ collectionId: zod.z.string() }), zod.z.array(RetrainFrameSchema).readonly(), {
26877
+ kind: "query",
26878
+ auth: "admin"
26879
+ }),
26282
26880
  /**
26283
26881
  * The media an EVENT owns.
26284
26882
  *
@@ -27225,13 +27823,31 @@ var RecommendationReasonSchema = zod.z.discriminatedUnion("kind", [
27225
27823
  zod.z.object({
27226
27824
  kind: zod.z.literal("no-family-build"),
27227
27825
  format: ModelFormatSchema$1
27826
+ }),
27827
+ zod.z.object({
27828
+ kind: zod.z.literal("kept-custom-pin"),
27829
+ modelId: zod.z.string(),
27830
+ deviceKey: zod.z.string()
27228
27831
  })
27229
27832
  ]);
27833
+ /** Why a device is left exactly as it is, whatever the plan would pick (D786). */
27834
+ var KeptReasonSchema = zod.z.enum(["custom-pin"]);
27835
+ /**
27836
+ * Where a choice's latency came from (D791): this node's own benchmark
27837
+ * result, or the hardware-class table. Measured on the node beats the table.
27838
+ */
27839
+ var LatencySourceSchema = zod.z.discriminatedUnion("kind", [zod.z.object({ kind: zod.z.literal("table") }), zod.z.object({
27840
+ kind: zod.z.literal("node-benchmark"),
27841
+ resultId: zod.z.string(),
27842
+ measuredAtMs: zod.z.number()
27843
+ })]);
27230
27844
  var DeviceModelChoiceSchema = zod.z.object({
27231
27845
  modelId: zod.z.string(),
27232
27846
  p50Ms: zod.z.number(),
27233
27847
  fps: zod.z.number(),
27234
27848
  measured: zod.z.boolean(),
27849
+ /** Absent on a plan from before D791 — read as the table. */
27850
+ source: LatencySourceSchema.optional(),
27235
27851
  /** Parallel sessions at the camera rate with the headroom kept free: ⌊fps × (1 − headroom) / camera fps⌋. */
27236
27852
  capacitySessions: zod.z.number(),
27237
27853
  personRecall: zod.z.number()
@@ -27242,6 +27858,8 @@ var DeviceRecommendationSchema = zod.z.object({
27242
27858
  enabled: zod.z.boolean(),
27243
27859
  available: zod.z.boolean(),
27244
27860
  chosen: DeviceModelChoiceSchema.nullable(),
27861
+ /** Present when the device is kept as is: Apply writes nothing on it. */
27862
+ kept: KeptReasonSchema.optional(),
27245
27863
  reasons: zod.z.array(RecommendationReasonSchema).readonly()
27246
27864
  });
27247
27865
  var NodeRecommendationSchema = zod.z.object({
@@ -27295,6 +27913,17 @@ var AutoTuneWarningSchema = zod.z.discriminatedUnion("kind", [
27295
27913
  kind: zod.z.literal("coral-enabled"),
27296
27914
  nodeId: zod.z.string(),
27297
27915
  deviceKey: zod.z.string()
27916
+ }),
27917
+ zod.z.object({
27918
+ kind: zod.z.literal("custom-pin-kept"),
27919
+ nodeId: zod.z.string(),
27920
+ deviceKey: zod.z.string().nullable(),
27921
+ deviceId: zod.z.number().nullable(),
27922
+ modelId: zod.z.string()
27923
+ }),
27924
+ zod.z.object({
27925
+ kind: zod.z.literal("custom-registry-unreadable"),
27926
+ error: zod.z.string()
27298
27927
  })
27299
27928
  ]);
27300
27929
  var AutoTuneOptionsSchema = zod.z.object({
@@ -27487,13 +28116,14 @@ var SuggestSharesResultSchema = zod.z.object({
27487
28116
  nodes: zod.z.array(SuggestedNodeShareSchema).readonly()
27488
28117
  });
27489
28118
  /**
27490
- * Where the node and device shares come from (D750, D755).
27491
- * - `hardware` (default) — computed by the system from each node's static
27492
- * capacity (its accelerators at their Auto tune models, from the measured
27493
- * latency table), recomputed whenever a node or device joins, leaves, is
27494
- * switched on or off, or changes model. No load input.
27495
- * - `benchmark` — the same, from each node's measured capacity (node
27496
- * benchmark results); a node without results falls back to `hardware`.
28119
+ * Where the node and device shares come from (D750, D755, D791).
28120
+ * - `benchmark` (default since D791) — each node's capacity as its own node
28121
+ * benchmark measured it; a node without fresh results is sized from
28122
+ * `hardware` and says so. Measured on the node beats the table.
28123
+ * - `hardware` — computed from each node's static capacity only (its
28124
+ * accelerators at their Auto tune models, from the latency table).
28125
+ * Both are recomputed whenever a node or device joins, leaves, is switched
28126
+ * on or off, changes model, or a benchmark result is written. No load input.
27497
28127
  * - `manual` — the operator's stored sliders.
27498
28128
  * Either way a node or device that cannot take sessions gives its share to
27499
28129
  * the others in proportion; the stored values are never rewritten for that.
@@ -27503,7 +28133,7 @@ var ShareSourceSchema = zod.z.enum([
27503
28133
  "benchmark",
27504
28134
  "manual"
27505
28135
  ]);
27506
- var DEFAULT_SHARE_SOURCE = "hardware";
28136
+ var DEFAULT_SHARE_SOURCE = "benchmark";
27507
28137
  /** `hardware` or `benchmark`: the system computes the shares. */
27508
28138
  function isAutomaticShareSource(source) {
27509
28139
  return source !== "manual";
@@ -27517,6 +28147,7 @@ var SHARE_SOURCE_SETTING_KEY = "shareSource";
27517
28147
  * D755 split it) reads as `hardware` — that is what it computed.
27518
28148
  */
27519
28149
  function parseShareSource(value) {
28150
+ if (value === "auto") return "hardware";
27520
28151
  const parsed = ShareSourceSchema.safeParse(value);
27521
28152
  return parsed.success ? parsed.data : DEFAULT_SHARE_SOURCE;
27522
28153
  }
@@ -27561,6 +28192,371 @@ var EffectiveSharesSchema = zod.z.object({
27561
28192
  deviceWeights: zod.z.record(zod.z.string(), zod.z.record(zod.z.string(), zod.z.number()))
27562
28193
  });
27563
28194
  //#endregion
28195
+ //#region src/pipeline/node-benchmark/schemas.ts
28196
+ /**
28197
+ * Wire shapes of the node benchmark (D791): the operator's plan, the
28198
+ * preflight the confirmation shows, the run the orchestrator owns, what the
28199
+ * measuring runner reports, and the result rows Auto tune and the automatic
28200
+ * shares read.
28201
+ *
28202
+ * ONE node at a time, owned by the pipeline orchestrator. While a run is
28203
+ * active the cluster is in BENCHMARK MODE for that node: it is not a
28204
+ * detection candidate, camera pins naming it are ignored so its sessions move
28205
+ * elsewhere, and both come back when the mode ends — after a crash or a hub
28206
+ * restart too (a persisted manifest, reconciled against the registry).
28207
+ *
28208
+ * Two measurements, both on the node, driven by its own runner (frames never
28209
+ * cross a process at frame rate, D9):
28210
+ * - `device` — one accelerator × one candidate detector, root only, open
28211
+ * loop: how many streams at the camera rate it carries inside the frame
28212
+ * interval;
28213
+ * - `pipeline` — the chosen detector plus the operator's detail steps
28214
+ * (faces, plates, classifiers, CLIP…), on varied frames from the bench
28215
+ * clip: how many parallel sessions the node carries before latency, drops,
28216
+ * CPU, RAM or the event loop give out.
28217
+ */
28218
+ /** Defaults and bounds, one place. */
28219
+ var NODE_BENCHMARK_DEFAULTS = {
28220
+ fpsPerStream: 10,
28221
+ budgetMinutes: 45,
28222
+ minBudgetMinutes: 10,
28223
+ maxBudgetMinutes: 120,
28224
+ /** A result older than this no longer beats the table. */
28225
+ staleAfterDays: 30,
28226
+ /** Warm-in per ramp step (not accounted). */
28227
+ settleSec: 5,
28228
+ /** Accounted window per ramp step. */
28229
+ measureSec: 20,
28230
+ /** Longest the drain may take before the run is refused. */
28231
+ drainTimeoutSec: 120,
28232
+ /** Candidate models per device in one run. */
28233
+ maxModelsPerDevice: 6
28234
+ };
28235
+ /** The two measurements a run can make. */
28236
+ var NodeBenchmarkPhaseSchema = zod.z.enum(["device", "pipeline"]);
28237
+ var NodeBenchmarkDevicePlanSchema = zod.z.object({
28238
+ /** `<backend>:<device>` — `openvino:npu`, `coreml:all`, `cpu`. */
28239
+ deviceKey: zod.z.string().min(1),
28240
+ /**
28241
+ * Root detector candidates for the `device` measurement, in the order
28242
+ * measured. The FIRST is the one the `pipeline` measurement runs.
28243
+ */
28244
+ modelIds: zod.z.array(zod.z.string().min(1)).min(1).max(NODE_BENCHMARK_DEFAULTS.maxModelsPerDevice)
28245
+ });
28246
+ /** What the operator confirmed. */
28247
+ var NodeBenchmarkPlanSchema = zod.z.object({
28248
+ nodeId: zod.z.string().min(1),
28249
+ devices: zod.z.array(NodeBenchmarkDevicePlanSchema).min(1),
28250
+ /** Which measurements run. At least one. */
28251
+ phases: zod.z.array(NodeBenchmarkPhaseSchema).min(1).default(["device", "pipeline"]),
28252
+ /**
28253
+ * Detail steps (catalog step ids under the root: faces, plates,
28254
+ * classifiers, CLIP…) the `pipeline` measurement enables. The root
28255
+ * detector always runs.
28256
+ */
28257
+ steps: zod.z.array(zod.z.string().min(1)).default([]),
28258
+ /** Offered rate of one stream / session. */
28259
+ fpsPerStream: zod.z.number().int().min(1).max(30).default(NODE_BENCHMARK_DEFAULTS.fpsPerStream),
28260
+ /** Hard deadline: the mode ends and the cluster is restored when it passes. */
28261
+ budgetMinutes: zod.z.number().int().min(NODE_BENCHMARK_DEFAULTS.minBudgetMinutes).max(NODE_BENCHMARK_DEFAULTS.maxBudgetMinutes).default(NODE_BENCHMARK_DEFAULTS.budgetMinutes),
28262
+ /** Keep the models the run downloaded (default: delete what was not installed before). */
28263
+ keepDownloadedModels: zod.z.boolean().default(false),
28264
+ /** Start although the other nodes' capacity does not cover the sessions running now. */
28265
+ acceptInsufficientHeadroom: zod.z.boolean().default(false)
28266
+ });
28267
+ /** Why a run cannot start. `overridable` ones are lifted by a plan flag. */
28268
+ var NodeBenchmarkRefusalKindSchema = zod.z.enum([
28269
+ "benchmark-active",
28270
+ "node-offline",
28271
+ "unknown-device",
28272
+ "no-phase",
28273
+ "insufficient-headroom"
28274
+ ]);
28275
+ var NodeBenchmarkRefusalSchema = zod.z.object({
28276
+ kind: NodeBenchmarkRefusalKindSchema,
28277
+ detail: zod.z.string(),
28278
+ overridable: zod.z.boolean()
28279
+ });
28280
+ /** A camera whose detection leaves the node for the run. */
28281
+ var NodeBenchmarkMovingCameraSchema = zod.z.object({
28282
+ deviceId: zod.z.number(),
28283
+ /** Placed on the node now (a standing attach or a running session). */
28284
+ placedOnNode: zod.z.boolean(),
28285
+ /** A node pin naming this node, ignored for the run. */
28286
+ pinnedToNode: zod.z.boolean()
28287
+ });
28288
+ /** A camera that cannot leave: no other node can obtain its frames. */
28289
+ var NodeBenchmarkStayingCameraSchema = zod.z.object({
28290
+ deviceId: zod.z.number(),
28291
+ reason: zod.z.literal("only-frame-source")
28292
+ });
28293
+ var NodeBenchmarkPreflightSchema = zod.z.object({
28294
+ nodeId: zod.z.string(),
28295
+ online: zod.z.boolean(),
28296
+ moving: zod.z.array(NodeBenchmarkMovingCameraSchema).readonly(),
28297
+ /** Keep running on the node during the run; the result is flagged contaminated. */
28298
+ staying: zod.z.array(NodeBenchmarkStayingCameraSchema).readonly(),
28299
+ estimatedDurationMs: zod.z.number(),
28300
+ /** The run ends and the cluster is restored at the latest after this long. */
28301
+ budgetMs: zod.z.number(),
28302
+ phases: zod.z.array(NodeBenchmarkPhaseSchema).readonly(),
28303
+ steps: zod.z.array(zod.z.string()).readonly(),
28304
+ devices: zod.z.array(NodeBenchmarkDevicePlanSchema).readonly(),
28305
+ /** Parallel sessions the cluster runs now, and what the other nodes can carry. */
28306
+ headroom: zod.z.object({
28307
+ sessionsNow: zod.z.number(),
28308
+ otherNodesCapacitySessions: zod.z.number().nullable()
28309
+ }),
28310
+ refusals: zod.z.array(NodeBenchmarkRefusalSchema).readonly(),
28311
+ canStart: zod.z.boolean()
28312
+ });
28313
+ /** Where the measuring runner is. */
28314
+ var NodeBenchProgressSchema = zod.z.object({
28315
+ phase: zod.z.enum([
28316
+ "preparing",
28317
+ "device",
28318
+ "pipeline",
28319
+ "cleanup"
28320
+ ]),
28321
+ deviceKey: zod.z.string().nullable(),
28322
+ modelId: zod.z.string().nullable(),
28323
+ /** Streams (device) or sessions (pipeline) of the step running now. */
28324
+ load: zod.z.number().nullable(),
28325
+ cellsDone: zod.z.number(),
28326
+ cellsTotal: zod.z.number(),
28327
+ message: zod.z.string()
28328
+ });
28329
+ /** What limited a ramp. `none` = the ramp ran out of steps still passing. */
28330
+ var NodeBenchLimitSchema = zod.z.enum([
28331
+ "p95",
28332
+ "drops",
28333
+ "errors",
28334
+ "stall",
28335
+ "cpu",
28336
+ "ram",
28337
+ "none"
28338
+ ]);
28339
+ var NodeBenchRampStepSchema = zod.z.object({
28340
+ load: zod.z.number(),
28341
+ pass: zod.z.boolean(),
28342
+ p95Ms: zod.z.number(),
28343
+ dropRatio: zod.z.number(),
28344
+ /** Completed frames per second over the accounted window. */
28345
+ fps: zod.z.number(),
28346
+ cpuPct: zod.z.number().nullable(),
28347
+ ramFreePct: zod.z.number().nullable(),
28348
+ failReasons: zod.z.array(zod.z.string()).readonly()
28349
+ });
28350
+ /** One measured device × detector (the `device` measurement). */
28351
+ var NodeBenchDeviceCellSchema = zod.z.object({
28352
+ phase: zod.z.literal("device"),
28353
+ deviceKey: zod.z.string(),
28354
+ modelId: zod.z.string(),
28355
+ /** Single-stream latency (the K = 1 step). */
28356
+ p50Ms: zod.z.number(),
28357
+ p95Ms: zod.z.number(),
28358
+ p99Ms: zod.z.number(),
28359
+ /** Frames per second sustained at the last passing step. */
28360
+ fps: zod.z.number(),
28361
+ /** Streams at the camera rate the device carried inside the frame interval; 0 = not even one. */
28362
+ kMax: zod.z.number(),
28363
+ limitedBy: NodeBenchLimitSchema,
28364
+ /** First call (model load + warm-up). */
28365
+ warmupMs: zod.z.number(),
28366
+ ramp: zod.z.array(NodeBenchRampStepSchema).readonly()
28367
+ });
28368
+ /** One measured pipeline (the `pipeline` measurement) on a device. */
28369
+ var NodeBenchPipelineCellSchema = zod.z.object({
28370
+ phase: zod.z.literal("pipeline"),
28371
+ deviceKey: zod.z.string(),
28372
+ modelId: zod.z.string(),
28373
+ steps: zod.z.array(zod.z.string()).readonly(),
28374
+ /** Parallel sessions at the camera rate the node carried; 0 = not even one. */
28375
+ maxSessions: zod.z.number(),
28376
+ limitedBy: NodeBenchLimitSchema,
28377
+ /** Detail steps that produced at least one result on the clip — a step that never fired measured nothing. */
28378
+ stepsFired: zod.z.array(zod.z.string()).readonly(),
28379
+ warmupMs: zod.z.number(),
28380
+ ramp: zod.z.array(NodeBenchRampStepSchema).readonly()
28381
+ });
28382
+ var NodeBenchCellSchema = zod.z.discriminatedUnion("phase", [NodeBenchDeviceCellSchema, NodeBenchPipelineCellSchema]);
28383
+ /**
28384
+ * What a result was measured ON. A result whose fingerprint no longer matches
28385
+ * the node no longer beats the table.
28386
+ */
28387
+ var NodeBenchFingerprintSchema = zod.z.object({
28388
+ pipelineVersion: zod.z.string().nullable(),
28389
+ cpuModel: zod.z.string().nullable(),
28390
+ ramGb: zod.z.number().nullable(),
28391
+ os: zod.z.string().nullable(),
28392
+ /** Per device: the pool the cells ran on (runtime + tuning). */
28393
+ pools: zod.z.record(zod.z.string(), zod.z.object({
28394
+ runtime: zod.z.string(),
28395
+ numWorkers: zod.z.number(),
28396
+ concurrency: zod.z.number(),
28397
+ batchMode: zod.z.string()
28398
+ })).default({})
28399
+ });
28400
+ /** The frames the run used. */
28401
+ var NodeBenchClipSchema = zod.z.object({
28402
+ /** `camstack-bench-v1` or `reference-images` (the fallback when the clip is not reachable). */
28403
+ id: zod.z.string(),
28404
+ revision: zod.z.string().nullable(),
28405
+ frames: zod.z.number(),
28406
+ width: zod.z.number(),
28407
+ height: zod.z.number()
28408
+ });
28409
+ var NodeBenchRunnerInputSchema = zod.z.object({
28410
+ runId: zod.z.string().min(1),
28411
+ devices: zod.z.array(NodeBenchmarkDevicePlanSchema).min(1),
28412
+ phases: zod.z.array(NodeBenchmarkPhaseSchema).min(1),
28413
+ /** The full detail step tree root for the `pipeline` measurement is built on the node from these ids. */
28414
+ steps: zod.z.array(zod.z.string()).default([]),
28415
+ fpsPerStream: zod.z.number().int().min(1).max(30),
28416
+ /** The runner stops on its own past this instant, whatever the hub does. */
28417
+ deadlineAtMs: zod.z.number(),
28418
+ settleSec: zod.z.number().min(0).max(60).default(NODE_BENCHMARK_DEFAULTS.settleSec),
28419
+ measureSec: zod.z.number().min(2).max(300).default(NODE_BENCHMARK_DEFAULTS.measureSec),
28420
+ keepDownloadedModels: zod.z.boolean().default(false)
28421
+ });
28422
+ var NodeBenchRunnerStateSchema = zod.z.enum([
28423
+ "running",
28424
+ "done",
28425
+ "failed",
28426
+ "aborted"
28427
+ ]);
28428
+ var NodeBenchRunnerStatusSchema = zod.z.object({
28429
+ runId: zod.z.string(),
28430
+ nodeId: zod.z.string(),
28431
+ state: NodeBenchRunnerStateSchema,
28432
+ progress: NodeBenchProgressSchema.nullable(),
28433
+ /** Every finished cell so far — a run stopped half way keeps what it measured. */
28434
+ cells: zod.z.array(NodeBenchCellSchema).readonly(),
28435
+ fingerprint: NodeBenchFingerprintSchema.nullable(),
28436
+ clip: NodeBenchClipSchema.nullable(),
28437
+ /** Cameras seen running on the node during the run (they share its pools). */
28438
+ activeCameraIds: zod.z.array(zod.z.number()).readonly(),
28439
+ /** Models the run downloaded and then deleted (not installed before). */
28440
+ deletedModels: zod.z.array(zod.z.string()).readonly(),
28441
+ error: zod.z.string().nullable(),
28442
+ startedAtMs: zod.z.number(),
28443
+ finishedAtMs: zod.z.number().nullable()
28444
+ });
28445
+ var NodeBenchmarkStateSchema = zod.z.enum([
28446
+ "draining",
28447
+ "measuring",
28448
+ "restoring",
28449
+ "done",
28450
+ "failed",
28451
+ "aborted"
28452
+ ]);
28453
+ /** Why a run ended. */
28454
+ var NodeBenchmarkEndReasonSchema = zod.z.enum([
28455
+ "completed",
28456
+ "operator-abort",
28457
+ "deadline",
28458
+ "node-lost",
28459
+ "runner-lost",
28460
+ "hub-restart",
28461
+ "drain-timeout",
28462
+ "failed"
28463
+ ]);
28464
+ var NodeBenchmarkRunSchema = zod.z.object({
28465
+ runId: zod.z.string(),
28466
+ nodeId: zod.z.string(),
28467
+ state: NodeBenchmarkStateSchema,
28468
+ plan: NodeBenchmarkPlanSchema,
28469
+ startedAtMs: zod.z.number(),
28470
+ deadlineAtMs: zod.z.number(),
28471
+ finishedAtMs: zod.z.number().nullable(),
28472
+ endReason: NodeBenchmarkEndReasonSchema.nullable(),
28473
+ error: zod.z.string().nullable(),
28474
+ /** Cameras moved off the node for the run. */
28475
+ moved: zod.z.array(zod.z.number()).readonly(),
28476
+ /** Cameras that stayed (their only frame source is the node). */
28477
+ staying: zod.z.array(zod.z.number()).readonly(),
28478
+ /** Something else ran on the node's pools during the run. */
28479
+ contaminated: zod.z.boolean(),
28480
+ progress: NodeBenchProgressSchema.nullable(),
28481
+ resultIds: zod.z.array(zod.z.string()).readonly()
28482
+ });
28483
+ /** `getNodeBenchmarkStatus`: the active run (or the last one), and whether benchmark mode is on. */
28484
+ var NodeBenchmarkStatusSchema = zod.z.object({
28485
+ /** The node the cluster is in benchmark mode for; null = none. */
28486
+ modeNodeId: zod.z.string().nullable(),
28487
+ run: NodeBenchmarkRunSchema.nullable()
28488
+ });
28489
+ /**
28490
+ * One stored measurement — the only authority Auto tune and the automatic
28491
+ * shares read measured capacity from. Written by the orchestrator when a run
28492
+ * ends, never by anyone else.
28493
+ */
28494
+ var NodeBenchmarkResultSchema = zod.z.object({
28495
+ id: zod.z.string(),
28496
+ runId: zod.z.string(),
28497
+ nodeId: zod.z.string(),
28498
+ cell: NodeBenchCellSchema,
28499
+ fpsPerStream: zod.z.number(),
28500
+ fingerprint: NodeBenchFingerprintSchema.nullable(),
28501
+ clip: NodeBenchClipSchema.nullable(),
28502
+ /** Other work shared the node's pools (a camera that could not move, or the hub's own duties). */
28503
+ contaminated: zod.z.boolean(),
28504
+ stayingCameras: zod.z.array(zod.z.number()).readonly(),
28505
+ /** The run ended early; the cell itself completed. */
28506
+ partialRun: zod.z.boolean(),
28507
+ measuredAtMs: zod.z.number()
28508
+ });
28509
+ var ListNodeBenchmarkResultsInputSchema = zod.z.object({
28510
+ nodeId: zod.z.string().optional(),
28511
+ deviceKey: zod.z.string().optional()
28512
+ });
28513
+ /** A result with its standing today: does it still beat the table? */
28514
+ var NodeBenchmarkResultViewSchema = NodeBenchmarkResultSchema.extend({
28515
+ /** `fresh` beats the table; `stale` falls back to it; `superseded` = a newer row covers the same cell. */
28516
+ standing: zod.z.enum([
28517
+ "fresh",
28518
+ "stale",
28519
+ "superseded"
28520
+ ]),
28521
+ staleWhy: zod.z.enum([
28522
+ "age",
28523
+ "runtime",
28524
+ "pool-tuning"
28525
+ ]).nullable()
28526
+ });
28527
+ /** The manifest persisted BEFORE benchmark mode changes anything; its presence means "restore". */
28528
+ var NodeBenchmarkManifestSchema = zod.z.object({
28529
+ runId: zod.z.string(),
28530
+ nodeId: zod.z.string(),
28531
+ startedAtMs: zod.z.number(),
28532
+ deadlineAtMs: zod.z.number(),
28533
+ plan: NodeBenchmarkPlanSchema,
28534
+ moved: zod.z.array(zod.z.number()).readonly(),
28535
+ staying: zod.z.array(zod.z.number()).readonly()
28536
+ });
28537
+ /** Candidate detectors per device, for the plan editor. */
28538
+ var NodeBenchmarkCandidatesSchema = zod.z.object({
28539
+ nodeId: zod.z.string(),
28540
+ reachable: zod.z.boolean(),
28541
+ devices: zod.z.array(zod.z.object({
28542
+ deviceKey: zod.z.string(),
28543
+ enabled: zod.z.boolean(),
28544
+ available: zod.z.boolean(),
28545
+ /** Ordered: what Auto tune would pick first, then the rest of the family by accuracy. */
28546
+ suggested: zod.z.array(zod.z.string()).readonly(),
28547
+ /** Every root detector the device has a build for. */
28548
+ all: zod.z.array(zod.z.string()).readonly(),
28549
+ /** The model the device runs now, when pinned. */
28550
+ currentModelId: zod.z.string().nullable()
28551
+ })).readonly(),
28552
+ /** Detail steps the node's catalog offers under the root (for the `pipeline` measurement). */
28553
+ steps: zod.z.array(zod.z.object({
28554
+ id: zod.z.string(),
28555
+ name: zod.z.string(),
28556
+ slot: zod.z.string()
28557
+ })).readonly()
28558
+ });
28559
+ //#endregion
27564
28560
  //#region src/capabilities/schemas/orchestrator-metrics.ts
27565
28561
  /** Shared Zod schemas for the runtime pipeline orchestrator metrics. */
27566
28562
  var OrchestratorMetricsSchema = zod.z.object({
@@ -29078,7 +30074,30 @@ var pipelineRunnerCapability = {
29078
30074
  releaseParkedTrackFrames: require_sleep.method(zod.z.object({
29079
30075
  deviceId: zod.z.number(),
29080
30076
  trackId: zod.z.string()
29081
- }), zod.z.object({ released: zod.z.number().int().nonnegative() }), { kind: "mutation" })
30077
+ }), zod.z.object({ released: zod.z.number().int().nonnegative() }), { kind: "mutation" }),
30078
+ /**
30079
+ * Start measuring THIS node for the orchestrator's node benchmark: the
30080
+ * bench clip decoded once into RAM, each device × candidate detector on an
30081
+ * open-loop ramp (`device`), then the chosen pipeline with the requested
30082
+ * detail steps (`pipeline`). Everything runs in-process with the executor
30083
+ * — no frame crosses a node (D9) — and writes nothing: no track, event,
30084
+ * media or notification. Reached by `nodePin(nodeId)`. Answers at once;
30085
+ * one run per node; the run stops itself at `deadlineAtMs`.
30086
+ */
30087
+ startNodeBench: require_sleep.method(NodeBenchRunnerInputSchema, zod.z.object({
30088
+ accepted: zod.z.literal(true),
30089
+ runId: zod.z.string()
30090
+ }), {
30091
+ kind: "mutation",
30092
+ auth: "admin"
30093
+ }),
30094
+ /** The run's progress and every finished cell; null when this runner does not know `runId`. */
30095
+ getNodeBenchStatus: require_sleep.method(zod.z.object({ runId: zod.z.string() }), NodeBenchRunnerStatusSchema.nullable(), { auth: "admin" }),
30096
+ /** Stop the run; what it finished is kept. */
30097
+ abortNodeBench: require_sleep.method(zod.z.object({ runId: zod.z.string() }), zod.z.object({ aborted: zod.z.boolean() }), {
30098
+ kind: "mutation",
30099
+ auth: "admin"
30100
+ })
29082
30101
  }
29083
30102
  };
29084
30103
  //#endregion
@@ -30054,6 +31073,51 @@ var pipelineOrchestratorCapability = {
30054
31073
  kind: "mutation",
30055
31074
  auth: "admin"
30056
31075
  }),
31076
+ /**
31077
+ * Node benchmark — what a run of this plan would do, without doing it:
31078
+ * the cameras that leave the node, those that cannot (the node is their
31079
+ * only frame source; they stay and flag the run), the estimated duration
31080
+ * and every reason it may not start. The confirmation shows this.
31081
+ */
31082
+ getNodeBenchmarkPreflight: require_sleep.method(NodeBenchmarkPlanSchema, NodeBenchmarkPreflightSchema, { auth: "admin" }),
31083
+ /**
31084
+ * Node benchmark — start ONE run (cluster-wide lock). The orchestrator
31085
+ * persists a restore manifest, enters benchmark mode for the node (out of
31086
+ * placement, its camera pins ignored, nothing rewritten), drains it, drives
31087
+ * the node's own runner, then restores — always, including after an
31088
+ * abort, a lost node or a hub restart. Answers at once; poll
31089
+ * `getNodeBenchmarkStatus`. Refused runs carry the preflight.
31090
+ */
31091
+ startNodeBenchmark: require_sleep.method(NodeBenchmarkPlanSchema, zod.z.discriminatedUnion("kind", [zod.z.object({
31092
+ kind: zod.z.literal("started"),
31093
+ runId: zod.z.string()
31094
+ }), zod.z.object({
31095
+ kind: zod.z.literal("refused"),
31096
+ preflight: NodeBenchmarkPreflightSchema
31097
+ })]), {
31098
+ kind: "mutation",
31099
+ auth: "admin"
31100
+ }),
31101
+ /** Node benchmark — the active run (or the last one) and the node in benchmark mode. */
31102
+ getNodeBenchmarkStatus: require_sleep.method(zod.z.void(), NodeBenchmarkStatusSchema, { auth: "admin" }),
31103
+ /** Node benchmark — stop the active run; the cluster is restored as it was. */
31104
+ abortNodeBenchmark: require_sleep.method(zod.z.object({ runId: zod.z.string() }), zod.z.object({ aborted: zod.z.boolean() }), {
31105
+ kind: "mutation",
31106
+ auth: "admin"
31107
+ }),
31108
+ /**
31109
+ * Node benchmark — root detector candidates per device (what Auto tune
31110
+ * would pick first, then the family) and the detail steps the node's
31111
+ * catalog offers, for the plan editor.
31112
+ */
31113
+ getNodeBenchmarkCandidates: require_sleep.method(zod.z.object({ nodeId: zod.z.string() }), NodeBenchmarkCandidatesSchema, { auth: "admin" }),
31114
+ /** Node benchmark — stored results, newest first, each with its standing today. */
31115
+ listNodeBenchmarkResults: require_sleep.method(ListNodeBenchmarkResultsInputSchema, zod.z.array(NodeBenchmarkResultViewSchema).readonly(), { auth: "admin" }),
31116
+ /** Node benchmark — delete one result; Auto tune and the shares stop reading it. */
31117
+ deleteNodeBenchmarkResult: require_sleep.method(zod.z.object({ id: zod.z.string() }), zod.z.object({ deleted: zod.z.boolean() }), {
31118
+ kind: "mutation",
31119
+ auth: "admin"
31120
+ }),
30057
31121
  /** Read one camera's settings. Null when never touched (inherits agent defaults fully). */
30058
31122
  getCameraSettings: require_sleep.method(zod.z.object({ deviceId: zod.z.number() }), CameraPipelineSettingsSchema.nullable()),
30059
31123
  /** Set or clear the 3-state toggle for one (camera, addonId). Pass `enabled: null` to clear and revert to agent default. */
@@ -38162,6 +39226,9 @@ var CreateIntegrationInputSchema = zod.z.object({
38162
39226
  enabled: zod.z.boolean().optional(),
38163
39227
  info: zod.z.record(zod.z.string(), zod.z.unknown()).optional(),
38164
39228
  settings: zod.z.record(zod.z.string(), zod.z.unknown()).optional(),
39229
+ /** Keys of `settings` the form's schema declares secret (by type) — kept in
39230
+ * the keychain, not the table (D787). */
39231
+ secretKeys: zod.z.array(zod.z.string()).optional(),
38165
39232
  skipRestart: zod.z.boolean().optional()
38166
39233
  });
38167
39234
  var UpdateIntegrationInputSchema = zod.z.object({
@@ -38197,7 +39264,9 @@ var integrationsCapability = {
38197
39264
  getSettings: require_sleep.method(zod.z.object({ id: zod.z.string() }), zod.z.record(zod.z.string(), zod.z.unknown()), { auth: "admin" }),
38198
39265
  setSettings: require_sleep.method(zod.z.object({
38199
39266
  id: zod.z.string(),
38200
- settings: zod.z.record(zod.z.string(), zod.z.unknown())
39267
+ settings: zod.z.record(zod.z.string(), zod.z.unknown()),
39268
+ /** Keys the form's schema declares secret (by type) — keychain-stored (D787). */
39269
+ secretKeys: zod.z.array(zod.z.string()).optional()
38201
39270
  }), zod.z.object({ success: zod.z.boolean() }), {
38202
39271
  kind: "mutation",
38203
39272
  auth: "admin"
@@ -49891,7 +50960,8 @@ var BaseDevice = class {
49891
50960
  this.role = options.role;
49892
50961
  this.parentDeviceId = ctx.parentDeviceId;
49893
50962
  const seedData = ctx.persistedConfig ?? {};
49894
- this.config = DeviceConfig.fromSchema(schema, (data) => ctx.persistConfig(data), seedData, ({ droppedKeys, issues }) => {
50963
+ const declaredSecretPaths = require_sleep.collectZodSecretPaths(schema);
50964
+ this.config = DeviceConfig.fromSchema(schema, (data) => ctx.persistConfig(data, { secretConfigPaths: declaredSecretPaths }), seedData, ({ droppedKeys, issues }) => {
49895
50965
  ctx.logger.warn("Device config recovery: dropping invalid persisted fields", {
49896
50966
  tags: {
49897
50967
  deviceId: ctx.id,
@@ -54395,6 +55465,90 @@ var METHOD_ACCESS_MAP = Object.freeze({
54395
55465
  addonId: null,
54396
55466
  access: "create"
54397
55467
  },
55468
+ "keychain.delete": {
55469
+ capName: "keychain",
55470
+ capScope: "system",
55471
+ addonId: null,
55472
+ access: "delete"
55473
+ },
55474
+ "keychain.getState": {
55475
+ capName: "keychain",
55476
+ capScope: "system",
55477
+ addonId: null,
55478
+ access: "view"
55479
+ },
55480
+ "keychain.listMeta": {
55481
+ capName: "keychain",
55482
+ capScope: "system",
55483
+ addonId: null,
55484
+ access: "view"
55485
+ },
55486
+ "keychain.put": {
55487
+ capName: "keychain",
55488
+ capScope: "system",
55489
+ addonId: null,
55490
+ access: "create"
55491
+ },
55492
+ "keychain.resolve": {
55493
+ capName: "keychain",
55494
+ capScope: "system",
55495
+ addonId: null,
55496
+ access: "view"
55497
+ },
55498
+ "keychainAdmin.deleteOrphans": {
55499
+ capName: "keychain-admin",
55500
+ capScope: "system",
55501
+ addonId: null,
55502
+ access: "delete"
55503
+ },
55504
+ "keychainAdmin.downloadRecoveryKey": {
55505
+ capName: "keychain-admin",
55506
+ capScope: "system",
55507
+ addonId: null,
55508
+ access: "create"
55509
+ },
55510
+ "keychainAdmin.listAudit": {
55511
+ capName: "keychain-admin",
55512
+ capScope: "system",
55513
+ addonId: null,
55514
+ access: "view"
55515
+ },
55516
+ "keychainAdmin.listSecrets": {
55517
+ capName: "keychain-admin",
55518
+ capScope: "system",
55519
+ addonId: null,
55520
+ access: "view"
55521
+ },
55522
+ "keychainAdmin.purgeRetiredKeys": {
55523
+ capName: "keychain-admin",
55524
+ capScope: "system",
55525
+ addonId: null,
55526
+ access: "delete"
55527
+ },
55528
+ "keychainAdmin.resetKeychain": {
55529
+ capName: "keychain-admin",
55530
+ capScope: "system",
55531
+ addonId: null,
55532
+ access: "delete"
55533
+ },
55534
+ "keychainAdmin.reveal": {
55535
+ capName: "keychain-admin",
55536
+ capScope: "system",
55537
+ addonId: null,
55538
+ access: "create"
55539
+ },
55540
+ "keychainAdmin.rotateMasterKey": {
55541
+ capName: "keychain-admin",
55542
+ capScope: "system",
55543
+ addonId: null,
55544
+ access: "create"
55545
+ },
55546
+ "keychainAdmin.status": {
55547
+ capName: "keychain-admin",
55548
+ capScope: "system",
55549
+ addonId: null,
55550
+ access: "view"
55551
+ },
54398
55552
  "lawnMowerControl.dock": {
54399
55553
  capName: "lawn-mower-control",
54400
55554
  capScope: "device",
@@ -55769,6 +56923,18 @@ var METHOD_ACCESS_MAP = Object.freeze({
55769
56923
  addonId: null,
55770
56924
  access: "create"
55771
56925
  },
56926
+ "pipelineAnalytics.addRetrainFrameFromRecording": {
56927
+ capName: "pipeline-analytics",
56928
+ capScope: "device",
56929
+ addonId: null,
56930
+ access: "create"
56931
+ },
56932
+ "pipelineAnalytics.addRetrainFramesToCollection": {
56933
+ capName: "pipeline-analytics",
56934
+ capScope: "device",
56935
+ addonId: null,
56936
+ access: "create"
56937
+ },
55772
56938
  "pipelineAnalytics.applyDeviceSettingsPatch": {
55773
56939
  capName: "pipeline-analytics",
55774
56940
  capScope: "device",
@@ -55817,12 +56983,36 @@ var METHOD_ACCESS_MAP = Object.freeze({
55817
56983
  addonId: null,
55818
56984
  access: "view"
55819
56985
  },
56986
+ "pipelineAnalytics.createRetrainCollection": {
56987
+ capName: "pipeline-analytics",
56988
+ capScope: "device",
56989
+ addonId: null,
56990
+ access: "create"
56991
+ },
56992
+ "pipelineAnalytics.createRetrainDatasetVersion": {
56993
+ capName: "pipeline-analytics",
56994
+ capScope: "device",
56995
+ addonId: null,
56996
+ access: "create"
56997
+ },
55820
56998
  "pipelineAnalytics.deleteDeviceEvents": {
55821
56999
  capName: "pipeline-analytics",
55822
57000
  capScope: "device",
55823
57001
  addonId: null,
55824
57002
  access: "delete"
55825
57003
  },
57004
+ "pipelineAnalytics.deleteRetrainCollection": {
57005
+ capName: "pipeline-analytics",
57006
+ capScope: "device",
57007
+ addonId: null,
57008
+ access: "delete"
57009
+ },
57010
+ "pipelineAnalytics.deleteRetrainDatasetVersion": {
57011
+ capName: "pipeline-analytics",
57012
+ capScope: "device",
57013
+ addonId: null,
57014
+ access: "delete"
57015
+ },
55826
57016
  "pipelineAnalytics.deleteTracks": {
55827
57017
  capName: "pipeline-analytics",
55828
57018
  capScope: "device",
@@ -56027,6 +57217,30 @@ var METHOD_ACCESS_MAP = Object.freeze({
56027
57217
  addonId: null,
56028
57218
  access: "view"
56029
57219
  },
57220
+ "pipelineAnalytics.listRetrainAssistProfiles": {
57221
+ capName: "pipeline-analytics",
57222
+ capScope: "device",
57223
+ addonId: null,
57224
+ access: "view"
57225
+ },
57226
+ "pipelineAnalytics.listRetrainCollectionFrames": {
57227
+ capName: "pipeline-analytics",
57228
+ capScope: "device",
57229
+ addonId: null,
57230
+ access: "view"
57231
+ },
57232
+ "pipelineAnalytics.listRetrainCollections": {
57233
+ capName: "pipeline-analytics",
57234
+ capScope: "device",
57235
+ addonId: null,
57236
+ access: "view"
57237
+ },
57238
+ "pipelineAnalytics.listRetrainDatasetVersions": {
57239
+ capName: "pipeline-analytics",
57240
+ capScope: "device",
57241
+ addonId: null,
57242
+ access: "view"
57243
+ },
56030
57244
  "pipelineAnalytics.listRetrainFrames": {
56031
57245
  capName: "pipeline-analytics",
56032
57246
  capScope: "device",
@@ -56069,12 +57283,24 @@ var METHOD_ACCESS_MAP = Object.freeze({
56069
57283
  addonId: null,
56070
57284
  access: "create"
56071
57285
  },
57286
+ "pipelineAnalytics.previewRetrainDataset": {
57287
+ capName: "pipeline-analytics",
57288
+ capScope: "device",
57289
+ addonId: null,
57290
+ access: "view"
57291
+ },
56072
57292
  "pipelineAnalytics.proposeRetrainAnnotations": {
56073
57293
  capName: "pipeline-analytics",
56074
57294
  capScope: "device",
56075
57295
  addonId: null,
56076
57296
  access: "create"
56077
57297
  },
57298
+ "pipelineAnalytics.proposeRetrainAnnotationsWithLlm": {
57299
+ capName: "pipeline-analytics",
57300
+ capScope: "device",
57301
+ addonId: null,
57302
+ access: "create"
57303
+ },
56078
57304
  "pipelineAnalytics.pruneEvents": {
56079
57305
  capName: "pipeline-analytics",
56080
57306
  capScope: "device",
@@ -56129,6 +57355,18 @@ var METHOD_ACCESS_MAP = Object.freeze({
56129
57355
  addonId: null,
56130
57356
  access: "create"
56131
57357
  },
57358
+ "pipelineAnalytics.removeRetrainFrameFromCollection": {
57359
+ capName: "pipeline-analytics",
57360
+ capScope: "device",
57361
+ addonId: null,
57362
+ access: "delete"
57363
+ },
57364
+ "pipelineAnalytics.renameRetrainCollection": {
57365
+ capName: "pipeline-analytics",
57366
+ capScope: "device",
57367
+ addonId: null,
57368
+ access: "create"
57369
+ },
56132
57370
  "pipelineAnalytics.restageRetrainTrack": {
56133
57371
  capName: "pipeline-analytics",
56134
57372
  capScope: "device",
@@ -56189,6 +57427,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56189
57427
  addonId: null,
56190
57428
  access: "create"
56191
57429
  },
57430
+ "pipelineAnalytics.verifyRetrainDatasetVersion": {
57431
+ capName: "pipeline-analytics",
57432
+ capScope: "device",
57433
+ addonId: null,
57434
+ access: "view"
57435
+ },
56192
57436
  "pipelineAnalytics.wipeAllAnalytics": {
56193
57437
  capName: "pipeline-analytics",
56194
57438
  capScope: "device",
@@ -56417,6 +57661,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56417
57661
  addonId: null,
56418
57662
  access: "view"
56419
57663
  },
57664
+ "pipelineOrchestrator.abortNodeBenchmark": {
57665
+ capName: "pipeline-orchestrator",
57666
+ capScope: "system",
57667
+ addonId: null,
57668
+ access: "create"
57669
+ },
56420
57670
  "pipelineOrchestrator.applyAutoTune": {
56421
57671
  capName: "pipeline-orchestrator",
56422
57672
  capScope: "system",
@@ -56441,6 +57691,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56441
57691
  addonId: null,
56442
57692
  access: "create"
56443
57693
  },
57694
+ "pipelineOrchestrator.deleteNodeBenchmarkResult": {
57695
+ capName: "pipeline-orchestrator",
57696
+ capScope: "system",
57697
+ addonId: null,
57698
+ access: "delete"
57699
+ },
56444
57700
  "pipelineOrchestrator.getAgentLoad": {
56445
57701
  capName: "pipeline-orchestrator",
56446
57702
  capScope: "system",
@@ -56549,6 +57805,24 @@ var METHOD_ACCESS_MAP = Object.freeze({
56549
57805
  addonId: null,
56550
57806
  access: "view"
56551
57807
  },
57808
+ "pipelineOrchestrator.getNodeBenchmarkCandidates": {
57809
+ capName: "pipeline-orchestrator",
57810
+ capScope: "system",
57811
+ addonId: null,
57812
+ access: "view"
57813
+ },
57814
+ "pipelineOrchestrator.getNodeBenchmarkPreflight": {
57815
+ capName: "pipeline-orchestrator",
57816
+ capScope: "system",
57817
+ addonId: null,
57818
+ access: "view"
57819
+ },
57820
+ "pipelineOrchestrator.getNodeBenchmarkStatus": {
57821
+ capName: "pipeline-orchestrator",
57822
+ capScope: "system",
57823
+ addonId: null,
57824
+ access: "view"
57825
+ },
56552
57826
  "pipelineOrchestrator.getNodeInferenceDevices": {
56553
57827
  capName: "pipeline-orchestrator",
56554
57828
  capScope: "system",
@@ -56591,6 +57865,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56591
57865
  addonId: null,
56592
57866
  access: "view"
56593
57867
  },
57868
+ "pipelineOrchestrator.listNodeBenchmarkResults": {
57869
+ capName: "pipeline-orchestrator",
57870
+ capScope: "system",
57871
+ addonId: null,
57872
+ access: "view"
57873
+ },
56594
57874
  "pipelineOrchestrator.pauseForStorageMigration": {
56595
57875
  capName: "pipeline-orchestrator",
56596
57876
  capScope: "system",
@@ -56735,6 +58015,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56735
58015
  addonId: null,
56736
58016
  access: "create"
56737
58017
  },
58018
+ "pipelineOrchestrator.startNodeBenchmark": {
58019
+ capName: "pipeline-orchestrator",
58020
+ capScope: "system",
58021
+ addonId: null,
58022
+ access: "create"
58023
+ },
56738
58024
  "pipelineOrchestrator.suggestShares": {
56739
58025
  capName: "pipeline-orchestrator",
56740
58026
  capScope: "system",
@@ -56753,6 +58039,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56753
58039
  addonId: null,
56754
58040
  access: "create"
56755
58041
  },
58042
+ "pipelineRunner.abortNodeBench": {
58043
+ capName: "pipeline-runner",
58044
+ capScope: "system",
58045
+ addonId: null,
58046
+ access: "create"
58047
+ },
56756
58048
  "pipelineRunner.attachCamera": {
56757
58049
  capName: "pipeline-runner",
56758
58050
  capScope: "system",
@@ -56801,6 +58093,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56801
58093
  addonId: null,
56802
58094
  access: "view"
56803
58095
  },
58096
+ "pipelineRunner.getNodeBenchStatus": {
58097
+ capName: "pipeline-runner",
58098
+ capScope: "system",
58099
+ addonId: null,
58100
+ access: "view"
58101
+ },
56804
58102
  "pipelineRunner.getParkedTrackFrame": {
56805
58103
  capName: "pipeline-runner",
56806
58104
  capScope: "system",
@@ -56843,6 +58141,12 @@ var METHOD_ACCESS_MAP = Object.freeze({
56843
58141
  addonId: null,
56844
58142
  access: "create"
56845
58143
  },
58144
+ "pipelineRunner.startNodeBench": {
58145
+ capName: "pipeline-runner",
58146
+ capScope: "system",
58147
+ addonId: null,
58148
+ access: "create"
58149
+ },
56846
58150
  "plateGallery.assignPlate": {
56847
58151
  capName: "plate-gallery",
56848
58152
  capScope: "system",
@@ -59189,6 +60493,8 @@ var KNOWN_CAP_NAMES = [
59189
60493
  "image-settings",
59190
60494
  "integrations",
59191
60495
  "intercom",
60496
+ "keychain",
60497
+ "keychain-admin",
59192
60498
  "lawn-mower-control",
59193
60499
  "llm",
59194
60500
  "llm-runtime",
@@ -59406,6 +60712,8 @@ var SYSTEM_CAP_NAMES = [
59406
60712
  "failure-contribution",
59407
60713
  "filesystem-browse",
59408
60714
  "integrations",
60715
+ "keychain",
60716
+ "keychain-admin",
59409
60717
  "llm",
59410
60718
  "llm-runtime",
59411
60719
  "load-contribution",
@@ -62875,6 +64183,8 @@ var CAPABILITY_NAMES = {
62875
64183
  imageSettings: "image-settings",
62876
64184
  integrations: "integrations",
62877
64185
  intercom: "intercom",
64186
+ keychain: "keychain",
64187
+ keychainAdmin: "keychain-admin",
62878
64188
  lawnMowerControl: "lawn-mower-control",
62879
64189
  llm: "llm",
62880
64190
  llmRuntime: "llm-runtime",
@@ -63268,6 +64578,14 @@ var CAPABILITY_ROUTER_KEYS = [
63268
64578
  key: "intercom",
63269
64579
  name: "intercom"
63270
64580
  },
64581
+ {
64582
+ key: "keychain",
64583
+ name: "keychain"
64584
+ },
64585
+ {
64586
+ key: "keychainAdmin",
64587
+ name: "keychain-admin"
64588
+ },
63271
64589
  {
63272
64590
  key: "lawnMowerControl",
63273
64591
  name: "lawn-mower-control"
@@ -63714,6 +65032,8 @@ var ALL_CAPABILITY_DEFINITIONS = [
63714
65032
  imageSettingsCapability,
63715
65033
  integrationsCapability,
63716
65034
  intercomCapability,
65035
+ keychainCapability,
65036
+ keychainAdminCapability,
63717
65037
  lawnMowerControlCapability,
63718
65038
  llmCapability,
63719
65039
  llmRuntimeCapability,
@@ -65142,6 +66462,11 @@ var METHOD_DEVICE_SELECTORS = Object.freeze({
65142
66462
  form: "single",
65143
66463
  optional: false
65144
66464
  }],
66465
+ "pipelineAnalytics.addRetrainFrameFromRecording": [{
66466
+ name: "deviceId",
66467
+ form: "single",
66468
+ optional: false
66469
+ }],
65145
66470
  "pipelineAnalytics.applyDeviceSettingsPatch": [{
65146
66471
  name: "deviceId",
65147
66472
  form: "single",
@@ -65332,6 +66657,11 @@ var METHOD_DEVICE_SELECTORS = Object.freeze({
65332
66657
  form: "single",
65333
66658
  optional: false
65334
66659
  }],
66660
+ "pipelineAnalytics.proposeRetrainAnnotationsWithLlm": [{
66661
+ name: "deviceId",
66662
+ form: "single",
66663
+ optional: false
66664
+ }],
65335
66665
  "pipelineAnalytics.pruneEventsBefore": [{
65336
66666
  name: "deviceId",
65337
66667
  form: "single",
@@ -67297,6 +68627,17 @@ function createSystemProxy(api) {
67297
68627
  getAvailableTypes: (input) => dispatch("integrations", "getAvailableTypes", "query", input),
67298
68628
  testConnection: (input) => dispatch("integrations", "testConnection", "mutation", input)
67299
68629
  },
68630
+ keychainAdmin: {
68631
+ status: (input) => dispatch("keychainAdmin", "status", "query", input),
68632
+ listSecrets: (input) => dispatch("keychainAdmin", "listSecrets", "query", input),
68633
+ listAudit: (input) => dispatch("keychainAdmin", "listAudit", "query", input),
68634
+ reveal: (input) => dispatch("keychainAdmin", "reveal", "mutation", input),
68635
+ deleteOrphans: (input) => dispatch("keychainAdmin", "deleteOrphans", "mutation", input),
68636
+ rotateMasterKey: (input) => dispatch("keychainAdmin", "rotateMasterKey", "mutation", input),
68637
+ purgeRetiredKeys: (input) => dispatch("keychainAdmin", "purgeRetiredKeys", "mutation", input),
68638
+ downloadRecoveryKey: (input) => dispatch("keychainAdmin", "downloadRecoveryKey", "mutation", input),
68639
+ resetKeychain: (input) => dispatch("keychainAdmin", "resetKeychain", "mutation", input)
68640
+ },
67300
68641
  llm: {
67301
68642
  generate: (input) => dispatch("llm", "generate", "mutation", input),
67302
68643
  generateVision: (input) => dispatch("llm", "generateVision", "mutation", input),
@@ -67516,6 +68857,13 @@ function createSystemProxy(api) {
67516
68857
  suggestShares: (input) => dispatch("pipelineOrchestrator", "suggestShares", "query", input),
67517
68858
  getEffectiveShares: (input) => dispatch("pipelineOrchestrator", "getEffectiveShares", "query", input),
67518
68859
  setShareSource: (input) => dispatch("pipelineOrchestrator", "setShareSource", "mutation", input),
68860
+ getNodeBenchmarkPreflight: (input) => dispatch("pipelineOrchestrator", "getNodeBenchmarkPreflight", "query", input),
68861
+ startNodeBenchmark: (input) => dispatch("pipelineOrchestrator", "startNodeBenchmark", "mutation", input),
68862
+ getNodeBenchmarkStatus: (input) => dispatch("pipelineOrchestrator", "getNodeBenchmarkStatus", "query", input),
68863
+ abortNodeBenchmark: (input) => dispatch("pipelineOrchestrator", "abortNodeBenchmark", "mutation", input),
68864
+ getNodeBenchmarkCandidates: (input) => dispatch("pipelineOrchestrator", "getNodeBenchmarkCandidates", "query", input),
68865
+ listNodeBenchmarkResults: (input) => dispatch("pipelineOrchestrator", "listNodeBenchmarkResults", "query", input),
68866
+ deleteNodeBenchmarkResult: (input) => dispatch("pipelineOrchestrator", "deleteNodeBenchmarkResult", "mutation", input),
67519
68867
  getCameraStatuses: (input) => dispatch("pipelineOrchestrator", "getCameraStatuses", "query", input),
67520
68868
  setCameraSensors: (input) => dispatch("pipelineOrchestrator", "setCameraSensors", "mutation", input),
67521
68869
  reconcileFromDisk: (input) => dispatch("pipelineOrchestrator", "reconcileFromDisk", "mutation", input),
@@ -67529,7 +68877,10 @@ function createSystemProxy(api) {
67529
68877
  getAllCameraMetrics: (input) => dispatch("pipelineRunner", "getAllCameraMetrics", "query", input),
67530
68878
  getLocalCameras: (input) => dispatch("pipelineRunner", "getLocalCameras", "query", input),
67531
68879
  getNativeCrop: (input) => dispatch("pipelineRunner", "getNativeCrop", "query", input),
67532
- runStatelessStep: (input) => dispatch("pipelineRunner", "runStatelessStep", "mutation", input)
68880
+ runStatelessStep: (input) => dispatch("pipelineRunner", "runStatelessStep", "mutation", input),
68881
+ startNodeBench: (input) => dispatch("pipelineRunner", "startNodeBench", "mutation", input),
68882
+ getNodeBenchStatus: (input) => dispatch("pipelineRunner", "getNodeBenchStatus", "query", input),
68883
+ abortNodeBench: (input) => dispatch("pipelineRunner", "abortNodeBench", "mutation", input)
67533
68884
  },
67534
68885
  plateGallery: {
67535
68886
  getPlateMedia: (input) => dispatch("plateGallery", "getPlateMedia", "query", input),
@@ -73116,6 +74467,22 @@ function capacitySessionsOf(fps, headroom, cameraFps) {
73116
74467
  if (!(fps > 0) || !(cameraFps > 0)) return 0;
73117
74468
  return Math.max(0, Math.floor(fps * (1 - headroom) / cameraFps + 1e-9));
73118
74469
  }
74470
+ /** The table column with the node's own measurements laid over it. */
74471
+ function overlayMeasured(table, measured) {
74472
+ if (measured === void 0 || Object.keys(measured).length === 0) return table;
74473
+ const out = { ...table };
74474
+ for (const [modelId, m] of Object.entries(measured)) out[modelId] = {
74475
+ p50Ms: m.p50Ms,
74476
+ fps: m.fps,
74477
+ measured: true,
74478
+ source: {
74479
+ kind: "node-benchmark",
74480
+ resultId: m.resultId,
74481
+ measuredAtMs: m.measuredAtMs
74482
+ }
74483
+ };
74484
+ return out;
74485
+ }
73119
74486
  function round(value, digits = 3) {
73120
74487
  const f = 10 ** digits;
73121
74488
  return Math.round(value * f) / f;
@@ -73188,6 +74555,7 @@ function choiceOn(ctx, modelId, sizing) {
73188
74555
  p50Ms: cell.p50Ms,
73189
74556
  fps: cell.fps,
73190
74557
  measured: cell.measured,
74558
+ source: cell.source ?? { kind: "table" },
73191
74559
  capacitySessions: sessionsOn(cell, sizing),
73192
74560
  personRecall: DETECTOR_ACCURACY[modelId]?.personRecall ?? 0
73193
74561
  };
@@ -73236,11 +74604,14 @@ function recommendNode(input) {
73236
74604
  if (node.hardware === null) return skippedNode(node, { kind: "no-hardware-facts" }, null);
73237
74605
  const hardware = node.hardware;
73238
74606
  const { hardwareClass, cpuModel } = classifyInferenceHardware(hardware);
73239
- const classTable = perf[hardwareClass];
73240
- if (hardwareClass === "unknown" || classTable === void 0) return skippedNode(node, {
74607
+ const measured = input.measured ?? {};
74608
+ const hasMeasured = Object.values(measured).some((m) => Object.keys(m).length > 0);
74609
+ const knownTable = hardwareClass === "unknown" ? void 0 : perf[hardwareClass];
74610
+ if (knownTable === void 0 && !hasMeasured) return skippedNode(node, {
73241
74611
  kind: "no-measured-data",
73242
74612
  hardwareClass
73243
74613
  }, hardwareClass);
74614
+ const classTable = knownTable ?? {};
73244
74615
  const devices = node.devices.toSorted((a, b) => a.key.localeCompare(b.key));
73245
74616
  const contexts = /* @__PURE__ */ new Map();
73246
74617
  const early = /* @__PURE__ */ new Map();
@@ -73258,7 +74629,7 @@ function recommendNode(input) {
73258
74629
  early.set(device.key, [{ kind: "device-unavailable" }]);
73259
74630
  continue;
73260
74631
  }
73261
- const column = accelerator === null ? void 0 : classTable[accelerator];
74632
+ const column = accelerator === null ? void 0 : overlayMeasured(classTable[accelerator], measured[device.key]);
73262
74633
  if (accelerator === null || column === void 0) {
73263
74634
  early.set(device.key, [{
73264
74635
  kind: "no-family-build",
@@ -73273,13 +74644,28 @@ function recommendNode(input) {
73273
74644
  });
73274
74645
  }
73275
74646
  const isCpu = (a) => a === "x86-cpu" || a === "arm-cpu";
73276
- const accelerators = [...contexts.values()].filter((c) => !isCpu(c.accelerator));
73277
- const cpus = [...contexts.values()].filter((c) => isCpu(c.accelerator));
74647
+ const keptByKey = /* @__PURE__ */ new Map();
74648
+ const keptReasonOf = (group) => {
74649
+ const pinned = group.find((c) => c.device.customPinModelId !== void 0);
74650
+ if (pinned?.device.customPinModelId === void 0) return null;
74651
+ const reason = {
74652
+ kind: "kept-custom-pin",
74653
+ modelId: pinned.device.customPinModelId,
74654
+ deviceKey: pinned.device.key
74655
+ };
74656
+ for (const c of group) keptByKey.set(c.device.key, [reason]);
74657
+ return reason;
74658
+ };
74659
+ const acceleratorGroup = [...contexts.values()].filter((c) => !isCpu(c.accelerator));
74660
+ const acceleratorKept = keptReasonOf(acceleratorGroup);
74661
+ const accelerators = acceleratorKept === null ? acceleratorGroup : [];
74662
+ const cpus = [...contexts.values()].filter((c) => isCpu(c.accelerator)).filter((c) => keptReasonOf([c]) === null);
73278
74663
  const chosenByKey = /* @__PURE__ */ new Map();
73279
74664
  const reasonsByKey = /* @__PURE__ */ new Map();
73280
74665
  const nodeReasons = [];
73281
74666
  let acceleratorModelId = null;
73282
74667
  const groupPick = accelerators.length > 0 ? pickForGroup(accelerators, node.formatsByModel, sizing) : null;
74668
+ if (acceleratorKept !== null) nodeReasons.push(acceleratorKept);
73283
74669
  if (groupPick !== null) {
73284
74670
  acceleratorModelId = groupPick.modelId;
73285
74671
  nodeReasons.push(...groupPick.reasons);
@@ -73323,7 +74709,8 @@ function recommendNode(input) {
73323
74709
  enabled: device.enabled,
73324
74710
  available: device.available,
73325
74711
  chosen: chosenByKey.get(device.key) ?? null,
73326
- reasons: early.get(device.key) ?? reasonsByKey.get(device.key) ?? []
74712
+ ...keptByKey.has(device.key) ? { kept: "custom-pin" } : {},
74713
+ reasons: early.get(device.key) ?? keptByKey.get(device.key) ?? reasonsByKey.get(device.key) ?? []
73327
74714
  })),
73328
74715
  reasons: nodeReasons
73329
74716
  };
@@ -73573,6 +74960,287 @@ function computeCapacityShares(input) {
73573
74960
  };
73574
74961
  }
73575
74962
  //#endregion
74963
+ //#region src/pipeline/node-benchmark/benchmark-mode.ts
74964
+ /**
74965
+ * Benchmark mode (D791) — the pure rules of "one node under test". Pure.
74966
+ *
74967
+ * While the cluster is in benchmark mode for node N:
74968
+ * - N is not a detection candidate for any camera that another node can
74969
+ * serve ({@link eligibleUnderBenchmark});
74970
+ * - a node pin naming N is ignored for such a camera
74971
+ * ({@link pinUnderBenchmark}) — the stored pin is never rewritten, so it
74972
+ * is "restored" the moment the mode ends;
74973
+ * - a camera whose ONLY frame source is N stays on N (never blind) and the
74974
+ * run is flagged contaminated.
74975
+ */
74976
+ /** The detection candidates of one camera while `benchNodeId` is under test. */
74977
+ function eligibleUnderBenchmark(eligible, benchNodeId) {
74978
+ if (benchNodeId === null || !eligible.includes(benchNodeId)) return eligible;
74979
+ const others = eligible.filter((n) => n !== benchNodeId);
74980
+ return others.length > 0 ? others : eligible;
74981
+ }
74982
+ /** A camera's node pin while `benchNodeId` is under test (null = no pin). */
74983
+ function pinUnderBenchmark(pin, benchNodeId, eligible) {
74984
+ if (pin === null || benchNodeId === null || pin !== benchNodeId) return pin;
74985
+ return eligible.some((n) => n !== benchNodeId) ? null : pin;
74986
+ }
74987
+ /** Which cameras leave the node for the run, and which cannot. */
74988
+ function classifyCamerasForBenchmark(nodeId, cameras) {
74989
+ const moving = [];
74990
+ const staying = [];
74991
+ for (const cam of cameras.toSorted((a, b) => a.deviceId - b.deviceId)) {
74992
+ const placedOnNode = cam.placedNodeId === nodeId;
74993
+ const pinnedToNode = cam.nodePin === nodeId;
74994
+ if (!placedOnNode && !pinnedToNode) continue;
74995
+ if (!cam.frameSourceNodes.some((n) => n !== nodeId)) staying.push({
74996
+ deviceId: cam.deviceId,
74997
+ reason: "only-frame-source"
74998
+ });
74999
+ else moving.push({
75000
+ deviceId: cam.deviceId,
75001
+ placedOnNode,
75002
+ pinnedToNode
75003
+ });
75004
+ }
75005
+ return {
75006
+ moving,
75007
+ staying
75008
+ };
75009
+ }
75010
+ /** Ramp steps the runner tries per cell, at most. */
75011
+ var DEVICE_RAMP = [
75012
+ 1,
75013
+ 2,
75014
+ 4,
75015
+ 6,
75016
+ 8,
75017
+ 12,
75018
+ 16,
75019
+ 24,
75020
+ 32
75021
+ ];
75022
+ var PIPELINE_RAMP = [
75023
+ 1,
75024
+ 2,
75025
+ 3,
75026
+ 4,
75027
+ 6,
75028
+ 8,
75029
+ 10,
75030
+ 12,
75031
+ 16
75032
+ ];
75033
+ /** Fixed costs around the measurement: drain, clip, warm-ups, restore. */
75034
+ var OVERHEAD_MS = 3 * 6e4;
75035
+ var WARMUP_PER_CELL_MS = 2e4;
75036
+ /**
75037
+ * An upper bound on how long the run takes: every ramp step of every cell,
75038
+ * plus the drain, the clip and the restore — capped at the budget, which is
75039
+ * the hard deadline anyway. A ramp usually stops well before its last step.
75040
+ */
75041
+ function estimateNodeBenchmarkDurationMs(plan, timing = {}) {
75042
+ const stepMs = ((timing.settleSec ?? NODE_BENCHMARK_DEFAULTS.settleSec) + (timing.measureSec ?? NODE_BENCHMARK_DEFAULTS.measureSec)) * 1e3;
75043
+ let total = OVERHEAD_MS;
75044
+ if (plan.phases.includes("device")) for (const device of plan.devices) total += device.modelIds.length * (WARMUP_PER_CELL_MS + DEVICE_RAMP.length * stepMs);
75045
+ if (plan.phases.includes("pipeline")) total += plan.devices.length * (WARMUP_PER_CELL_MS + PIPELINE_RAMP.length * stepMs);
75046
+ return Math.min(total, plan.budgetMinutes * 6e4);
75047
+ }
75048
+ /** Why a run cannot start, in the order the operator should read them. */
75049
+ function nodeBenchmarkRefusals(input) {
75050
+ const out = [];
75051
+ if (input.activeRunNodeId !== null) out.push({
75052
+ kind: "benchmark-active",
75053
+ detail: `A benchmark of ${input.activeRunNodeId} is running — one node at a time.`,
75054
+ overridable: false
75055
+ });
75056
+ if (!input.online) out.push({
75057
+ kind: "node-offline",
75058
+ detail: `${input.plan.nodeId} is not online.`,
75059
+ overridable: false
75060
+ });
75061
+ const unknown = input.plan.devices.map((d) => d.deviceKey).filter((k) => !input.knownDeviceKeys.includes(k));
75062
+ if (unknown.length > 0) out.push({
75063
+ kind: "unknown-device",
75064
+ detail: `${input.plan.nodeId} reports no device ${unknown.join(", ")}.`,
75065
+ overridable: false
75066
+ });
75067
+ if (input.plan.phases.length === 0) out.push({
75068
+ kind: "no-phase",
75069
+ detail: "Choose at least one measurement.",
75070
+ overridable: false
75071
+ });
75072
+ const capacity = input.otherNodesCapacitySessions;
75073
+ if (capacity !== null && input.sessionsNow > capacity && !input.plan.acceptInsufficientHeadroom) out.push({
75074
+ kind: "insufficient-headroom",
75075
+ detail: `The cluster runs ${input.sessionsNow} sessions now; the other nodes can carry ${capacity}.`,
75076
+ overridable: true
75077
+ });
75078
+ return out;
75079
+ }
75080
+ //#endregion
75081
+ //#region src/pipeline/node-benchmark/results.ts
75082
+ /** The cell a row measures — two rows with the same key measure the same thing. */
75083
+ function resultCellKey(row) {
75084
+ const { cell } = row;
75085
+ const steps = cell.phase === "pipeline" ? cell.steps.toSorted().join(",") : "";
75086
+ return [
75087
+ row.nodeId,
75088
+ cell.deviceKey,
75089
+ cell.phase,
75090
+ cell.modelId,
75091
+ steps
75092
+ ].join("|");
75093
+ }
75094
+ function staleWhy(row, ctx) {
75095
+ const bound = ctx.staleAfterMs ?? NODE_BENCHMARK_DEFAULTS.staleAfterDays * 864e5;
75096
+ if (ctx.nowMs - row.measuredAtMs > bound) return "age";
75097
+ const now = ctx.currentPools[row.nodeId]?.[row.cell.deviceKey];
75098
+ const then = row.fingerprint?.pools[row.cell.deviceKey];
75099
+ if (now === void 0 || then === void 0) return null;
75100
+ if (now.runtime !== then.runtime) return "runtime";
75101
+ if (now.numWorkers !== then.numWorkers || now.concurrency !== then.concurrency || now.batchMode !== then.batchMode) return "pool-tuning";
75102
+ return null;
75103
+ }
75104
+ /** The standing of every row, by id. */
75105
+ function resultStandings(rows, ctx) {
75106
+ const newest = /* @__PURE__ */ new Map();
75107
+ for (const row of rows) {
75108
+ const key = resultCellKey(row);
75109
+ const held = newest.get(key);
75110
+ if (held === void 0 || row.measuredAtMs > held.measuredAtMs) newest.set(key, row);
75111
+ }
75112
+ const out = /* @__PURE__ */ new Map();
75113
+ for (const row of rows) {
75114
+ if (newest.get(resultCellKey(row))?.id !== row.id) {
75115
+ out.set(row.id, {
75116
+ standing: "superseded",
75117
+ staleWhy: null
75118
+ });
75119
+ continue;
75120
+ }
75121
+ const why = staleWhy(row, ctx);
75122
+ out.set(row.id, why === null ? {
75123
+ standing: "fresh",
75124
+ staleWhy: null
75125
+ } : {
75126
+ standing: "stale",
75127
+ staleWhy: why
75128
+ });
75129
+ }
75130
+ return out;
75131
+ }
75132
+ /** Rows that beat the table today. */
75133
+ function freshResults(rows, ctx) {
75134
+ const standings = resultStandings(rows, ctx);
75135
+ return rows.filter((r) => standings.get(r.id)?.standing === "fresh");
75136
+ }
75137
+ /** deviceKey → modelId → the fresh `device` measurement on `nodeId`. */
75138
+ function measuredDetectorCells(rows, nodeId, ctx) {
75139
+ const out = {};
75140
+ for (const row of freshResults(rows, ctx)) {
75141
+ if (row.nodeId !== nodeId || row.cell.phase !== "device") continue;
75142
+ const perDevice = out[row.cell.deviceKey] ?? {};
75143
+ perDevice[row.cell.modelId] = {
75144
+ p50Ms: Math.round(row.cell.p50Ms * 100) / 100,
75145
+ fps: row.cell.fps,
75146
+ resultId: row.id,
75147
+ measuredAtMs: row.measuredAtMs
75148
+ };
75149
+ out[row.cell.deviceKey] = perDevice;
75150
+ }
75151
+ return out;
75152
+ }
75153
+ /**
75154
+ * Per node, each device at its newest fresh `pipeline` measurement — the
75155
+ * `NodeCapacitySource` answer the automatic shares read.
75156
+ */
75157
+ function measuredCapacityFromResults(rows, nodeIds, ctx) {
75158
+ const byNode = /* @__PURE__ */ new Map();
75159
+ for (const row of freshResults(rows, ctx)) {
75160
+ if (!nodeIds.includes(row.nodeId) || row.cell.phase !== "pipeline") continue;
75161
+ const devices = byNode.get(row.nodeId) ?? /* @__PURE__ */ new Map();
75162
+ const held = devices.get(row.cell.deviceKey);
75163
+ if (held === void 0 || row.measuredAtMs > held.measuredAtMs) devices.set(row.cell.deviceKey, row);
75164
+ byNode.set(row.nodeId, devices);
75165
+ }
75166
+ const out = /* @__PURE__ */ new Map();
75167
+ for (const nodeId of nodeIds) {
75168
+ const devices = byNode.get(nodeId);
75169
+ if (devices === void 0) continue;
75170
+ out.set(nodeId, {
75171
+ nodeId,
75172
+ devices: [...devices.values()].toSorted((a, b) => a.cell.deviceKey.localeCompare(b.cell.deviceKey)).map((r) => ({
75173
+ deviceKey: r.cell.deviceKey,
75174
+ maxSessions: r.cell.phase === "pipeline" ? r.cell.maxSessions : 0,
75175
+ modelId: r.cell.modelId,
75176
+ measuredAtMs: r.measuredAtMs
75177
+ }))
75178
+ });
75179
+ }
75180
+ return out;
75181
+ }
75182
+ //#endregion
75183
+ //#region src/pipeline/node-benchmark/step-tree.ts
75184
+ var BENCH_ROOT_STEP_ID = "object-detection";
75185
+ function slotAddons(schema, slot) {
75186
+ return schema.slots.find((s) => s.id === slot)?.addons ?? [];
75187
+ }
75188
+ var feeds = (from, to) => to.inputClasses.some((c) => from.outputClasses.includes(c));
75189
+ function layout(schema) {
75190
+ const root = slotAddons(schema, "detector").find((a) => a.id === BENCH_ROOT_STEP_ID);
75191
+ if (root === void 0) return null;
75192
+ const classifiers = slotAddons(schema, "classifier");
75193
+ const croppers = slotAddons(schema, "cropper").filter((c) => feeds(root, c)).map((cropper) => ({
75194
+ cropper,
75195
+ recognizers: classifiers.filter((k) => feeds(cropper, k))
75196
+ }));
75197
+ const underCropper = new Set(croppers.flatMap((c) => c.recognizers.map((r) => r.id)));
75198
+ return {
75199
+ root,
75200
+ croppers,
75201
+ classifiers: classifiers.filter((k) => feeds(root, k) && !underCropper.has(k.id)),
75202
+ refiners: slotAddons(schema, "refiner")
75203
+ };
75204
+ }
75205
+ /** The detail steps the operator can choose, in tree order. */
75206
+ function listBenchDetailSteps(schema) {
75207
+ const l = layout(schema);
75208
+ if (l === null) return [];
75209
+ const of = (a) => ({
75210
+ id: a.id,
75211
+ name: a.name,
75212
+ slot: a.slot
75213
+ });
75214
+ return [
75215
+ ...l.croppers.flatMap((c) => [of(c.cropper), ...c.recognizers.map(of)]),
75216
+ ...l.classifiers.map(of),
75217
+ ...l.refiners.map(of)
75218
+ ];
75219
+ }
75220
+ /** Build the tree. Throws when the node's catalog has no object-detection root. */
75221
+ function buildBenchStepTree(schema, rootModelId, enabledStepIds) {
75222
+ const l = layout(schema);
75223
+ if (l === null) throw new Error(`the node's catalog has no ${BENCH_ROOT_STEP_ID} step`);
75224
+ const on = new Set(enabledStepIds);
75225
+ const step = (a, enabled) => ({
75226
+ addonId: a.id,
75227
+ enabled
75228
+ });
75229
+ return [{
75230
+ addonId: l.root.id,
75231
+ modelId: rootModelId,
75232
+ enabled: true,
75233
+ children: [
75234
+ ...l.croppers.map(({ cropper, recognizers }) => ({
75235
+ ...step(cropper, on.has(cropper.id) || recognizers.some((r) => on.has(r.id))),
75236
+ children: recognizers.map((r) => step(r, on.has(r.id)))
75237
+ })),
75238
+ ...l.classifiers.map((k) => step(k, on.has(k.id))),
75239
+ ...l.refiners.map((r) => step(r, on.has(r.id)))
75240
+ ]
75241
+ }];
75242
+ }
75243
+ //#endregion
73576
75244
  //#region src/pipeline/root-face-crop.ts
73577
75245
  /** Side of the square, as a multiple of the face box's longer side. */
73578
75246
  var ROOT_FACE_REFINE_SCALE = 1.6;
@@ -75723,6 +77391,7 @@ exports.AcceleratorKindSchema = AcceleratorKindSchema;
75723
77391
  exports.AccessoriesStatusSchema = AccessoriesStatusSchema;
75724
77392
  exports.AccessoryKind = AccessoryKind;
75725
77393
  exports.AddBrokerInputSchema = AddBrokerInputSchema;
77394
+ exports.AddRetrainFrameFromRecordingResultSchema = AddRetrainFrameFromRecordingResultSchema;
75726
77395
  exports.AddonAutoUpdateSchema = AddonAutoUpdateSchema;
75727
77396
  exports.AddonListItemSchema = AddonListItemSchema;
75728
77397
  exports.AddonPageDeclarationSchema = AddonPageDeclarationSchema;
@@ -75804,6 +77473,7 @@ exports.BASE_DEVICE_CAPS = BASE_DEVICE_CAPS;
75804
77473
  exports.BASE_LIVE_EGRESS_PROFILE = BASE_LIVE_EGRESS_PROFILE;
75805
77474
  exports.BATTERY_DEVICE_PROFILE = BATTERY_DEVICE_PROFILE;
75806
77475
  exports.BATTERY_UNREACHABLE_AFTER_MS = BATTERY_UNREACHABLE_AFTER_MS;
77476
+ exports.BENCH_ROOT_STEP_ID = BENCH_ROOT_STEP_ID;
75807
77477
  exports.BIRTH_DECISION_DEFAULT_LIMIT = BIRTH_DECISION_DEFAULT_LIMIT;
75808
77478
  exports.BOOT_RECOVERY_BACKOFF_MS = require_sleep.BOOT_RECOVERY_BACKOFF_MS;
75809
77479
  exports.BUILTIN_RESULT_KINDS = BUILTIN_RESULT_KINDS;
@@ -76059,6 +77729,7 @@ exports.CoverStatusSchema = CoverStatusSchema;
76059
77729
  exports.CreateApiKeyInputSchema = CreateApiKeyInputSchema;
76060
77730
  exports.CreateApiKeyResultSchema = CreateApiKeyResultSchema;
76061
77731
  exports.CreateIntegrationInputSchema = CreateIntegrationInputSchema;
77732
+ exports.CreateRetrainDatasetVersionResultSchema = CreateRetrainDatasetVersionResultSchema;
76062
77733
  exports.CreateScopedTokenInputSchema = CreateScopedTokenInputSchema;
76063
77734
  exports.CreateScopedTokenResultSchema = CreateScopedTokenResultSchema;
76064
77735
  exports.CreateUserInputSchema = CreateUserInputSchema;
@@ -76112,6 +77783,7 @@ exports.DEVICE_CAP_NAMES = DEVICE_CAP_NAMES;
76112
77783
  exports.DEVICE_CHILDREN_BATCH_MAX = require_sleep.DEVICE_CHILDREN_BATCH_MAX;
76113
77784
  exports.DEVICE_DO_ACTIONS = DEVICE_DO_ACTIONS;
76114
77785
  exports.DEVICE_PROFILES = DEVICE_PROFILES;
77786
+ exports.DEVICE_RAMP = DEVICE_RAMP;
76115
77787
  exports.DEVICE_RESTORE_RETRY_CONCURRENCY = DEVICE_RESTORE_RETRY_CONCURRENCY;
76116
77788
  exports.DEVICE_RESTORE_RETRY_DELAYS_MS = DEVICE_RESTORE_RETRY_DELAYS_MS;
76117
77789
  exports.DEVICE_SCOPED_CAPS = require_sleep.DEVICE_SCOPED_CAPS;
@@ -76334,8 +78006,24 @@ exports.IntegrationLiteSchema = IntegrationLiteSchema;
76334
78006
  exports.IntegrationWithStateSchema = IntegrationWithStateSchema;
76335
78007
  exports.IntercomAbilitySchema = IntercomAbilitySchema;
76336
78008
  exports.IntercomStatusSchema = IntercomStatusSchema;
78009
+ exports.KEYCHAIN_MAX_REFS_PER_CALL = KEYCHAIN_MAX_REFS_PER_CALL;
78010
+ exports.KEYCHAIN_RESET_CONFIRMATION = KEYCHAIN_RESET_CONFIRMATION;
76337
78011
  exports.KNOWN_CAP_NAMES = KNOWN_CAP_NAMES;
78012
+ exports.KeptReasonSchema = KeptReasonSchema;
76338
78013
  exports.KeyEventSchema = KeyEventSchema;
78014
+ exports.KeychainAdminSecretSchema = KeychainAdminSecretSchema;
78015
+ exports.KeychainAuditActionSchema = KeychainAuditActionSchema;
78016
+ exports.KeychainAuditEntrySchema = KeychainAuditEntrySchema;
78017
+ exports.KeychainKeySourceKindSchema = KeychainKeySourceKindSchema;
78018
+ exports.KeychainKeySourceSchema = KeychainKeySourceSchema;
78019
+ exports.KeychainResolveEntrySchema = KeychainResolveEntrySchema;
78020
+ exports.KeychainResolveResultSchema = KeychainResolveResultSchema;
78021
+ exports.KeychainSecretMetaSchema = KeychainSecretMetaSchema;
78022
+ exports.KeychainSecretUsageSchema = KeychainSecretUsageSchema;
78023
+ exports.KeychainStateSchema = KeychainStateSchema;
78024
+ exports.KeychainStatusSchema = KeychainStatusSchema;
78025
+ exports.KeychainUnavailableReasonSchema = KeychainUnavailableReasonSchema;
78026
+ exports.KeychainWriteRefusedError = require_sleep.KeychainWriteRefusedError;
76339
78027
  exports.LABEL_SUPPLY_MACRO = LABEL_SUPPLY_MACRO;
76340
78028
  exports.LABEL_SUPPLY_STEP_IDS = LABEL_SUPPLY_STEP_IDS;
76341
78029
  exports.LABEL_SUPPLY_VOCABULARIES = LABEL_SUPPLY_VOCABULARIES;
@@ -76353,6 +78041,7 @@ exports.LTS_SCOPE_CLASS_SEPARATOR = LTS_SCOPE_CLASS_SEPARATOR;
76353
78041
  exports.LabelAttributionSchema = LabelAttributionSchema;
76354
78042
  exports.LabelDefinitionSchema = LabelDefinitionSchema;
76355
78043
  exports.LabelTierSchema = LabelTierSchema;
78044
+ exports.LatencySourceSchema = LatencySourceSchema;
76356
78045
  exports.LawnMowerActivitySchema = LawnMowerActivitySchema;
76357
78046
  exports.LawnMowerControlStatusSchema = LawnMowerControlStatusSchema;
76358
78047
  exports.LedgerWalkDeviceReportSchema = LedgerWalkDeviceReportSchema;
@@ -76365,6 +78054,7 @@ exports.LegacyStorageLocationDefaultSchema = LegacyStorageLocationDefaultSchema;
76365
78054
  exports.LinkedDeviceSchema = LinkedDeviceSchema;
76366
78055
  exports.LinkedDevicesModeSchema = LinkedDevicesModeSchema;
76367
78056
  exports.LinkedDevicesSlotValueSchema = LinkedDevicesSlotValueSchema;
78057
+ exports.ListNodeBenchmarkResultsInputSchema = ListNodeBenchmarkResultsInputSchema;
76368
78058
  exports.ListTrackRelationsInputSchema = ListTrackRelationsInputSchema;
76369
78059
  exports.ListTrackRelationsResultSchema = ListTrackRelationsResultSchema;
76370
78060
  exports.LlmDefaultSchema = LlmDefaultSchema;
@@ -76452,6 +78142,7 @@ exports.MEDIA_PRESENCE_OWNER_KINDS = MEDIA_PRESENCE_OWNER_KINDS;
76452
78142
  exports.METHOD_ACCESS_MAP = METHOD_ACCESS_MAP;
76453
78143
  exports.METHOD_DEVICE_SELECTORS = METHOD_DEVICE_SELECTORS;
76454
78144
  exports.MINUTES_PER_DAY = MINUTES_PER_DAY;
78145
+ exports.MIN_SCRUBBED_LENGTH = require_sleep.MIN_SCRUBBED_LENGTH;
76455
78146
  exports.MIN_SESSIONS_PER_DEVICE_RANGE = MIN_SESSIONS_PER_DEVICE_RANGE;
76456
78147
  exports.MODEL_FORMATS = MODEL_FORMATS;
76457
78148
  exports.MODEL_HOSTING = MODEL_HOSTING;
@@ -76615,6 +78306,7 @@ exports.NC_TEMPLATE_VARS = NC_TEMPLATE_VARS;
76615
78306
  exports.NC_UPDATE_EVENT_PACKAGE_NAMES = NC_UPDATE_EVENT_PACKAGE_NAMES;
76616
78307
  exports.NETWORK_LINK_TYPES = NETWORK_LINK_TYPES;
76617
78308
  exports.NETWORK_LINK_UNKNOWN = NETWORK_LINK_UNKNOWN;
78309
+ exports.NODE_BENCHMARK_DEFAULTS = NODE_BENCHMARK_DEFAULTS;
76618
78310
  exports.NO_MEASURED_CAPACITY = NO_MEASURED_CAPACITY;
76619
78311
  exports.NativeCropBboxSchema = NativeCropBboxSchema;
76620
78312
  exports.NativeCropRefSchema = NativeCropRefSchema;
@@ -76736,6 +78428,33 @@ exports.NetworkAccessStatusSchema = NetworkAccessStatusSchema;
76736
78428
  exports.NetworkAddressSchema = NetworkAddressSchema;
76737
78429
  exports.NetworkEndpointSchema = NetworkEndpointSchema;
76738
78430
  exports.NetworkLinkStatusSchema = NetworkLinkStatusSchema;
78431
+ exports.NodeBenchCellSchema = NodeBenchCellSchema;
78432
+ exports.NodeBenchClipSchema = NodeBenchClipSchema;
78433
+ exports.NodeBenchDeviceCellSchema = NodeBenchDeviceCellSchema;
78434
+ exports.NodeBenchFingerprintSchema = NodeBenchFingerprintSchema;
78435
+ exports.NodeBenchLimitSchema = NodeBenchLimitSchema;
78436
+ exports.NodeBenchPipelineCellSchema = NodeBenchPipelineCellSchema;
78437
+ exports.NodeBenchProgressSchema = NodeBenchProgressSchema;
78438
+ exports.NodeBenchRampStepSchema = NodeBenchRampStepSchema;
78439
+ exports.NodeBenchRunnerInputSchema = NodeBenchRunnerInputSchema;
78440
+ exports.NodeBenchRunnerStateSchema = NodeBenchRunnerStateSchema;
78441
+ exports.NodeBenchRunnerStatusSchema = NodeBenchRunnerStatusSchema;
78442
+ exports.NodeBenchmarkCandidatesSchema = NodeBenchmarkCandidatesSchema;
78443
+ exports.NodeBenchmarkDevicePlanSchema = NodeBenchmarkDevicePlanSchema;
78444
+ exports.NodeBenchmarkEndReasonSchema = NodeBenchmarkEndReasonSchema;
78445
+ exports.NodeBenchmarkManifestSchema = NodeBenchmarkManifestSchema;
78446
+ exports.NodeBenchmarkMovingCameraSchema = NodeBenchmarkMovingCameraSchema;
78447
+ exports.NodeBenchmarkPhaseSchema = NodeBenchmarkPhaseSchema;
78448
+ exports.NodeBenchmarkPlanSchema = NodeBenchmarkPlanSchema;
78449
+ exports.NodeBenchmarkPreflightSchema = NodeBenchmarkPreflightSchema;
78450
+ exports.NodeBenchmarkRefusalKindSchema = NodeBenchmarkRefusalKindSchema;
78451
+ exports.NodeBenchmarkRefusalSchema = NodeBenchmarkRefusalSchema;
78452
+ exports.NodeBenchmarkResultSchema = NodeBenchmarkResultSchema;
78453
+ exports.NodeBenchmarkResultViewSchema = NodeBenchmarkResultViewSchema;
78454
+ exports.NodeBenchmarkRunSchema = NodeBenchmarkRunSchema;
78455
+ exports.NodeBenchmarkStateSchema = NodeBenchmarkStateSchema;
78456
+ exports.NodeBenchmarkStatusSchema = NodeBenchmarkStatusSchema;
78457
+ exports.NodeBenchmarkStayingCameraSchema = NodeBenchmarkStayingCameraSchema;
76739
78458
  exports.NodeDeviceChangeSchema = NodeDeviceChangeSchema;
76740
78459
  exports.NodeDirectoryEntrySchema = NodeDirectoryEntrySchema;
76741
78460
  exports.NodeDirectorySchema = NodeDirectorySchema;
@@ -76796,6 +78515,7 @@ exports.PET_FEEDER_MANUAL_FEED_MIN = PET_FEEDER_MANUAL_FEED_MIN;
76796
78515
  exports.PIPELINE_ANALYTICS_CAP_NAME = PIPELINE_ANALYTICS_CAP_NAME;
76797
78516
  exports.PIPELINE_FLOW_CAPABILITY_NAMES = PIPELINE_FLOW_CAPABILITY_NAMES;
76798
78517
  exports.PIPELINE_OWNER_CAPABILITY_NAMES = PIPELINE_OWNER_CAPABILITY_NAMES;
78518
+ exports.PIPELINE_RAMP = PIPELINE_RAMP;
76799
78519
  exports.PRIVACY_MASK_CAP_NAME = PRIVACY_MASK_CAP_NAME;
76800
78520
  exports.PROVIDER_KIND_CAP_NAMES = PROVIDER_KIND_CAP_NAMES;
76801
78521
  exports.PROVIDER_PIN_FIELD = require_sleep.PROVIDER_PIN_FIELD;
@@ -76872,11 +78592,12 @@ exports.RECORDING_EXPORT_MAX_READ_BYTES = RECORDING_EXPORT_MAX_READ_BYTES;
76872
78592
  exports.RECORDING_SOURCE_CAMSTACK = RECORDING_SOURCE_CAMSTACK;
76873
78593
  exports.RECORDING_SOURCE_CAMSTACK_ADDON = RECORDING_SOURCE_CAMSTACK_ADDON;
76874
78594
  exports.RECORDING_TIMELINE_BATCH_MAX = RECORDING_TIMELINE_BATCH_MAX;
76875
- exports.REDACTED_SECRET = REDACTED_SECRET;
78595
+ exports.REDACTED_SECRET = require_sleep.REDACTED_SECRET;
76876
78596
  exports.REMOVED_MODEL_IDS = REMOVED_MODEL_IDS;
76877
78597
  exports.RESERVED_BINDING_NAMES = require_composition.RESERVED_BINDING_NAMES;
76878
78598
  exports.RESERVED_COLLECTION_SOURCES = RESERVED_COLLECTION_SOURCES;
76879
78599
  exports.RESTORED_CAP_NAMES = RESTORED_CAP_NAMES;
78600
+ exports.REVALIDATE_AFTER_MS = require_sleep.REVALIDATE_AFTER_MS;
76880
78601
  exports.ROOM_EXAMPLE_MOTION_SOURCES = ROOM_EXAMPLE_MOTION_SOURCES;
76881
78602
  exports.ROOM_EXAMPLE_TEMPERATURE_SOURCES = ROOM_EXAMPLE_TEMPERATURE_SOURCES;
76882
78603
  exports.ROOM_OCCUPANCY_WINDOW_MS = ROOM_OCCUPANCY_WINDOW_MS;
@@ -76960,16 +78681,28 @@ exports.RetrainAnnotationSchema = RetrainAnnotationSchema;
76960
78681
  exports.RetrainAnnotationSourceSchema = RetrainAnnotationSourceSchema;
76961
78682
  exports.RetrainArchiveResultSchema = RetrainArchiveResultSchema;
76962
78683
  exports.RetrainArchiveTargetSchema = RetrainArchiveTargetSchema;
78684
+ exports.RetrainAssistProfileSchema = RetrainAssistProfileSchema;
76963
78685
  exports.RetrainAssistResultSchema = RetrainAssistResultSchema;
76964
78686
  exports.RetrainAssistSubjectSchema = RetrainAssistSubjectSchema;
78687
+ exports.RetrainCollectionCreateResultSchema = RetrainCollectionCreateResultSchema;
78688
+ exports.RetrainCollectionRenameResultSchema = RetrainCollectionRenameResultSchema;
78689
+ exports.RetrainCollectionSchema = RetrainCollectionSchema;
76965
78690
  exports.RetrainCopyRefusalSchema = RetrainCopyRefusalSchema;
78691
+ exports.RetrainDatasetSelectionSchema = RetrainDatasetSelectionSchema;
78692
+ exports.RetrainDatasetStatsSchema = RetrainDatasetStatsSchema;
78693
+ exports.RetrainDatasetVersionSchema = RetrainDatasetVersionSchema;
76966
78694
  exports.RetrainExportFilterSchema = RetrainExportFilterSchema;
76967
78695
  exports.RetrainExportLayoutSchema = RetrainExportLayoutSchema;
76968
78696
  exports.RetrainFrameCandidateSchema = RetrainFrameCandidateSchema;
76969
78697
  exports.RetrainFrameListSchema = RetrainFrameListSchema;
78698
+ exports.RetrainFrameOriginSchema = RetrainFrameOriginSchema;
76970
78699
  exports.RetrainFrameSchema = RetrainFrameSchema;
76971
78700
  exports.RetrainFrameSelectionSchema = RetrainFrameSelectionSchema;
78701
+ exports.RetrainLlmAssistResultSchema = RetrainLlmAssistResultSchema;
78702
+ exports.RetrainLlmProposalSchema = RetrainLlmProposalSchema;
78703
+ exports.RetrainLlmReviewSchema = RetrainLlmReviewSchema;
76972
78704
  exports.RetrainMacroClassSchema = RetrainMacroClassSchema;
78705
+ exports.RetrainPipelineBoxSchema = RetrainPipelineBoxSchema;
76973
78706
  exports.RetrainStatusSchema = RetrainStatusSchema;
76974
78707
  exports.RetrainTrackSchema = RetrainTrackSchema;
76975
78708
  exports.RetrainTransitionResultSchema = RetrainTransitionResultSchema;
@@ -76995,7 +78728,9 @@ exports.SCENE_DEFAULT_UNCOVERED_POLICY = SCENE_DEFAULT_UNCOVERED_POLICY;
76995
78728
  exports.SCENE_DIVERGED = SCENE_DIVERGED;
76996
78729
  exports.SCENE_RESET_RECAPTURES = SCENE_RESET_RECAPTURES;
76997
78730
  exports.SCOPE_PRESETS = SCOPE_PRESETS;
78731
+ exports.SECRET_CLEAR = require_sleep.SECRET_CLEAR;
76998
78732
  exports.SECRET_META = require_sleep.SECRET_META;
78733
+ exports.SECRET_REF_SCHEME = require_sleep.SECRET_REF_SCHEME;
76999
78734
  exports.SENSOR_FEATURES = SENSOR_FEATURES;
77000
78735
  exports.SENSOR_MAP = SENSOR_MAP;
77001
78736
  exports.SESSION_PLACEMENT_SETTING_KEY = SESSION_PLACEMENT_SETTING_KEY;
@@ -77302,6 +79037,7 @@ exports.applyModeDeviceListEdit = applyModeDeviceListEdit;
77302
79037
  exports.applyModelBoundSettings = applyModelBoundSettings;
77303
79038
  exports.applyNonBlockingEdit = applyNonBlockingEdit;
77304
79039
  exports.applySecureOnArmEdit = applySecureOnArmEdit;
79040
+ exports.arrayItemFieldPath = require_sleep.arrayItemFieldPath;
77305
79041
  exports.asBoolean = require_sleep.asBoolean;
77306
79042
  exports.asJsonArray = require_sleep.asJsonArray;
77307
79043
  exports.asJsonObject = require_sleep.asJsonObject;
@@ -77333,6 +79069,7 @@ exports.brightnessCapability = brightnessCapability;
77333
79069
  exports.brokerCapability = brokerCapability;
77334
79070
  exports.buildAddonRouteProvider = buildAddonRouteProvider;
77335
79071
  exports.buildAudioArgs = require_composition.buildAudioArgs;
79072
+ exports.buildBenchStepTree = buildBenchStepTree;
77336
79073
  exports.buildCapabilityLookup = buildCapabilityLookup;
77337
79074
  exports.buildDeviceAdminUrl = buildDeviceAdminUrl;
77338
79075
  exports.buildDoorbellCompositionFeature = buildDoorbellCompositionFeature;
@@ -77343,6 +79080,7 @@ exports.buildInputArgs = require_composition.buildInputArgs;
77343
79080
  exports.buildModelVariantGroups = buildModelVariantGroups;
77344
79081
  exports.buildNcTaxonomy = buildNcTaxonomy;
77345
79082
  exports.buildRoleScopes = buildRoleScopes;
79083
+ exports.buildSecretRef = require_sleep.buildSecretRef;
77346
79084
  exports.buildStreamParamsConfigSchema = buildStreamParamsConfigSchema;
77347
79085
  exports.buildVideoArgs = require_composition.buildVideoArgs;
77348
79086
  exports.buildViewerLink = buildViewerLink;
@@ -77363,9 +79101,12 @@ exports.carbonMonoxideCapability = carbonMonoxideCapability;
77363
79101
  exports.cellsToRects = cellsToRects;
77364
79102
  exports.checkRoleAddress = checkRoleAddress;
77365
79103
  exports.classifyBearerPrincipal = classifyBearerPrincipal;
79104
+ exports.classifyCamerasForBenchmark = classifyCamerasForBenchmark;
77366
79105
  exports.classifyInferenceHardware = classifyInferenceHardware;
79106
+ exports.classifySecretWrite = require_sleep.classifySecretWrite;
77367
79107
  exports.classifyStream = classifyStream;
77368
79108
  exports.classifyStreams = classifyStreams;
79109
+ exports.clearKnownSecrets = require_sleep.clearKnownSecrets;
77369
79110
  exports.clearModelBoundOverrides = clearModelBoundOverrides;
77370
79111
  exports.clearModelBoundSetting = clearModelBoundSetting;
77371
79112
  exports.climateControlCapability = climateControlCapability;
@@ -77380,8 +79121,10 @@ exports.clusterStepSettingKey = clusterStepSettingKey;
77380
79121
  exports.codecIsAccepted = codecIsAccepted;
77381
79122
  exports.collectHydratedFieldEntries = require_sleep.collectHydratedFieldEntries;
77382
79123
  exports.collectHydratedFieldValues = require_sleep.collectHydratedFieldValues;
79124
+ exports.collectKeychainStoredKeys = require_sleep.collectKeychainStoredKeys;
77383
79125
  exports.collectModelBoundKeys = collectModelBoundKeys;
77384
- exports.collectSecretConfigKeys = collectSecretConfigKeys;
79126
+ exports.collectSecretConfigKeys = require_sleep.collectSecretConfigKeys;
79127
+ exports.collectSecretMarkerRefs = require_sleep.collectSecretMarkerRefs;
77385
79128
  exports.collectZodSecretPaths = require_sleep.collectZodSecretPaths;
77386
79129
  exports.colorCapability = colorCapability;
77387
79130
  exports.colorForKind = colorForKind;
@@ -77434,6 +79177,7 @@ exports.createLazyTrpcSource = require_sleep.createLazyTrpcSource;
77434
79177
  exports.createLogChannelsProvider = createLogChannelsProvider;
77435
79178
  exports.createMirrorSource = require_sleep.createMirrorSource;
77436
79179
  exports.createRuntimeStateBridge = createRuntimeStateBridge;
79180
+ exports.createSecretsAccess = require_sleep.createSecretsAccess;
77437
79181
  exports.createSliceHandle = require_sleep.createSliceHandle;
77438
79182
  exports.createStatefulExpressionMemory = require_composition.createStatefulExpressionMemory;
77439
79183
  exports.createSystemProxy = createSystemProxy;
@@ -77500,6 +79244,7 @@ exports.effectiveStepSettings = effectiveStepSettings;
77500
79244
  exports.egressTranscodeSharingKey = egressTranscodeSharingKey;
77501
79245
  exports.egressTransportFromRequest = egressTransportFromRequest;
77502
79246
  exports.electByShare = electByShare;
79247
+ exports.eligibleUnderBenchmark = eligibleUnderBenchmark;
77503
79248
  exports.embeddingEncoderCapability = embeddingEncoderCapability;
77504
79249
  exports.embeddingModelFailedError = embeddingModelFailedError;
77505
79250
  exports.embeddingModelFailedOf = embeddingModelFailedOf;
@@ -77517,6 +79262,7 @@ exports.enumerateInferenceDevices = enumerateInferenceDevices;
77517
79262
  exports.enumerateItemArrayFields = enumerateItemArrayFields;
77518
79263
  exports.enumerateSchemaFields = enumerateSchemaFields;
77519
79264
  exports.errMsg = require_err_msg.errMsg;
79265
+ exports.estimateNodeBenchmarkDurationMs = estimateNodeBenchmarkDurationMs;
77520
79266
  exports.evaluateAst = require_composition.evaluateAst;
77521
79267
  exports.evaluateCompositionField = evaluateCompositionField;
77522
79268
  exports.evaluateCount = require_composition.evaluateCount;
@@ -77560,10 +79306,13 @@ exports.findCompositionCycles = findCompositionCycles;
77560
79306
  exports.findTimezone = findTimezone;
77561
79307
  exports.floodCapability = floodCapability;
77562
79308
  exports.foldSnapshotByFunction = foldSnapshotByFunction;
79309
+ exports.forgetKnownSecret = require_sleep.forgetKnownSecret;
77563
79310
  exports.formatForRuntime = formatForRuntime;
77564
79311
  exports.formatMediaOwnerKey = formatMediaOwnerKey;
77565
79312
  exports.formatMinutes = formatMinutes;
77566
79313
  exports.formatParkedFor = formatParkedFor;
79314
+ exports.formatSecretScope = require_sleep.formatSecretScope;
79315
+ exports.freshResults = freshResults;
77567
79316
  exports.frigateDefaultClassFloors = frigateDefaultClassFloors;
77568
79317
  exports.frigateLabelFields = frigateLabelFields;
77569
79318
  exports.gasCapability = gasCapability;
@@ -77577,6 +79326,7 @@ exports.getTaxonomyEntry = getTaxonomyEntry;
77577
79326
  exports.gifDeriveSpeed = gifDeriveSpeed;
77578
79327
  exports.gifFilterComplex = gifFilterComplex;
77579
79328
  exports.gifFromMp4Args = gifFromMp4Args;
79329
+ exports.globalSecretScope = require_sleep.globalSecretScope;
77580
79330
  exports.hasModelBoundOverrides = hasModelBoundOverrides;
77581
79331
  exports.hasMotionTrigger = hasMotionTrigger;
77582
79332
  exports.hfModelUrl = hfModelUrl;
@@ -77626,6 +79376,7 @@ exports.isEventOwnerType = isEventOwnerType;
77626
79376
  exports.isFirstLevelMacroClass = isFirstLevelMacroClass;
77627
79377
  exports.isHeldBackTemplateVar = isHeldBackTemplateVar;
77628
79378
  exports.isIsolatedBuiltin = isIsolatedBuiltin;
79379
+ exports.isKeychainStoredField = require_sleep.isKeychainStoredField;
77629
79380
  exports.isKnownTemplateVar = isKnownTemplateVar;
77630
79381
  exports.isLabelSupplyStepId = isLabelSupplyStepId;
77631
79382
  exports.isLocationEnabled = isLocationEnabled;
@@ -77640,7 +79391,12 @@ exports.isRetiredClearKey = isRetiredClearKey;
77640
79391
  exports.isRootSuppliableStepId = isRootSuppliableStepId;
77641
79392
  exports.isSameAddonId = isSameAddonId;
77642
79393
  exports.isScheduleActive = isScheduleActive;
77643
- exports.isSecretConfigField = isSecretConfigField;
79394
+ exports.isSecretClear = require_sleep.isSecretClear;
79395
+ exports.isSecretConfigField = require_sleep.isSecretConfigField;
79396
+ exports.isSecretFieldView = require_sleep.isSecretFieldView;
79397
+ exports.isSecretMarker = require_sleep.isSecretMarker;
79398
+ exports.isSecretMarkerLike = require_sleep.isSecretMarkerLike;
79399
+ exports.isSecretRef = require_sleep.isSecretRef;
77644
79400
  exports.isSingleHubAddressRole = isSingleHubAddressRole;
77645
79401
  exports.isSoftwareDecode = require_composition.isSoftwareDecode;
77646
79402
  exports.isSourceCap = require_composition.isSourceCap;
@@ -77657,8 +79413,11 @@ exports.isZodSecret = require_sleep.isZodSecret;
77657
79413
  exports.ituDbfsFromPreEpoch = ituDbfsFromPreEpoch;
77658
79414
  exports.jobKindSchema = jobKindSchema;
77659
79415
  exports.kebabToCamel = kebabToCamel;
79416
+ exports.keychainAdminCapability = keychainAdminCapability;
79417
+ exports.keychainCapability = keychainCapability;
77660
79418
  exports.kindOfValue = kindOfValue;
77661
79419
  exports.kindsForDiscriminator = kindsForDiscriminator;
79420
+ exports.knownSecretCount = require_sleep.knownSecretCount;
77662
79421
  exports.knownValues = knownValues;
77663
79422
  exports.lawnMowerControlCapability = lawnMowerControlCapability;
77664
79423
  exports.legacyAutoLinkIds = legacyAutoLinkIds;
@@ -77669,6 +79428,7 @@ exports.lifecycleJobStateSchema = lifecycleJobStateSchema;
77669
79428
  exports.lifecycleTaskSchema = lifecycleTaskSchema;
77670
79429
  exports.linkedLabelStepId = linkedLabelStepId;
77671
79430
  exports.linkedStepOf = linkedStepOf;
79431
+ exports.listBenchDetailSteps = listBenchDetailSteps;
77672
79432
  exports.llmCapability = llmCapability;
77673
79433
  exports.llmRuntimeCapability = llmRuntimeCapability;
77674
79434
  exports.loadContributionCapability = loadContributionCapability;
@@ -77683,6 +79443,7 @@ exports.logLevelAtMost = logLevelAtMost;
77683
79443
  exports.loginMethodCapability = loginMethodCapability;
77684
79444
  exports.looseSchema = looseSchema;
77685
79445
  exports.makeProfileBrokerId = require_sleep.makeProfileBrokerId;
79446
+ exports.makeSecretMarker = require_sleep.makeSecretMarker;
77686
79447
  exports.makeSourceBrokerId = require_sleep.makeSourceBrokerId;
77687
79448
  exports.mapAudioLabelToMacro = mapAudioLabelToMacro;
77688
79449
  exports.markdownToHtmlLite = markdownToHtmlLite;
@@ -77691,8 +79452,11 @@ exports.maskUrlCredentials = maskUrlCredentials;
77691
79452
  exports.matchDoAction = matchDoAction;
77692
79453
  exports.mayReadLocation = mayReadLocation;
77693
79454
  exports.mayWriteToLocation = mayWriteToLocation;
79455
+ exports.measuredCapacityFromResults = measuredCapacityFromResults;
79456
+ exports.measuredDetectorCells = measuredDetectorCells;
77694
79457
  exports.mediaPlayerCapability = mediaPlayerCapability;
77695
79458
  exports.memoizePinnedFfmpeg = memoizePinnedFfmpeg;
79459
+ exports.mergeSecretStatePaths = require_sleep.mergeSecretStatePaths;
77696
79460
  exports.mergeSettingsBags = mergeSettingsBags;
77697
79461
  exports.mergeSourceInfo = mergeSourceInfo;
77698
79462
  exports.meshNetworkCapability = meshNetworkCapability;
@@ -77719,6 +79483,7 @@ exports.ncAlarmSystemDefaultSettings = ncAlarmSystemDefaultSettings;
77719
79483
  exports.networkAccessCapability = networkAccessCapability;
77720
79484
  exports.networkLinkCapability = networkLinkCapability;
77721
79485
  exports.networkQualityCapability = networkQualityCapability;
79486
+ exports.nodeBenchmarkRefusals = nodeBenchmarkRefusals;
77722
79487
  exports.nodePickerItems = nodePickerItems;
77723
79488
  exports.nodePin = require_sleep.nodePin;
77724
79489
  exports.nodesCapability = nodesCapability;
@@ -77726,6 +79491,7 @@ exports.normalizeAddonInitResult = require_sleep.normalizeAddonInitResult;
77726
79491
  exports.normalizeAudioLabel = normalizeAudioLabel;
77727
79492
  exports.normalizeCoreBlockWrite = normalizeCoreBlockWrite;
77728
79493
  exports.normalizeNodeId = require_sleep.normalizeNodeId;
79494
+ exports.normalizeSecretOwner = require_sleep.normalizeSecretOwner;
77729
79495
  exports.normalizeTokenScopes = normalizeTokenScopes;
77730
79496
  exports.normalizeUnit = normalizeUnit;
77731
79497
  exports.notificationOutputCapability = notificationOutputCapability;
@@ -77753,6 +79519,8 @@ exports.parseOccupancyScope = parseOccupancyScope;
77753
79519
  exports.parseProcStatus = parseProcStatus;
77754
79520
  exports.parseProfileBrokerId = require_sleep.parseProfileBrokerId;
77755
79521
  exports.parseRuleSection = parseRuleSection;
79522
+ exports.parseSecretRef = require_sleep.parseSecretRef;
79523
+ exports.parseSecretStatePath = require_sleep.parseSecretStatePath;
77756
79524
  exports.parseSessionPlacementPolicy = parseSessionPlacementPolicy;
77757
79525
  exports.parseShareSource = parseShareSource;
77758
79526
  exports.parseStreamParamsFormPatch = parseStreamParamsFormPatch;
@@ -77770,6 +79538,7 @@ exports.pickRestartCandidate = pickRestartCandidate;
77770
79538
  exports.pickVideoEncoder = require_composition.pickVideoEncoder;
77771
79539
  exports.pickerForCondition = pickerForCondition;
77772
79540
  exports.pickerForRuleClasses = pickerForRuleClasses;
79541
+ exports.pinUnderBenchmark = pinUnderBenchmark;
77773
79542
  exports.pipelineAnalyticsCapability = pipelineAnalyticsCapability;
77774
79543
  exports.pipelineExecutorCapability = pipelineExecutorCapability;
77775
79544
  exports.pipelineOrchestratorCapability = pipelineOrchestratorCapability;
@@ -77815,6 +79584,7 @@ exports.recordingOnboardCapability = recordingOnboardCapability;
77815
79584
  exports.recordingSignalCapability = recordingSignalCapability;
77816
79585
  exports.rectsToCells = rectsToCells;
77817
79586
  exports.reducePoints = reducePoints;
79587
+ exports.registerKnownSecret = require_sleep.registerKnownSecret;
77818
79588
  exports.renameAlarmProfile = renameAlarmProfile;
77819
79589
  exports.replacedFieldKeys = replacedFieldKeys;
77820
79590
  exports.requiredTopLevelKeys = requiredTopLevelKeys;
@@ -77856,9 +79626,13 @@ exports.resolvePublicEndpoint = resolvePublicEndpoint;
77856
79626
  exports.resolveRecordingProfiles = resolveRecordingProfiles;
77857
79627
  exports.resolveRootSupply = resolveRootSupply;
77858
79628
  exports.resolveRunnerId = resolveRunnerId;
79629
+ exports.resolveSecretMarkers = require_sleep.resolveSecretMarkers;
79630
+ exports.resolveSecretViewsIn = require_sleep.resolveSecretViewsIn;
77859
79631
  exports.resolveStreamMaps = require_composition.resolveStreamMaps;
77860
79632
  exports.resolveVariantModelId = resolveVariantModelId;
77861
79633
  exports.resolveViewableDeviceIds = resolveViewableDeviceIds;
79634
+ exports.resultCellKey = resultCellKey;
79635
+ exports.resultStandings = resultStandings;
77862
79636
  exports.roleSpec = roleSpec;
77863
79637
  exports.roomCompositionExample = roomCompositionExample;
77864
79638
  exports.rootSuppliesOf = rootSuppliesOf;
@@ -77882,14 +79656,17 @@ exports.runtimeStatePolicyFor = runtimeStatePolicyFor;
77882
79656
  exports.sameDoFamily = sameDoFamily;
77883
79657
  exports.sceneMonitorCapability = sceneMonitorCapability;
77884
79658
  exports.scheduleForSendTimes = scheduleForSendTimes;
77885
- exports.schemaDeclaresAnyField = schemaDeclaresAnyField;
79659
+ exports.schemaDeclaresAnyField = require_sleep.schemaDeclaresAnyField;
77886
79660
  exports.scopeInherits = scopeInherits;
77887
79661
  exports.scopeKey = require_sleep.scopeKey;
77888
79662
  exports.scopesAllowAddon = scopesAllowAddon;
77889
79663
  exports.scopesAllowDeviceCap = scopesAllowDeviceCap;
77890
79664
  exports.scoreRuntimes = scoreRuntimes;
77891
79665
  exports.scriptRunnerCapability = scriptRunnerCapability;
79666
+ exports.scrubKnownSecrets = require_sleep.scrubKnownSecrets;
77892
79667
  exports.searchDisplayIcons = searchDisplayIcons;
79668
+ exports.secretTreeFromPaths = require_sleep.secretTreeFromPaths;
79669
+ exports.secretTreeFromSchema = require_sleep.secretTreeFromSchema;
77893
79670
  exports.secureActuationFor = secureActuationFor;
77894
79671
  exports.selectAppConnectionEndpoints = selectAppConnectionEndpoints;
77895
79672
  exports.selectAssignedProfileSlots = require_sleep.selectAssignedProfileSlots;
@@ -77904,6 +79681,7 @@ exports.setByPath = setByPath;
77904
79681
  exports.settingValuesEqual = settingValuesEqual;
77905
79682
  exports.settingsBelow = settingsBelow;
77906
79683
  exports.settingsStoreCapability = settingsStoreCapability;
79684
+ exports.shortSecretRefHash = require_sleep.shortSecretRefHash;
77907
79685
  exports.signalPercentFromBars = signalPercentFromBars;
77908
79686
  exports.signalPercentFromRssi = signalPercentFromRssi;
77909
79687
  exports.siteZoneKey = siteZoneKey;
@@ -77972,11 +79750,13 @@ exports.toDeviceSummary = toDeviceSummary;
77972
79750
  exports.toExpressionValue = require_composition.toExpressionValue;
77973
79751
  exports.toNodeId = require_sleep.toNodeId;
77974
79752
  exports.toPercentShares = toPercentShares;
79753
+ exports.toSecretFieldView = require_sleep.toSecretFieldView;
77975
79754
  exports.toStreamSourceEntry = toStreamSourceEntry;
77976
79755
  exports.toastCapability = toastCapability;
77977
79756
  exports.toggleAudioLabel = toggleAudioLabel;
77978
79757
  exports.tokenize = require_composition.tokenize;
77979
79758
  exports.transcodeBody = transcodeBody;
79759
+ exports.transformSecretWrite = require_sleep.transformSecretWrite;
77980
79760
  exports.tryConvertUnit = tryConvertUnit;
77981
79761
  exports.turnProviderCapability = turnProviderCapability;
77982
79762
  exports.unitDimension = unitDimension;