diff --git a/authentication/tests.py b/authentication/tests.py index 6edb60b..16a01b6 100644 --- a/authentication/tests.py +++ b/authentication/tests.py @@ -265,6 +265,15 @@ class TwoFactorPageTests(TestCase): self.assertContains(self.response, 'name="code"') self.assertContains(self.response, "otp otp-lg") + def test_the_input_comes_after_the_boxes(self): + # daisyUI places each box with nth-child, which counts every child. With the input + # first, all six boxes shift a stride right, the container grows to seven strides + # and the ::after focus marker appears as a phantom seventh box. + html = self.response.content.decode() + otp = html[html.index('class="otp otp-lg"') : html.index('name="code"')] + + self.assertEqual(otp.count(""), 6) + def test_the_otp_field_has_no_placeholder(self): # allauth sets placeholder="Code"; inside the boxes it reads as a typed-in code. self.assertNotContains(self.response, 'placeholder="Code"') diff --git a/templates/allauth/elements/fields.html b/templates/allauth/elements/fields.html index 163444a..a6de64a 100644 --- a/templates/allauth/elements/fields.html +++ b/templates/allauth/elements/fields.html @@ -43,20 +43,26 @@ {% with icon=field|field_icon %} {% if field|is_otp %} {% comment %} - daisyUI's otp is one input overlaid on the boxes, and it sizes itself from - its `span` children — so the sr-only label goes OUTSIDE the container, or it - would count as a seventh box and throw the width off. + daisyUI's otp is one input overlaid on the boxes. Child order is load-bearing: + it places each box with `nth-child`, which counts *every* child, not just the + spans — so the input must come LAST. Put it first and all six boxes shift one + stride right, the container matches :has(>span:nth-child(7)) and grows to + seven strides, and the ::after active-box marker (invisible until focus) shows + up in the gap as a phantom seventh box. + + For the same reason the sr-only label lives outside the container: another + child would throw the count off again. {% endcomment %} {% if attrs.unlabeled %}{% endif %}