web/flows: fix helper form not being removed from identification stage (improve password manager compatibility)
Signed-off-by: Jens Langhammer <jens.langhammer@beryju.org>
This commit is contained in:
parent
ab17a12184
commit
e72097292c
|
@ -131,7 +131,7 @@ export class FlowExecutor extends LitElement implements StageHost {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
submit(payload?: FlowChallengeResponseRequest): Promise<void> {
|
submit(payload?: FlowChallengeResponseRequest): Promise<boolean> {
|
||||||
if (!payload) return Promise.reject();
|
if (!payload) return Promise.reject();
|
||||||
if (!this.challenge) return Promise.reject();
|
if (!this.challenge) return Promise.reject();
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
|
@ -153,12 +153,18 @@ export class FlowExecutor extends LitElement implements StageHost {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
this.challenge = data;
|
this.challenge = data;
|
||||||
|
if (this.challenge.responseErrors) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
})
|
})
|
||||||
.catch((e: Error | Response) => {
|
.catch((e: Error | Response) => {
|
||||||
this.errorMessage(e);
|
this.errorMessage(e);
|
||||||
|
return false;
|
||||||
})
|
})
|
||||||
.finally(() => {
|
.finally(() => {
|
||||||
this.loading = false;
|
this.loading = false;
|
||||||
|
return false;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -7,7 +7,7 @@ export interface StageHost {
|
||||||
challenge?: unknown;
|
challenge?: unknown;
|
||||||
flowSlug: string;
|
flowSlug: string;
|
||||||
loading: boolean;
|
loading: boolean;
|
||||||
submit(payload: unknown): Promise<void>;
|
submit(payload: unknown): Promise<boolean>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class BaseStage<Tin, Tout> extends LitElement {
|
export class BaseStage<Tin, Tout> extends LitElement {
|
||||||
|
@ -16,14 +16,19 @@ export class BaseStage<Tin, Tout> extends LitElement {
|
||||||
@property({ attribute: false })
|
@property({ attribute: false })
|
||||||
challenge!: Tin;
|
challenge!: Tin;
|
||||||
|
|
||||||
submitForm(e: Event): void {
|
async submitForm(e: Event): Promise<boolean> {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
const object: {
|
const object: {
|
||||||
[key: string]: unknown;
|
[key: string]: unknown;
|
||||||
} = {};
|
} = {};
|
||||||
const form = new FormData(this.shadowRoot?.querySelector("form") || undefined);
|
const form = new FormData(this.shadowRoot?.querySelector("form") || undefined);
|
||||||
form.forEach((value, key) => (object[key] = value));
|
form.forEach((value, key) => (object[key] = value));
|
||||||
this.host?.submit(object as unknown as Tout);
|
return this.host?.submit(object as unknown as Tout).then((successful) => {
|
||||||
|
if (successful) {
|
||||||
|
this.cleanup();
|
||||||
|
}
|
||||||
|
return successful;
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
renderNonFieldErrors(errors: ErrorDetail[]): TemplateResult {
|
renderNonFieldErrors(errors: ErrorDetail[]): TemplateResult {
|
||||||
|
@ -41,4 +46,9 @@ export class BaseStage<Tin, Tout> extends LitElement {
|
||||||
})}
|
})}
|
||||||
</div>`;
|
</div>`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cleanup(): void {
|
||||||
|
// Method that can be overridden by stages
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -41,6 +41,8 @@ export class IdentificationStage extends BaseStage<
|
||||||
IdentificationChallenge,
|
IdentificationChallenge,
|
||||||
IdentificationChallengeResponseRequest
|
IdentificationChallengeResponseRequest
|
||||||
> {
|
> {
|
||||||
|
form?: HTMLFormElement;
|
||||||
|
|
||||||
static get styles(): CSSResult[] {
|
static get styles(): CSSResult[] {
|
||||||
return [
|
return [
|
||||||
PFBase,
|
PFBase,
|
||||||
|
@ -72,8 +74,8 @@ export class IdentificationStage extends BaseStage<
|
||||||
}
|
}
|
||||||
|
|
||||||
firstUpdated(): void {
|
firstUpdated(): void {
|
||||||
const wrapperForm = document.createElement("form");
|
this.form = document.createElement("form");
|
||||||
document.documentElement.appendChild(wrapperForm);
|
document.documentElement.appendChild(this.form);
|
||||||
// This is a workaround for the fact that we're in a shadow dom
|
// This is a workaround for the fact that we're in a shadow dom
|
||||||
// adapted from https://github.com/home-assistant/frontend/issues/3133
|
// adapted from https://github.com/home-assistant/frontend/issues/3133
|
||||||
const username = document.createElement("input");
|
const username = document.createElement("input");
|
||||||
|
@ -91,7 +93,7 @@ export class IdentificationStage extends BaseStage<
|
||||||
input.focus();
|
input.focus();
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
wrapperForm.appendChild(username);
|
this.form.appendChild(username);
|
||||||
const password = document.createElement("input");
|
const password = document.createElement("input");
|
||||||
password.setAttribute("type", "password");
|
password.setAttribute("type", "password");
|
||||||
password.setAttribute("name", "password");
|
password.setAttribute("name", "password");
|
||||||
|
@ -115,7 +117,7 @@ export class IdentificationStage extends BaseStage<
|
||||||
input.focus();
|
input.focus();
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
wrapperForm.appendChild(password);
|
this.form.appendChild(password);
|
||||||
const totp = document.createElement("input");
|
const totp = document.createElement("input");
|
||||||
totp.setAttribute("type", "text");
|
totp.setAttribute("type", "text");
|
||||||
totp.setAttribute("name", "code");
|
totp.setAttribute("name", "code");
|
||||||
|
@ -139,7 +141,13 @@ export class IdentificationStage extends BaseStage<
|
||||||
input.focus();
|
input.focus();
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
wrapperForm.appendChild(totp);
|
this.form.appendChild(totp);
|
||||||
|
}
|
||||||
|
|
||||||
|
cleanup(): void {
|
||||||
|
if (this.form) {
|
||||||
|
document.documentElement.removeChild(this.form);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
renderSource(source: LoginSource): TemplateResult {
|
renderSource(source: LoginSource): TemplateResult {
|
||||||
|
|
Reference in New Issue