@camstack/addon-provider-dreame 0.2.35 → 0.2.36

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 (3) hide show
  1. package/dist/addon.js +255 -25
  2. package/dist/addon.mjs +255 -25
  3. package/package.json +1 -1
package/dist/addon.js CHANGED
@@ -50504,7 +50504,7 @@ objectType({
50504
50504
  })
50505
50505
  });
50506
50506
  //#endregion
50507
- //#region ../types/dist/event-category-CIa_iT6b.mjs
50507
+ //#region ../types/dist/event-category-BZL-fdNj.mjs
50508
50508
  var EventCategory = /* @__PURE__ */ function(EventCategory) {
50509
50509
  EventCategory["SystemBoot"] = "system.boot";
50510
50510
  EventCategory["SystemAddonsReady"] = "system.addons-ready";
@@ -50941,7 +50941,7 @@ var EventCategory = /* @__PURE__ */ function(EventCategory) {
50941
50941
  EventCategory["MetricsNodeResourcesSnapshot"] = "metrics.node-resources-snapshot";
50942
50942
  /**
50943
50943
  * Periodic per-node process-tree snapshot (camstack-related pids
50944
- * with ghost / managed / root classification). Emitted ~0.2 Hz by
50944
+ * with root / managed / system classification). Emitted ~0.2 Hz by
50945
50945
  * the metrics-provider addon. Drives the Cluster → Processes tab
50946
50946
  * without polling `metricsProvider.listNodeProcesses`.
50947
50947
  */
@@ -61733,6 +61733,19 @@ var SettingsRecordSchema = object({
61733
61733
  data: record(string(), unknown())
61734
61734
  });
61735
61735
  /**
61736
+ * One record of a BULK insert — {@link SettingsRecordSchema} with the id made
61737
+ * optional.
61738
+ *
61739
+ * A separate schema rather than loosening the shared one: every other method
61740
+ * on this cap addresses a row BY its id, and making that field optional
61741
+ * everywhere would turn a forgotten key into a silently generated one on
61742
+ * `update` and `delete` as well.
61743
+ */
61744
+ var BulkRecordSchema = object({
61745
+ id: string().optional(),
61746
+ data: record(string(), unknown())
61747
+ });
61748
+ /**
61736
61749
  * Column declaration for a structured (SQL-backed) collection.
61737
61750
  *
61738
61751
  * Logical types — the backend translates each to the matching SQLite
@@ -61789,6 +61802,10 @@ method(object({
61789
61802
  collection: string(),
61790
61803
  record: SettingsRecordSchema
61791
61804
  }), _void(), { kind: "mutation" }), method(object({
61805
+ namespace: string().optional(),
61806
+ collection: string(),
61807
+ records: array(BulkRecordSchema).readonly()
61808
+ }), object({ inserted: number().int() }), { kind: "mutation" }), method(object({
61792
61809
  namespace: string().optional(),
61793
61810
  collection: string(),
61794
61811
  id: string(),
@@ -61897,6 +61914,13 @@ method(_void(), EngineInfoSchema, { auth: "admin" }), method(object({
61897
61914
  }), _void(), {
61898
61915
  kind: "mutation",
61899
61916
  auth: "admin"
61917
+ }), method(object({
61918
+ namespace: string().optional(),
61919
+ collection: string(),
61920
+ records: array(BulkRecordSchema).readonly()
61921
+ }), object({ inserted: number().int() }), {
61922
+ kind: "mutation",
61923
+ auth: "admin"
61900
61924
  }), method(object({
61901
61925
  namespace: string().optional(),
61902
61926
  collection: string(),
@@ -63844,6 +63868,68 @@ method(LogEntrySchema, _void(), { kind: "mutation" }), method(object({
63844
63868
  limit: number().optional(),
63845
63869
  tags: record(string(), string()).optional()
63846
63870
  }), array(LogEntrySchema).readonly());
63871
+ var LoadContributionSchema = object({
63872
+ role: _enum([
63873
+ "decode",
63874
+ "transcode",
63875
+ "recording",
63876
+ "streaming",
63877
+ "detection"
63878
+ ]),
63879
+ /**
63880
+ * The NUMERIC device id — the same value every log line carries as
63881
+ * `tags.deviceId`. `null` means this cost genuinely belongs to no single
63882
+ * camera (a shared pool), NOT that the contributor forgot to look it up: a
63883
+ * contributor that cannot name its camera must not emit the entry at all,
63884
+ * because an unnamed per-camera entry is indistinguishable from a shared one
63885
+ * and would quietly turn one camera's cost into everybody's.
63886
+ */
63887
+ deviceId: number().int().positive().nullable(),
63888
+ attribution: _enum([
63889
+ "measured",
63890
+ "accounted",
63891
+ "unattributable"
63892
+ ]),
63893
+ /**
63894
+ * What ONE entry is, in the contributor's own words — `615/high`,
63895
+ * `617/native`, `cuda:0 shared pool`. Free text because the unit differs per
63896
+ * family and inventing a common one would lose the only information that
63897
+ * makes two entries for the same camera distinguishable.
63898
+ */
63899
+ unit: string(),
63900
+ /**
63901
+ * The OS process this cost lives in, when there is one. Present so a
63902
+ * consumer can (a) tell two generations of the same unit apart across a
63903
+ * restart, and (b) subtract claimed processes from the node's process
63904
+ * snapshot to see what NOBODY claimed. Absent for an entry that owns no
63905
+ * process of its own.
63906
+ */
63907
+ pid: number().int().positive().optional(),
63908
+ /**
63909
+ * When this generation started. The pid's incarnation marker: a consumer
63910
+ * differencing {@link LoadContributionSchema.shape.cpuSeconds} must drop the
63911
+ * window when this changes, because the counter restarted from zero in a new
63912
+ * process.
63913
+ */
63914
+ startedAtMs: number().optional(),
63915
+ /**
63916
+ * CUMULATIVE CPU seconds this unit has consumed since it started — user +
63917
+ * system, read from the child's own `/proc/<pid>/stat` at the moment the
63918
+ * contribution is asked for.
63919
+ *
63920
+ * Cumulative and not a rate on purpose: a rate needs a window, a window
63921
+ * needs a sampler, and a new per-node sampler is the defect half of
63922
+ * `docs/architecture/load-ledger.md` documents. A counter can be differenced
63923
+ * by whoever already keeps a history; a rate cannot be un-averaged.
63924
+ *
63925
+ * Absent — never zero — on a node with no `/proc`, on a read failure, and on
63926
+ * an entry with no process.
63927
+ */
63928
+ cpuSeconds: number().optional(),
63929
+ /** Resident bytes of this unit's process, same source and same rules. */
63930
+ rssBytes: number().optional()
63931
+ });
63932
+ method(_void(), array(LoadContributionSchema).readonly());
63847
63933
  /**
63848
63934
  * `login-method` — collection cap through which auth addons contribute
63849
63935
  * their pre-auth login surfaces to the login page. This is the SINGLE,
@@ -64047,8 +64133,7 @@ var NodeProcessSchema = object({
64047
64133
  classification: _enum([
64048
64134
  "root",
64049
64135
  "managed",
64050
- "system",
64051
- "ghost"
64136
+ "system"
64052
64137
  ]),
64053
64138
  /** `$process` addon binding when `managed`, else null. */
