Add configurable support for persisting a single remember me token across multiple browser logins#690
Add configurable support for persisting a single remember me token across multiple browser logins#690arnvald merged 5 commits intoNoamB:masterfrom graffletopia:remember-me-persist-globally
Conversation
…ross multiple browser logins This addresses functionality discussed in issue #190. Previously (and still by default after this commit), logging in to one browser would effectively invalidate the remember me token stored as a cookie in all other browsers the user may have logged in with. This in practice made it difficult to support remembering logins for users with different devices (desktop & tablet). This change adds a new configuration option "remember_me_token_persist_globally" (default: false) which, if set to true, will maintain the first remember me token used for all subsequent cookies. Rails.application.config.sorcery.configure do |config| config.user_config do |user| user.remember_me_token_persist_globally = true # Make remembered logins work across browsers end end This causes the remember me module to: 1. Skip overwriting the token when logging in, in Model#remember_me! 2. Skip clearing the token when logging out, in Model#forget_me! Enabling this option has potential security ramifications, especially on websites not using SSL, a single token value being long-lived will increase the risk of session fixation attacks. Since even logging out does not clear the token (since other browsers may still be relying on it), there is also no direct way to invalidate a user's remembered login (short of manually setting the token to NULL). As such, anyone enabling this option should understand and accept this security/functionality trade-off (and ideally use SSL across-the-board).
|
Here's a suggestion for a better name for What about |
|
Hi @rubiety, thanks a lot for your contribution! I like the idea, I was thinking about it for some time, and I like the approach, where you leave the current situation as default, and add the feature as optional. I'll think about the name for this setting. @mokolabs suggestion sounds good, although it does not suggest that logout will not clear all sessions. It would be useful to add this option to initializer template with proper comment. I'll review code in detail later this week and I'll provide some comments on it. For now I think there are 2 things to add: comment in initializer template and method like I think this additional method is important, because it gives users protection - if they know they left session open at some public computer, they can invalidate it. Of course not all developers will add the option to invalidate all sessions, but if it's as easy as running |
…he remember me token Normally logout will not invalidate the remember me token if remember_me_token_persist_globally is set to true, since other browser may still be relying on that session. We now expose a new logout_all_sessions method which forces this token value to be cleared, effectively destroying remember me for that user on all browsers. Note that the implementation is a bit wonky due to the coupling with the callback queues we have. Must of this messiness can be removed if we decide to just expose force_forget_me! instead of a new wrapper logout_all_sessions.
|
I've added to the initializer template, but implementing a Currently Implementing a new So the only real way to do that is to call both and then have remember me do There is also some potential confusion in having this Despite these potential reservations, I have pushed a commit that attempts to implement this, but I'm not particularly happy with the implementation, for the reasons discussed above. It exposes new queues Note that one option to help simplify this implementation is to just expose |
|
@rubiety thanks for tackling this problem and for detailed summary. I agree that the approach with separate callbacks is too complex. Also, I should add changing the controller callbacks architecture to my TODO list for version 1.0. How about an implementation where def logout_all_sessions
if logged_in?
force_forget_me!
logout
end
endI need to check it locally, if it won't cause any issues. I've checked your first 2 commits as well, nothing to add there, if we find a way to add |
|
That makes sense, but it also means the |
|
Yes, I'm aware it will be available only if the module is included, but at this point it makes sense - since without There is, however, one thing that bothers me (which is my fault, as I came up with the name). I'll think for a while about a better name, and if I can't of anything less confusing, I'll leave it this way for now. I need to add option to invalidate all the sessions anyway, so that would be good place to start working on it. @rubiety thanks once again for your work! If you have any idea how to rename |
|
About the only thing I can suggest is removing the Aside from your valid critique of the name, I cringe a bit at a name so generic being stuffed in a specific module. |
|
I agree, let's just leave |
|
Sweet! |
…t_me! separately (described in README)
|
Okay, this has been done and we're back to just a |
Add configurable support for persisting a single remember me token across multiple browser logins
|
Nice, finally a solution to this! |
|
Thanks a bunch. This was like a Heisenbug to us 👯 |
This addresses functionality discussed in issue #190.
Previously (and still by default after this commit), logging in to one browser would effectively invalidate the remember me token stored as a cookie in all other browsers the user may have logged in with. This in practice made it difficult to support remembering logins for users with
different devices (desktop & tablet).
This change adds a new configuration option
remember_me_token_persist_globally(default: false) which, if set to true, will maintain the first remember me token used for all subsequentcookies.
This causes the remember me module to:
Enabling this option has potential security ramifications, especially on websites not using SSL, a single token value being long-lived will increase the risk of session fixation attacks. Since even logging out does not clear the token (since other browsers may still be relying on it), there is also no direct way to invalidate a user's remembered login (short of manually setting the token to NULL).
As such, anyone enabling this option should understand and accept this security/functionality trade-off (and ideally use SSL across-the-board).
A few notes about this implementation for consideration:
remember_me_token_persist_globally) - it might deserve renaming for more clarity.remember_me_token_reset_on_loginandremember_me_token_clear_on_logout. Thus you could set the former to false and the latter to true to still allow logging out clobbering all remembered logins for that user. I opted against this in the interest of simplicity, and figuring most users would want both.