@camstack/addon-provider-homeassistant 1.2.660 → 1.2.661

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -7,6 +7,12 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
7
7
 
8
8
  ## [Unreleased]
9
9
 
10
+ ## [1.2.661] - 2026-11-05
11
+
12
+ ### Changed
13
+
14
+ - Copying an integration into its record reads the leftover rows through the migration-only door and resolves their secrets in this addon
15
+
10
16
  ## [1.2.660] - 2026-11-05
11
17
 
12
18
  ### Changed
package/dist/addon.js CHANGED
@@ -1,5 +1,5 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_legacy_integration_rows = require("./legacy-integration-rows-BWVmjfDO.js");
2
+ const require_legacy_integration_rows = require("./legacy-integration-rows-B_X4VL29.js");
3
3
  let node_crypto = require("node:crypto");
4
4
  let node_zlib = require("node:zlib");
5
5
  //#region src/ha-admin-link.ts
@@ -9107,7 +9107,12 @@ var HaProviderAddon = class HaProviderAddon extends require_legacy_integration_r
9107
9107
  if (this.ctx.secrets === void 0) throw new Error("provider-homeassistant: ctx.secrets is required");
9108
9108
  return {
9109
9109
  readStored: (key) => this.readStoredGlobalKey(key),
9110
- ...require_legacy_integration_rows.haInstanceSettingsPortsOver(this.ctx.api.integrations),
9110
+ ...require_legacy_integration_rows.haInstanceSettingsPortsOver({
9111
+ list: this.ctx.api.integrations.list,
9112
+ readLegacyIntegrationRows: this.ctx.api.migrations.readLegacyIntegrationRows,
9113
+ patchLegacyIntegrationRows: this.ctx.api.migrations.patchLegacyIntegrationRows,
9114
+ deleteLegacyIntegrationRowKeys: this.ctx.api.migrations.deleteLegacyIntegrationRowKeys
9115
+ }, this.ctx.secrets ?? null),
9111
9116
  ...haInstanceRecordPortsOver(records.kind(haBrokersEntryKind)),
9112
9117
  ...require_legacy_integration_rows.flattenPortsOver(records.kind(haBrokersEntryKind))
9113
9118
  };
