@camstack/addon-provider-homeassistant 1.2.166 → 1.2.170

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/dist/addon.js CHANGED
@@ -1,5 +1,5 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_dist = require("./dist-BKSNuxYV.js");
2
+ const require_dist = require("./dist-B7c8ebLd.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
@@ -7363,14 +7363,20 @@ async function fetchEventsForEntities(manager, entityIds, startIso, endIso) {
7363
7363
  }
7364
7364
  return out;
7365
7365
  }
7366
+ /** Empty selection = import nothing (operator must pick calendars explicitly). */
7367
+ function isSelected(entityId, selected) {
7368
+ return selected.size > 0 && selected.has(entityId);
7369
+ }
7366
7370
  function createHaCalendarSource(deps) {
7367
7371
  return {
7368
7372
  listCalendars: async () => {
7373
+ const selected = deps.selectedCalendarIds();
7369
7374
  const out = [];
7370
7375
  for (const { manager } of deps.brokers.listManagers()) {
7371
7376
  const states = manager.snapshotAllStates();
7372
7377
  for (const [entityId, raw] of Object.entries(states)) {
7373
7378
  if (!isCalendarEntity(entityId)) continue;
7379
+ if (!isSelected(entityId, selected)) continue;
7374
7380
  const state = asEntityState(raw);
7375
7381
  if (state === null) continue;
7376
7382
  out.push({
@@ -7386,11 +7392,16 @@ function createHaCalendarSource(deps) {
7386
7392
  listEvents: async (input) => {
7387
7393
  const startIso = new Date(input.startMs).toISOString();
7388
7394
  const endIso = new Date(input.endMs).toISOString();
7395
+ const selected = deps.selectedCalendarIds();
7389
7396
  const wanted = input.calendarIds !== void 0 && input.calendarIds.length > 0 ? new Set(input.calendarIds) : null;
7390
7397
  const out = [];
7391
7398
  for (const { brokerId, manager } of deps.brokers.listManagers()) {
7392
7399
  const states = manager.snapshotAllStates();
7393
- const entityIds = Object.keys(states).filter((id) => isCalendarEntity(id) && (wanted === null || wanted.has(id)));
7400
+ const entityIds = Object.keys(states).filter((id) => {
7401
+ if (!isCalendarEntity(id)) return false;
7402
+ if (!isSelected(id, selected)) return false;
7403
+ return wanted === null || wanted.has(id);
7404
+ });
7394
7405
  if (entityIds.length === 0) continue;
7395
7406
  try {
7396
7407
  const events = await fetchEventsForEntities(manager, entityIds, startIso, endIso);
@@ -7407,6 +7418,25 @@ function createHaCalendarSource(deps) {
7407
7418
  }
7408
7419
  };
7409
7420
  }
7421
+ /** Discover every HA calendar entity (ignores the import filter) — for settings catalog. */
7422
+ function listHaCalendarCatalog(brokers) {
7423
+ const out = [];
7424
+ const seen = /* @__PURE__ */ new Set();
7425
+ for (const { manager } of brokers.listManagers()) {
7426
+ const states = manager.snapshotAllStates();
7427
+ for (const [entityId, raw] of Object.entries(states)) {
7428
+ if (!isCalendarEntity(entityId) || seen.has(entityId)) continue;
7429
+ const state = asEntityState(raw);
7430
+ if (state === null) continue;
7431
+ seen.add(entityId);
7432
+ out.push({
7433
+ value: entityId,
7434
+ label: calendarName(state)
7435
+ });
7436
+ }
7437
+ }
7438
+ return out.toSorted((a, b) => a.label.localeCompare(b.label));
7439
+ }
7410
7440
  //#endregion
7411
7441
  //#region src/ha-reconcile-broker.ts
7412
7442
  /**
@@ -7841,7 +7871,10 @@ function planStandaloneReconcile(devices, freshById, brokerId) {
7841
7871
  var ADOPTION_FILTER_DEVICES = "devices";
7842
7872
  var ADOPTION_FILTER_ENTITIES = "entities";
7843
7873
  var HA_KIND = "home-assistant";
7844
- var DEFAULT_CONFIG = { brokers: [] };
7874
+ var DEFAULT_CONFIG = {
7875
+ brokers: [],
7876
+ calendarIds: []
7877
+ };
7845
7878
  /**
7846
7879
  * Home Assistant provider addon.
7847
7880
  *
@@ -7938,7 +7971,8 @@ var HaProviderAddon = class HaProviderAddon extends require_dist.BaseDeviceProvi
7938
7971
  capability: require_dist.calendarSourceCapability,
7939
7972
  provider: createHaCalendarSource({
7940
7973
  brokers: this.requireRegistry(),
7941
- logger: this.ctx.logger.child("calendar-source")
7974
+ logger: this.ctx.logger.child("calendar-source"),
7975
+ selectedCalendarIds: () => new Set(this.config.calendarIds ?? [])
7942
7976
  })
7943
7977
  }
7944
7978
  ];
@@ -8065,20 +8099,43 @@ var HaProviderAddon = class HaProviderAddon extends require_dist.BaseDeviceProvi
8065
8099
  eb.subscribe({ category: "integration.disabled" }, handler);
8066
8100
  eb.subscribe({ category: "integration.deleted" }, handler);
8067
8101
  }
8068
- globalSettingsSchema() {
8102
+ globalSettingsSchema(cap) {
8103
+ if (cap === "calendar-source") return this.schema({ sections: [{
8104
+ id: "ha-calendars-import",
8105
+ title: "Calendars to import",
8106
+ description: "Pick which Home Assistant calendar entities feed System → Calendars. Nothing selected = no calendars imported.",
8107
+ columns: 1,
8108
+ fields: [{
8109
+ type: "multiselect",
8110
+ key: "calendarIds",
8111
+ label: "Calendars",
8112
+ options: [],
8113
+ optionsFrom: "_calendarCatalog",
8114
+ description: "Discovered from connected HA brokers. Select at least one to import; leave empty to import none."
8115
+ }]
8116
+ }] });
8069
8117
  return this.schema({ sections: [{
8070
8118
  id: "ha-broker",
8071
8119
  title: "Home Assistant broker",
8072
- description: "Home Assistant brokers are managed in the External systems → Brokers tab.",
8120
+ description: "Home Assistant brokers are managed in Connectivity → Brokers.",
8073
8121
  columns: 1,
8074
8122
  fields: [{
8075
8123
  type: "info",
8076
8124
  key: "brokerHelp",
8077
8125
  label: "Brokers are managed separately",
8078
- content: "This integration links to a Home Assistant broker. Add, edit, or remove brokers from External systems → Brokers. The integration only stores a reference to its broker — no credentials are kept here."
8126
+ content: "This integration links to a Home Assistant broker. Add, edit, or remove brokers from Connectivity → Brokers. The integration only stores a reference to its broker — no credentials are kept here."
8079
8127
  }]
8080
8128
  }] });
8081
8129
  }
8130
+ async getGlobalSettings(overlay, cap, nodeId) {
8131
+ if (cap !== "calendar-source") return super.getGlobalSettings(overlay, cap, nodeId);
8132
+ const catalog = this.registry ? listHaCalendarCatalog(this.registry) : [];
8133
+ return super.getGlobalSettings({
8134
+ ...overlay,
8135
+ calendarIds: this.config.calendarIds ?? [],
8136
+ ...catalog.length > 0 ? { _calendarCatalog: catalog } : {}
8137
+ }, cap, nodeId);
8138
+ }
8082
8139
  async onShutdown() {
8083
8140
  if (this.resyncTimer) {
8084
8141
  clearInterval(this.resyncTimer);
@@ -8185,7 +8242,7 @@ var HaProviderAddon = class HaProviderAddon extends require_dist.BaseDeviceProvi
8185
8242
  }],
8186
8243
  add: async ({ kind, name, settings, id }) => {
8187
8244
  if (kind !== HA_KIND) throw new Error(`provider-homeassistant: only kind '${HA_KIND}' is handled here (got '${kind}')`);
8188
- const entry = await this.requireRegistry().createEntry(name, settings, { ...id !== void 0 ? { id } : {} });
8245
+ const entry = await this.requireRegistry().createEntry(name, settings, id !== void 0 ? { id } : {});
8189
8246
  if (id !== void 0) this.ctx.logger.info("broker restored under an adopted id", { meta: {
8190
8247
  brokerId: entry.id,
8191
8248
  name
package/dist/addon.mjs CHANGED
@@ -1,4 +1,4 @@
1
- import { A as connectivityCapability, At as record, B as floodCapability, C as buildAddonRouteProvider, Ct as _enum, D as carbonMonoxideCapability, Dt as literal, E as calendarSourceCapability, Et as discriminatedUnion, F as deviceAdoptionCapability, Ft as EventCategory, G as lawnMowerControlCapability, H as humidifierCapability, J as motionCapability, K as lockControlCapability, L as enumSensorCapability, M as controlCapability, Mt as union, N as coverCapability, Nt as unknown, O as climateControlCapability, Ot as number, P as deviceAdminLinkCapability, Pt as url, Q as numericSensorCapability, R as eventEmitterCapability, S as brokerCapability, T as buttonCapability, Tt as boolean, U as humiditySensorCapability, V as gasCapability, W as imageCapability, X as notificationOutputCapability, Y as normalizeUnit, Z as notifierCapability, _ as automationControlCapability, _t as DeviceRole, at as scriptRunnerCapability, b as binaryCapability, ct as tamperCapability, d as TargetSchema, dt as vacuumControlCapability, et as parseAdminBase, f as accessoriesCapability, ft as valveCapability, g as ambientLightSensorCapability, gt as DeviceFeature, h as alarmPanelCapability, ht as weatherCapability, it as pressureSensorCapability, j as contactCapability, jt as string, k as colorCapability, kt as object, lt as temperatureSensorCapability, m as airQualitySensorCapability, mt as waterHeaterCapability, n as BaseDevice, nt as prepareNotification, ot as smokeCapability, p as addonRoutesCapability, pt as vibrationCapability, q as mediaPlayerCapability, r as BaseDeviceProvider, rt as presenceCapability, s as EnumSensorDateTimeFormatSchema, st as switchCapability, tt as powerMeterCapability, ut as updateCapability, v as batteryCapability, vt as DeviceType, w as buildDeviceAdminUrl, wt as array, x as brightnessCapability, xt as createEvent, y as bestLocationMatch, yt as errMsg, z as fanControlCapability } from "./dist-CkOgR9ep.mjs";
1
+ import { A as connectivityCapability, At as record, B as floodCapability, C as buildAddonRouteProvider, Ct as _enum, D as carbonMonoxideCapability, Dt as literal, E as calendarSourceCapability, Et as discriminatedUnion, F as deviceAdoptionCapability, Ft as EventCategory, G as lawnMowerControlCapability, H as humidifierCapability, J as motionCapability, K as lockControlCapability, L as enumSensorCapability, M as controlCapability, Mt as union, N as coverCapability, Nt as unknown, O as climateControlCapability, Ot as number, P as deviceAdminLinkCapability, Pt as url, Q as numericSensorCapability, R as eventEmitterCapability, S as brokerCapability, T as buttonCapability, Tt as boolean, U as humiditySensorCapability, V as gasCapability, W as imageCapability, X as notificationOutputCapability, Y as normalizeUnit, Z as notifierCapability, _ as automationControlCapability, _t as DeviceRole, at as scriptRunnerCapability, b as binaryCapability, ct as tamperCapability, d as TargetSchema, dt as vacuumControlCapability, et as parseAdminBase, f as accessoriesCapability, ft as valveCapability, g as ambientLightSensorCapability, gt as DeviceFeature, h as alarmPanelCapability, ht as weatherCapability, it as pressureSensorCapability, j as contactCapability, jt as string, k as colorCapability, kt as object, lt as temperatureSensorCapability, m as airQualitySensorCapability, mt as waterHeaterCapability, n as BaseDevice, nt as prepareNotification, ot as smokeCapability, p as addonRoutesCapability, pt as vibrationCapability, q as mediaPlayerCapability, r as BaseDeviceProvider, rt as presenceCapability, s as EnumSensorDateTimeFormatSchema, st as switchCapability, tt as powerMeterCapability, ut as updateCapability, v as batteryCapability, vt as DeviceType, w as buildDeviceAdminUrl, wt as array, x as brightnessCapability, xt as createEvent, y as bestLocationMatch, yt as errMsg, z as fanControlCapability } from "./dist-BaG2A4xn.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
@@ -7362,14 +7362,20 @@ async function fetchEventsForEntities(manager, entityIds, startIso, endIso) {
7362
7362
  }
7363
7363
  return out;
7364
7364
  }
7365
+ /** Empty selection = import nothing (operator must pick calendars explicitly). */
7366
+ function isSelected(entityId, selected) {
7367
+ return selected.size > 0 && selected.has(entityId);
7368
+ }
7365
7369
  function createHaCalendarSource(deps) {
7366
7370
  return {
7367
7371
  listCalendars: async () => {
7372
+ const selected = deps.selectedCalendarIds();
7368
7373
  const out = [];
7369
7374
  for (const { manager } of deps.brokers.listManagers()) {
7370
7375
  const states = manager.snapshotAllStates();
7371
7376
  for (const [entityId, raw] of Object.entries(states)) {
7372
7377
  if (!isCalendarEntity(entityId)) continue;
7378
+ if (!isSelected(entityId, selected)) continue;
7373
7379
  const state = asEntityState(raw);
7374
7380
  if (state === null) continue;
7375
7381
  out.push({
@@ -7385,11 +7391,16 @@ function createHaCalendarSource(deps) {
7385
7391
  listEvents: async (input) => {
7386
7392
  const startIso = new Date(input.startMs).toISOString();
7387
7393
  const endIso = new Date(input.endMs).toISOString();
7394
+ const selected = deps.selectedCalendarIds();
7388
7395
  const wanted = input.calendarIds !== void 0 && input.calendarIds.length > 0 ? new Set(input.calendarIds) : null;
7389
7396
  const out = [];
7390
7397
  for (const { brokerId, manager } of deps.brokers.listManagers()) {
7391
7398
  const states = manager.snapshotAllStates();
7392
- const entityIds = Object.keys(states).filter((id) => isCalendarEntity(id) && (wanted === null || wanted.has(id)));
7399
+ const entityIds = Object.keys(states).filter((id) => {
7400
+ if (!isCalendarEntity(id)) return false;
7401
+ if (!isSelected(id, selected)) return false;
7402
+ return wanted === null || wanted.has(id);
7403
+ });
7393
7404
  if (entityIds.length === 0) continue;
7394
7405
  try {
7395
7406
  const events = await fetchEventsForEntities(manager, entityIds, startIso, endIso);
@@ -7406,6 +7417,25 @@ function createHaCalendarSource(deps) {
7406
7417
  }
7407
7418
  };
7408
7419
  }
7420
+ /** Discover every HA calendar entity (ignores the import filter) — for settings catalog. */
7421
+ function listHaCalendarCatalog(brokers) {
7422
+ const out = [];
7423
+ const seen = /* @__PURE__ */ new Set();
7424
+ for (const { manager } of brokers.listManagers()) {
7425
+ const states = manager.snapshotAllStates();
7426
+ for (const [entityId, raw] of Object.entries(states)) {
7427
+ if (!isCalendarEntity(entityId) || seen.has(entityId)) continue;
7428
+ const state = asEntityState(raw);
7429
+ if (state === null) continue;
7430
+ seen.add(entityId);
7431
+ out.push({
7432
+ value: entityId,
7433
+ label: calendarName(state)
7434
+ });
7435
+ }
7436
+ }
7437
+ return out.toSorted((a, b) => a.label.localeCompare(b.label));
7438
+ }
7409
7439
  //#endregion
7410
7440
  //#region src/ha-reconcile-broker.ts
7411
7441
  /**
@@ -7840,7 +7870,10 @@ function planStandaloneReconcile(devices, freshById, brokerId) {
7840
7870
  var ADOPTION_FILTER_DEVICES = "devices";
7841
7871
  var ADOPTION_FILTER_ENTITIES = "entities";
7842
7872
  var HA_KIND = "home-assistant";
7843
- var DEFAULT_CONFIG = { brokers: [] };
7873
+ var DEFAULT_CONFIG = {
7874
+ brokers: [],
7875
+ calendarIds: []
7876
+ };
7844
7877
  /**
7845
7878
  * Home Assistant provider addon.
7846
7879
  *
@@ -7937,7 +7970,8 @@ var HaProviderAddon = class HaProviderAddon extends BaseDeviceProvider {
7937
7970
  capability: calendarSourceCapability,
7938
7971
  provider: createHaCalendarSource({
7939
7972
  brokers: this.requireRegistry(),
7940
- logger: this.ctx.logger.child("calendar-source")
7973
+ logger: this.ctx.logger.child("calendar-source"),
7974
+ selectedCalendarIds: () => new Set(this.config.calendarIds ?? [])
7941
7975
  })
7942
7976
  }
7943
7977
  ];
@@ -8064,20 +8098,43 @@ var HaProviderAddon = class HaProviderAddon extends BaseDeviceProvider {
8064
8098
  eb.subscribe({ category: "integration.disabled" }, handler);
8065
8099
  eb.subscribe({ category: "integration.deleted" }, handler);
8066
8100
  }
8067
- globalSettingsSchema() {
8101
+ globalSettingsSchema(cap) {
8102
+ if (cap === "calendar-source") return this.schema({ sections: [{
8103
+ id: "ha-calendars-import",
8104
+ title: "Calendars to import",
8105
+ description: "Pick which Home Assistant calendar entities feed System → Calendars. Nothing selected = no calendars imported.",
8106
+ columns: 1,
8107
+ fields: [{
8108
+ type: "multiselect",
8109
+ key: "calendarIds",
8110
+ label: "Calendars",
8111
+ options: [],
8112
+ optionsFrom: "_calendarCatalog",
8113
+ description: "Discovered from connected HA brokers. Select at least one to import; leave empty to import none."
8114
+ }]
8115
+ }] });
8068
8116
  return this.schema({ sections: [{
8069
8117
  id: "ha-broker",
8070
8118
  title: "Home Assistant broker",
8071
- description: "Home Assistant brokers are managed in the External systems → Brokers tab.",
8119
+ description: "Home Assistant brokers are managed in Connectivity → Brokers.",
8072
8120
  columns: 1,
8073
8121
  fields: [{
8074
8122
  type: "info",
8075
8123
  key: "brokerHelp",
8076
8124
  label: "Brokers are managed separately",
8077
- content: "This integration links to a Home Assistant broker. Add, edit, or remove brokers from External systems → Brokers. The integration only stores a reference to its broker — no credentials are kept here."
8125
+ content: "This integration links to a Home Assistant broker. Add, edit, or remove brokers from Connectivity → Brokers. The integration only stores a reference to its broker — no credentials are kept here."
8078
8126
  }]
8079
8127
  }] });
8080
8128
  }
8129
+ async getGlobalSettings(overlay, cap, nodeId) {
8130
+ if (cap !== "calendar-source") return super.getGlobalSettings(overlay, cap, nodeId);
8131
+ const catalog = this.registry ? listHaCalendarCatalog(this.registry) : [];
8132
+ return super.getGlobalSettings({
8133
+ ...overlay,
8134
+ calendarIds: this.config.calendarIds ?? [],
8135
+ ...catalog.length > 0 ? { _calendarCatalog: catalog } : {}
8136
+ }, cap, nodeId);
8137
+ }
8081
8138
  async onShutdown() {
8082
8139
  if (this.resyncTimer) {
8083
8140
  clearInterval(this.resyncTimer);
@@ -8184,7 +8241,7 @@ var HaProviderAddon = class HaProviderAddon extends BaseDeviceProvider {
8184
8241
  }],
8185
8242
  add: async ({ kind, name, settings, id }) => {
8186
8243
  if (kind !== HA_KIND) throw new Error(`provider-homeassistant: only kind '${HA_KIND}' is handled here (got '${kind}')`);
8187
- const entry = await this.requireRegistry().createEntry(name, settings, { ...id !== void 0 ? { id } : {} });
8244
+ const entry = await this.requireRegistry().createEntry(name, settings, id !== void 0 ? { id } : {});
8188
8245
  if (id !== void 0) this.ctx.logger.info("broker restored under an adopted id", { meta: {
8189
8246
  brokerId: entry.id,
8190
8247
  name