UNPKG

@hakit/core

Version:

A collection of React hooks and helpers for Home Assistant to easily communicate with the Home Assistant WebSocket API.

153 lines (152 loc) 5.56 kB
import "lodash"; import "../../utils/light/index.js"; import { computeDomain as f } from "../../utils/computeDomain.js"; import { l as y } from "../../../index-BfdcdUoC.js"; import "../../HassConnect/HassContext.js"; import "react"; import "@iconify/react"; import "use-debounce"; import "home-assistant-js-websocket"; import "../useLocale/locales/index.js"; const g = ["climate", "humidifier", "water_heater"], H = ["climate", "humidifier", "input_datetime", "thermostat", "water_heater", "person", "device_tracker"], _ = [ "temperature", "current_temperature", "target_temp_low", "target_temp_high", "hvac_action", "humidity", "mode", "action", "current_humidity" ], S = (i) => i.substr(i.indexOf(".") + 1), b = (i, s) => s?.friendly_name === void 0 ? S(i).replace(/_/g, " ") : s.friendly_name || "", E = (i) => H.includes(f(i)), L = ({ connection: i, entityIds: s, callbackFunction: n, hoursToShow: e = 24, minimalResponse: t = !0, significantChangesOnly: r = !0, noAttributes: o }) => { const u = { type: "history/stream", entity_ids: s, start_time: new Date((/* @__PURE__ */ new Date()).getTime() - 3600 * e * 1e3).toISOString(), minimal_response: t, significant_changes_only: r, no_attributes: o ?? !s.some((l) => E(l)) }, a = new T(i, e); return i.subscribeMessage((l) => n(a.processMessage(l)), u); }; class T { connection; hoursToShow; combinedHistory; constructor(s, n) { this.connection = s, this.hoursToShow = n, this.combinedHistory = {}; } processMessage(s) { if (!this.combinedHistory || !Object.keys(this.combinedHistory).length) return this.combinedHistory = s.states, this.combinedHistory; if (!Object.keys(s.states).length) return this.combinedHistory; const n = this.hoursToShow ? ((/* @__PURE__ */ new Date()).getTime() - 60 * 60 * this.hoursToShow * 1e3) / 1e3 : void 0, e = {}; for (const t of Object.keys(this.combinedHistory)) e[t] = []; for (const t of Object.keys(s.states)) e[t] = []; for (const t of Object.keys(e)) { if (t in this.combinedHistory && t in s.states) { const r = this.combinedHistory[t], o = r[r.length - 1]; e[t] = r.concat(s.states[t]), s.states[t][0].lu < o.lu && (e[t] = e[t].sort((u, a) => u.lu - a.lu)); } else t in this.combinedHistory ? e[t] = this.combinedHistory[t] : e[t] = s.states[t]; if (n && t in this.combinedHistory) { const r = e[t].filter((u) => u.lu < n); if (!r.length || (e[t] = e[t].filter((u) => u.lu >= n), e[t].length && e[t][0].lu === n)) continue; const o = r[r.length - 1]; o.lu = n, e[t].unshift(o); } } return this.combinedHistory = e, this.combinedHistory; } } const d = (i, s) => i.state === s.state && // Only compare attributes if both states have an attributes object. // When `minimal_response` is sent, only the first and last state // will have attributes except for domains in DOMAINS_USE_LAST_UPDATED. (!i.attributes || !s.attributes || _.every((n) => i.attributes[n] === s.attributes[n])), O = (i, s, n) => { const e = []; return Object.keys(s).forEach((t) => { const r = s[t], o = r[0], u = f(t), a = []; for (const c of r) { let m; if (g.includes(u)) { m = { state: c.s, last_changed: c.lu * 1e3, attributes: {} }; for (const h of _) h in c.a && (m.attributes[h] = c.a[h]); } else m = { state: c.s, // lc (last_changed) may be omitted if its the same // as lu (last_updated). last_changed: (c.lc ? c.lc : c.lu) * 1e3, attributes: {} }; a.length > 1 && d(m, a[a.length - 1]) && d(m, a[a.length - 2]) || a.push(m); } const l = t in n ? n[t].attributes : "friendly_name" in o.a ? o.a : void 0; e.push({ domain: u, name: b(t, l || {}), entity_id: t, states: a }); }), { unit: i, identifier: Object.keys(n).join(""), data: e }; }, w = (i, s, n) => { const e = [], t = s[0]; for (const r of s) e.length > 0 && r.s === e[e.length - 1].state || (n?.attributes.device_class && n?.attributes.device_class, e.push({ state: r.s, // lc (last_changed) may be omitted if its the same // as lu (last_updated). last_changed: (r.lc ? r.lc : r.lu) * 1e3 })); return { name: b(i, n?.attributes || t.a), entity_id: i, data: e }; }, D = (i) => p(i.attributes), p = (i) => "unit_of_measurement" in i || "state_class" in i, P = (i, s, n) => { const e = {}, t = []; return n ? (Object.keys(n).forEach((o) => { const u = n[o]; if (u.length === 0) return; const a = o in s ? s[o] : void 0, l = !a && u.find((m) => m.a && p(m.a)); let c; a && D(a) ? c = a.attributes.unit_of_measurement || " " : l ? c = l.a.unit_of_measurement || " " : c = { zone: y("people_in_zone"), climate: i.unit_system.temperature, counter: "#", humidifier: "%", input_number: "#", number: "#", water_heater: i.unit_system.temperature }[f(o)], c ? c in e && o in e[c] ? e[c][o].push(...u) : (c in e || (e[c] = {}), e[c][o] = u) : t.push(w(o, u, a)); }), { line: Object.keys(e).map((o) => O(o, e[o], s)), timeline: t }) : { line: [], timeline: [] }; }; export { P as computeHistory, S as computeObjectId, b as computeStateNameFromEntityAttributes, E as entityIdHistoryNeedsAttributes, L as subscribeHistory }; //# sourceMappingURL=history.js.map