Replies: 3 comments 1 reply
|
For the initial password setup, we can handle the entire process through flows and only allow credential updates when the credential values already exist. The flow can enforce the necessary user verification steps before allowing the credential to be set, similar to how we handle credential recovery flows. |
|
Updated design after the reviewThanks @UdeshAthukorala and @Dilusha-Madushan. Here is where this landed and what is now implemented in #5290. What changed from the original proposal
On the first two, @UdeshAthukorala was right on both counts. There was no reason to add a second method that does the same hash comparison, and Final behaviour
Verification runs for any credential type being written, not only when the new value is a password. Answer to Q1, the first-time setWe are allowing it with no proof, for now. There is nothing to check the request against, so the only options were to allow it or to reject it. We tried rejecting it first. Rejecting would have taken away something that works today from federated users, OTP only users, and invited users, and given them nothing in return. They would have had no way to ever set a password. So the order matters here. Build the verified setup path first, then close this door. Closing it first just breaks people. Worth noting this is the safer direction to move in later. Going from allowed to rejected is a breaking change. Going from rejected back to allowed is not. So shipping the permissive version now does not paint us into a corner. On handling initial setup through flows@Dilusha-Madushan this is the right long term answer and I agree with it. It is also bigger than this change. It is wider than self-service credential updates. I am raising it as its own design discussion rather than folding it into this one, and I will link it here once it is up. The idea is one flow per credential type, pointed at from server config the same way One thing that will need care there: flow composition is open ended and there is no validation rule stopping someone putting Client sideThe SDK reads the user type schema from The current password field is not required on the client. Only the server knows whether the account has a password, so blocking submission on that field would lock out the users who do not have one. If the server does need it and it is missing or wrong, the Not covered here
|
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Related Feature Issue
#5291
Problem Summary
POST /users/me/update-credentialsaccepts{"attributes": {"password": "..."}}and writes the new credential immediately. The only thing authorizing that write today is possession of an access token for the account, so anyone holding a stolen token, a leaked cookie, or an unlocked laptop can set a new password and permanently lock the real owner out.High-Level Approach
internal/user(used by the Console) is a separate handler and stays as-is, since an admin resetting someone else's password has no way to supply that user's current secret.Architecture Overview
internal/entityinternal/userself-service handlercurrentPasswordfieldinternal/useradmin reset handlerapi/user.yamlProposed wire shape:
Proposed request flow
sequenceDiagram participant C as Client (SDK) participant A as Self-service API participant V as Credential Verification participant D as Data Store C->>A: POST /users/me/update-credentials<br/>{currentPassword, attributes: {password}} A->>V: verify(entityID, "password", currentPassword) V->>D: read stored credential D-->>V: stored hash (or none) alt no credential stored yet V-->>A: nothing to check against Note over A: open question — see Q4 else credential stored V->>V: compare against stored hash alt match V-->>A: verified A->>D: write new credential A-->>C: 204 No Content else no match V-->>A: not verified A-->>C: 401 end endSecurity Considerations
Impacted Areas
internal/user(self-service and admin credential handlers, service, model)internal/entity(credential verification)api/user.yamlAlternatives Considered
Alternative 1: Step-up re-authentication instead of a payload field
Alternative 2: Rely on the endpoint already being protected and change nothing
Questions for Community Input
All reactions