package/dist/addon.mjs CHANGED
@@ -1,4 +1,4 @@
1
- import { $ as fanControlCapability, $t as createEvent, A as bestLocationMatch, At as runningFromMediaPlayer, B as climateControlCapability, Bt as tryConvertDelta, C as accessoriesCapability, Ct as pressureSensorCapability, D as ambientLightSensorCapability, Dt as resolveAttachmentUrls, E as alarmPanelCapability, Et as quantityFromUnit, F as buildAddonRouteProvider, Ft as smokeCapability, G as contactCapability, Gt as vibrationCapability, H as connectivityCapability, Ht as updateCapability, I as buildDeviceAdminUrl, J as deviceAdminLinkCapability, K as controlCapability, Kt as waterHeaterCapability, L as buttonCapability, Lt as switchCapability, M as boardKeySourceCapability, Mt as runningStateCapability, N as brightnessCapability, Nt as scriptRunnerCapability, O as automationControlCapability, P as brokerCapability, Q as eventEmitterCapability, Qt as baseUnitOf, R as calendarSourceCapability, Rt as tamperCapability, S as TargetSchema, Sn as EventCategory, St as presenceCapability, T as airQualitySensorCapability, Tt as publicEndpointReaderFrom, Ut as vacuumControlCapability, V as colorCapability, Vt as tryConvertUnit, Wt as valveCapability, Xt as RecordSecretUnavailableError, Y as deviceAdoptionCapability, Z as enumSensorCapability, _n as url, at as humiditySensorCapability, b as RUNNING_STATE_COLD, bn as DeviceType, bt as preconditionOf, cn as boolean, ct as integrationInstancesCapability, dn as number, dt as mediaPlayerCapability, en as defineAddonMigrations, et as flattenNestedRecords, fn as object, ft as motionCapability, gn as unknown, gt as numericSensorCapability, hn as union, ht as notifierCapability, it as humidifierCapability, j as binaryCapability, jt as runningFromVacuumState, k as batteryCapability, kt as runningFromLawnMower, ln as discriminatedUnion, lt as lawnMowerControlCapability, m as EnumSensorDateTimeFormatSchema, mn as string, mt as notificationOutputCapability, n as HA_BROKER_KIND, nn as defineRecordKinds, nt as floodCapability, o as BaseDevice, on as _enum, ot as imageCapability, pn as record, pt as normalizeUnit, q as coverCapability, qt as weatherCapability, rn as entryBody, rt as gasCapability, s as BaseDeviceProvider, sn as array, st as ingestReading, t as haInstanceSettingsPortsOver, tn as defineEntryKind, tt as flattenPortsOver, un as literal, ut as lockControlCapability, vn as DeviceFeature, vt as parseAdminBase, w as addonRoutesCapability, x as RecordIntegrationInstances, xn as errMsg, xt as prepareNotification, yn as DeviceRole, yt as powerMeterCapability, z as carbonMonoxideCapability, zt as temperatureSensorCapability } from "./legacy-integration-rows-BIbFoT26.mjs";
1
+ import { $ as fanControlCapability, $t as createEvent, A as bestLocationMatch, At as runningFromMediaPlayer, B as climateControlCapability, Bt as tryConvertDelta, C as accessoriesCapability, Ct as pressureSensorCapability, D as ambientLightSensorCapability, Dt as resolveAttachmentUrls, E as alarmPanelCapability, Et as quantityFromUnit, F as buildAddonRouteProvider, Ft as smokeCapability, G as contactCapability, Gt as vibrationCapability, H as connectivityCapability, Ht as updateCapability, I as buildDeviceAdminUrl, J as deviceAdminLinkCapability, K as controlCapability, Kt as waterHeaterCapability, L as buttonCapability, Lt as switchCapability, M as boardKeySourceCapability, Mt as runningStateCapability, N as brightnessCapability, Nt as scriptRunnerCapability, O as automationControlCapability, P as brokerCapability, Q as eventEmitterCapability, Qt as baseUnitOf, R as calendarSourceCapability, Rt as tamperCapability, S as TargetSchema, Sn as EventCategory, St as presenceCapability, T as airQualitySensorCapability, Tt as publicEndpointReaderFrom, Ut as vacuumControlCapability, V as colorCapability, Vt as tryConvertUnit, Wt as valveCapability, Xt as RecordSecretUnavailableError, Y as deviceAdoptionCapability, Z as enumSensorCapability, _n as url, at as humiditySensorCapability, b as RUNNING_STATE_COLD, bn as DeviceType, bt as preconditionOf, cn as boolean, ct as integrationInstancesCapability, dn as number, dt as mediaPlayerCapability, en as defineAddonMigrations, et as flattenNestedRecords, fn as object, ft as motionCapability, gn as unknown, gt as numericSensorCapability, hn as union, ht as notifierCapability, it as humidifierCapability, j as binaryCapability, jt as runningFromVacuumState, k as batteryCapability, kt as runningFromLawnMower, ln as discriminatedUnion, lt as lawnMowerControlCapability, m as EnumSensorDateTimeFormatSchema, mn as string, mt as notificationOutputCapability, n as HA_BROKER_KIND, nn as defineRecordKinds, nt as floodCapability, o as BaseDevice, on as _enum, ot as imageCapability, pn as record, pt as normalizeUnit, q as coverCapability, qt as weatherCapability, rn as entryBody, rt as gasCapability, s as BaseDeviceProvider, sn as array, st as ingestReading, t as haInstanceSettingsPortsOver, tn as defineEntryKind, tt as flattenPortsOver, un as literal, ut as lockControlCapability, vn as DeviceFeature, vt as parseAdminBase, w as addonRoutesCapability, x as RecordIntegrationInstances, xn as errMsg, xt as prepareNotification, yn as DeviceRole, yt as powerMeterCapability, z as carbonMonoxideCapability, zt as temperatureSensorCapability } from "./legacy-integration-rows-Bhvthv-s.mjs";
2
2
  import { randomUUID } from "node:crypto";
3
3
  import { brotliCompressSync, deflateSync, gzipSync } from "node:zlib";
4
4
  //#region src/ha-admin-link.ts
@@ -9086,7 +9086,12 @@ var HaProviderAddon = class HaProviderAddon extends BaseDeviceProvider {
9086
9086
  if (this.ctx.secrets === void 0) throw new Error("provider-homeassistant: ctx.secrets is required");
9087
9087
  return {
9088
9088
  readStored: (key) => this.readStoredGlobalKey(key),
9089
- ...haInstanceSettingsPortsOver(this.ctx.api.integrations),
9089
+ ...haInstanceSettingsPortsOver({
9090
+ list: this.ctx.api.integrations.list,
9091
+ readLegacyIntegrationRows: this.ctx.api.migrations.readLegacyIntegrationRows,
9092
+ patchLegacyIntegrationRows: this.ctx.api.migrations.patchLegacyIntegrationRows,
9093
+ deleteLegacyIntegrationRowKeys: this.ctx.api.migrations.deleteLegacyIntegrationRowKeys
9094
+ }, this.ctx.secrets ?? null),
9090
9095
  ...haInstanceRecordPortsOver(records.kind(haBrokersEntryKind)),
9091
9096
  ...flattenPortsOver(records.kind(haBrokersEntryKind))
9092
9097
  };
@@ -24,7 +24,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
24
24
  enumerable: true
25
25
  }) : target, mod));
26
26
  //#endregion
27
- const require_legacy_integration_rows = require("../legacy-integration-rows-BWVmjfDO.js");
27
+ const require_legacy_integration_rows = require("../legacy-integration-rows-B_X4VL29.js");
28
28
  let node_crypto = require("node:crypto");
29
29
  require("node:zlib");
30
30
  let node_fs = require("node:fs");
