-
Notifications
You must be signed in to change notification settings - Fork 2.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Move auth components from shadow DOM to light DOM #18015
Conversation
src/components/ha-form/ha-form.ts
Outdated
protected fieldElementName(type: string) { | ||
return `ha-form-${type}`; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be handled in core eventually, it can provide a different type for the auth text fields.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I thought that too at the beginning.
Don't you think we can keep this in front-end as it is a front-end issue. We can remove this code once shadow dom support is added to password manager (never? 😂)
src/auth/ha-auth-form.ts
Outdated
protected fieldElementName(type: string): string { | ||
if (type === "string") { | ||
return "ha-auth-form-string"; | ||
} | ||
return super.fieldElementName(type); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be handled in core eventually, it can provide a different type for the auth text fields.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, so we don't have to duplicate ha-form but only add an option to render without shadow dom.
I can review for a11y if and when we might be ready to merge, so just let me know. Also, just throwing out an idea, maybe use Vaadin components here to gain most of the Material styling (e.g. their canned login form)? Advantage is that they already proxy everything to light DOM by design, and it might be easier to maintain/swap out when the bigger password managers actually decide to implement support. |
If we use Vaadin we will stil need to place that inside the light DOM, and it gives us a lot less flexibility. |
AFAIK, they switched most if not all their components to use this "teleport" system to render in the light DOM. One of the impetuses was for better a11y because a lot of ARIA attributes take ID references, which quickly break when shadow trees get involved. In other words, I think just using them inside the existing |
Only if you use the
|
Hmm... RTFM Steve 😊 |
8a17af6
to
b3bb005
Compare
I found a way to load @bramkragten I preferred to duplicate some component for auth instead of adding option to |
Ready to review ! |
<style> | ||
.action { | ||
margin: 24px 0 8px; | ||
text-align: center; | ||
} | ||
.store-token { | ||
margin-top: 10px; | ||
margin-left: -16px; | ||
} | ||
</style> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's keep this in static get styles
, that should also work when using light dom right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
static styles doesn't work with light dom. That's the reason I use this hacky thing 😅
const style = document.createElement("style");
style.innerHTML = HaTextField.elementStyles as unknown as string;
this.append(style);
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I thought Lit would do that for use, but ok 🤷♂️
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Because that's something that's done in the default createRenderRoot
implementation.
667a84a
to
4f9df62
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Was in the middle of reviewing... 😞
Aside from my comments inline, there is a significant a11y issue now. The password field is labeled with the username text. This is because the input
has aria-labelledby="label"
, so now it just finds the first element in the document with that ID, which is of course for the username. Note they don't have helpers so not strictly a problem, but aria-controls
and aria-describedby
would also be broken.
Either need to give everything distinct id
attributes, or delete the aria-labelledby
as it's redundant with the wrapping label
element anyway.
// add parent style to light dom | ||
const style = document.createElement("style"); | ||
style.innerHTML = HaForm.elementStyles as unknown as string; | ||
this.append(style); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Most browsers don't care I think, but strictly speaking, it should be attached to document.head
.
// add parent style to light dom | ||
const style = document.createElement("style"); | ||
style.innerHTML = HaTextField.elementStyles as unknown as string; | ||
this.append(style); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same here
protected createRenderRoot() { | ||
// add parent style to light dom | ||
const style = document.createElement("style"); | ||
style.innerHTML = HaFormString.elementStyles as unknown as string; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should use textContent
instead for security and performance
@steverep I pushed a fix for this issue : #18032. Good catch! |
This is causing some jankiness, at least in Firefox. See the attached screen recording. This was recorded using a development build on the latest version of |
@KTibow Let's keep track of such things in issues, instead of handled/closed PRs. Thanks 👍 ../Frenck |
Proposed change
Move the auth component from shadow DOM to light DOM to have better (full?) password manager support.
It's seems to work (at least with 1password). Tested in Chrome desktop, Safari desktop, Chrome Android and Safari iOS.
Some components are duplicated (
ha-auth-form
,ha-auth-textfield
,ha-auth-form-string
) so we don't need to touch original component to add light dom support.All previous features works and the design is the same as before.
Type of change
Example configuration
Additional information
Checklist
If user exposed functionality or configuration variables are added/changed: