mirror of
https://github.com/home-assistant/frontend.git
synced 2025-11-05 17:09:48 +00:00
Improve onboarding backup restore (#23340)
* Improve onboarding backup restore * Fix onboarding backup restore * Fix restoring value in onboarding-restore-backup
This commit is contained in:
@@ -8,9 +8,11 @@ import { atLeastVersion } from "../../../../src/common/config/version";
|
||||
import { fireEvent } from "../../../../src/common/dom/fire_event";
|
||||
import { stopPropagation } from "../../../../src/common/dom/stop_propagation";
|
||||
import { slugify } from "../../../../src/common/string/slugify";
|
||||
import "../../../../src/components/ha-dialog";
|
||||
import "../../../../src/components/ha-md-dialog";
|
||||
import "../../../../src/components/ha-dialog-header";
|
||||
import "../../../../src/components/buttons/ha-progress-button";
|
||||
import "../../../../src/components/ha-alert";
|
||||
import "../../../../src/components/ha-button";
|
||||
import "../../../../src/components/ha-button-menu";
|
||||
import "../../../../src/components/ha-header-bar";
|
||||
import "../../../../src/components/ha-icon-button";
|
||||
@@ -19,6 +21,7 @@ import type { HassioBackupDetail } from "../../../../src/data/hassio/backup";
|
||||
import {
|
||||
fetchHassioBackupInfo,
|
||||
removeBackup,
|
||||
restoreBackup,
|
||||
} from "../../../../src/data/hassio/backup";
|
||||
import { extractApiErrorMessage } from "../../../../src/data/hassio/common";
|
||||
import {
|
||||
@@ -33,6 +36,7 @@ import "../../components/supervisor-backup-content";
|
||||
import type { SupervisorBackupContent } from "../../components/supervisor-backup-content";
|
||||
import type { HassioBackupDialogParams } from "./show-dialog-hassio-backup";
|
||||
import type { BackupOrRestoreKey } from "../../util/translations";
|
||||
import type { HaMdDialog } from "../../../../src/components/ha-md-dialog";
|
||||
|
||||
@customElement("dialog-hassio-backup")
|
||||
class HassioBackupDialog
|
||||
@@ -52,13 +56,20 @@ class HassioBackupDialog
|
||||
@query("supervisor-backup-content")
|
||||
private _backupContent!: SupervisorBackupContent;
|
||||
|
||||
@query("ha-md-dialog") private _dialog?: HaMdDialog;
|
||||
|
||||
public async showDialog(dialogParams: HassioBackupDialogParams) {
|
||||
this._backup = await fetchHassioBackupInfo(this.hass, dialogParams.slug);
|
||||
this._dialogParams = dialogParams;
|
||||
this._backup = await fetchHassioBackupInfo(this.hass, dialogParams.slug);
|
||||
if (!this._backup) {
|
||||
this._error = this._localize("no_backup_found");
|
||||
} else if (this._dialogParams.onboarding && !this._backup.homeassistant) {
|
||||
this._error = this._localize("restore_no_home_assistant");
|
||||
}
|
||||
this._restoringBackup = false;
|
||||
}
|
||||
|
||||
public closeDialog() {
|
||||
private _dialogClosed(): void {
|
||||
this._backup = undefined;
|
||||
this._dialogParams = undefined;
|
||||
this._restoringBackup = false;
|
||||
@@ -66,6 +77,10 @@ class HassioBackupDialog
|
||||
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
||||
}
|
||||
|
||||
public closeDialog(): void {
|
||||
this._dialog?.close();
|
||||
}
|
||||
|
||||
private _localize(key: BackupOrRestoreKey) {
|
||||
return (
|
||||
this._dialogParams!.supervisor?.localize(`backup.${key}`) ||
|
||||
@@ -78,100 +93,80 @@ class HassioBackupDialog
|
||||
return nothing;
|
||||
}
|
||||
return html`
|
||||
<ha-dialog
|
||||
<ha-md-dialog
|
||||
open
|
||||
scrimClickAction
|
||||
@closed=${this.closeDialog}
|
||||
.heading=${this._backup.name}
|
||||
.disableCancelAction=${!this._error}
|
||||
@closed=${this._dialogClosed}
|
||||
>
|
||||
<div slot="heading">
|
||||
<ha-header-bar>
|
||||
<span slot="title">${this._backup.name}</span>
|
||||
<ha-icon-button
|
||||
.label=${this._localize("close")}
|
||||
.path=${mdiClose}
|
||||
slot="actionItems"
|
||||
dialogAction="cancel"
|
||||
></ha-icon-button>
|
||||
</ha-header-bar>
|
||||
<ha-dialog-header slot="headline">
|
||||
<ha-icon-button
|
||||
slot="navigationIcon"
|
||||
.label=${this._localize("close")}
|
||||
.path=${mdiClose}
|
||||
@click=${this.closeDialog}
|
||||
.disabled=${this._restoringBackup}
|
||||
></ha-icon-button>
|
||||
<span slot="title" .title=${this._backup.name}
|
||||
>${this._backup.name}</span
|
||||
>
|
||||
${!this._dialogParams.onboarding && this._dialogParams.supervisor
|
||||
? html`<ha-button-menu
|
||||
slot="actionItems"
|
||||
fixed
|
||||
@action=${this._handleMenuAction}
|
||||
@closed=${stopPropagation}
|
||||
>
|
||||
<ha-icon-button
|
||||
.label=${this._dialogParams.supervisor.localize(
|
||||
"backup.more_actions"
|
||||
)}
|
||||
.path=${mdiDotsVertical}
|
||||
slot="trigger"
|
||||
></ha-icon-button>
|
||||
<mwc-list-item
|
||||
>${this._dialogParams.supervisor.localize(
|
||||
"backup.download_backup"
|
||||
)}</mwc-list-item
|
||||
>
|
||||
<mwc-list-item class="error"
|
||||
>${this._dialogParams.supervisor.localize(
|
||||
"backup.delete_backup_title"
|
||||
)}</mwc-list-item
|
||||
>
|
||||
</ha-button-menu>`
|
||||
: nothing}
|
||||
</ha-dialog-header>
|
||||
<div slot="content">
|
||||
${this._error
|
||||
? html`<ha-alert alert-type="error">${this._error}</ha-alert>`
|
||||
: this._restoringBackup
|
||||
? html`<div class="loading">
|
||||
<ha-circular-progress indeterminate></ha-circular-progress>
|
||||
</div>`
|
||||
: html`
|
||||
<supervisor-backup-content
|
||||
.hass=${this.hass}
|
||||
.supervisor=${this._dialogParams.supervisor}
|
||||
.backup=${this._backup}
|
||||
.onboarding=${this._dialogParams.onboarding || false}
|
||||
.localize=${this._dialogParams.localize}
|
||||
dialogInitialFocus
|
||||
>
|
||||
</supervisor-backup-content>
|
||||
`}
|
||||
</div>
|
||||
${this._restoringBackup
|
||||
? html`<ha-circular-progress indeterminate></ha-circular-progress>`
|
||||
: html`
|
||||
<supervisor-backup-content
|
||||
.hass=${this.hass}
|
||||
.supervisor=${this._dialogParams.supervisor}
|
||||
.backup=${this._backup}
|
||||
.onboarding=${this._dialogParams.onboarding || false}
|
||||
.localize=${this._dialogParams.localize}
|
||||
dialogInitialFocus
|
||||
>
|
||||
</supervisor-backup-content>
|
||||
`}
|
||||
${this._error
|
||||
? html`<ha-alert alert-type="error">${this._error}</ha-alert>`
|
||||
: nothing}
|
||||
|
||||
<mwc-button
|
||||
.disabled=${this._restoringBackup}
|
||||
slot="secondaryAction"
|
||||
@click=${this._restoreClicked}
|
||||
>
|
||||
${this._localize("restore")}
|
||||
</mwc-button>
|
||||
|
||||
${!this._dialogParams.onboarding && this._dialogParams.supervisor
|
||||
? html`<ha-button-menu
|
||||
fixed
|
||||
slot="primaryAction"
|
||||
@action=${this._handleMenuAction}
|
||||
@closed=${stopPropagation}
|
||||
>
|
||||
<ha-icon-button
|
||||
.label=${this._dialogParams.supervisor.localize(
|
||||
"backup.more_actions"
|
||||
)}
|
||||
.path=${mdiDotsVertical}
|
||||
slot="trigger"
|
||||
></ha-icon-button>
|
||||
<mwc-list-item
|
||||
>${this._dialogParams.supervisor.localize(
|
||||
"backup.download_backup"
|
||||
)}</mwc-list-item
|
||||
>
|
||||
<mwc-list-item class="error"
|
||||
>${this._dialogParams.supervisor.localize(
|
||||
"backup.delete_backup_title"
|
||||
)}</mwc-list-item
|
||||
>
|
||||
</ha-button-menu>`
|
||||
: nothing}
|
||||
</ha-dialog>
|
||||
<div slot="actions">
|
||||
<ha-button
|
||||
.disabled=${this._restoringBackup || !!this._error}
|
||||
@click=${this._restoreClicked}
|
||||
>
|
||||
${this._localize("restore")}
|
||||
</ha-button>
|
||||
</div>
|
||||
</ha-md-dialog>
|
||||
`;
|
||||
}
|
||||
|
||||
static get styles(): CSSResultGroup {
|
||||
return [
|
||||
haStyle,
|
||||
haStyleDialog,
|
||||
css`
|
||||
ha-circular-progress {
|
||||
display: block;
|
||||
text-align: center;
|
||||
}
|
||||
ha-header-bar {
|
||||
--mdc-theme-on-primary: var(--primary-text-color);
|
||||
--mdc-theme-primary: var(--mdc-theme-surface);
|
||||
flex-shrink: 0;
|
||||
display: block;
|
||||
}
|
||||
ha-icon-button {
|
||||
color: var(--secondary-text-color);
|
||||
}
|
||||
`,
|
||||
];
|
||||
}
|
||||
|
||||
private _handleMenuAction(ev: CustomEvent<ActionDetail>) {
|
||||
switch (ev.detail.index) {
|
||||
case 0:
|
||||
@@ -184,18 +179,9 @@ class HassioBackupDialog
|
||||
}
|
||||
|
||||
private async _restoreClicked() {
|
||||
const backupDetails = this._backupContent.backupDetails();
|
||||
this._restoringBackup = true;
|
||||
this._dialogParams?.onRestoring?.();
|
||||
if (this._backupContent.backupType === "full") {
|
||||
await this._fullRestoreClicked(backupDetails);
|
||||
} else {
|
||||
await this._partialRestoreClicked(backupDetails);
|
||||
}
|
||||
this._restoringBackup = false;
|
||||
}
|
||||
const backupDetails = this._backupContent.backupDetails();
|
||||
|
||||
private async _partialRestoreClicked(backupDetails) {
|
||||
const supervisor = this._dialogParams?.supervisor;
|
||||
if (supervisor !== undefined && supervisor.info.state !== "running") {
|
||||
await showAlertDialog(this, {
|
||||
@@ -204,91 +190,45 @@ class HassioBackupDialog
|
||||
state: supervisor.info.state,
|
||||
}),
|
||||
});
|
||||
this._restoringBackup = false;
|
||||
return;
|
||||
}
|
||||
if (
|
||||
!(await showConfirmationDialog(this, {
|
||||
title: this._localize("confirm_restore_partial_backup_title"),
|
||||
text: this._localize("confirm_restore_partial_backup_text"),
|
||||
title: this._localize(
|
||||
this._backupContent.backupType === "full"
|
||||
? "confirm_restore_full_backup_title"
|
||||
: "confirm_restore_partial_backup_title"
|
||||
),
|
||||
text: this._localize(
|
||||
this._backupContent.backupType === "full"
|
||||
? "confirm_restore_full_backup_text"
|
||||
: "confirm_restore_partial_backup_text"
|
||||
),
|
||||
confirmText: this._localize("restore"),
|
||||
dismissText: this._localize("cancel"),
|
||||
}))
|
||||
) {
|
||||
this._restoringBackup = false;
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this._dialogParams?.onboarding) {
|
||||
try {
|
||||
await this.hass!.callApi(
|
||||
"POST",
|
||||
|
||||
`hassio/${
|
||||
atLeastVersion(this.hass!.config.version, 2021, 9)
|
||||
? "backups"
|
||||
: "snapshots"
|
||||
}/${this._backup!.slug}/restore/partial`,
|
||||
backupDetails
|
||||
);
|
||||
this.closeDialog();
|
||||
} catch (error: any) {
|
||||
this._error = error.body.message;
|
||||
}
|
||||
} else {
|
||||
this._dialogParams?.onRestoring?.();
|
||||
await fetch(`/api/hassio/backups/${this._backup!.slug}/restore/partial`, {
|
||||
method: "POST",
|
||||
body: JSON.stringify(backupDetails),
|
||||
});
|
||||
this.closeDialog();
|
||||
}
|
||||
}
|
||||
|
||||
private async _fullRestoreClicked(backupDetails) {
|
||||
const supervisor = this._dialogParams?.supervisor;
|
||||
if (supervisor !== undefined && supervisor.info.state !== "running") {
|
||||
await showAlertDialog(this, {
|
||||
title: supervisor.localize("backup.could_not_restore"),
|
||||
text: supervisor.localize("backup.restore_blocked_not_running", {
|
||||
state: supervisor.info.state,
|
||||
}),
|
||||
});
|
||||
return;
|
||||
}
|
||||
if (
|
||||
!(await showConfirmationDialog(this, {
|
||||
title: this._localize("confirm_restore_full_backup_title"),
|
||||
text: this._localize("confirm_restore_full_backup_text"),
|
||||
confirmText: this._localize("restore"),
|
||||
dismissText: this._localize("cancel"),
|
||||
}))
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this._dialogParams?.onboarding) {
|
||||
this.hass!.callApi(
|
||||
"POST",
|
||||
`hassio/${
|
||||
atLeastVersion(this.hass!.config.version, 2021, 9)
|
||||
? "backups"
|
||||
: "snapshots"
|
||||
}/${this._backup!.slug}/restore/full`,
|
||||
backupDetails
|
||||
).then(
|
||||
() => {
|
||||
this.closeDialog();
|
||||
},
|
||||
(error) => {
|
||||
this._error = error.body.message;
|
||||
}
|
||||
try {
|
||||
await restoreBackup(
|
||||
this.hass,
|
||||
this._backupContent.backupType,
|
||||
this._backup!.slug,
|
||||
backupDetails,
|
||||
!!this.hass && atLeastVersion(this.hass.config.version, 2021, 9)
|
||||
);
|
||||
} else {
|
||||
|
||||
this._dialogParams?.onRestoring?.();
|
||||
fetch(`/api/hassio/backups/${this._backup!.slug}/restore/full`, {
|
||||
method: "POST",
|
||||
body: JSON.stringify(backupDetails),
|
||||
});
|
||||
this.closeDialog();
|
||||
} catch (error: any) {
|
||||
this._error =
|
||||
error?.body?.message || this._localize("restore_start_failed");
|
||||
} finally {
|
||||
this._restoringBackup = false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -361,7 +301,36 @@ class HassioBackupDialog
|
||||
private get _computeName() {
|
||||
return this._backup
|
||||
? this._backup.name || this._backup.slug
|
||||
: "Unnamed backup";
|
||||
: this._localize("unnamed_backup");
|
||||
}
|
||||
|
||||
static get styles(): CSSResultGroup {
|
||||
return [
|
||||
haStyle,
|
||||
haStyleDialog,
|
||||
css`
|
||||
ha-circular-progress {
|
||||
display: block;
|
||||
text-align: center;
|
||||
}
|
||||
ha-header-bar {
|
||||
--mdc-theme-on-primary: var(--primary-text-color);
|
||||
--mdc-theme-primary: var(--mdc-theme-surface);
|
||||
flex-shrink: 0;
|
||||
display: block;
|
||||
}
|
||||
ha-icon-button {
|
||||
color: var(--secondary-text-color);
|
||||
}
|
||||
.loading {
|
||||
width: 100%;
|
||||
display: flex;
|
||||
height: 100%;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
`,
|
||||
];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user