@@ -5781,7 +5781,12 @@ async function readAllLinks(handle) {
5781
5781
  function haExportMigrationPorts(deps) {
5782
5782
  return {
5783
5783
  readStored: deps.readStored,
5784
- ...require_legacy_integration_rows.haInstanceSettingsPortsOver(deps.api.integrations),
5784
+ ...require_legacy_integration_rows.haInstanceSettingsPortsOver({
5785
+ list: deps.api.integrations.list,
5786
+ readLegacyIntegrationRows: deps.api.migrations.readLegacyIntegrationRows,
5787
+ patchLegacyIntegrationRows: deps.api.migrations.patchLegacyIntegrationRows,
5788
+ deleteLegacyIntegrationRowKeys: deps.api.migrations.deleteLegacyIntegrationRowKeys
5789
+ }, deps.secrets ?? null),
5785
5790
  warn: deps.warn,
5786
5791
  putLinks: async (brokerId, body) => {
5787
5792
  if (await deps.links.get(brokerId) !== null) return "exists";
@@ -8108,6 +8113,7 @@ var HaExportAddon = class extends require_legacy_integration_rows.BaseAddon {
8108
8113
  await this.runMigrations(require_legacy_integration_rows.defineAddonMigrations(ADDON_MIGRATIONS, haExportMigrationPorts({
8109
8114
  readStored: async () => this.resolveGlobalStore(),
8110
8115
  api: this.ctx.api,
8116
+ secrets: this.ctx.secrets ?? null,
8111
8117
  links: legacyLinks,
8112
8118
  targets: targetsHandle,
8113
8119
  clearSettingKeys: async (keys) => {
@@ -1,4 +1,4 @@
1
- import { F as buildAddonRouteProvider, It as statusInstanceOf, Jt as BaseAddon, Ot as runExportedAction, Pt as sendToExportedTarget, Qt as baseUnitOf, Sn as EventCategory, U as consumableFormOf, W as consumableKindOf, X as deviceExportCapability, Zt as RevConflictError, _ as HvacModeSchema, _t as oauthIntegrationCapability, a as AlarmArmModeSchema, an as nodePin, bt as preconditionOf, c as CAMERA_SWITCH_ORDER, cn as boolean, ct as integrationInstancesCapability, d as ConsumableFormSchema, dn as number, en as defineAddonMigrations, f as ConsumableItemSchema, fn as object, g as FanDirectionSchema, gn as unknown, h as ExportInstanceUnknownError, i as listHomeAssistantBrokers, in as isReadingQuantity, l as COCO_TO_MACRO, mn as string, on as _enum, p as ConsumableStatusSchema, sn as array, t as haInstanceSettingsPortsOver, tn as defineEntryKind, u as CameraSwitchIdSchema, v as MediaPlayerRepeatSchema, w as addonRoutesCapability, wt as pruneDeletedEntities, x as RecordIntegrationInstances, y as PLUG_APPLIANCE_TYPES } from "../legacy-integration-rows-BIbFoT26.mjs";
1
+ import { F as buildAddonRouteProvider, It as statusInstanceOf, Jt as BaseAddon, Ot as runExportedAction, Pt as sendToExportedTarget, Qt as baseUnitOf, Sn as EventCategory, U as consumableFormOf, W as consumableKindOf, X as deviceExportCapability, Zt as RevConflictError, _ as HvacModeSchema, _t as oauthIntegrationCapability, a as AlarmArmModeSchema, an as nodePin, bt as preconditionOf, c as CAMERA_SWITCH_ORDER, cn as boolean, ct as integrationInstancesCapability, d as ConsumableFormSchema, dn as number, en as defineAddonMigrations, f as ConsumableItemSchema, fn as object, g as FanDirectionSchema, gn as unknown, h as ExportInstanceUnknownError, i as listHomeAssistantBrokers, in as isReadingQuantity, l as COCO_TO_MACRO, mn as string, on as _enum, p as ConsumableStatusSchema, sn as array, t as haInstanceSettingsPortsOver, tn as defineEntryKind, u as CameraSwitchIdSchema, v as MediaPlayerRepeatSchema, w as addonRoutesCapability, wt as pruneDeletedEntities, x as RecordIntegrationInstances, y as PLUG_APPLIANCE_TYPES } from "../legacy-integration-rows-Bhvthv-s.mjs";
2
2
  import { createHmac, timingSafeEqual } from "node:crypto";
3
3
  import "node:zlib";
4
4
  import "node:fs";
@@ -5743,7 +5743,12 @@ async function readAllLinks(handle) {
5743
5743
  function haExportMigrationPorts(deps) {
5744
5744
  return {
5745
5745
  readStored: deps.readStored,
5746
- ...haInstanceSettingsPortsOver(deps.api.integrations),
5746
+ ...haInstanceSettingsPortsOver({
5747
+ list: deps.api.integrations.list,
5748
+ readLegacyIntegrationRows: deps.api.migrations.readLegacyIntegrationRows,
5749
+ patchLegacyIntegrationRows: deps.api.migrations.patchLegacyIntegrationRows,
5750
+ deleteLegacyIntegrationRowKeys: deps.api.migrations.deleteLegacyIntegrationRowKeys
5751
+ }, deps.secrets ?? null),
5747
5752
  warn: deps.warn,
5748
5753
  putLinks: async (brokerId, body) => {
5749
5754
  if (await deps.links.get(brokerId) !== null) return "exists";
@@ -8070,6 +8075,7 @@ var HaExportAddon = class extends BaseAddon {
8070
8075
  await this.runMigrations(defineAddonMigrations(ADDON_MIGRATIONS, haExportMigrationPorts({
8071
8076
  readStored: async () => this.resolveGlobalStore(),
8072
8077
  api: this.ctx.api,
8078
+ secrets: this.ctx.secrets ?? null,
8073
8079
  links: legacyLinks,
8074
8080
  targets: targetsHandle,
8075
8081
  clearSettingKeys: async (keys) => {
@@ -5981,7 +5981,7 @@ var ZodIssueCode = {
5981
5981
  var ZodFirstPartyTypeKind;
5982
5982
  ZodFirstPartyTypeKind || (ZodFirstPartyTypeKind = {});
5983
5983
  //#endregion
5984
- //#region ../types/dist/sleep-D1jjWAr8.mjs
5984
+ //#region ../types/dist/sleep-9TIHFj1w.mjs
5985
5985
  /**
5986
5986
  * The audio chunk plane's byte format, and the ONE expansion from a coded
5987
5987
  * window to float samples (D455).
@@ -7935,10 +7935,9 @@ var BaseAddon = class {
7935
7935
  *
7936
7936
  * Override it only when an `instanceMode: multiple` addon's instances differ: an NVR integration
7937
7937
  * needs its connection fields, the default integration the addon's own sections. It is the
7938
- * SHAPE of the form only — the values live in `integrations.getSettings`, and the write path is
7939
- * unchanged (`integrations.setSettings` for an account integration).
7938
+ * SHAPE of the form only — the values live on the instance record.
7940
7939
  */
7941
- async integrationSettingsSchema(_instance) {
7940
+ async integrationFormSchema(_instance) {
7942
7941
  return null;
7943
7942
  }
7944
7943
  /**
@@ -7984,7 +7983,7 @@ var BaseAddon = class {
7984
7983
  * per-instance schema when it declares one, else its global schema (what they always showed).
7985
7984
  */
7986
7985
  async getIntegrationFormSchema(instance, nodeId) {
7987
- const scoped = await this.integrationSettingsSchema(instance);
7986
+ const scoped = await this.integrationFormSchema(instance);
7988
7987
  if (scoped === null) return this.getGlobalSettings(void 0, void 0, nodeId);
7989
7988
  return hydrateSchema(scoped, {}, { inlineSecretsAsViews: true });
7990
7989
  }
@@ -56784,11 +56783,7 @@ var CreateIntegrationInputSchema = object({
56784
56783
  info: record(string(), unknown()).optional(),
56785
56784
  /** `stableId` of the discovery candidate the form was seeded from (D984). */
56786
56785
  originStableId: string().optional(),
56787
- settings: record(string(), unknown()).optional(),
56788
- /** Keys of `settings` the form's schema declares secret (by type) — kept in
56789
- * the keychain, not the table (D787). */
56790
- secretKeys: array(string()).optional(),
56791
- skipRestart: boolean().optional()
56786
+ settings: record(string(), unknown()).optional()
56792
56787
  });
56793
56788
  var UpdateIntegrationInputSchema = object({
56794
56789
  id: string(),
@@ -56809,22 +56804,6 @@ method(_void(), array(IntegrationWithStateSchema)), method(object({ id: string()
56809
56804
  }), method(object({ id: string() }), DeleteIntegrationResultSchema, {
56810
56805
  kind: "mutation",
56811
56806
  auth: "admin"
56812
- }), method(object({ id: string() }), record(string(), unknown()), { auth: "admin" }), method(object({
56813
- id: string(),
56814
- settings: record(string(), unknown()),
56815
- /** Keys the form's schema declares secret (by type) — keychain-stored (D787). */
56816
- secretKeys: array(string()).optional(),
56817
- /** The integration's own addon applies the change in-process and asks the hub not to respawn it. */
56818
- skipRestart: boolean().optional()
56819
- }), object({ success: boolean() }), {
56820
- kind: "mutation",
56821
- auth: "admin"
56822
- }), method(object({ id: string() }), object({
56823
- rows: number().int().nonnegative(),
56824
- secrets: number().int().nonnegative()
56825
- }), {
56826
- kind: "mutation",
56827
- auth: "admin"
56828
56807
  }), method(_void(), array(AvailableIntegrationTypeSchema), { auth: "admin" }), method(object({
56829
56808
  addonId: string(),
56830
56809
  settings: record(string(), unknown())
@@ -59801,6 +59780,27 @@ method(object({}), object({ entries: array(MigrationLedgerEntrySchema) }), { aut
59801
59780
  }), {
59802
59781
  kind: "mutation",
59803
59782
  auth: "admin"
59783
+ }), method(object({ integrationId: string().min(1) }), record(string(), unknown()), { auth: "admin" }), method(object({ integrationId: string().min(1) }), object({
59784
+ rows: number().int().nonnegative(),
59785
+ secrets: number().int().nonnegative()
59786
+ }), {
59787
+ kind: "mutation",
59788
+ auth: "admin"
59789
+ }), method(object({
59790
+ integrationId: string().min(1),
59791
+ patch: record(string(), unknown())
59792
+ }), object({ written: boolean() }), {
59793
+ kind: "mutation",
59794
+ auth: "admin"
59795
+ }), method(object({
59796
+ integrationId: string().min(1),
59797
+ keys: array(string().min(1))
59798
+ }), object({
59799
+ present: boolean(),
59800
+ removed: record(string(), unknown())
59801
+ }), {
59802
+ kind: "mutation",
59803
+ auth: "admin"
59804
59804
  });
59805
59805
  method(object({
59806
59806
  sourceUrl: string(),
@@ -86621,13 +86621,6 @@ Object.freeze({
86621
86621
  access: "create",
86622
86622
  role: "admin"
86623
86623
  },
86624
- "integrations.clearSettings": {
86625
- capName: "integrations",
86626
- capScope: "system",
86627
- addonId: null,
86628
- access: "delete",
86629
- role: "admin"
86630
- },
86631
86624
  "integrations.create": {
86632
86625
  capName: "integrations",
86633
86626
  capScope: "system",
@@ -86663,13 +86656,6 @@ Object.freeze({
86663
86656
  access: "view",
86664
86657
  role: "admin"
86665
86658
  },
86666
- "integrations.getSettings": {
86667
- capName: "integrations",
86668
- capScope: "system",
86669
- addonId: null,
86670
- access: "view",
86671
- role: "admin"
86672
- },
86673
86659
  "integrations.list": {
86674
86660
  capName: "integrations",
86675
86661
  capScope: "system",
@@ -86677,13 +86663,6 @@ Object.freeze({
86677
86663
  access: "view",
86678
86664
  role: "admin"
86679
86665
  },
86680
- "integrations.setSettings": {
86681
- capName: "integrations",
86682
- capScope: "system",
86683
- addonId: null,
86684
- access: "create",
86685
- role: "admin"
86686
- },
86687
86666
  "integrations.testConnection": {
86688
86667
  capName: "integrations",
86689
86668
  capScope: "system",
@@ -87678,6 +87657,13 @@ Object.freeze({
87678
87657
  access: "view",
87679
87658
  role: "admin"
87680
87659
  },
87660
+ "migrations.clearLegacyIntegrationRows": {
87661
+ capName: "migrations",
87662
+ capScope: "system",
87663
+ addonId: null,
87664
+ access: "delete",
87665
+ role: "admin"
87666
+ },
87681
87667
  "migrations.declareOwner": {
87682
87668
  capName: "migrations",
87683
87669
  capScope: "system",
@@ -87685,6 +87671,13 @@ Object.freeze({
87685
87671
  access: "create",
87686
87672
  role: "admin"
87687
87673
  },
87674
+ "migrations.deleteLegacyIntegrationRowKeys": {
87675
+ capName: "migrations",
87676
+ capScope: "system",
87677
+ addonId: null,
87678
+ access: "delete",
87679
+ role: "admin"
87680
+ },
87688
87681
  "migrations.dryRun": {
87689
87682
  capName: "migrations",
87690
87683
  capScope: "system",
@@ -87720,6 +87713,20 @@ Object.freeze({
87720
87713
  access: "create",
87721
87714
  role: "admin"
87722
87715
  },
87716
+ "migrations.patchLegacyIntegrationRows": {
87717
+ capName: "migrations",
87718
+ capScope: "system",
87719
+ addonId: null,
87720
+ access: "create",
87721
+ role: "admin"
87722
+ },
87723
+ "migrations.readLegacyIntegrationRows": {
87724
+ capName: "migrations",
87725
+ capScope: "system",
87726
+ addonId: null,
87727
+ access: "view",
87728
+ role: "admin"
87729
+ },
87723
87730
  "migrations.restorePreMigration": {
87724
87731
  capName: "migrations",
87725
87732
  capScope: "system",
@@ -98399,13 +98406,18 @@ var HA_BROKER_KIND = "home-assistant";
98399
98406
  async function listHomeAssistantBrokers(query) {
98400
98407
  return (await query({})).filter((broker) => broker.kind === HA_BROKER_KIND);
98401
98408
  }
98402
- function haInstanceSettingsPortsOver(api) {
98409
+ function refsOfKeys(stored, keys) {
98410
+ const picked = {};
98411
+ for (const key of keys) if (Object.prototype.hasOwnProperty.call(stored, key)) picked[key] = stored[key];
98412
+ return collectSecretMarkerRefs(picked);
98413
+ }
98414
+ function haInstanceSettingsPortsOver(api, secrets = null) {
98403
98415
  const listInstances = async () => {
98404
98416
  const all = await api.list.query();
98405
98417
  const rows = [];
98406
98418
  for (const integration of all) {
98407
98419
  if (integration.addonId !== "provider-homeassistant") continue;
98408
- const settings = await api.getSettings.query({ id: integration.id });
98420
+ const settings = await api.readLegacyIntegrationRows.query({ integrationId: integration.id });
98409
98421
  const brokerId = settings["brokerId"];
98410
98422
  rows.push({
98411
98423
  integrationId: integration.id,
@@ -98415,31 +98427,26 @@ function haInstanceSettingsPortsOver(api) {
98415
98427
  }
98416
98428
  return rows;
98417
98429
  };
98430
+ const owns = async (integrationId) => {
98431
+ return (await api.list.query()).some((i) => i.id === integrationId && i.addonId === "provider-homeassistant");
98432
+ };
98418
98433
  return {
98419
98434
  listInstances,
98420
98435
  patchInstanceSettings: async (integrationId, patch) => {
98421
- if (!(await api.list.query()).some((i) => i.id === integrationId && i.addonId === "provider-homeassistant")) return false;
98422
- const stored = await api.getSettings.query({ id: integrationId });
98423
- await api.setSettings.mutate({
98424
- id: integrationId,
98425
- settings: {
98426
- ...stored,
98427
- ...patch
98428
- },
98429
- skipRestart: true
98430
- });
98431
- return true;
98436
+ if (!await owns(integrationId)) return false;
98437
+ return (await api.patchLegacyIntegrationRows.mutate({
98438
+ integrationId,
98439
+ patch: { ...patch }
98440
+ })).written;
98432
98441
  },
98433
98442
  clearInstanceSettingsKeys: async (integrationId, keys) => {
98434
- if (!(await api.list.query()).some((i) => i.id === integrationId && i.addonId === "provider-homeassistant")) return false;
98435
- const stored = await api.getSettings.query({ id: integrationId });
98436
- const drop = new Set(keys);
98437
- await api.setSettings.mutate({
98438
- id: integrationId,
98439
- settings: Object.fromEntries(Object.entries(stored).filter(([key]) => !drop.has(key))),
98440
- skipRestart: true
98441
- });
98442
- return true;
98443
+ if (!await owns(integrationId)) return false;
98444
+ const refs = refsOfKeys(await api.readLegacyIntegrationRows.query({ integrationId }), keys);
98445
+ if (refs.length > 0 && secrets !== null) await secrets.delete(refs);
98446
+ return (await api.deleteLegacyIntegrationRowKeys.mutate({
98447
+ integrationId,
98448
+ keys
98449
+ })).present;
98443
98450
  }
98444
98451
  };
98445
98452
  }
@@ -5980,7 +5980,7 @@ var ZodIssueCode = {
5980
5980
  var ZodFirstPartyTypeKind;
5981
5981
  ZodFirstPartyTypeKind || (ZodFirstPartyTypeKind = {});
5982
5982
  //#endregion
5983
- //#region ../types/dist/sleep-D1jjWAr8.mjs
5983
+ //#region ../types/dist/sleep-9TIHFj1w.mjs
5984
5984
  /**
5985
5985
  * The audio chunk plane's byte format, and the ONE expansion from a coded
5986
5986
  * window to float samples (D455).
@@ -7934,10 +7934,9 @@ var BaseAddon = class {
7934
7934
  *
7935
7935
  * Override it only when an `instanceMode: multiple` addon's instances differ: an NVR integration
7936
7936
  * needs its connection fields, the default integration the addon's own sections. It is the
7937
- * SHAPE of the form only — the values live in `integrations.getSettings`, and the write path is
7938
- * unchanged (`integrations.setSettings` for an account integration).
7937
+ * SHAPE of the form only — the values live on the instance record.
7939
7938
  */
7940
- async integrationSettingsSchema(_instance) {
7939
+ async integrationFormSchema(_instance) {
7941
7940
  return null;
7942
7941
  }
7943
7942
  /**
@@ -7983,7 +7982,7 @@ var BaseAddon = class {
7983
7982
  * per-instance schema when it declares one, else its global schema (what they always showed).
7984
7983
  */
7985
7984
  async getIntegrationFormSchema(instance, nodeId) {
7986
- const scoped = await this.integrationSettingsSchema(instance);
7985
+ const scoped = await this.integrationFormSchema(instance);
7987
7986
  if (scoped === null) return this.getGlobalSettings(void 0, void 0, nodeId);
7988
7987
  return hydrateSchema(scoped, {}, { inlineSecretsAsViews: true });
7989
7988
  }
@@ -56783,11 +56782,7 @@ var CreateIntegrationInputSchema = object({
56783
56782
  info: record(string(), unknown()).optional(),
56784
56783
  /** `stableId` of the discovery candidate the form was seeded from (D984). */
56785
56784
  originStableId: string().optional(),
56786
- settings: record(string(), unknown()).optional(),
56787
- /** Keys of `settings` the form's schema declares secret (by type) — kept in
56788
- * the keychain, not the table (D787). */
56789
- secretKeys: array(string()).optional(),
56790
- skipRestart: boolean().optional()
56785
+ settings: record(string(), unknown()).optional()
56791
56786
  });
56792
56787
  var UpdateIntegrationInputSchema = object({
56793
56788
  id: string(),
@@ -56808,22 +56803,6 @@ method(_void(), array(IntegrationWithStateSchema)), method(object({ id: string()
56808
56803
  }), method(object({ id: string() }), DeleteIntegrationResultSchema, {
56809
56804
  kind: "mutation",
56810
56805
  auth: "admin"
56811
- }), method(object({ id: string() }), record(string(), unknown()), { auth: "admin" }), method(object({
56812
- id: string(),
56813
- settings: record(string(), unknown()),
56814
- /** Keys the form's schema declares secret (by type) — keychain-stored (D787). */
56815
- secretKeys: array(string()).optional(),
56816
- /** The integration's own addon applies the change in-process and asks the hub not to respawn it. */
56817
- skipRestart: boolean().optional()
56818
- }), object({ success: boolean() }), {
56819
- kind: "mutation",
56820
- auth: "admin"
56821
- }), method(object({ id: string() }), object({
56822
- rows: number().int().nonnegative(),
56823
- secrets: number().int().nonnegative()
56824
- }), {
56825
- kind: "mutation",
56826
- auth: "admin"
56827
56806
  }), method(_void(), array(AvailableIntegrationTypeSchema), { auth: "admin" }), method(object({
56828
56807
  addonId: string(),
56829
56808
  settings: record(string(), unknown())
@@ -59800,6 +59779,27 @@ method(object({}), object({ entries: array(MigrationLedgerEntrySchema) }), { aut
59800
59779
  }), {
59801
59780
  kind: "mutation",
59802
59781
  auth: "admin"
59782
+ }), method(object({ integrationId: string().min(1) }), record(string(), unknown()), { auth: "admin" }), method(object({ integrationId: string().min(1) }), object({
59783
+ rows: number().int().nonnegative(),
59784
+ secrets: number().int().nonnegative()
59785
+ }), {
59786
+ kind: "mutation",
59787
+ auth: "admin"
59788
+ }), method(object({
59789
+ integrationId: string().min(1),
59790
+ patch: record(string(), unknown())
59791
+ }), object({ written: boolean() }), {
59792
+ kind: "mutation",
59793
+ auth: "admin"
59794
+ }), method(object({
59795
+ integrationId: string().min(1),
59796
+ keys: array(string().min(1))
59797
+ }), object({
59798
+ present: boolean(),
59799
+ removed: record(string(), unknown())
59800
+ }), {
59801
+ kind: "mutation",
59802
+ auth: "admin"
59803
59803
  });
59804
59804
  method(object({
59805
59805
  sourceUrl: string(),
@@ -86620,13 +86620,6 @@ Object.freeze({
86620
86620
  access: "create",
86621
86621
  role: "admin"
86622
86622
  },
86623
- "integrations.clearSettings": {
86624
- capName: "integrations",
86625
- capScope: "system",
86626
- addonId: null,
86627
- access: "delete",
86628
- role: "admin"
86629
- },
86630
86623
  "integrations.create": {
86631
86624
  capName: "integrations",
86632
86625
  capScope: "system",
@@ -86662,13 +86655,6 @@ Object.freeze({
86662
86655
  access: "view",
86663
86656
  role: "admin"
86664
86657
  },
86665
- "integrations.getSettings": {
86666
- capName: "integrations",
86667
- capScope: "system",
86668
- addonId: null,
86669
- access: "view",
86670
- role: "admin"
86671
- },
86672
86658
  "integrations.list": {
86673
86659
  capName: "integrations",
86674
86660
  capScope: "system",
@@ -86676,13 +86662,6 @@ Object.freeze({
86676
86662
  access: "view",
86677
86663
  role: "admin"
86678
86664
  },
86679
- "integrations.setSettings": {
86680
- capName: "integrations",
86681
- capScope: "system",
86682
- addonId: null,
86683
- access: "create",
86684
- role: "admin"
86685
- },
86686
86665
  "integrations.testConnection": {
86687
86666
  capName: "integrations",
86688
86667
  capScope: "system",
@@ -87677,6 +87656,13 @@ Object.freeze({
87677
87656
  access: "view",
87678
87657
  role: "admin"
87679
87658
  },
87659
+ "migrations.clearLegacyIntegrationRows": {
87660
+ capName: "migrations",
87661
+ capScope: "system",
87662
+ addonId: null,
87663
+ access: "delete",
87664
+ role: "admin"
87665
+ },
87680
87666
  "migrations.declareOwner": {
87681
87667
  capName: "migrations",
87682
87668
  capScope: "system",
@@ -87684,6 +87670,13 @@ Object.freeze({
87684
87670
  access: "create",
87685
87671
  role: "admin"
87686
87672
  },
87673
+ "migrations.deleteLegacyIntegrationRowKeys": {
87674
+ capName: "migrations",
87675
+ capScope: "system",
87676
+ addonId: null,
87677
+ access: "delete",
87678
+ role: "admin"
87679
+ },
87687
87680
  "migrations.dryRun": {
87688
87681
  capName: "migrations",
87689
87682
  capScope: "system",
@@ -87719,6 +87712,20 @@ Object.freeze({
87719
87712
  access: "create",
87720
87713
  role: "admin"
87721
87714
  },
87715
+ "migrations.patchLegacyIntegrationRows": {
87716
+ capName: "migrations",
87717
+ capScope: "system",
87718
+ addonId: null,
87719
+ access: "create",
87720
+ role: "admin"
87721
+ },
87722
+ "migrations.readLegacyIntegrationRows": {
87723
+ capName: "migrations",
87724
+ capScope: "system",
87725
+ addonId: null,
87726
+ access: "view",
87727
+ role: "admin"
87728
+ },
87722
87729
  "migrations.restorePreMigration": {
87723
87730
  capName: "migrations",
87724
87731
  capScope: "system",
@@ -98398,13 +98405,18 @@ var HA_BROKER_KIND = "home-assistant";
98398
98405
  async function listHomeAssistantBrokers(query) {
98399
98406
  return (await query({})).filter((broker) => broker.kind === HA_BROKER_KIND);
98400
98407
  }
98401
- function haInstanceSettingsPortsOver(api) {
98408
+ function refsOfKeys(stored, keys) {
98409
+ const picked = {};
98410
+ for (const key of keys) if (Object.prototype.hasOwnProperty.call(stored, key)) picked[key] = stored[key];
98411
+ return collectSecretMarkerRefs(picked);
98412
+ }
98413
+ function haInstanceSettingsPortsOver(api, secrets = null) {
98402
98414
  const listInstances = async () => {
98403
98415
  const all = await api.list.query();
98404
98416
  const rows = [];
98405
98417
  for (const integration of all) {
98406
98418
  if (integration.addonId !== "provider-homeassistant") continue;
98407
- const settings = await api.getSettings.query({ id: integration.id });
98419
+ const settings = await api.readLegacyIntegrationRows.query({ integrationId: integration.id });
98408
98420
  const brokerId = settings["brokerId"];
98409
98421
  rows.push({
98410
98422
  integrationId: integration.id,
@@ -98414,31 +98426,26 @@ function haInstanceSettingsPortsOver(api) {
98414
98426
  }
98415
98427
  return rows;
98416
98428
  };
98429
+ const owns = async (integrationId) => {
98430
+ return (await api.list.query()).some((i) => i.id === integrationId && i.addonId === "provider-homeassistant");
98431
+ };
98417
98432
  return {
98418
98433
  listInstances,
98419
98434
  patchInstanceSettings: async (integrationId, patch) => {
98420
- if (!(await api.list.query()).some((i) => i.id === integrationId && i.addonId === "provider-homeassistant")) return false;
98421
- const stored = await api.getSettings.query({ id: integrationId });
98422
- await api.setSettings.mutate({
98423
- id: integrationId,
98424
- settings: {
98425
- ...stored,
98426
- ...patch
98427
- },
98428
- skipRestart: true
98429
- });
98430
- return true;
98435
+ if (!await owns(integrationId)) return false;
98436
+ return (await api.patchLegacyIntegrationRows.mutate({
98437
+ integrationId,
98438
+ patch: { ...patch }
98439
+ })).written;
98431
98440
  },
98432
98441
  clearInstanceSettingsKeys: async (integrationId, keys) => {
98433
- if (!(await api.list.query()).some((i) => i.id === integrationId && i.addonId === "provider-homeassistant")) return false;
98434
- const stored = await api.getSettings.query({ id: integrationId });
98435
- const drop = new Set(keys);
98436
- await api.setSettings.mutate({
98437
- id: integrationId,
98438
- settings: Object.fromEntries(Object.entries(stored).filter(([key]) => !drop.has(key))),
98439
- skipRestart: true
98440
- });
98441
- return true;
98442
+ if (!await owns(integrationId)) return false;
98443
+ const refs = refsOfKeys(await api.readLegacyIntegrationRows.query({ integrationId }), keys);
98444
+ if (refs.length > 0 && secrets !== null) await secrets.delete(refs);
98445
+ return (await api.deleteLegacyIntegrationRowKeys.mutate({
98446
+ integrationId,
98447
+ keys
98448
+ })).present;
98442
98449
  }
98443
98450
  };
98444
98451
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@camstack/addon-provider-homeassistant",
3
- "version": "1.2.660",
3
+ "version": "1.2.661",
4
4
  "description": "Home Assistant device provider addon for CamStack",
5
5
  "keywords": [
6
6
  "camstack",
@@ -137,7 +137,7 @@
137
137
  "description": "Device provider (import) + native entity export (push). Two addons, one bundle, separate processes."
138
138
  },
139
139
  "requires": {
140
- "server": ">=1.2.769"
140
+ "server": ">=1.2.770"
141
141
  }
142
142
  },
143
143
  "files": [