Show which integrations are being setup at startup (#8834)

Co-authored-by: Bram Kragten <mail@bramkragten.nl>
This commit is contained in:
J. Nick Koston 2021-04-08 07:30:47 -10:00 committed by GitHub
parent 7758bd89c1
commit 1127750c5e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 96 additions and 1 deletions

View File

@ -0,0 +1,16 @@
import { HomeAssistant } from "../types";
export type BootstrapIntegrationsTimings = { [key: string]: number };
export const subscribeBootstrapIntegrations = (
hass: HomeAssistant,
callback: (message: BootstrapIntegrationsTimings) => void
) => {
const unsubProm = hass.connection.subscribeMessage<
BootstrapIntegrationsTimings
>((message) => callback(message), {
type: "subscribe_bootstrap_integrations",
});
return unsubProm;
};

View File

@ -2,13 +2,21 @@ import {
STATE_NOT_RUNNING,
STATE_RUNNING,
STATE_STARTING,
UnsubscribeFunc,
} from "home-assistant-js-websocket";
import { Constructor } from "../types";
import { showToast } from "../util/toast";
import { HassBaseEl } from "./hass-base-mixin";
import { domainToName } from "../data/integration";
import {
subscribeBootstrapIntegrations,
BootstrapIntegrationsTimings,
} from "../data/bootstrap_integrations";
export default <T extends Constructor<HassBaseEl>>(superClass: T) =>
class extends superClass {
private _subscribedBootstrapIntegrations?: Promise<UnsubscribeFunc>;
protected firstUpdated(changedProps) {
super.firstUpdated(changedProps);
// Need to load in advance because when disconnected, can't dynamically load code.
@ -35,15 +43,19 @@ export default <T extends Constructor<HassBaseEl>>(superClass: T) =>
action: {
text:
this.hass!.localize("ui.notification_toast.dismiss") || "Dismiss",
action: () => {},
action: () => {
this._unsubscribeBootstrapIntergrations();
},
},
});
this._subscribeBootstrapIntergrations();
} else if (
oldHass?.config &&
oldHass.config.state === STATE_NOT_RUNNING &&
(this.hass!.config.state === STATE_STARTING ||
this.hass!.config.state === STATE_RUNNING)
) {
this._unsubscribeBootstrapIntergrations();
showToast(this, {
message: this.hass!.localize("ui.notification_toast.started"),
duration: 5000,
@ -68,4 +80,69 @@ export default <T extends Constructor<HassBaseEl>>(superClass: T) =>
dismissable: false,
});
}
private _handleMessage(message: BootstrapIntegrationsTimings): void {
if (this.hass!.config.state !== STATE_NOT_RUNNING) {
return;
}
if (Object.keys(message).length === 0) {
showToast(this, {
message:
this.hass!.localize("ui.notification_toast.wrapping_up_startup") ||
`Wrapping up startup, not everything will be available until it is finished.`,
duration: 0,
dismissable: false,
action: {
text:
this.hass!.localize("ui.notification_toast.dismiss") || "Dismiss",
action: () => {},
},
});
return;
}
// Show the integration that has been starting for the longest time
const integration = Object.entries(message).sort(
([, a], [, b]) => b - a
)[0][0];
showToast(this, {
message:
this.hass!.localize(
"ui.notification_toast.intergration_starting",
"integration",
domainToName(this.hass!.localize, integration)
) ||
`Starting ${integration}, not everything will be available until it is finished.`,
duration: 0,
dismissable: false,
action: {
text:
this.hass!.localize("ui.notification_toast.dismiss") || "Dismiss",
action: () => {
this._unsubscribeBootstrapIntergrations();
},
},
});
}
private _unsubscribeBootstrapIntergrations() {
if (this._subscribedBootstrapIntegrations) {
this._subscribedBootstrapIntegrations.then((unsub) => unsub());
this._subscribedBootstrapIntegrations = undefined;
}
}
private _subscribeBootstrapIntergrations() {
if (!this.hass) {
return;
}
this._subscribedBootstrapIntegrations = subscribeBootstrapIntegrations(
this.hass!,
(message) => {
this._handleMessage(message);
}
);
}
};

View File

@ -850,6 +850,8 @@
"connection_lost": "Connection lost. Reconnecting…",
"started": "Home Assistant has started!",
"starting": "Home Assistant is starting, not everything will be available until it is finished.",
"wrapping_up_startup": "Wrapping up startup, not everything will be available until it is finished.",
"intergration_starting": "Starting {integration}, not everything will be available until it is finished.",
"triggered": "Triggered {name}",
"dismiss": "Dismiss"
},