Closed (fixed)
Project:
Drupal core
Version:
8.0.x-dev
Component:
openid.module
Priority:
Critical
Category:
Bug report
Assigned:
Issue tags:
Reporter:
Created:
18 Apr 2012 at 18:20 UTC
Updated:
29 Jul 2014 at 20:36 UTC
Jump to comment: Most recent, Most recent file
Comments
Comment #1
sunHm. This means that the login form is always altered and required validation is disabled both on the server-side as well as on the client-side.
I'm concerned about unexpected security consequences of this.
I.e., what happens if you submit the login form with no values at all -- are we sure that all code is smart enough to handle that case? Likewise, what happens if you only submit a password but no username? [...]
Lastly, an OpenID module test should have prevented the HTML5 required patch from landing in the first place. ;)
Comment #2
attiks commentedComment #3
c960657 commentedOpenID has module tests. The problem is that the Simpletest framework doesn't emulate a client-side check for the HTML5 required attribute (the server-side check is intentionally disabled in the existing code).
A possibly cleaner solution would be to turn the current login form into two different forms, the username/password form and the OpenID login form. I think it could be made in way so there would be no visible difference for users with JavaScript enabled. Users without JavaScript will get an additional submit button, but I think that makes the form easier to understand (right now it is not very obvious that you have to fill out either the OpenID identifier field or the username and password fields).
One thing that would make the implementation slightly easier and the UI cleaner (IMO) would be to move to two “Create new account” and “Request new password” links down below the submit button. I don't think they are part of the form, so I think they should be moved outside it. The button was above the links in D6, but it seems they changed place as an unintentional effect of #482816: Make a consistent wrapper around submit buttons, so I suggest that we move them back. What do you think of this?
Comment #4
c960657 commentedThis patch implements two different forms as suggested in #3.
The patch introduces some user-visible changes. I intentionally didn't try to make it look 100%. I think the new approach is cleaner from a code-perspective and thus also improves consistency of the UI if we just fall back to the theme's default way of displaying things (this wasn't possible with the old code due to the somewhat hackish way that the OpenID controls were injected into the login form).
Now the JS switching logic is made declaratively using #states. This required adding a new trigger state based on location.hash. This may be useful for other purposes as well. It just matches the entire fragment part, e.g. #openid-login. Would it be better to treat the fragment as key-value pairs, i.e. #login=openid (like the Overlay module does it: #overlay=admin)?
UX-wise the user login block looks works like before, though the layout is slightly different (as mentioned above). Also, the indentation of the link that switches between the two states is now no longer indented. This is because the links were previously implemented as a &ul> list, but I don't really think they are a list, so now they are just implemented as basic links with the default spacing according to the theme. I think this is fine.
I split up the OpenID part of login form on user/login into user/login/login as a MENU_LOCAL_TASK. This is consistent with elsewhere in Drupal were such tab-like functionality is implemented via the menu system and not via custom JS code.
Comment #5
c960657 commentedComment #6
Dave.Ingram commentedI came across this looking at some other things in OpenID and this patch fixed the problem. I've clicked through all of the OpenID functionality and think this patch takes care of it all.
I don't fully understand all the changes to states.js though, so someone may need to look over that before committing.
Comment #7
sunSorry, this needs more reviews.
The changes to states.js look a bit spooky to me as well. Don't have time to review them in detail right now. Perhaps @nod_ or @xjm or someone else familiar with the states code can look into them.
Also, these are massive UI and CSS changes - needs manual testing.
Let's also look in the html5 folks to make 'em aware of this gotcha.
Comment #8
Niklas Fiekas commentedWhen adding #required we were using the 'formnovalidate' attribute to work with #states. We could do the same thing here. That keeps all the server side validation and the required attribute itself (for screenreaders, etc.) ...
Edit: Reading more of the issue: Refactoring the whole thing could be a seperate issue. @c960657's patch would probably be a good start.
Comment #9
c960657 commentedHere is plain reroll of the refactoring patch.
I tried to find a way to implement the #login=openid instead of #openid-login, but I cannot find a good way to do it with making big changes to states.js (of course, this is not forbidded, but I'd like a second opinion on this first) and without adding a dependency on jquery.ba-bbq.js.
Comment #10
c960657 commentedReroll.
Comment #11
xjm#10: openid-required-4.patch queued for re-testing.
Comment #13
xjmWe'll reroll this and work on testing it during MWDS.
Comment #14
xjmTo test the #states behaviors:
sites/all/modulesdirectory and install it.http://drupal.org/project/1269964/git-instructions
http://drupal.org/node/735528#comment-5473144
http://drupal.org/node/735528#comment-5499236
states-exercisein your local D8 install. (A menu link should appear in the Navigation menu.)We'll organize people to each test a certain section of the module during today's sprint.
Comment #15
attiks commented@xjm, if you don't want to do it manually, consider extending the testswarm tests
Comment #16
c960657 commentedCool!
Here is a reroll of the patch.
Comment #18
c960657 commentedReroll.
Comment #20
c960657 commentedComment #21
c960657 commentedComment #22
star-szrRemoving reroll tag.
Comment #23
Niklas Fiekas commentedThanks for the patch and the rerolls, c960657!
I applied it locally and could confirm that the login block is fixed (in that you can login via OpenId after clicking the link to switch) and also that the seperate OpenId login page is working.
However I don't understand some parts in the code.
What is this about?
And much more high level, to see if were heading in the right direction: Having a seperate page might indeed be cleaner. Not sure about the pros and cons. Tagging for usability review.
Not sure why we need this one. Was the equivalent available in offline mode before?
Comment #24
c960657 commentedIt is used by this code:
Contrary to other types of events used in #states, the hashchange event is not triggered on an element inside the DOM but on the window object (i.e. an object that you cannot select using a regular jQuery selector). The patch adds support for the magic strings "window" and "document" (they don't match any HTML tag names, so they cannot be confused with jQuery selectors). The "document" type is not used by the patch but is only added for completeness.
Yes (see #363580: OpenID login fails when in maintenance mode). The login form itself was included on /user that is white-listed in
user_menu_site_status_alter().
Comment #25
Niklas Fiekas commentedThanks for explaining everything, @c960657! On to a more nitpicky round ;)
Maybe add a short inline comment stating your explanation here.
Why are these changes nescessary? (To be 100% sure I understand your comment there correctly.)
We should have a @see reference to the submit handler.
While were refactoring a large part of this, maybe add a paragraph of doxygen?
I continued testing manually, this time without JavaScript and block and form work fine. Yay!
The UI change is this:

(OpenID now on a seperate tab.) I think this looks pretty clean. Let's go with that, unless there are some terrible effects of this I am missing.
I'll try to ping @nod_ in IRC, because I am not too comfortable with the JavaScript parts. If no objections, then I'd say RTBC after the above changes.
Comment #26
nod_I'm not really happy to add window and document thing to #states.
the
#link should be changed to#nogoat least, it's annoying to be sent to the top when toggling. Why can't we use a button to do that? Buttons can live outside of forms.It's two different forms i'm sure we can find something a bit better than was we used to do in D7.
Comment #27
c960657 commentedIn the recent fix for #375397: Make Node module optional, the default front page changed from "node" to "user". For testing purposes we need to test both the login form on user and the login block some other page. To avoid any confusion for test writers, the patch makes sure that the "user" page is only accessible on /user, not on the front page.
Could you please explain your concerns?
An alternative to the magic strings "window" and "document", we could use a colon prefix like the :input jquery selector. This syntax would allow for the key=value syntax mentioned in #9.
I'll change the # link. Perhaps I can remove it completely using e.g. history.pushState().
I think a link is better UX than a button (not that I'm a UX expert), because pressing it does not execute anything but just takes you to another place (without reloading the page, but apart from that, the result is the same).
Comment #28
nod_The states API is a convenience, JS has events, that's what we should be using for this. it makes sense to use #states inside of a form, not so much outside of it. Adding window and document opens things up to messy horrible things people will want to come up with. And #states is still bugged adding that would just add problems. People will expect that
"document, input[type='text']"will match. It wont.the link doesn't actually goes anywhere, and with JS off, it simply doesn't show up. Clear case for a button and not a link.
localStorage can be used for storing the value, we'll be able to do neat things with that, not so much with pushState. localStorage is already used in tabledrag :D
Comment #29
c960657 commented@nod_: I understand you concerns about the states API, and I agree. I have reverted to some hybrid between the current code and the previous patch that also fixes #897794: OpenID login link can hide the wrong fields and #1663140: Clean up css in openid.
With this change, there are two forms in the user login block (the username/password form and the OpenID form). We need to specify which of these should be submitted.
Done. I also moved the submit handler upwards in the file so that it appears right after the form builder.
Done:
I agree. But this is a slightly bigger change, because the cookies are currently set server-side using user_cookie_save(). This is outside the scope of this task, so let's pursue the idea in a separate ticket.
I disagree. We use links for similar purposes several places in Drupal:
I couldn't find anywhere in core where we use buttons for toggling visibility (or for anything else for that matter).
If you don't agree, let's hear a second opinion.
Comment #30
nod_Check out #1719640: Use 'button' element instead of empty links.
agreed for local storage. there is the same thing for the toolbar state. easy enough to fix somewhere else.
Comment #31
c960657 commentedAh, I see. I suggest we deal with the buttons vs. links issue in #1719640: Use 'button' element instead of empty links. For now I think we should commit the patch based on links (like we have today). Then we can change the links to buttons in #1719640 in a consistent manner across core.
I think it's a bit dangerous to try to anticipate what other tickets may or may not be fixed in the near future (Drupal works in mysterious ways). If for some reason #1719640 is not committed but this ticket is, then we would have introduced an inconsistency, and that is IMO even worse than having one sub-optimal solution.
If #1719640 lands in trunk first, then we can easily update the patch for this ticket.
Comment #32
nod_fair enough. I'll keep an eye on the different issues an follow up.
thanks.
Comment #33
c960657 commentedReroll. Also fixes a regression introduced in #1737148: Explicitly declare all JS dependencies, don't use drupal_add_js
Comment #34
catchRemoving tag, bumping to critical.
Comment #35
Bojhan commentedGood to me.
Comment #36
sunI'd love to move forward here, and really want to say THANKS to @c960657 for keeping this alive!
This patch looks good to me. I only have two issues with it, which I hope can be addressed quickly:
I have to admit that I always wondered why the user login form and the user login block form are two separate forms, but I think this refactoring should be discussed in a separate issue -- this patch does not seem to depend on that, unless I overlooked something.
The weight of the default local task should be -10.
I'm not sure whether it makes sense to repeat "Log in" in the local task, since it is in the parent/root tab already... which would also shorten the other tab to just "OpenID".
Comment #37
c960657 commentedThanks for the review.
This patch addresses the concerns raised in #36. I will file a separate bug about the user_login_block() refactoring.
Comment #38
podarok#37 looks good for me
didn`t review css styles
Comment #39
nod_Wasn't happy with the JS. Rerolled.
interdiff with #37
Comment #40
andypostManually tested this - it works!
I found a new tab for openid login a bit confusing but now it's possible to make it primary login form!
PS: About login_form refactoring see #1772584: Get rid of user_login_block() & user_login() in favour of user_login_form()
Comment #41
webchickAwesome. Thanks so much for the hard work on this, folks!
Committed and pushed to 8.x. Thanks.