Skip to content

Commit

Permalink
Load registries in core, wait them to be loaded before generating das… (
Browse files Browse the repository at this point in the history
#19356)

* load registries in core, wait them to be loaded before generating dashboard

* import

* improve

* Split out subscribe functions
  • Loading branch information
bramkragten authored Jan 11, 2024
1 parent b9069b2 commit 03751d2
Show file tree
Hide file tree
Showing 8 changed files with 153 additions and 115 deletions.
44 changes: 2 additions & 42 deletions src/data/area_registry.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
import { Connection, createCollection } from "home-assistant-js-websocket";
import { Store } from "home-assistant-js-websocket/dist/store";
import { stringCompare } from "../common/string/compare";
import { debounce } from "../common/util/debounce";
import { HomeAssistant } from "../types";
import { DeviceRegistryEntry } from "./device_registry";
import { EntityRegistryEntry } from "./entity_registry";

export { subscribeAreaRegistry } from "./ws-area_registry";

export interface AreaRegistryEntry {
area_id: string;
name: string;
Expand Down Expand Up @@ -53,45 +52,6 @@ export const deleteAreaRegistryEntry = (hass: HomeAssistant, areaId: string) =>
area_id: areaId,
});

const fetchAreaRegistry = (conn: Connection) =>
conn
.sendMessagePromise({
type: "config/area_registry/list",
})
.then((areas) =>
(areas as AreaRegistryEntry[]).sort((ent1, ent2) =>
stringCompare(ent1.name, ent2.name)
)
);

const subscribeAreaRegistryUpdates = (
conn: Connection,
store: Store<AreaRegistryEntry[]>
) =>
conn.subscribeEvents(
debounce(
() =>
fetchAreaRegistry(conn).then((areas: AreaRegistryEntry[]) =>
store.setState(areas, true)
),
500,
true
),
"area_registry_updated"
);

export const subscribeAreaRegistry = (
conn: Connection,
onChange: (areas: AreaRegistryEntry[]) => void
) =>
createCollection<AreaRegistryEntry[]>(
"_areaRegistry",
fetchAreaRegistry,
subscribeAreaRegistryUpdates,
conn,
onChange
);

