Skip to content
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

ZMI logout handler overrides challenge plugin configuration #107

Closed
rpatterson opened this issue Dec 28, 2021 · 15 comments · Fixed by #108
Closed

ZMI logout handler overrides challenge plugin configuration #107

rpatterson opened this issue Dec 28, 2021 · 15 comments · Fixed by #108
Assignees
Labels

Comments

@rpatterson
Copy link

BUG/PROBLEM REPORT (OR OTHER COMMON ISSUE)

What I did:

In the Zope root /acl_users, I deactivated the HTTPBasicAuthHelper plugin for the IChallengePlugin interface and activated the CookieAuthHelper plugin for the IChallengePlugin interface. Then, while logged in as a Manager, I clicked the manage_zmi_logout ZMI link.

What I expect to happen:

I expect to see either some sort of "You have been logged out" page or to be redirected to the CookieAuthHelper.login_form.

IMO, ZMI logout should not immediately re-challenge the user to authenticate as this leads to a confusing user experience for most, if not all, authentication types. Specifically, the user never sees a clear confirmation of the effect of their action, some sort of "You have been logged out" message, and they're left to infer that from being challenged for credentials again.

If, despite that poor UX, we decide that ZMI logout should immediately re-challenge, then the decision for how to challenge the user should be delegated to the plugins configuration for the IChallengePlugin interface.

What actually happened:

The browser prompts for HTTP Authorization: Basic ... credentials. This happens because HTTP Authorization: Basic ... assumptions are hard-coded into Products.PluggableAuthService.manage_zmi_logout(...). Namely it sets WWW-Authenticate: basic ... and Status: 401 Unauthorized.

What version of Python and Zope/Addons I am using:

Python 3.9
Plone's buildout.coredev, branch 6.0, Products.PlonePAS added to buildout:auto-checkout

rpatterson added a commit to plone/plone.restapi that referenced this issue Dec 28, 2021
rpatterson added a commit to plone/plone.restapi that referenced this issue Dec 28, 2021
rpatterson added a commit to plone/plone.restapi that referenced this issue Dec 28, 2021
@d-maurer
Copy link
Contributor

d-maurer commented Dec 28, 2021 via email

rpatterson added a commit to plone/plone.restapi that referenced this issue Dec 28, 2021
rpatterson added a commit to plone/plone.restapi that referenced this issue Dec 28, 2021
@dataflake
Copy link
Member

As Dieter says, that logout link is hardcoded in Zope and only works for basic HTTP authentication as used by the default user folder that ships with Zope itself. Different user folder implementations may define their own logout methods, but stock Zope simply cannot account for all of those.

@rpatterson
Copy link
Author

This is not a Products.PluggableAuthService issue: manage_zmi_logout is defined by Zope's App.Management.Navigation.

From Products.PluggableAuthService.manage_zmi_logout:

# monkey patch Zope to cause zmi logout to be PAS-aware

So this is PAS code, hence I reported the issue here.

For HTTP authentication, you cannot log out the user without browser interaction...

Correct, and this is an implementation detail of that particular form of authentication. Supporting different forms of authentication is a core use case of PAS. Hence PAS has a plugin for this specific form of authentication, Products.PluggableAuthService.plugins.HTTPBasicAuthHelper.HTTPBasicAuthHelper. That's where the implementation details of this form of authentication that you describe belong, not in a monkey patch and not in such a way that it can't be controlled by the plugin configurations.

If you have done this, the ZMI's logout should work in your special case.

Configuring different forms of authentication, such as turning them on and off, isn't a special case. It's a core use case of PAS.

...stock Zope simply cannot account for all of those.

Definitely not and that's not what's described as the issue here. This monkey patch makes PAS behave less like PAS, and it need not do so. This is not a report asking for PAS to do everything and cover every case. This is a report about behavior that works against a core use case of PAS.

@dataflake
Copy link
Member

I didn't read the original report closely enough, now I get what you're saying. I had totally forgotten that the code contains the override for the ZMI link. I do agree, just setting the WWW-Authenticate header without considering the configuration at all is inappropriate. I bet this hasn't come up before because very few people will replace the root user folder and configure it for an authentication scheme other than basic HTTP auth. I'll take a look when I have time.