64054
64139
  addonId: string().nullable(),
@@ -64056,22 +64141,39 @@ var NodeProcessSchema = object({
64056
64141
  nodeId: string().nullable(),
64057
64142
  /** Truncated command line. */
64058
64143
  command: string(),
64144
+ /**
64145
+ * `ps pcpu` — CPU averaged over the process's WHOLE LIFETIME, not a rate.
64146
+ * On a runner up for days it barely moves. Fine as a column, useless as a
64147
+ * series: use `cpuMainPercent + cpuGcPercent` for anything time-varying.
64148
+ */
64059
64149
  cpuPercent: number(),
64060
64150
  memoryRssBytes: number(),
64151
+ /**
64152
+ * Instantaneous CPU% of the process's own threads over the last
64153
+ * process-snapshot window, from a `/proc/<pid>/task/*` tick delta.
64154
+ *
64155
+ * `null` = UNKNOWN, never zero: no previous sample yet (first tick after
64156
+ * boot), the pid was recycled, or this node is not Linux.
64157
+ */
64158
+ cpuMainPercent: number().nullable(),
64159
+ /**
64160
+ * Instantaneous CPU% of V8's `V8Worker` platform pool over the same window.
64161
+ *
64162
+ * This is the number that rewrote the 2026-08-27 diagnosis — hub-main 73%,
64163
+ * `stream-broker` 61% (`docs/architecture/load-ledger.md`). A CPU chart that
64164
+ * does not separate it from `cpuMainPercent` shows "busy" where the truth is
64165
+ * "allocating too much".
64166
+ *
64167
+ * Concurrent GC is the dominant tenant of that pool but not the only one
64168
+ * (background compilation runs there too), so it is reported as
64169
+ * "GC / V8 helpers" rather than as pure collection time. `null` has the same
64170
+ * meaning as on `cpuMainPercent`.
64171
+ */
64172
+ cpuGcPercent: number().nullable(),
64173
+ /** Threads seen in the tick scan. `null` under the same conditions. */
64174
+ threadCount: number().nullable(),
64061
64175
  /** Wall-clock uptime (seconds). Parsed from `ps etime`. */
64062
- uptimeSec: number(),
64063
- /** True when ancestor walk reaches `ppid=1` (reparented to init/launchd). */
64064
- orphaned: boolean()
64065
- });
64066
- var KillProcessInputSchema = object({
64067
- pid: number(),
64068
- /** Force = SIGKILL. Default is SIGTERM. */
64069
- force: boolean().optional()
64070
- });
64071
- var KillProcessResultSchema = object({
64072
- success: boolean(),
64073
- reason: string().optional(),
64074
- signal: _enum(["SIGTERM", "SIGKILL"]).optional()
64176
+ uptimeSec: number()
64075
64177
  });
64076
64178
  var DumpHeapSnapshotInputSchema = object({
64077
64179
  /** The addon whose runner should dump a heap snapshot. */
@@ -64084,6 +64186,104 @@ var DumpHeapSnapshotResultSchema = object({
64084
64186
  pid: number().optional(),
64085
64187
  reason: string().optional()
64086
64188
  });
64189
+ /**
64190
+ * One point of one function's series.
64191
+ *
64192
+ * The unsuffixed fields are the bucket's **MAXIMUM**, and that choice is the
64193
+ * point of the whole surface. The two obvious reductions both lie: a mean per
64194
+ * bucket smears a spike away, and taking every Nth sample skips it outright.
64195
+ * Either would give us a tool built to find peaks that does not show peaks.
64196
+ * `...Min` carries the other end, `samples` says how many raw snapshots folded
64197
+ * into the bucket, and a mean stays derivable where it is wanted.
64198
+ *
64199
+ * An UNREDUCED point is a one-sample bucket: `samples === 1` and each `...Min`
64200
+ * equals its unsuffixed twin. Reduced and unreduced are the same shape, so a
64201
+ * caller cannot tell which it received — which is what "one reader" means.
64202
+ */
64203
+ var LoadPointSchema = object({
64204
+ /** Bucket START, or the snapshot's own timestamp when unreduced. */
64205
+ atMs: number(),
64206
+ /** Raw snapshots in this bucket. Never 0 — AN EMPTY BUCKET IS ABSENT. */
64207
+ samples: number().int(),
64208
+ /**
64209
+ * `null` = UNKNOWN and it PROPAGATES: a bucket is null unless every process
64210
+ * of every snapshot in it reported a thread split. A partial sum is a
64211
+ * smaller number that looks exactly as real as a complete one.
64212
+ */
64213
+ cpuMainPercent: number().nullable(),
64214
+ cpuMainPercentMin: number().nullable(),
64215
+ cpuGcPercent: number().nullable(),
64216
+ cpuGcPercentMin: number().nullable(),
64217
+ /** Lifetime-average CPU%, summed. Always known — and never a rate. */
64218
+ cpuLifetimePercent: number(),
64219
+ cpuLifetimePercentMin: number(),
64220
+ memoryRssBytes: number(),
64221
+ memoryRssBytesMin: number(),
64222
+ processCount: number().int(),
64223
+ processCountMin: number().int()
64224
+ });
64225
+ /** One function's series. `key` is an addonId, `__root__` or `__unattributed__`. */
64226
+ var LoadFunctionSeriesSchema = object({
64227
+ key: string(),
64228
+ kind: _enum([
64229
+ "addon",
64230
+ "root",
64231
+ "unattributed"
64232
+ ]),
64233
+ /** Oldest-first. A missing interval is MISSING — never zero-filled. */
64234
+ points: array(LoadPointSchema).readonly()
64235
+ });
64236
+ var NodeLoadSeriesSchema = object({
64237
+ nodeId: string(),
64238
+ /** One entry per function seen in the window, heaviest-first. */
64239
+ series: array(LoadFunctionSeriesSchema).readonly(),
64240
+ /**
64241
+ * Width of one returned bucket, in ms. Equals the sampling cadence when no
64242
+ * reduction was needed — so a caller can always say what one point covers
64243
+ * without having to know whether it was reduced.
64244
+ */
64245
+ bucketMs: number(),
64246
+ /** Raw snapshots that went into this answer, across both tiers. */
64247
+ retainedSamples: number(),
64248
+ /** Oldest snapshot represented, or `null` when nothing is retained. */
64249
+ oldestAtMs: number().nullable(),
64250
+ /** The fixed sampling cadence in force on the cluster, in ms. */
64251
+ cadenceMs: number(),
64252
+ /**
64253
+ * Did the DURABLE tier contribute? `false` means the answer is the hot ring
64254
+ * alone — an agent (which holds no table), or a store that refused.
64255
+ * Reported because "the last hour" and "the last six hours" are different
64256
+ * questions and an operator must not have to guess which was answered.
64257
+ */
64258
+ durable: boolean()
64259
+ });
64260
+ var GetLoadSeriesInputSchema = object({
64261
+ /**
64262
+ * The node whose series is wanted.
64263
+ *
64264
+ * NOT named `nodeId`: the generated cap router strips a top-level
64265
+ * `nodeId` from every method input and uses it to ROUTE the call to
64266
+ * that node's provider (`generated-cap-routers.ts`). A series target
64267
+ * called `nodeId` would silently become a routing pin and never reach
64268
+ * the provider. The hub holds every node it hears from, so the
64269
+ * ordinary call is unpinned — answered by the hub, for any node.
64270
+ */
64271
+ forNodeId: string(),
64272
+ /**
64273
+ * EXCLUSIVE lower bound. A caller passes the newest `atMs` it already
64274
+ * holds and receives only what it is missing, so seeding a live chart
64275
+ * from this method cannot double a point already drawn.
64276
+ */
64277
+ sinceMs: number().optional(),
64278
+ /**
64279
+ * Most points the caller wants PER FUNCTION. The window is reduced to fit,
64280
+ * preserving min and max per bucket.
64281
+ *
64282
+ * Absent means NO reduction — legitimate for a short window and a trap for a
64283
+ * long one, which is why a chart passes its own pixel width.
64284
+ */
64285
+ maxPoints: number().int().positive().optional()
64286
+ });
64087
64287
  var SystemMetricsSchema = object({
64088
64288
  cpuPercent: number(),
64089
64289
  memoryPercent: number(),
@@ -64094,10 +64294,7 @@ var SystemMetricsSchema = object({
64094
64294
  gpuPercent: number().optional(),
64095
64295
  gpuMemoryPercent: number().optional()
64096
64296
  });
64097
- method(_void(), SystemResourceSnapshotSchema), method(_void(), SystemResourceSnapshotSchema.nullable()), method(_void(), SystemMetricsSchema), method(object({ dirPath: string() }), DiskSpaceInfoSchema), method(_void(), MetricsGpuInfoSchema.nullable()), method(_void(), number().nullable()), method(object({ pids: array(number()) }), array(PidResourceStatsSchema)), method(_void(), array(AddonInstanceSchema).readonly()), method(object({ addonId: string() }), PidResourceStatsSchema.nullable()), method(_void(), array(NodeProcessSchema).readonly()), method(KillProcessInputSchema, KillProcessResultSchema, {
64098
- kind: "mutation",
64099
- auth: "admin"
64100
- }), method(DumpHeapSnapshotInputSchema, DumpHeapSnapshotResultSchema, {
64297
+ method(_void(), SystemResourceSnapshotSchema), method(_void(), SystemResourceSnapshotSchema.nullable()), method(_void(), SystemMetricsSchema), method(object({ dirPath: string() }), DiskSpaceInfoSchema), method(_void(), MetricsGpuInfoSchema.nullable()), method(_void(), number().nullable()), method(object({ pids: array(number()) }), array(PidResourceStatsSchema)), method(_void(), array(AddonInstanceSchema).readonly()), method(object({ addonId: string() }), PidResourceStatsSchema.nullable()), method(_void(), array(NodeProcessSchema).readonly()), method(GetLoadSeriesInputSchema, NodeLoadSeriesSchema), method(DumpHeapSnapshotInputSchema, DumpHeapSnapshotResultSchema, {
64101
64298
  kind: "mutation",
64102
64299
  auth: "admin"
64103
64300
  });
@@ -79452,6 +79649,15 @@ var LoggingSettingsPatchSchema = object({
79452
79649
  * authority over the whole hierarchy and answers for every layer, so the
79453
79650
  * layer selector needs a name the transport does not already own.
79454
79651
  */
79652
+ /**
79653
+ * One contribution, plus WHO reported it.
79654
+ *
79655
+ * The addon and node are added by the hub as it enumerates providers, never by
79656
+ * the contributor: an addon reporting its own identity could report somebody
79657
+ * else's, and the whole point of this surface is that no claim is made by
79658
+ * anyone but its owner.
79659
+ */
79660
+ var ReportedLoadContributionSchema = LoadContributionSchema.extend({ addonId: string() });
79455
79661
  var GetLoggingSettingsInputSchema = object({
79456
79662
  scopeNodeId: string().optional(),
79457
79663
  /**
@@ -79510,7 +79716,7 @@ method(_void(), FeatureManifestSchema), method(_void(), HealthStatusSchema), met
79510
79716
  }), method(_void(), SiteLocationStatusSchema, {
79511
79717
  kind: "mutation",
79512
79718
  auth: "admin"
79513
- }), method(_void(), RequestCensusStatusSchema, { auth: "admin" }), method(GetLoggingSettingsInputSchema, LoggingSettingsStateSchema, { auth: "admin" }), method(SetLoggingSettingsInputSchema, LoggingSettingsStateSchema, {
79719
+ }), method(_void(), RequestCensusStatusSchema, { auth: "admin" }), method(_void(), array(ReportedLoadContributionSchema).readonly(), { auth: "admin" }), method(GetLoggingSettingsInputSchema, LoggingSettingsStateSchema, { auth: "admin" }), method(SetLoggingSettingsInputSchema, LoggingSettingsStateSchema, {
79514
79720
  kind: "mutation",
79515
79721
  auth: "admin"
79516
79722
  });
@@ -82534,6 +82740,12 @@ Object.freeze({
82534
82740
  addonId: null,
82535
82741
  access: "create"
82536
82742
  },
82743
+ "dataStoreProvider.insertMany": {
82744
+ capName: "data-store-provider",
82745
+ capScope: "system",
82746
+ addonId: null,
82747
+ access: "create"
82748
+ },
82537
82749
  "dataStoreProvider.isEmpty": {
82538
82750
  capName: "data-store-provider",
82539
82751
  capScope: "system",
@@ -83848,6 +84060,12 @@ Object.freeze({
83848
84060
  addonId: null,
83849
84061
  access: "create"
83850
84062
  },
84063
+ "loadContribution.list": {
84064
+ capName: "load-contribution",
84065
+ capScope: "system",
84066
+ addonId: null,
84067
+ access: "view"
84068
+ },
83851
84069
  "localNetwork.downloadCa": {
83852
84070
  capName: "local-network",
83853
84071
  capScope: "system",
@@ -84148,17 +84366,17 @@ Object.freeze({
84148
84366
  addonId: null,
84149
84367
  access: "view"
84150
84368
  },
84151
- "metricsProvider.getProcessStats": {
84369
+ "metricsProvider.getLoadSeries": {
84152
84370
  capName: "metrics-provider",
84153
84371
  capScope: "system",
84154
84372
  addonId: null,
84155
84373
  access: "view"
84156
84374
  },
84157
- "metricsProvider.killProcess": {
84375
+ "metricsProvider.getProcessStats": {
84158
84376
  capName: "metrics-provider",
84159
84377
  capScope: "system",
84160
84378
  addonId: null,
84161
- access: "create"
84379
+ access: "view"
84162
84380
  },
84163
84381
  "metricsProvider.listAddonInstances": {
84164
84382
  capName: "metrics-provider",
@@ -86170,6 +86388,12 @@ Object.freeze({
86170
86388
  addonId: null,
86171
86389
  access: "create"
86172
86390
  },
86391
+ "settingsStore.insertMany": {
86392
+ capName: "settings-store",
86393
+ capScope: "system",
86394
+ addonId: null,
86395
+ access: "create"
86396
+ },
86173
86397
  "settingsStore.isEmpty": {
86174
86398
  capName: "settings-store",
86175
86399
  capScope: "system",
@@ -86782,6 +87006,12 @@ Object.freeze({
86782
87006
  addonId: null,
86783
87007
  access: "create"
86784
87008
  },
87009
+ "system.getLoadContributions": {
87010
+ capName: "system",
87011
+ capScope: "system",
87012
+ addonId: null,
87013
+ access: "view"
87014
+ },
86785
87015
  "system.getLoggingSettings": {
86786
87016
  capName: "system",
86787
87017
  capScope: "system",
package/dist/addon.mjs CHANGED
@@ -50504,7 +50504,7 @@ objectType({
50504
50504
  })
50505
50505
  });
50506
50506
  //#endregion
50507
- //#region ../types/dist/event-category-CIa_iT6b.mjs
50507
+ //#region ../types/dist/event-category-BZL-fdNj.mjs
50508
50508
  var EventCategory = /* @__PURE__ */ function(EventCategory) {
50509
50509
  EventCategory["SystemBoot"] = "system.boot";
50510
50510
  EventCategory["SystemAddonsReady"] = "system.addons-ready";
@@ -50941,7 +50941,7 @@ var EventCategory = /* @__PURE__ */ function(EventCategory) {
50941
50941
  EventCategory["MetricsNodeResourcesSnapshot"] = "metrics.node-resources-snapshot";
50942
50942
  /**
50943
50943
  * Periodic per-node process-tree snapshot (camstack-related pids
50944
- * with ghost / managed / root classification). Emitted ~0.2 Hz by
50944
+ * with root / managed / system classification). Emitted ~0.2 Hz by
50945
50945
  * the metrics-provider addon. Drives the Cluster → Processes tab
50946
50946
  * without polling `metricsProvider.listNodeProcesses`.
50947
50947
  */
@@ -61733,6 +61733,19 @@ var SettingsRecordSchema = object({
61733
61733
  data: record(string(), unknown())
61734
61734
  });
61735
61735
  /**
61736
+ * One record of a BULK insert — {@link SettingsRecordSchema} with the id made
61737
+ * optional.
61738
+ *
61739
+ * A separate schema rather than loosening the shared one: every other method
61740
+ * on this cap addresses a row BY its id, and making that field optional
61741
+ * everywhere would turn a forgotten key into a silently generated one on
61742
+ * `update` and `delete` as well.
61743
+ */
61744
+ var BulkRecordSchema = object({
61745
+ id: string().optional(),
61746
+ data: record(string(), unknown())
61747
+ });
61748
+ /**
61736
61749
  * Column declaration for a structured (SQL-backed) collection.
61737
61750
  *
61738
61751
  * Logical types — the backend translates each to the matching SQLite
@@ -61789,6 +61802,10 @@ method(object({
61789
61802
  collection: string(),
61790
61803
  record: SettingsRecordSchema
61791
61804
  }), _void(), { kind: "mutation" }), method(object({
61805
+ namespace: string().optional(),
61806
+ collection: string(),
61807
+ records: array(BulkRecordSchema).readonly()
61808
+ }), object({ inserted: number().int() }), { kind: "mutation" }), method(object({
61792
61809
  namespace: string().optional(),
61793
61810
  collection: string(),
61794
61811
  id: string(),
@@ -61897,6 +61914,13 @@ method(_void(), EngineInfoSchema, { auth: "admin" }), method(object({
61897
61914
  }), _void(), {
61898
61915
  kind: "mutation",
61899
61916
  auth: "admin"
61917
+ }), method(object({
61918
+ namespace: string().optional(),
61919
+ collection: string(),
61920
+ records: array(BulkRecordSchema).readonly()
61921
+ }), object({ inserted: number().int() }), {
61922
+ kind: "mutation",
61923
+ auth: "admin"
61900
61924
  }), method(object({
61901
61925
  namespace: string().optional(),
61902
61926
  collection: string(),
@@ -63844,6 +63868,68 @@ method(LogEntrySchema, _void(), { kind: "mutation" }), method(object({
63844
63868
  limit: number().optional(),
63845
63869
  tags: record(string(), string()).optional()
63846
63870
  }), array(LogEntrySchema).readonly());
63871
+ var LoadContributionSchema = object({
63872
+ role: _enum([
63873
+ "decode",
63874
+ "transcode",
63875
+ "recording",
63876
+ "streaming",
63877
+ "detection"
63878
+ ]),
63879
+ /**
63880
+ * The NUMERIC device id — the same value every log line carries as
63881
+ * `tags.deviceId`. `null` means this cost genuinely belongs to no single
63882
+ * camera (a shared pool), NOT that the contributor forgot to look it up: a
63883
+ * contributor that cannot name its camera must not emit the entry at all,
63884
+ * because an unnamed per-camera entry is indistinguishable from a shared one
63885
+ * and would quietly turn one camera's cost into everybody's.
63886
+ */
63887
+ deviceId: number().int().positive().nullable(),
63888
+ attribution: _enum([
63889
+ "measured",
63890
+ "accounted",
63891
+ "unattributable"
63892
+ ]),
63893
+ /**
63894
+ * What ONE entry is, in the contributor's own words — `615/high`,
63895
+ * `617/native`, `cuda:0 shared pool`. Free text because the unit differs per
63896
+ * family and inventing a common one would lose the only information that
63897
+ * makes two entries for the same camera distinguishable.
63898
+ */
63899
+ unit: string(),
63900
+ /**
63901
+ * The OS process this cost lives in, when there is one. Present so a
63902
+ * consumer can (a) tell two generations of the same unit apart across a
63903
+ * restart, and (b) subtract claimed processes from the node's process
63904
+ * snapshot to see what NOBODY claimed. Absent for an entry that owns no
63905
+ * process of its own.
63906
+ */
63907
+ pid: number().int().positive().optional(),
63908
+ /**
63909
+ * When this generation started. The pid's incarnation marker: a consumer
63910
+ * differencing {@link LoadContributionSchema.shape.cpuSeconds} must drop the
63911
+ * window when this changes, because the counter restarted from zero in a new
63912
+ * process.
63913
+ */
63914
+ startedAtMs: number().optional(),
63915
+ /**
63916
+ * CUMULATIVE CPU seconds this unit has consumed since it started — user +
63917
+ * system, read from the child's own `/proc/<pid>/stat` at the moment the
63918
+ * contribution is asked for.
63919
+ *
63920
+ * Cumulative and not a rate on purpose: a rate needs a window, a window
63921
+ * needs a sampler, and a new per-node sampler is the defect half of
63922
+ * `docs/architecture/load-ledger.md` documents. A counter can be differenced
63923
+ * by whoever already keeps a history; a rate cannot be un-averaged.
63924
+ *
63925
+ * Absent — never zero — on a node with no `/proc`, on a read failure, and on
63926
+ * an entry with no process.
63927
+ */
63928
+ cpuSeconds: number().optional(),
63929
+ /** Resident bytes of this unit's process, same source and same rules. */
63930
+ rssBytes: number().optional()
63931
+ });
63932
+ method(_void(), array(LoadContributionSchema).readonly());
63847
63933
  /**
63848
63934
  * `login-method` — collection cap through which auth addons contribute
63849
63935
  * their pre-auth login surfaces to the login page. This is the SINGLE,
@@ -64047,8 +64133,7 @@ var NodeProcessSchema = object({
64047
64133
  classification: _enum([
64048
64134
  "root",
64049
64135
  "managed",
64050
- "system",
64051
- "ghost"
64136
+ "system"
64052
64137
  ]),
64053
64138
  /** `$process` addon binding when `managed`, else null. */
64054
64139
  addonId: string().nullable(),
@@ -64056,22 +64141,39 @@ var NodeProcessSchema = object({
64056
64141
  nodeId: string().nullable(),
64057
64142
  /** Truncated command line. */
64058
64143
  command: string(),
64144
+ /**
64145
+ * `ps pcpu` — CPU averaged over the process's WHOLE LIFETIME, not a rate.
64146
+ * On a runner up for days it barely moves. Fine as a column, useless as a
64147
+ * series: use `cpuMainPercent + cpuGcPercent` for anything time-varying.
64148
+ */
64059
64149
  cpuPercent: number(),
64060
64150
  memoryRssBytes: number(),
64151
+ /**
64152
+ * Instantaneous CPU% of the process's own threads over the last
64153
+ * process-snapshot window, from a `/proc/<pid>/task/*` tick delta.
64154
+ *
64155
+ * `null` = UNKNOWN, never zero: no previous sample yet (first tick after
64156
+ * boot), the pid was recycled, or this node is not Linux.
64157
+ */
64158
+ cpuMainPercent: number().nullable(),
64159
+ /**
64160
+ * Instantaneous CPU% of V8's `V8Worker` platform pool over the same window.
64161
+ *
64162
+ * This is the number that rewrote the 2026-08-27 diagnosis — hub-main 73%,
64163
+ * `stream-broker` 61% (`docs/architecture/load-ledger.md`). A CPU chart that
64164
+ * does not separate it from `cpuMainPercent` shows "busy" where the truth is
64165
+ * "allocating too much".
64166
+ *
64167
+ * Concurrent GC is the dominant tenant of that pool but not the only one
64168
+ * (background compilation runs there too), so it is reported as
64169
+ * "GC / V8 helpers" rather than as pure collection time. `null` has the same
64170
+ * meaning as on `cpuMainPercent`.
64171
+ */
64172
+ cpuGcPercent: number().nullable(),
64173
+ /** Threads seen in the tick scan. `null` under the same conditions. */
64174
+ threadCount: number().nullable(),
64061
64175
  /** Wall-clock uptime (seconds). Parsed from `ps etime`. */
64062
- uptimeSec: number(),
64063
- /** True when ancestor walk reaches `ppid=1` (reparented to init/launchd). */
64064
- orphaned: boolean()
64065
- });
64066
- var KillProcessInputSchema = object({
64067
- pid: number(),
64068
- /** Force = SIGKILL. Default is SIGTERM. */
64069
- force: boolean().optional()
64070
- });
64071
- var KillProcessResultSchema = object({
64072
- success: boolean(),
64073
- reason: string().optional(),
64074
- signal: _enum(["SIGTERM", "SIGKILL"]).optional()
64176
+ uptimeSec: number()
64075
64177
  });
64076
64178
  var DumpHeapSnapshotInputSchema = object({
64077
64179
  /** The addon whose runner should dump a heap snapshot. */
@@ -64084,6 +64186,104 @@ var DumpHeapSnapshotResultSchema = object({
64084
64186
  pid: number().optional(),
64085
64187
  reason: string().optional()
64086
64188
  });
64189
+ /**
64190
+ * One point of one function's series.
64191
+ *
64192
+ * The unsuffixed fields are the bucket's **MAXIMUM**, and that choice is the
64193
+ * point of the whole surface. The two obvious reductions both lie: a mean per
64194
+ * bucket smears a spike away, and taking every Nth sample skips it outright.
64195
+ * Either would give us a tool built to find peaks that does not show peaks.
64196
+ * `...Min` carries the other end, `samples` says how many raw snapshots folded
64197
+ * into the bucket, and a mean stays derivable where it is wanted.
64198
+ *
64199
+ * An UNREDUCED point is a one-sample bucket: `samples === 1` and each `...Min`
64200
+ * equals its unsuffixed twin. Reduced and unreduced are the same shape, so a
64201
+ * caller cannot tell which it received — which is what "one reader" means.
64202
+ */
64203
+ var LoadPointSchema = object({
64204
+ /** Bucket START, or the snapshot's own timestamp when unreduced. */
64205
+ atMs: number(),
64206
+ /** Raw snapshots in this bucket. Never 0 — AN EMPTY BUCKET IS ABSENT. */
64207
+ samples: number().int(),
64208
+ /**
64209
+ * `null` = UNKNOWN and it PROPAGATES: a bucket is null unless every process
64210
+ * of every snapshot in it reported a thread split. A partial sum is a
64211
+ * smaller number that looks exactly as real as a complete one.
64212
+ */
64213
+ cpuMainPercent: number().nullable(),
64214
+ cpuMainPercentMin: number().nullable(),
64215
+ cpuGcPercent: number().nullable(),
64216
+ cpuGcPercentMin: number().nullable(),
64217
+ /** Lifetime-average CPU%, summed. Always known — and never a rate. */
64218
+ cpuLifetimePercent: number(),
64219
+ cpuLifetimePercentMin: number(),
64220
+ memoryRssBytes: number(),
64221
+ memoryRssBytesMin: number(),
64222
+ processCount: number().int(),
64223
+ processCountMin: number().int()
64224
+ });
64225
+ /** One function's series. `key` is an addonId, `__root__` or `__unattributed__`. */
64226
+ var LoadFunctionSeriesSchema = object({
64227
+ key: string(),
64228
+ kind: _enum([
64229
+ "addon",
64230
+ "root",
64231
+ "unattributed"
64232
+ ]),
64233
+ /** Oldest-first. A missing interval is MISSING — never zero-filled. */
64234
+ points: array(LoadPointSchema).readonly()
64235
+ });
64236
+ var NodeLoadSeriesSchema = object({
64237
+ nodeId: string(),
64238
+ /** One entry per function seen in the window, heaviest-first. */
64239
+ series: array(LoadFunctionSeriesSchema).readonly(),
64240
+ /**
64241
+ * Width of one returned bucket, in ms. Equals the sampling cadence when no
64242
+ * reduction was needed — so a caller can always say what one point covers
64243
+ * without having to know whether it was reduced.
64244
+ */
64245
+ bucketMs: number(),
64246
+ /** Raw snapshots that went into this answer, across both tiers. */
64247
+ retainedSamples: number(),
64248
+ /** Oldest snapshot represented, or `null` when nothing is retained. */
64249
+ oldestAtMs: number().nullable(),
64250
+ /** The fixed sampling cadence in force on the cluster, in ms. */
64251
+ cadenceMs: number(),
64252
+ /**
64253
+ * Did the DURABLE tier contribute? `false` means the answer is the hot ring
64254
+ * alone — an agent (which holds no table), or a store that refused.
64255
+ * Reported because "the last hour" and "the last six hours" are different
64256
+ * questions and an operator must not have to guess which was answered.
64257
+ */
64258
+ durable: boolean()
64259
+ });
64260
+ var GetLoadSeriesInputSchema = object({
64261
+ /**
64262
+ * The node whose series is wanted.
64263
+ *
64264
+ * NOT named `nodeId`: the generated cap router strips a top-level
64265
+ * `nodeId` from every method input and uses it to ROUTE the call to
64266
+ * that node's provider (`generated-cap-routers.ts`). A series target
64267
+ * called `nodeId` would silently become a routing pin and never reach
64268
+ * the provider. The hub holds every node it hears from, so the
64269
+ * ordinary call is unpinned — answered by the hub, for any node.
64270
+ */
64271
+ forNodeId: string(),
64272
+ /**
64273
+ * EXCLUSIVE lower bound. A caller passes the newest `atMs` it already
64274
+ * holds and receives only what it is missing, so seeding a live chart
64275
+ * from this method cannot double a point already drawn.
64276
+ */
64277
+ sinceMs: number().optional(),
64278
+ /**
64279
+ * Most points the caller wants PER FUNCTION. The window is reduced to fit,
64280
+ * preserving min and max per bucket.
64281
+ *
64282
+ * Absent means NO reduction — legitimate for a short window and a trap for a
64283
+ * long one, which is why a chart passes its own pixel width.
64284
+ */
64285
+ maxPoints: number().int().positive().optional()
64286
+ });
64087
64287
  var SystemMetricsSchema = object({
64088
64288
  cpuPercent: number(),
64089
64289
  memoryPercent: number(),
@@ -64094,10 +64294,7 @@ var SystemMetricsSchema = object({
64094
64294
  gpuPercent: number().optional(),
64095
64295
  gpuMemoryPercent: number().optional()
64096
64296
  });
64097
- method(_void(), SystemResourceSnapshotSchema), method(_void(), SystemResourceSnapshotSchema.nullable()), method(_void(), SystemMetricsSchema), method(object({ dirPath: string() }), DiskSpaceInfoSchema), method(_void(), MetricsGpuInfoSchema.nullable()), method(_void(), number().nullable()), method(object({ pids: array(number()) }), array(PidResourceStatsSchema)), method(_void(), array(AddonInstanceSchema).readonly()), method(object({ addonId: string() }), PidResourceStatsSchema.nullable()), method(_void(), array(NodeProcessSchema).readonly()), method(KillProcessInputSchema, KillProcessResultSchema, {
64098
- kind: "mutation",
64099
- auth: "admin"
64100
- }), method(DumpHeapSnapshotInputSchema, DumpHeapSnapshotResultSchema, {
64297
+ method(_void(), SystemResourceSnapshotSchema), method(_void(), SystemResourceSnapshotSchema.nullable()), method(_void(), SystemMetricsSchema), method(object({ dirPath: string() }), DiskSpaceInfoSchema), method(_void(), MetricsGpuInfoSchema.nullable()), method(_void(), number().nullable()), method(object({ pids: array(number()) }), array(PidResourceStatsSchema)), method(_void(), array(AddonInstanceSchema).readonly()), method(object({ addonId: string() }), PidResourceStatsSchema.nullable()), method(_void(), array(NodeProcessSchema).readonly()), method(GetLoadSeriesInputSchema, NodeLoadSeriesSchema), method(DumpHeapSnapshotInputSchema, DumpHeapSnapshotResultSchema, {
64101
64298
  kind: "mutation",
64102
64299
  auth: "admin"
64103
64300
  });
@@ -79452,6 +79649,15 @@ var LoggingSettingsPatchSchema = object({
79452
79649
  * authority over the whole hierarchy and answers for every layer, so the
79453
79650
  * layer selector needs a name the transport does not already own.
79454
79651
  */
79652
+ /**
79653
+ * One contribution, plus WHO reported it.
79654
+ *
79655
+ * The addon and node are added by the hub as it enumerates providers, never by
79656
+ * the contributor: an addon reporting its own identity could report somebody
79657
+ * else's, and the whole point of this surface is that no claim is made by
79658
+ * anyone but its owner.
79659
+ */
79660
+ var ReportedLoadContributionSchema = LoadContributionSchema.extend({ addonId: string() });
79455
79661
  var GetLoggingSettingsInputSchema = object({
79456
79662
  scopeNodeId: string().optional(),
79457
79663
  /**
@@ -79510,7 +79716,7 @@ method(_void(), FeatureManifestSchema), method(_void(), HealthStatusSchema), met
79510
79716
  }), method(_void(), SiteLocationStatusSchema, {
79511
79717
  kind: "mutation",
79512
79718
  auth: "admin"
79513
- }), method(_void(), RequestCensusStatusSchema, { auth: "admin" }), method(GetLoggingSettingsInputSchema, LoggingSettingsStateSchema, { auth: "admin" }), method(SetLoggingSettingsInputSchema, LoggingSettingsStateSchema, {
79719
+ }), method(_void(), RequestCensusStatusSchema, { auth: "admin" }), method(_void(), array(ReportedLoadContributionSchema).readonly(), { auth: "admin" }), method(GetLoggingSettingsInputSchema, LoggingSettingsStateSchema, { auth: "admin" }), method(SetLoggingSettingsInputSchema, LoggingSettingsStateSchema, {
79514
79720
  kind: "mutation",
79515
79721
  auth: "admin"
79516
79722
  });
@@ -82534,6 +82740,12 @@ Object.freeze({
82534
82740
  addonId: null,
82535
82741
  access: "create"
82536
82742
  },
82743
+ "dataStoreProvider.insertMany": {
82744
+ capName: "data-store-provider",
82745
+ capScope: "system",
82746
+ addonId: null,
82747
+ access: "create"
82748
+ },
82537
82749
  "dataStoreProvider.isEmpty": {
82538
82750
  capName: "data-store-provider",
82539
82751
  capScope: "system",
@@ -83848,6 +84060,12 @@ Object.freeze({
83848
84060
  addonId: null,
83849
84061
  access: "create"
83850
84062
  },
84063
+ "loadContribution.list": {
84064
+ capName: "load-contribution",
84065
+ capScope: "system",
84066
+ addonId: null,
84067
+ access: "view"
84068
+ },
83851
84069
  "localNetwork.downloadCa": {
83852
84070
  capName: "local-network",
83853
84071
  capScope: "system",
@@ -84148,17 +84366,17 @@ Object.freeze({
84148
84366
  addonId: null,
84149
84367
  access: "view"
84150
84368
  },
84151
- "metricsProvider.getProcessStats": {
84369
+ "metricsProvider.getLoadSeries": {
84152
84370
  capName: "metrics-provider",
84153
84371
  capScope: "system",
84154
84372
  addonId: null,
84155
84373
  access: "view"
84156
84374
  },
84157
- "metricsProvider.killProcess": {
84375
+ "metricsProvider.getProcessStats": {
84158
84376
  capName: "metrics-provider",
84159
84377
  capScope: "system",
84160
84378
  addonId: null,
84161
- access: "create"
84379
+ access: "view"
84162
84380
  },
84163
84381
  "metricsProvider.listAddonInstances": {
84164
84382
  capName: "metrics-provider",
@@ -86170,6 +86388,12 @@ Object.freeze({
86170
86388
  addonId: null,
86171
86389
  access: "create"
86172
86390
  },
86391
+ "settingsStore.insertMany": {
86392
+ capName: "settings-store",
86393
+ capScope: "system",
86394
+ addonId: null,
86395
+ access: "create"
86396
+ },
86173
86397
  "settingsStore.isEmpty": {
86174
86398
  capName: "settings-store",
86175
86399
  capScope: "system",
@@ -86782,6 +87006,12 @@ Object.freeze({
86782
87006
  addonId: null,
86783
87007
  access: "create"
86784
87008
  },
87009
+ "system.getLoadContributions": {
87010
+ capName: "system",
87011
+ capScope: "system",
87012
+ addonId: null,
87013
+ access: "view"
87014
+ },
86785
87015
  "system.getLoggingSettings": {
86786
87016
  capName: "system",
86787
87017
  capScope: "system",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@camstack/addon-provider-dreame",
3
- "version": "0.2.35",
3
+ "version": "0.2.36",
4
4
  "description": "Dreame robot-vacuum / lawn-mower device-provider addon for CamStack — wraps the @apocaliss92/nodedreame Dreamehome cloud client",
5
5
  "keywords": [
6
6
  "camstack",