@camstack/addon-provider-ecowitt 0.2.121 → 0.2.123

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 +267 -11
  2. package/dist/addon.mjs +267 -11
  3. package/package.json +1 -1
package/dist/addon.js CHANGED
@@ -5373,7 +5373,7 @@ var ZodIssueCode$1 = {
5373
5373
  var ZodFirstPartyTypeKind$1;
5374
5374
  ZodFirstPartyTypeKind$1 || (ZodFirstPartyTypeKind$1 = {});
5375
5375
  //#endregion
5376
- //#region ../types/dist/sleep-BNeXenvr.mjs
5376
+ //#region ../types/dist/sleep-B0JG7-_F.mjs
5377
5377
  /**
5378
5378
  * The audio chunk plane's byte format, and the ONE expansion from a coded
5379
5379
  * window to float samples (D455).
@@ -15195,6 +15195,10 @@ var DeviceInfoSchema = object({
15195
15195
  isCamera: boolean(),
15196
15196
  /** Current config values — serializable snapshot */
15197
15197
  config: record(string(), unknown()),
15198
+ /** Paths inside `config` the device's schema declares secret (D783) —
15199
+ * what the non-admin redaction withholds. Paths, never values. Absent
15200
+ * when the owning runner has not reported them. */
15201
+ secretConfigPaths: array(string()).optional(),
15198
15202
  /** Hardware + identity blob (manufacturer / model / firmware / sn /
15199
15203
  * uid / mac / …). Populated by drivers; editable via setMetadata. */
15200
15204
  metadata: record(string(), unknown()).nullable().optional(),
@@ -15400,7 +15404,13 @@ var DeviceRegisterPayloadSchema = object({
15400
15404
  * call (workers re-register on init), so probe-driven updates
15401
15405
  * (e.g. PTZ flag flipping after the abilities probe) propagate. */
15402
15406
  features: array(string()).optional(),
15403
- config: record(string(), unknown())
15407
+ config: record(string(), unknown()),
15408
+ /** Config paths the device's own schema DECLARES secret
15409
+ * (`.meta({ secret: true })` — dotted, `[]` for array items, e.g.
15410
+ * `connection.password`). Re-published on every register; the non-admin
15411
+ * redaction withholds them at any depth (D783). Optional: an older runner
15412
+ * omits it and the keyword backstop applies. */
15413
+ secretConfigPaths: array(string()).optional()
15404
15414
  });
15405
15415
  var DeviceRemovePayloadSchema = object({ deviceId: number() });
15406
15416
  var DevicePersistConfigPayloadSchema = object({
@@ -17059,7 +17069,14 @@ var LoginMethodContributionSchema = discriminatedUnion("kind", [
17059
17069
  icon: string().optional(),
17060
17070
  /** Addon-owned HTTP route the button navigates to (GET). */
17061
17071
  startUrl: string(),
17062
- stage: LoginStageEnum
17072
+ stage: LoginStageEnum,
17073
+ /**
17074
+ * The provider names an external identity a signed-in user can link to
17075
+ * their own account (D782): `auth.listLinkableProviders` /
17076
+ * `beginExternalLink` offer exactly the redirect methods that set this,
17077
+ * whatever their id. Absent / false — a login button only (magic-link).
17078
+ */
17079
+ linkable: boolean().optional()
17063
17080
  }),
17064
17081
  object({
17065
17082
  kind: literal("widget"),
@@ -22494,7 +22511,13 @@ var RetrainFrameSchema = object({
22494
22511
  sizeBytes: number().int(),
22495
22512
  width: number().int(),
22496
22513
  height: number().int(),
22497
- copiedAt: number()
22514
+ copiedAt: number(),
22515
+ /** When the CAMERA captured the frame. Absent on a copy taken before D785. */
22516
+ capturedAt: number().optional(),
22517
+ /** The operator's "every subject in this frame is boxed". Detector
22518
+ * evaluation keeps only complete frames: an unboxed subject would count as
22519
+ * a false positive. */
22520
+ complete: boolean()
22498
22521
  });
22499
22522
  /** Why a copy-on-select could not be honoured — named, never a silent skip. */
22500
22523
  var RetrainCopyRefusalSchema = _enum([
@@ -22515,6 +22538,51 @@ var RetrainFrameListSchema = object({
22515
22538
  /** What the page pre-selects — the native key frame when one survives. */
22516
22539
  autoPickMediaId: number().int().optional()
22517
22540
  });
22541
+ /**
22542
+ * Which frames an annotated export carries. Every field narrows; an empty
22543
+ * filter is every annotated copy. A dataset VERSION is a frozen `frameIds`
22544
+ * list owned by whoever trains (the training orchestrator), so `frameIds` is
22545
+ * the primitive a version export uses; `batchId` re-selects what an earlier
22546
+ * export carried (`exportedInBatch`).
22547
+ */
22548
+ var RetrainExportFilterSchema = object({
22549
+ deviceIds: array(number()).optional(),
22550
+ frameIds: array(string()).max(2e4).optional(),
22551
+ batchId: string().optional(),
22552
+ /** Only frames the operator marked complete (all subjects boxed). */
22553
+ completeOnly: boolean().optional()
22554
+ });
22555
+ /**
22556
+ * `frames`: the full frame copies, boxes in `annotations.json`.
22557
+ * `crops`: additionally one JPEG per subject, cut with the runtime detail-crop
22558
+ * convention — the classifier layout.
22559
+ */
22560
+ var RetrainExportLayoutSchema = _enum(["frames", "crops"]);
22561
+ /**
22562
+ * Where `writeRetrainArchive` streams the tar: one HTTP request whose body is
22563
+ * the archive, sent chunk by chunk. Covers a presigned PUT and a provider
22564
+ * addon's data-plane upload route alike. Headers are sent verbatim and never
22565
+ * logged.
22566
+ */
22567
+ var RetrainArchiveTargetSchema = object({
22568
+ kind: literal("http"),
22569
+ method: _enum(["PUT", "POST"]),
22570
+ url: string().url(),
22571
+ headers: record(string(), string()).optional()
22572
+ });
22573
+ var RetrainArchiveResultSchema = object({
22574
+ batchId: string(),
22575
+ frames: number().int(),
22576
+ crops: number().int(),
22577
+ annotations: number().int(),
22578
+ /** Frames planned but not shipped (unreadable copy, path too long). */
22579
+ missing: number().int(),
22580
+ bytes: number().int(),
22581
+ /** sha256 of the exact bytes sent. */
22582
+ sha256: string(),
22583
+ /** The target's HTTP status. */
22584
+ status: number().int()
22585
+ });
22518
22586
  /** What the operator asked the assist to look for. */
22519
22587
  var RetrainAssistSubjectSchema = discriminatedUnion("kind", [object({
22520
22588
  kind: literal("package"),
@@ -23309,9 +23377,25 @@ DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).rea
23309
23377
  }), RetrainTransitionResultSchema, {
23310
23378
  kind: "mutation",
23311
23379
  auth: "admin"
23312
- }), method(object({ deviceIds: array(number()).optional() }), object({ url: string() }), {
23380
+ }), method(RetrainExportFilterSchema.extend({ layout: RetrainExportLayoutSchema.optional() }), object({ url: string() }), {
23313
23381
  kind: "query",
23314
23382
  auth: "admin"
23383
+ }), method(object({
23384
+ deviceId: number(),
23385
+ trackId: string(),
23386
+ frameId: string(),
23387
+ complete: boolean()
23388
+ }), RetrainFrameSchema, {
23389
+ kind: "mutation",
23390
+ auth: "admin"
23391
+ }), method(object({
23392
+ filter: RetrainExportFilterSchema,
23393
+ layout: RetrainExportLayoutSchema,
23394
+ target: RetrainArchiveTargetSchema
23395
+ }), RetrainArchiveResultSchema, {
23396
+ kind: "mutation",
23397
+ auth: "admin",
23398
+ timeoutMs: 60 * 6e4
23315
23399
  }), method(object({
23316
23400
  /** Which of the three event tables owns the row. */
23317
23401
  ownerType: EventOwnerTypeSchema,
@@ -26641,7 +26725,19 @@ var SsoBridgeClaimsSchema = object({
26641
26725
  * editing a descriptor must not retroactively extend or shorten a link the
26642
26726
  * operator already consented to.
26643
26727
  */
26644
- refreshTtl: union([number().int().positive(), literal("never")]).optional()
26728
+ refreshTtl: union([number().int().positive(), literal("never")]).optional(),
26729
+ /**
26730
+ * Opaque handle of a hub-side LINK intent (D782). Set by an OIDC callback
26731
+ * that was started from a signed-in user's "Link" button: the finish then
26732
+ * links this identity to the intent's user instead of signing anyone in.
26733
+ * The handle carries no user id — the hub resolves it, single-use.
26734
+ */
26735
+ linkIntent: string().optional(),
26736
+ /**
26737
+ * Verified `iss` of the id_token behind an OIDC login bridge (D782). A
26738
+ * subject is unique only per issuer, so a link is bound to it.
26739
+ */
26740
+ issuer: string().optional()
26645
26741
  });
26646
26742
  method(object({
26647
26743
  claims: SsoBridgeClaimsSchema,
@@ -28576,7 +28672,22 @@ DeviceType.Camera, method(object({ deviceId: number().int().nonnegative() }), ar
28576
28672
  * field their hints were silently stripped by the schema and the
28577
28673
  * adaptive ladder started blind on the client's display size.
28578
28674
  */
28579
- hints: webrtcClientHintsSchema.optional()
28675
+ hints: webrtcClientHintsSchema.optional(),
28676
+ /**
28677
+ * Talk-back (D771): relay the PEER's audio to the device's speaker
28678
+ * through the `intercom` cap's push-talk triple. When `true` and the
28679
+ * offer lets the peer send audio, the answer's audio is `sendrecv`
28680
+ * and every inbound frame goes to `intercom.pushTalkAudio` for this
28681
+ * `deviceId`; absent/false answers `sendonly`, as for every viewer.
28682
+ *
28683
+ * TRUSTED-CALLER ONLY. Set by the Alexa export for an Echo on a camera
28684
+ * with `intercom`, when the linked user may control that camera. The
28685
+ * hub STRIPS it from every request-bound call (a browser), exactly as
28686
+ * it overwrites `relayOnly` — a viewer's talk permission is the
28687
+ * intercom cap's own surface (share tokens gate it there), and this
28688
+ * flag must not become a second door to the camera's speaker.
28689
+ */
28690
+ talkback: boolean().optional()
28580
28691
  }), object({
28581
28692
  sessionId: string(),
28582
28693
  sdpAnswer: string()
@@ -28878,6 +28989,59 @@ var AddonAutoUpdateSchema = ChannelWithInheritSchema;
28878
28989
  var RestartAddonResultSchema = unknown();
28879
28990
  var InstallPackageResultSchema = unknown();
28880
28991
  var ReloadPackagesResultSchema = unknown();
28992
+ /**
28993
+ * What an uninstall did on ONE node.
28994
+ * - `uninstalled` — removed: runner(s) stopped, caps gone, code deleted.
28995
+ * - `not-installed` — the node did not have it (nothing to do).
28996
+ * - `refused` — protected / bootstrap package; nothing touched.
28997
+ * - `failed` — attempted and did not complete; `error` says why.
28998
+ * - `pending-reconnect` — the node is OFFLINE: its record was pruned so the
28999
+ * back-fill never returns the package, and the stale-addon sweep removes the
29000
+ * copy when the node registers again (only once the hub no longer has it).
29001
+ */
29002
+ var UninstallNodeOutcomeSchema = _enum([
29003
+ "uninstalled",
29004
+ "not-installed",
29005
+ "refused",
29006
+ "failed",
29007
+ "pending-reconnect"
29008
+ ]);
29009
+ var UninstallNodeResultSchema = object({
29010
+ nodeId: string(),
29011
+ outcome: UninstallNodeOutcomeSchema,
29012
+ error: string().optional(),
29013
+ addonIds: array(string()).readonly(),
29014
+ runnersStopped: array(string()).readonly(),
29015
+ warnings: array(string()).readonly()
29016
+ });
29017
+ var UninstallPackageResultSchema = object({
29018
+ /** Every targeted node ended `uninstalled`, `not-installed` or `pending-reconnect`. */
29019
+ success: boolean(),
29020
+ packageName: string(),
29021
+ results: array(UninstallNodeResultSchema).readonly()
29022
+ });
29023
+ /**
29024
+ * `unreachable` lists online agents whose status read FAILED — absence from
29025
+ * `installations` is only "not installed" for a node that answered (D315).
29026
+ */
29027
+ var PackageInstallationsSchema = object({
29028
+ installations: array(object({
29029
+ packageName: string(),
29030
+ nodeId: string(),
29031
+ nodeName: string(),
29032
+ isHub: boolean(),
29033
+ isOnline: boolean(),
29034
+ version: string().nullable(),
29035
+ addonIds: array(string()).readonly(),
29036
+ source: _enum(["live", "recorded"]),
29037
+ /** The hub installs this package too. `false` on an agent row = an orphan. */
29038
+ onHub: boolean()
29039
+ })).readonly(),
29040
+ unreachable: array(object({
29041
+ nodeId: string(),
29042
+ error: string()
29043
+ })).readonly()
29044
+ });
28881
29045
  var BulkUpdateItemStatusSchema = _enum([
28882
29046
  "queued",
28883
29047
  "updating",
@@ -28960,10 +29124,14 @@ method(_void(), array(AddonListItemSchema).readonly()), method(object({
28960
29124
  }), method(object({ packageName: string() }), InstallPackageResultSchema, {
28961
29125
  kind: "mutation",
28962
29126
  auth: "admin"
28963
- }), method(_void(), boolean()), method(_void(), array(unknown()).readonly()), method(object({ packageName: string() }), unknown(), {
29127
+ }), method(_void(), boolean()), method(_void(), array(unknown()).readonly()), method(object({
29128
+ packageName: string().min(1),
29129
+ nodeId: string().optional(),
29130
+ everywhere: boolean().optional()
29131
+ }), UninstallPackageResultSchema, {
28964
29132
  kind: "mutation",
28965
29133
  auth: "admin"
28966
- }), method(_void(), ReloadPackagesResultSchema, {
29134
+ }), method(object({ packageName: string().optional() }), PackageInstallationsSchema, { auth: "admin" }), method(_void(), ReloadPackagesResultSchema, {
28967
29135
  kind: "mutation",
28968
29136
  auth: "admin"
28969
29137
  }), method(object({ query: string().optional() }), array(SearchResultSchema)), method(object({ nodeId: string().optional() }), array(PackageUpdateSchema).readonly(), { auth: "admin" }), method(object({
@@ -38873,6 +39041,32 @@ var TotpStatusSchema = object({
38873
39041
  /** Null when no row exists OR the row is still pending confirmation. */
38874
39042
  confirmedAt: number().nullable()
38875
39043
  });
39044
+ /**
39045
+ * user-management — singleton capability for user accounts, API keys,
39046
+ * and scoped tokens.
39047
+ *
39048
+ * v2 model: every method gated by `auth: 'admin'`. Admin-only delegation
39049
+ * — the subset check on `setUserScopes` / `createScopedToken` is moot
39050
+ * because non-admins never reach these. If/when we open non-admin
39051
+ * delegation, structural caller-scope subset check goes inside the
39052
+ * provider.
39053
+ */
39054
+ var ExternalIdentitySchema = object({
39055
+ /** Login-method id of the provider instance, e.g. `auth-oidc/authentik`. */
39056
+ provider: string(),
39057
+ /** The IdP's stable subject (`sub`) for this account. */
39058
+ subject: string(),
39059
+ /** The verified `iss` of the IdP the identity was linked under — `sub` is unique only per issuer. */
39060
+ issuer: string(),
39061
+ userId: string(),
39062
+ /** What the IdP called the account at link time (username / email) — display only. */
39063
+ label: string().optional(),
39064
+ linkedAt: number()
39065
+ });
39066
+ var ExternalIdentityKeySchema = object({
39067
+ provider: string().min(1),
39068
+ subject: string().min(1)
39069
+ });
38876
39070
  method(_void(), array(UserSummarySchema), { auth: "admin" }), method(CreateUserInputSchema, UserSummarySchema, {
38877
39071
  kind: "mutation",
38878
39072
  auth: "admin",
@@ -38986,7 +39180,22 @@ method(_void(), array(UserSummarySchema), { auth: "admin" }), method(CreateUserI
38986
39180
  userId: string(),
38987
39181
  username: string(),
38988
39182
  scopes: array(TokenScopeSchema)
38989
- }).nullable(), { access: "view" }), method(_void(), array(OauthSessionSummarySchema), { auth: "admin" }), method(object({ id: string() }), object({ success: boolean() }), {
39183
+ }).nullable(), { access: "view" }), method(object({ userId: string() }), array(ExternalIdentitySchema), { auth: "admin" }), method(ExternalIdentityKeySchema, object({
39184
+ userId: string(),
39185
+ issuer: string()
39186
+ }).nullable(), { auth: "admin" }), method(ExternalIdentityKeySchema.extend({
39187
+ userId: string(),
39188
+ issuer: string().min(1),
39189
+ label: string().optional()
39190
+ }), object({ success: literal(true) }), {
39191
+ kind: "mutation",
39192
+ auth: "admin",
39193
+ access: "create"
39194
+ }), method(ExternalIdentityKeySchema.extend({ userId: string() }), object({ success: boolean() }), {
39195
+ kind: "mutation",
39196
+ auth: "admin",
39197
+ access: "delete"
39198
+ }), method(_void(), array(OauthSessionSummarySchema), { auth: "admin" }), method(object({ id: string() }), object({ success: boolean() }), {
38990
39199
  kind: "mutation",
38991
39200
  auth: "admin",
38992
39201
  access: "delete"
@@ -41396,6 +41605,12 @@ Object.freeze({
41396
41605
  addonId: null,
41397
41606
  access: "view"
41398
41607
  },
41608
+ "addons.listInstallations": {
41609
+ capName: "addons",
41610
+ capScope: "system",
41611
+ addonId: null,
41612
+ access: "view"
41613
+ },
41399
41614
  "addons.listJobs": {
41400
41615
  capName: "addons",
41401
41616
  capScope: "system",
@@ -45620,6 +45835,12 @@ Object.freeze({
45620
45835
  addonId: null,
45621
45836
  access: "create"
45622
45837
  },
45838
+ "pipelineAnalytics.setRetrainFrameComplete": {
45839
+ capName: "pipeline-analytics",
45840
+ capScope: "device",
45841
+ addonId: null,
45842
+ access: "create"
45843
+ },
45623
45844
  "pipelineAnalytics.setTrackFlags": {
45624
45845
  capName: "pipeline-analytics",
45625
45846
  capScope: "device",
@@ -45656,6 +45877,12 @@ Object.freeze({
45656
45877
  addonId: null,
45657
45878
  access: "delete"
45658
45879
  },
45880
+ "pipelineAnalytics.writeRetrainArchive": {
45881
+ capName: "pipeline-analytics",
45882
+ capScope: "device",
45883
+ addonId: null,
45884
+ access: "create"
45885
+ },
45659
45886
  "pipelineExecutor.cacheFrameInPool": {
45660
45887
  capName: "pipeline-executor",
45661
45888
  capScope: "system",
@@ -48008,18 +48235,36 @@ Object.freeze({
48008
48235
  addonId: null,
48009
48236
  access: "delete"
48010
48237
  },
48238
+ "userManagement.findUserByExternalIdentity": {
48239
+ capName: "user-management",
48240
+ capScope: "system",
48241
+ addonId: null,
48242
+ access: "view"
48243
+ },
48011
48244
  "userManagement.getTotpStatus": {
48012
48245
  capName: "user-management",
48013
48246
  capScope: "system",
48014
48247
  addonId: null,
48015
48248
  access: "view"
48016
48249
  },
48250
+ "userManagement.linkExternalIdentity": {
48251
+ capName: "user-management",
48252
+ capScope: "system",
48253
+ addonId: null,
48254
+ access: "create"
48255
+ },
48017
48256
  "userManagement.listApiKeys": {
48018
48257
  capName: "user-management",
48019
48258
  capScope: "system",
48020
48259
  addonId: null,
48021
48260
  access: "view"
48022
48261
  },
48262
+ "userManagement.listExternalIdentities": {
48263
+ capName: "user-management",
48264
+ capScope: "system",
48265
+ addonId: null,
48266
+ access: "view"
48267
+ },
48023
48268
  "userManagement.listOauthSessions": {
48024
48269
  capName: "user-management",
48025
48270
  capScope: "system",
@@ -48098,6 +48343,12 @@ Object.freeze({
48098
48343
  addonId: null,
48099
48344
  access: "create"
48100
48345
  },
48346
+ "userManagement.unlinkExternalIdentity": {
48347
+ capName: "user-management",
48348
+ capScope: "system",
48349
+ addonId: null,
48350
+ access: "delete"
48351
+ },
48101
48352
  "userManagement.updateUser": {
48102
48353
  capName: "user-management",
48103
48354
  capScope: "system",
@@ -51437,6 +51688,11 @@ Object.freeze({
51437
51688
  form: "single",
51438
51689
  optional: false
51439
51690
  }],
51691
+ "pipelineAnalytics.setRetrainFrameComplete": [{
51692
+ name: "deviceId",
51693
+ form: "single",
51694
+ optional: false
51695
+ }],
51440
51696
  "pipelineAnalytics.setTrackFlags": [{
51441
51697
  name: "deviceId",
51442
51698
  form: "single",
@@ -59308,7 +59564,7 @@ var ecowittConfigSchema = discriminatedUnion("transport", [object({
59308
59564
  transport: literal("local"),
59309
59565
  host: string().min(1).describe("Ecowitt gateway host name or IP address"),
59310
59566
  port: preprocess((v) => v === "" || v === null ? void 0 : v, number().int().min(1).max(65535).default(80)).describe("Gateway HTTP port"),
59311
- password: string().default("").describe("Gateway password (optional — newer firmware)"),
59567
+ password: string().default("").describe("Gateway password (optional — newer firmware)").meta({ secret: true }),
59312
59568
  pollIntervalMs: preprocess((v) => v === "" || v === null ? void 0 : v, number().int().min(1e3).max(36e5).default(6e4)).describe("Live-data poll interval (ms)"),
59313
59569
  mappingIntervalMs: preprocess((v) => v === "" || v === null ? void 0 : v, number().int().min(1e4).max(864e5).default(6e5)).describe("Sensor-map refresh interval (ms)"),
59314
59570
  ...baseFields
package/dist/addon.mjs CHANGED
@@ -5372,7 +5372,7 @@ var ZodIssueCode$1 = {
5372
5372
  var ZodFirstPartyTypeKind$1;
5373
5373
  ZodFirstPartyTypeKind$1 || (ZodFirstPartyTypeKind$1 = {});
5374
5374
  //#endregion
5375
- //#region ../types/dist/sleep-BNeXenvr.mjs
5375
+ //#region ../types/dist/sleep-B0JG7-_F.mjs
5376
5376
  /**
5377
5377
  * The audio chunk plane's byte format, and the ONE expansion from a coded
5378
5378
  * window to float samples (D455).
@@ -15194,6 +15194,10 @@ var DeviceInfoSchema = object({
15194
15194
  isCamera: boolean(),
15195
15195
  /** Current config values — serializable snapshot */
15196
15196
  config: record(string(), unknown()),
15197
+ /** Paths inside `config` the device's schema declares secret (D783) —
15198
+ * what the non-admin redaction withholds. Paths, never values. Absent
15199
+ * when the owning runner has not reported them. */
15200
+ secretConfigPaths: array(string()).optional(),
15197
15201
  /** Hardware + identity blob (manufacturer / model / firmware / sn /
15198
15202
  * uid / mac / …). Populated by drivers; editable via setMetadata. */
15199
15203
  metadata: record(string(), unknown()).nullable().optional(),
@@ -15399,7 +15403,13 @@ var DeviceRegisterPayloadSchema = object({
15399
15403
  * call (workers re-register on init), so probe-driven updates
15400
15404
  * (e.g. PTZ flag flipping after the abilities probe) propagate. */
15401
15405
  features: array(string()).optional(),
15402
- config: record(string(), unknown())
15406
+ config: record(string(), unknown()),
15407
+ /** Config paths the device's own schema DECLARES secret
15408
+ * (`.meta({ secret: true })` — dotted, `[]` for array items, e.g.
15409
+ * `connection.password`). Re-published on every register; the non-admin
15410
+ * redaction withholds them at any depth (D783). Optional: an older runner
15411
+ * omits it and the keyword backstop applies. */
15412
+ secretConfigPaths: array(string()).optional()
15403
15413
  });
15404
15414
  var DeviceRemovePayloadSchema = object({ deviceId: number() });
15405
15415
  var DevicePersistConfigPayloadSchema = object({
@@ -17058,7 +17068,14 @@ var LoginMethodContributionSchema = discriminatedUnion("kind", [
17058
17068
  icon: string().optional(),
17059
17069
  /** Addon-owned HTTP route the button navigates to (GET). */
17060
17070
  startUrl: string(),
17061
- stage: LoginStageEnum
17071
+ stage: LoginStageEnum,
17072
+ /**
17073
+ * The provider names an external identity a signed-in user can link to
17074
+ * their own account (D782): `auth.listLinkableProviders` /
17075
+ * `beginExternalLink` offer exactly the redirect methods that set this,
17076
+ * whatever their id. Absent / false — a login button only (magic-link).
17077
+ */
17078
+ linkable: boolean().optional()
17062
17079
  }),
17063
17080
  object({
17064
17081
  kind: literal("widget"),
@@ -22493,7 +22510,13 @@ var RetrainFrameSchema = object({
22493
22510
  sizeBytes: number().int(),
22494
22511
  width: number().int(),
22495
22512
  height: number().int(),
22496
- copiedAt: number()
22513
+ copiedAt: number(),
22514
+ /** When the CAMERA captured the frame. Absent on a copy taken before D785. */
22515
+ capturedAt: number().optional(),
22516
+ /** The operator's "every subject in this frame is boxed". Detector
22517
+ * evaluation keeps only complete frames: an unboxed subject would count as
22518
+ * a false positive. */
22519
+ complete: boolean()
22497
22520
  });
22498
22521
  /** Why a copy-on-select could not be honoured — named, never a silent skip. */
22499
22522
  var RetrainCopyRefusalSchema = _enum([
@@ -22514,6 +22537,51 @@ var RetrainFrameListSchema = object({
22514
22537
  /** What the page pre-selects — the native key frame when one survives. */
22515
22538
  autoPickMediaId: number().int().optional()
22516
22539
  });
22540
+ /**
22541
+ * Which frames an annotated export carries. Every field narrows; an empty
22542
+ * filter is every annotated copy. A dataset VERSION is a frozen `frameIds`
22543
+ * list owned by whoever trains (the training orchestrator), so `frameIds` is
22544
+ * the primitive a version export uses; `batchId` re-selects what an earlier
22545
+ * export carried (`exportedInBatch`).
22546
+ */
22547
+ var RetrainExportFilterSchema = object({
22548
+ deviceIds: array(number()).optional(),
22549
+ frameIds: array(string()).max(2e4).optional(),
22550
+ batchId: string().optional(),
22551
+ /** Only frames the operator marked complete (all subjects boxed). */
22552
+ completeOnly: boolean().optional()
22553
+ });
22554
+ /**
22555
+ * `frames`: the full frame copies, boxes in `annotations.json`.
22556
+ * `crops`: additionally one JPEG per subject, cut with the runtime detail-crop
22557
+ * convention — the classifier layout.
22558
+ */
22559
+ var RetrainExportLayoutSchema = _enum(["frames", "crops"]);
22560
+ /**
22561
+ * Where `writeRetrainArchive` streams the tar: one HTTP request whose body is
22562
+ * the archive, sent chunk by chunk. Covers a presigned PUT and a provider
22563
+ * addon's data-plane upload route alike. Headers are sent verbatim and never
22564
+ * logged.
22565
+ */
22566
+ var RetrainArchiveTargetSchema = object({
22567
+ kind: literal("http"),
22568
+ method: _enum(["PUT", "POST"]),
22569
+ url: string().url(),
22570
+ headers: record(string(), string()).optional()
22571
+ });
22572
+ var RetrainArchiveResultSchema = object({
22573
+ batchId: string(),
22574
+ frames: number().int(),
22575
+ crops: number().int(),
22576
+ annotations: number().int(),
22577
+ /** Frames planned but not shipped (unreadable copy, path too long). */
22578
+ missing: number().int(),
22579
+ bytes: number().int(),
22580
+ /** sha256 of the exact bytes sent. */
22581
+ sha256: string(),
22582
+ /** The target's HTTP status. */
22583
+ status: number().int()
22584
+ });
22517
22585
  /** What the operator asked the assist to look for. */
22518
22586
  var RetrainAssistSubjectSchema = discriminatedUnion("kind", [object({
22519
22587
  kind: literal("package"),
@@ -23308,9 +23376,25 @@ DeviceType.Camera, method(object({ deviceId: number() }), array(TrackSchema).rea
23308
23376
  }), RetrainTransitionResultSchema, {
23309
23377
  kind: "mutation",
23310
23378
  auth: "admin"
23311
- }), method(object({ deviceIds: array(number()).optional() }), object({ url: string() }), {
23379
+ }), method(RetrainExportFilterSchema.extend({ layout: RetrainExportLayoutSchema.optional() }), object({ url: string() }), {
23312
23380
  kind: "query",
23313
23381
  auth: "admin"
23382
+ }), method(object({
23383
+ deviceId: number(),
23384
+ trackId: string(),
23385
+ frameId: string(),
23386
+ complete: boolean()
23387
+ }), RetrainFrameSchema, {
23388
+ kind: "mutation",
23389
+ auth: "admin"
23390
+ }), method(object({
23391
+ filter: RetrainExportFilterSchema,
23392
+ layout: RetrainExportLayoutSchema,
23393
+ target: RetrainArchiveTargetSchema
23394
+ }), RetrainArchiveResultSchema, {
23395
+ kind: "mutation",
23396
+ auth: "admin",
23397
+ timeoutMs: 60 * 6e4
23314
23398
  }), method(object({
23315
23399
  /** Which of the three event tables owns the row. */
23316
23400
  ownerType: EventOwnerTypeSchema,
@@ -26640,7 +26724,19 @@ var SsoBridgeClaimsSchema = object({
26640
26724
  * editing a descriptor must not retroactively extend or shorten a link the
26641
26725
  * operator already consented to.
26642
26726
  */
26643
- refreshTtl: union([number().int().positive(), literal("never")]).optional()
26727
+ refreshTtl: union([number().int().positive(), literal("never")]).optional(),
26728
+ /**
26729
+ * Opaque handle of a hub-side LINK intent (D782). Set by an OIDC callback
26730
+ * that was started from a signed-in user's "Link" button: the finish then
26731
+ * links this identity to the intent's user instead of signing anyone in.
26732
+ * The handle carries no user id — the hub resolves it, single-use.
26733
+ */
26734
+ linkIntent: string().optional(),
26735
+ /**
26736
+ * Verified `iss` of the id_token behind an OIDC login bridge (D782). A
26737
+ * subject is unique only per issuer, so a link is bound to it.
26738
+ */
26739
+ issuer: string().optional()
26644
26740
  });
26645
26741
  method(object({
26646
26742
  claims: SsoBridgeClaimsSchema,
@@ -28575,7 +28671,22 @@ DeviceType.Camera, method(object({ deviceId: number().int().nonnegative() }), ar
28575
28671
  * field their hints were silently stripped by the schema and the
28576
28672
  * adaptive ladder started blind on the client's display size.
28577
28673
  */
28578
- hints: webrtcClientHintsSchema.optional()
28674
+ hints: webrtcClientHintsSchema.optional(),
28675
+ /**
28676
+ * Talk-back (D771): relay the PEER's audio to the device's speaker
28677
+ * through the `intercom` cap's push-talk triple. When `true` and the
28678
+ * offer lets the peer send audio, the answer's audio is `sendrecv`
28679
+ * and every inbound frame goes to `intercom.pushTalkAudio` for this
28680
+ * `deviceId`; absent/false answers `sendonly`, as for every viewer.
28681
+ *
28682
+ * TRUSTED-CALLER ONLY. Set by the Alexa export for an Echo on a camera
28683
+ * with `intercom`, when the linked user may control that camera. The
28684
+ * hub STRIPS it from every request-bound call (a browser), exactly as
28685
+ * it overwrites `relayOnly` — a viewer's talk permission is the
28686
+ * intercom cap's own surface (share tokens gate it there), and this
28687
+ * flag must not become a second door to the camera's speaker.
28688
+ */
28689
+ talkback: boolean().optional()
28579
28690
  }), object({
28580
28691
  sessionId: string(),
28581
28692
  sdpAnswer: string()
@@ -28877,6 +28988,59 @@ var AddonAutoUpdateSchema = ChannelWithInheritSchema;
28877
28988
  var RestartAddonResultSchema = unknown();
28878
28989
  var InstallPackageResultSchema = unknown();
28879
28990
  var ReloadPackagesResultSchema = unknown();
28991
+ /**
28992
+ * What an uninstall did on ONE node.
28993
+ * - `uninstalled` — removed: runner(s) stopped, caps gone, code deleted.
28994
+ * - `not-installed` — the node did not have it (nothing to do).
28995
+ * - `refused` — protected / bootstrap package; nothing touched.
28996
+ * - `failed` — attempted and did not complete; `error` says why.
28997
+ * - `pending-reconnect` — the node is OFFLINE: its record was pruned so the
28998
+ * back-fill never returns the package, and the stale-addon sweep removes the
28999
+ * copy when the node registers again (only once the hub no longer has it).
29000
+ */
29001
+ var UninstallNodeOutcomeSchema = _enum([
29002
+ "uninstalled",
29003
+ "not-installed",
29004
+ "refused",
29005
+ "failed",
29006
+ "pending-reconnect"
29007
+ ]);
29008
+ var UninstallNodeResultSchema = object({
29009
+ nodeId: string(),
29010
+ outcome: UninstallNodeOutcomeSchema,
29011
+ error: string().optional(),
29012
+ addonIds: array(string()).readonly(),
29013
+ runnersStopped: array(string()).readonly(),
29014
+ warnings: array(string()).readonly()
29015
+ });
29016
+ var UninstallPackageResultSchema = object({
29017
+ /** Every targeted node ended `uninstalled`, `not-installed` or `pending-reconnect`. */
29018
+ success: boolean(),
29019
+ packageName: string(),
29020
+ results: array(UninstallNodeResultSchema).readonly()
29021
+ });
29022
+ /**
29023
+ * `unreachable` lists online agents whose status read FAILED — absence from
29024
+ * `installations` is only "not installed" for a node that answered (D315).
29025
+ */
29026
+ var PackageInstallationsSchema = object({
29027
+ installations: array(object({
29028
+ packageName: string(),
29029
+ nodeId: string(),
29030
+ nodeName: string(),
29031
+ isHub: boolean(),
29032
+ isOnline: boolean(),
29033
+ version: string().nullable(),
29034
+ addonIds: array(string()).readonly(),
29035
+ source: _enum(["live", "recorded"]),
29036
+ /** The hub installs this package too. `false` on an agent row = an orphan. */
29037
+ onHub: boolean()
29038
+ })).readonly(),
29039
+ unreachable: array(object({
29040
+ nodeId: string(),
29041
+ error: string()
29042
+ })).readonly()
29043
+ });
28880
29044
  var BulkUpdateItemStatusSchema = _enum([
28881
29045
  "queued",
28882
29046
  "updating",
@@ -28959,10 +29123,14 @@ method(_void(), array(AddonListItemSchema).readonly()), method(object({
28959
29123
  }), method(object({ packageName: string() }), InstallPackageResultSchema, {
28960
29124
  kind: "mutation",
28961
29125
  auth: "admin"
28962
- }), method(_void(), boolean()), method(_void(), array(unknown()).readonly()), method(object({ packageName: string() }), unknown(), {
29126
+ }), method(_void(), boolean()), method(_void(), array(unknown()).readonly()), method(object({
29127
+ packageName: string().min(1),
29128
+ nodeId: string().optional(),
29129
+ everywhere: boolean().optional()
29130
+ }), UninstallPackageResultSchema, {
28963
29131
  kind: "mutation",
28964
29132
  auth: "admin"
28965
- }), method(_void(), ReloadPackagesResultSchema, {
29133
+ }), method(object({ packageName: string().optional() }), PackageInstallationsSchema, { auth: "admin" }), method(_void(), ReloadPackagesResultSchema, {
28966
29134
  kind: "mutation",
28967
29135
  auth: "admin"
28968
29136
  }), method(object({ query: string().optional() }), array(SearchResultSchema)), method(object({ nodeId: string().optional() }), array(PackageUpdateSchema).readonly(), { auth: "admin" }), method(object({
@@ -38872,6 +39040,32 @@ var TotpStatusSchema = object({
38872
39040
  /** Null when no row exists OR the row is still pending confirmation. */
38873
39041
  confirmedAt: number().nullable()
38874
39042
  });
39043
+ /**
39044
+ * user-management — singleton capability for user accounts, API keys,
39045
+ * and scoped tokens.
39046
+ *
39047
+ * v2 model: every method gated by `auth: 'admin'`. Admin-only delegation
39048
+ * — the subset check on `setUserScopes` / `createScopedToken` is moot
39049
+ * because non-admins never reach these. If/when we open non-admin
39050
+ * delegation, structural caller-scope subset check goes inside the
39051
+ * provider.
39052
+ */
39053
+ var ExternalIdentitySchema = object({
39054
+ /** Login-method id of the provider instance, e.g. `auth-oidc/authentik`. */
39055
+ provider: string(),
39056
+ /** The IdP's stable subject (`sub`) for this account. */
39057
+ subject: string(),
39058
+ /** The verified `iss` of the IdP the identity was linked under — `sub` is unique only per issuer. */
39059
+ issuer: string(),
39060
+ userId: string(),
39061
+ /** What the IdP called the account at link time (username / email) — display only. */
39062
+ label: string().optional(),
39063
+ linkedAt: number()
39064
+ });
39065
+ var ExternalIdentityKeySchema = object({
39066
+ provider: string().min(1),
39067
+ subject: string().min(1)
39068
+ });
38875
39069
  method(_void(), array(UserSummarySchema), { auth: "admin" }), method(CreateUserInputSchema, UserSummarySchema, {
38876
39070
  kind: "mutation",
38877
39071
  auth: "admin",
@@ -38985,7 +39179,22 @@ method(_void(), array(UserSummarySchema), { auth: "admin" }), method(CreateUserI
38985
39179
  userId: string(),
38986
39180
  username: string(),
38987
39181
  scopes: array(TokenScopeSchema)
38988
- }).nullable(), { access: "view" }), method(_void(), array(OauthSessionSummarySchema), { auth: "admin" }), method(object({ id: string() }), object({ success: boolean() }), {
39182
+ }).nullable(), { access: "view" }), method(object({ userId: string() }), array(ExternalIdentitySchema), { auth: "admin" }), method(ExternalIdentityKeySchema, object({
39183
+ userId: string(),
39184
+ issuer: string()
39185
+ }).nullable(), { auth: "admin" }), method(ExternalIdentityKeySchema.extend({
39186
+ userId: string(),
39187
+ issuer: string().min(1),
39188
+ label: string().optional()
39189
+ }), object({ success: literal(true) }), {
39190
+ kind: "mutation",
39191
+ auth: "admin",
39192
+ access: "create"
39193
+ }), method(ExternalIdentityKeySchema.extend({ userId: string() }), object({ success: boolean() }), {
39194
+ kind: "mutation",
39195
+ auth: "admin",
39196
+ access: "delete"
39197
+ }), method(_void(), array(OauthSessionSummarySchema), { auth: "admin" }), method(object({ id: string() }), object({ success: boolean() }), {
38989
39198
  kind: "mutation",
38990
39199
  auth: "admin",
38991
39200
  access: "delete"
@@ -41395,6 +41604,12 @@ Object.freeze({
41395
41604
  addonId: null,
41396
41605
  access: "view"
41397
41606
  },
41607
+ "addons.listInstallations": {
41608
+ capName: "addons",
41609
+ capScope: "system",
41610
+ addonId: null,
41611
+ access: "view"
41612
+ },
41398
41613
  "addons.listJobs": {
41399
41614
  capName: "addons",
41400
41615
  capScope: "system",
@@ -45619,6 +45834,12 @@ Object.freeze({
45619
45834
  addonId: null,
45620
45835
  access: "create"
45621
45836
  },
45837
+ "pipelineAnalytics.setRetrainFrameComplete": {
45838
+ capName: "pipeline-analytics",
45839
+ capScope: "device",
45840
+ addonId: null,
45841
+ access: "create"
45842
+ },
45622
45843
  "pipelineAnalytics.setTrackFlags": {
45623
45844
  capName: "pipeline-analytics",
45624
45845
  capScope: "device",
@@ -45655,6 +45876,12 @@ Object.freeze({
45655
45876
  addonId: null,
45656
45877
  access: "delete"
45657
45878
  },
45879
+ "pipelineAnalytics.writeRetrainArchive": {
45880
+ capName: "pipeline-analytics",
45881
+ capScope: "device",
45882
+ addonId: null,
45883
+ access: "create"
45884
+ },
45658
45885
  "pipelineExecutor.cacheFrameInPool": {
45659
45886
  capName: "pipeline-executor",
45660
45887
  capScope: "system",
@@ -48007,18 +48234,36 @@ Object.freeze({
48007
48234
  addonId: null,
48008
48235
  access: "delete"
48009
48236
  },
48237
+ "userManagement.findUserByExternalIdentity": {
48238
+ capName: "user-management",
48239
+ capScope: "system",
48240
+ addonId: null,
48241
+ access: "view"
48242
+ },
48010
48243
  "userManagement.getTotpStatus": {
48011
48244
  capName: "user-management",
48012
48245
  capScope: "system",
48013
48246
  addonId: null,
48014
48247
  access: "view"
48015
48248
  },
48249
+ "userManagement.linkExternalIdentity": {
48250
+ capName: "user-management",
48251
+ capScope: "system",
48252
+ addonId: null,
48253
+ access: "create"
48254
+ },
48016
48255
  "userManagement.listApiKeys": {
48017
48256
  capName: "user-management",
48018
48257
  capScope: "system",
48019
48258
  addonId: null,
48020
48259
  access: "view"
48021
48260
  },
48261
+ "userManagement.listExternalIdentities": {
48262
+ capName: "user-management",
48263
+ capScope: "system",
48264
+ addonId: null,
48265
+ access: "view"
48266
+ },
48022
48267
  "userManagement.listOauthSessions": {
48023
48268
  capName: "user-management",
48024
48269
  capScope: "system",
@@ -48097,6 +48342,12 @@ Object.freeze({
48097
48342
  addonId: null,
48098
48343
  access: "create"
48099
48344
  },
48345
+ "userManagement.unlinkExternalIdentity": {
48346
+ capName: "user-management",
48347
+ capScope: "system",
48348
+ addonId: null,
48349
+ access: "delete"
48350
+ },
48100
48351
  "userManagement.updateUser": {
48101
48352
  capName: "user-management",
48102
48353
  capScope: "system",
@@ -51436,6 +51687,11 @@ Object.freeze({
51436
51687
  form: "single",
51437
51688
  optional: false
51438
51689
  }],
51690
+ "pipelineAnalytics.setRetrainFrameComplete": [{
51691
+ name: "deviceId",
51692
+ form: "single",
51693
+ optional: false
51694
+ }],
51439
51695
  "pipelineAnalytics.setTrackFlags": [{
51440
51696
  name: "deviceId",
51441
51697
  form: "single",
@@ -59307,7 +59563,7 @@ var ecowittConfigSchema = discriminatedUnion("transport", [object({
59307
59563
  transport: literal("local"),
59308
59564
  host: string().min(1).describe("Ecowitt gateway host name or IP address"),
59309
59565
  port: preprocess((v) => v === "" || v === null ? void 0 : v, number().int().min(1).max(65535).default(80)).describe("Gateway HTTP port"),
59310
- password: string().default("").describe("Gateway password (optional — newer firmware)"),
59566
+ password: string().default("").describe("Gateway password (optional — newer firmware)").meta({ secret: true }),
59311
59567
  pollIntervalMs: preprocess((v) => v === "" || v === null ? void 0 : v, number().int().min(1e3).max(36e5).default(6e4)).describe("Live-data poll interval (ms)"),
59312
59568
  mappingIntervalMs: preprocess((v) => v === "" || v === null ? void 0 : v, number().int().min(1e4).max(864e5).default(6e5)).describe("Sensor-map refresh interval (ms)"),
59313
59569
  ...baseFields
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@camstack/addon-provider-ecowitt",
3
- "version": "0.2.121",
3
+ "version": "0.2.123",
4
4
  "description": "Ecowitt weather-station device-provider addon for CamStack — wraps the @apocaliss92/nodewitt local-poll / push client",
5
5
  "keywords": [
6
6
  "camstack",