@dataflake dataflake reopened this Dec 30, 2021
@dataflake dataflake self-assigned this Dec 30, 2021
@dataflake dataflake added bug and removed invalid labels Dec 30, 2021
@d-maurer
Copy link
Contributor

d-maurer commented Dec 30, 2021 via email

@rpatterson
Copy link
Author

rpatterson commented Dec 30, 2021

I bet this hasn't come up before because very few people will replace the root user folder and configure it for an authentication scheme other than basic HTTP auth

Good point! I hadn't thought about that. I'm running into it because I'm working on the UX of sharing authentication between Volto which is using a JWT token plugin, Plone classic which is using the cookie/session plugins, and the ZMI. In that case we need a login "event" so that the ICredentialsUpdatePlugin interface is "triggered" so that all plugins can do what they need to do to initialize authentication no matter which method/UI the user uses. Hence having to switch Zope root /acl_users/ to cookie auth because Basic auth has no login "event". So if my work on that is merged, then at some point in the future we can expect many more users to have replaced Zope root /acl_users/ and enabled cookie auth.

I'll take a look when I have time.

Oh, I don't expect that just because I report an issue that someone else will do it for me. ;-) I was mainly reporting it so that at the very least it's a known issue and searchable. I'm a fan of #wontfix with a "Feel free to re-open if you'll do it" comment.

I have actually already partially implemented this in a overriding monkey patch in another package. I did it there because I didn't have much faith that a PR submitted to this repo would ever get to merging. Also, I haven't tested my overridden monkey patch with basic auth to see if that still works. From my reading of HTTPBasicAuthHelper, I don't think it's resetCredentials() actually does the full Basic auth logout "dance", so there's probably a non-trivial amount of futzing to get it working right in the plugin instead of the monkey patch. That said, I'd love to work on it if I got some reassurance that a PR on this matter would be welcome.

@rpatterson
Copy link
Author

Check if the following replacement satisfies your expectations.

Yeah, that's pretty much what I was thinking with the caveat from my previous comment that I don't think the HTTPBasicAuthHelper.resetCredentials() is sufficiently complete as is.

@dataflake
Copy link
Member

I'll take a look when I have time.

Oh, I don't expect that just because I report an issue that someone else will do it for me. ;-) I was mainly reporting it so that at the very least it's a known issue and searchable. I'm a fan of #wontfix with a "Feel free to re-open if you'll do it" comment.

So am I in many cases.

I didn't have much faith that a PR submitted to this repo would ever get to merging.

Why do you think that? A "good" PR (meaning one that is documented if needed and that contains unit tests) is the best way to get anything in here.

@d-maurer
Copy link
Contributor

d-maurer commented Dec 30, 2021 via email

@dataflake
Copy link
Member

For correct user folder implementations the user object should be acquisition-wrapped in the originating user folder, so that should be a safe way to find out where the login came from.

@rpatterson
Copy link
Author

rpatterson commented Dec 30, 2021

I didn't have much faith that a PR submitted to this repo would ever get to merging.

Why do you think that? A "good" PR (meaning one that is documented if needed and that contains unit tests) is the best way to get anything in here.

If you don't see why from my other recent interactions in this repo, then I would guess we just have different sensibilities and won't see eye to eye on this. I can tell you that I'm definitely not the only senior, gray beard, old-school Zope developer who practices TDD and understands that a development task isn't complete until the documentation is complete who learned long ago not to try with Zope'ish contributions. Recent interactions here haven't given me the sense that's changed.

At any rate, when I can carve out some time, I'll take a stab at a PR for this.

@d-maurer
Copy link
Contributor

d-maurer commented Dec 30, 2021 via email

@d-maurer
Copy link
Contributor

d-maurer commented Dec 30, 2021 via email

@dataflake
Copy link
Member

If you don't see why from my other recent interactions in this repo, then I would guess we just have different sensibilities and won't see eye to eye on this. I can tell you that I'd definitely not the only senior, gray beard, old-school Zope developer who practices TDD and understands that a development task isn't complete until the documentation is complete who learned long ago not to try with Zope'ish contributions. Recent interactions here haven't given me the sense that's changed

After reading through that issue I cannot find fault in how Dieter tried to help you. On the other hand some of your comments struck me as quite snide and condescending. Please stick to problem descriptions and, if needed for clarifications, a PR or code example.