export const getAreaEntityLookup = (
entities: EntityRegistryEntry[]
): AreaEntityLookup => {
Expand Down
41 changes: 5 additions & 36 deletions src/data/device_registry.ts
Original file line number Diff line number Diff line change
@@ -1,15 +1,17 @@
import { Connection, createCollection } from "home-assistant-js-websocket";
import type { Store } from "home-assistant-js-websocket/dist/store";
import { computeStateName } from "../common/entity/compute_state_name";
import { caseInsensitiveStringCompare } from "../common/string/compare";
import { debounce } from "../common/util/debounce";
import type { HomeAssistant } from "../types";
import type {
EntityRegistryDisplayEntry,
EntityRegistryEntry,
} from "./entity_registry";
import type { EntitySources } from "./entity_sources";

export {
fetchDeviceRegistry,
subscribeDeviceRegistry,
} from "./ws-device_registry";

export interface DeviceRegistryEntry {
id: string;
config_entries: string[];
Expand Down Expand Up @@ -96,39 +98,6 @@ export const removeConfigEntryFromDevice = (
config_entry_id: configEntryId,
});

export const fetchDeviceRegistry = (conn: Connection) =>
conn.sendMessagePromise<DeviceRegistryEntry[]>({
type: "config/device_registry/list",
});

const subscribeDeviceRegistryUpdates = (
conn: Connection,
store: Store<DeviceRegistryEntry[]>
) =>
conn.subscribeEvents(
debounce(
() =>
fetchDeviceRegistry(conn).then((devices) =>
store.setState(devices, true)
),
500,
true
),
"device_registry_updated"
);

export const subscribeDeviceRegistry = (
conn: Connection,
onChange: (devices: DeviceRegistryEntry[]) => void
) =>
createCollection<DeviceRegistryEntry[]>(
"_dr",
fetchDeviceRegistry,
subscribeDeviceRegistryUpdates,
conn,
onChange
);

export const sortDeviceRegistryByName = (
entries: DeviceRegistryEntry[],
language: string
Expand Down
32 changes: 3 additions & 29 deletions src/data/entity_registry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import { HomeAssistant } from "../types";
import { LightColor } from "./light";
import { computeDomain } from "../common/entity/compute_domain";

export { subscribeEntityRegistryDisplay } from "./ws-entity_registry_display";

type entityCategory = "config" | "diagnostic";

export interface EntityRegistryDisplayEntry {
Expand All @@ -22,7 +24,7 @@ export interface EntityRegistryDisplayEntry {
display_precision?: number;
}

interface EntityRegistryDisplayEntryResponse {
export interface EntityRegistryDisplayEntryResponse {
entities: {
ei: string;
di?: string;
Expand Down Expand Up @@ -255,34 +257,6 @@ export const subscribeEntityRegistry = (
onChange
);

const subscribeEntityRegistryDisplayUpdates = (
conn: Connection,
store: Store<EntityRegistryDisplayEntryResponse>
) =>
conn.subscribeEvents(
debounce(
() =>
fetchEntityRegistryDisplay(conn).then((entities) =>
store.setState(entities, true)
),
500,
true
),
"entity_registry_updated"
);

export const subscribeEntityRegistryDisplay = (
conn: Connection,
onChange: (entities: EntityRegistryDisplayEntryResponse) => void
) =>
createCollection<EntityRegistryDisplayEntryResponse>(
"_entityRegistryDisplay",
fetchEntityRegistryDisplay,
subscribeEntityRegistryDisplayUpdates,
conn,
onChange
);

export const sortEntityRegistryByName = (
entries: EntityRegistryEntry[],
language: string
Expand Down
44 changes: 44 additions & 0 deletions src/data/ws-area_registry.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import { Connection, createCollection } from "home-assistant-js-websocket";
import { Store } from "home-assistant-js-websocket/dist/store";
import { stringCompare } from "../common/string/compare";
import { AreaRegistryEntry } from "./area_registry";
import { debounce } from "../common/util/debounce";

const fetchAreaRegistry = (conn: Connection) =>
conn
.sendMessagePromise({
type: "config/area_registry/list",
})
.then((areas) =>
(areas as AreaRegistryEntry[]).sort((ent1, ent2) =>
stringCompare(ent1.name, ent2.name)
)
);

const subscribeAreaRegistryUpdates = (
conn: Connection,
store: Store<AreaRegistryEntry[]>
) =>
conn.subscribeEvents(
debounce(
() =>
fetchAreaRegistry(conn).then((areas: AreaRegistryEntry[]) =>
store.setState(areas, true)
),
500,
true
),
"area_registry_updated"
);

export const subscribeAreaRegistry = (
conn: Connection,
onChange: (areas: AreaRegistryEntry[]) => void
) =>
createCollection<AreaRegistryEntry[]>(
"_areaRegistry",
fetchAreaRegistry,
subscribeAreaRegistryUpdates,
conn,
onChange
);
37 changes: 37 additions & 0 deletions src/data/ws-device_registry.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
import { Connection, createCollection } from "home-assistant-js-websocket";
import { Store } from "home-assistant-js-websocket/dist/store";
import { DeviceRegistryEntry } from "./device_registry";
import { debounce } from "../common/util/debounce";

export const fetchDeviceRegistry = (conn: Connection) =>
conn.sendMessagePromise<DeviceRegistryEntry[]>({
type: "config/device_registry/list",
});

const subscribeDeviceRegistryUpdates = (
conn: Connection,
store: Store<DeviceRegistryEntry[]>
) =>
conn.subscribeEvents(
debounce(
() =>
fetchDeviceRegistry(conn).then((devices) =>
store.setState(devices, true)
),
500,
true
),
"device_registry_updated"
);

export const subscribeDeviceRegistry = (
conn: Connection,
onChange: (devices: DeviceRegistryEntry[]) => void
) =>
createCollection<DeviceRegistryEntry[]>(
"_dr",
fetchDeviceRegistry,
subscribeDeviceRegistryUpdates,
conn,
onChange
);
35 changes: 35 additions & 0 deletions src/data/ws-entity_registry_display.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import { Connection, createCollection } from "home-assistant-js-websocket";
import { Store } from "home-assistant-js-websocket/dist/store";
import {
EntityRegistryDisplayEntryResponse,
fetchEntityRegistryDisplay,
} from "./entity_registry";
import { debounce } from "../common/util/debounce";

const subscribeEntityRegistryDisplayUpdates = (
conn: Connection,
store: Store<EntityRegistryDisplayEntryResponse>
) =>
conn.subscribeEvents(
debounce(
() =>
fetchEntityRegistryDisplay(conn).then((entities) =>
store.setState(entities, true)
),
500,
true
),
"entity_registry_updated"
);

export const subscribeEntityRegistryDisplay = (
conn: Connection,
onChange: (entities: EntityRegistryDisplayEntryResponse) => void
) =>
createCollection<EntityRegistryDisplayEntryResponse>(
"_entityRegistryDisplay",
fetchEntityRegistryDisplay,
subscribeEntityRegistryDisplayUpdates,
conn,
onChange
);
14 changes: 10 additions & 4 deletions src/entrypoints/core.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,19 +11,22 @@ import {
import { loadTokens, saveTokens } from "../common/auth/token_storage";
import { hassUrl } from "../data/auth";
import { isExternal } from "../data/external";
import { getRecorderInfo } from "../data/recorder";
import { subscribeFrontendUserData } from "../data/frontend";
import { fetchConfig } from "../data/lovelace/config/types";
import { fetchResources } from "../data/lovelace/resource";
import { MAIN_WINDOW_NAME } from "../data/main_window";
import { WindowWithPreloads } from "../data/preloads";
import { getRecorderInfo } from "../data/recorder";
import { subscribeRepairsIssueRegistry } from "../data/repairs";
import { subscribeAreaRegistry } from "../data/ws-area_registry";
import { subscribeDeviceRegistry } from "../data/ws-device_registry";
import { subscribeEntityRegistryDisplay } from "../data/ws-entity_registry_display";
import { subscribePanels } from "../data/ws-panels";
import { subscribeThemes } from "../data/ws-themes";
import { subscribeRepairsIssueRegistry } from "../data/repairs";
import { subscribeUser } from "../data/ws-user";
import type { ExternalAuth } from "../external_app/external_auth";
import "../resources/array.flat.polyfill";
import "../resources/safari-14-attachshadow-patch";
import { MAIN_WINDOW_NAME } from "../data/main_window";
import { WindowWithPreloads } from "../data/preloads";

window.name = MAIN_WINDOW_NAME;
(window as any).frontendVersion = __VERSION__;
Expand Down Expand Up @@ -113,6 +116,9 @@ window.hassConnection.then(({ conn }) => {
// do nothing
};
subscribeEntities(conn, noop);
subscribeEntityRegistryDisplay(conn, noop);
subscribeDeviceRegistry(conn, noop);
subscribeAreaRegistry(conn, noop);
subscribeConfig(conn, noop);
subscribeServices(conn, noop);
subscribePanels(conn, noop);
Expand Down
21 changes: 17 additions & 4 deletions src/panels/lovelace/ha-panel-lovelace.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import "@material/mwc-button";
import deepFreeze from "deep-freeze";
import { UnsubscribeFunc } from "home-assistant-js-websocket";
import { html, LitElement, TemplateResult } from "lit";
import { html, LitElement, PropertyValues, TemplateResult } from "lit";
import { customElement, property, state } from "lit/decorators";
import { constructUrlCurrentPath } from "../../common/url/construct-url";
import {
Expand Down Expand Up @@ -161,10 +161,15 @@ export class LovelacePanel extends LitElement {
`;
}

protected firstUpdated(changedProps) {
super.firstUpdated(changedProps);
protected willUpdate(changedProps: PropertyValues) {
super.willUpdate(changedProps);
if (!this.lovelace && this._panelState !== "error") {
this._fetchConfig(false);
}
}

this._fetchConfig(false);
protected firstUpdated(changedProps: PropertyValues): void {
super.firstUpdated(changedProps);
if (!this._unsubUpdates) {
this._subscribeUpdates();
}
Expand Down Expand Up @@ -267,6 +272,10 @@ export class LovelacePanel extends LitElement {

// If strategy defined, apply it here.
if (isStrategyDashboard(rawConf)) {
if (!this.hass?.entities || !this.hass.devices || !this.hass.areas) {
// We need these to generate a dashboard, wait for them
return;
}
conf = await generateLovelaceDashboardStrategy(
rawConf.strategy,
this.hass!
Expand All @@ -282,6 +291,10 @@ export class LovelacePanel extends LitElement {
this._errorMsg = err.message;
return;
}
if (!this.hass?.entities || !this.hass.devices || !this.hass.areas) {
// We need these to generate a dashboard, wait for them
return;
}
conf = await generateLovelaceDashboardStrategy(
DEFAULT_CONFIG.strategy,
this.hass!
Expand Down

0 comments on commit 03751d2

Please sign in to comment.