@d-maurer
Copy link
Contributor

d-maurer commented Dec 31, 2021 via email

rpatterson added a commit to plone/plone.restapi that referenced this issue Jan 4, 2022
rpatterson added a commit to plone/plone.restapi that referenced this issue Jan 4, 2022
rpatterson added a commit to plone/plone.restapi that referenced this issue Feb 14, 2022
Integrate upstream `Products.PluggableAuthService` and `Products.PlonePAS` changes to
the Zope root `/acl_users`:

- fix some broken plugin configuration on install and upgrade

- add a `GenericSetup` profile to convert to a simple cookie login form which fixes
  logout issues when used with other plugins such as the JWT token plugin

Note that the only changes here are adding test coverage confirming the upstream changes
have the intended effect when combined with the JWT token plugin.

Upstream links:

zopefoundation/Products.PluggableAuthService#107 (comment)
zopefoundation/Products.PluggableAuthService@44ac67f
rpatterson added a commit to plone/plone.restapi that referenced this issue Feb 14, 2022
Integrate upstream `Products.PluggableAuthService` and `Products.PlonePAS` changes to
the Zope root `/acl_users`:

- fix some broken plugin configuration on install and upgrade

- add a `GenericSetup` profile to convert to a simple cookie login form which fixes
  logout issues when used with other plugins such as the JWT token plugin

Note that the only changes here are adding test coverage confirming the upstream changes
have the intended effect when combined with the JWT token plugin.

Upstream links:

zopefoundation/Products.PluggableAuthService#107 (comment)
zopefoundation/Products.PluggableAuthService@44ac67f
rpatterson added a commit to plone/plone.restapi that referenced this issue Feb 14, 2022
Integrate upstream `Products.PluggableAuthService` and `Products.PlonePAS` changes to
the Zope root `/acl_users`:

- fix some broken plugin configuration on install and upgrade

- add a `GenericSetup` profile to convert to a simple cookie login form which fixes
  logout issues when used with other plugins such as the JWT token plugin

Note that the only changes here are adding test coverage confirming the upstream changes
have the intended effect when combined with the JWT token plugin.

Upstream links:

zopefoundation/Products.PluggableAuthService#107 (comment)
zopefoundation/Products.PluggableAuthService@44ac67f
rpatterson added a commit to plone/plone.restapi that referenced this issue Feb 23, 2022
Integrate upstream `Products.PluggableAuthService` and `Products.PlonePAS` changes to
the Zope root `/acl_users`:

- fix some broken plugin configuration on install and upgrade

- add a `GenericSetup` profile to convert to a simple cookie login form which fixes
  logout issues when used with other plugins such as the JWT token plugin

Note that the only changes here are adding test coverage confirming the upstream changes
have the intended effect when combined with the JWT token plugin.

Upstream links:

zopefoundation/Products.PluggableAuthService#107 (comment)
zopefoundation/Products.PluggableAuthService@44ac67f
rpatterson added a commit to plone/plone.restapi that referenced this issue Mar 9, 2022
Integrate upstream `Products.PluggableAuthService` and `Products.PlonePAS` changes to
the Zope root `/acl_users`:

- fix some broken plugin configuration on install and upgrade

- add a `GenericSetup` profile to convert to a simple cookie login form which fixes
  logout issues when used with other plugins such as the JWT token plugin

Note that the only changes here are adding test coverage confirming the upstream changes
have the intended effect when combined with the JWT token plugin.

Upstream links:

zopefoundation/Products.PluggableAuthService#107 (comment)
zopefoundation/Products.PluggableAuthService@44ac67f
rpatterson added a commit to plone/plone.restapi that referenced this issue Apr 13, 2022
Integrate upstream `Products.PluggableAuthService` and `Products.PlonePAS` changes to
the Zope root `/acl_users`:

- fix some broken plugin configuration on install and upgrade

- add a `GenericSetup` profile to convert to a simple cookie login form which fixes
  logout issues when used with other plugins such as the JWT token plugin

Note that the only changes here are adding test coverage confirming the upstream changes
have the intended effect when combined with the JWT token plugin.

Upstream links:

zopefoundation/Products.PluggableAuthService#107 (comment)
zopefoundation/Products.PluggableAuthService@44ac67f
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants