Skip to content

Conversation

EhabY
Copy link
Collaborator

@EhabY EhabY commented Sep 23, 2025

Fixes #498

@mtojek mtojek requested a review from mafredri September 23, 2025 13:26
Comment on lines +292 to 314
if (!value) {
return null;
}
client.setSessionToken(value);
try {
user = await client.getAuthenticatedUser();
Copy link
Collaborator Author

@EhabY EhabY Sep 23, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we attempt to get the authenticated user when the token is a blank string (like when this first opens)?

@mafredri
Copy link
Member

I tried out this PR and while I see a "you've been logged in" popup in multiple windows, the other windows are still stuck on this screen and there is no attempt to re-connect to the workspace:

image

I imagine this dialogue should be dismissed and a connection re-attempted? The user experience of selecting cancel is pretty bad (closes the workspace and gives you an empty window). I did not try what happens if I select "login".

@EhabY
Copy link
Collaborator Author

EhabY commented Sep 24, 2025

I tried out this PR and while I see a "you've been logged in" popup in multiple windows, the other windows are still stuck on this screen and there is no attempt to re-connect to the workspace

Can you provide a reproducible for this? I am not sure what's special about some windows that they do not respond to the change 🤔

@mafredri
Copy link
Member

Can you provide a reproducible for this? I am not sure what's special about some windows that they do not respond to the change 🤔

@EhabY Sure, I'll write down what I did.

Open two VS Code windows to the same workspace (different folders in the same workspace, whilst logged in):

coder open vscode my-workspace.dev /home/coder/foo

and

coder open vscode my-workspace.dev /home/coder/bar

Now you should have two windows that are both. Make sure VS Code is set to restore previous windows after quitting.

Then:

  1. Quit VS Code
  2. Delete ~/Library/Application Support/Code/.../session (it's in globalStorage, not at the machine right now so I can't give you full path)
  3. Open VS Code
  4. Both windows should show the ^aforementioned dialogue
  5. Perform log in on one of the windows
  6. Notice the dialogue does not disappear on the second

Does this help?

@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch from 9b0ba3e to 05160e8 Compare September 25, 2025 09:09
@EhabY
Copy link
Collaborator Author

EhabY commented Sep 25, 2025

Yes, thanks for the detailed reproducer! I can see the issue now: VS Code modals aren't dismissible without user action, which is by design (see microsoft/vscode#2732). I can adjust our flow so we don't close the window if the user signs in in the meantime (whether they click cancel, login or x). The logs in the other window show that the sign-in succeeded, so the real problem is our fallback when a login completes after the modal appears.

Do keep in mind that we cannot change the content of the modal once it's shown, so we either go for something less intrusive or just handle the fallback correctly.

Using the status bar for messages which need to be updated / dismissed is suggested there as the recommended approach in the issue I mentioned. What do you think?

@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch from 05160e8 to c7df45f Compare September 25, 2025 13:01
@mafredri
Copy link
Member

Oh, that's unfortunate, but understandable (that the modals can't be dismissed).

Using the status bar for messages which need to be updated / dismissed is suggested there as the recommended approach in the issue I mentioned. What do you think?

It's one option but I don't think it's a good one. It's fairly hidden for something that's required for your editor to start working.

I think updating the modal is the way forward. It could say something like "If you already performed login in another window, please use the cancel button."

image

This is what it looks like, after logging in from another window. See how it says "Opening remote" at the bottom, but nothing happens? I think it would be nice if we could make it successfully load the workspace in the background. Without looking at the actual code, perhaps we could do something along the lines of await Promise.race([loginmodal, loginevent]). If the workspace has loaded in the background, that's further confirmation for the user they can just hit cancel. Wdyt?

@EhabY
Copy link
Collaborator Author

EhabY commented Sep 26, 2025

I like this idea. Updating the modal to clearly indicate that a login happens in another window, plus adding background login capability, would be a solid improvement. I think this is possible but I'll be careful to avoid any racey conditions.

I think the following makes sense:

Description:

You must log in to access ${workspaceName}. If you already performed login in another window, please close this popup.

Then it's a race between two conditions as you said, 1. Login event, 2. Modal interaction. In the case of a login event, if the user clicks anything (x, Cancel, Login) it will just dismiss the modal and show the already connected workspace. The flow for the modal interaction stays the same as before.

@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch 2 times, most recently from 53432cb to 569a462 Compare September 27, 2025 08:02
@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch from 67af845 to 4def400 Compare September 29, 2025 12:57
Copy link
Member

@mafredri mafredri left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice work @EhabY, the happy-path is now a pretty good user experience, thanks for implementing my proposal!

I noticed a situation where the login-into-other-windows functionality breaks.

  1. [Initial steps from previous repro]
  2. Select login in one (of two) windows
  3. Enter the wrong token (asdf), see a message like: "Failed to authenticate: You are ..."
  4. Enter the correct token -> Welcome in only one window
  5. In the other window, press login -> token prompt, press cancel -> close window, etc.

It's a bit strange to me that authentication is performed immediately after you've typed in your token, not when pressing [Enter]. (What if you're typing it manually.)

I'm also not sure why this breaks the login flow, perhaps a login attempt (even if failed) is considered a resolution of the promise.

@EhabY
Copy link
Collaborator Author

EhabY commented Sep 30, 2025

It's a bit strange to me that authentication is performed immediately after you've typed in your token, not when pressing [Enter]. (What if you're typing it manually.)

I think this is to provide feedback as soon as possible, VS Code allows this "validateInput" callback. If we want it on "Enter" only it might look a bit more awkward since we'd have to manually implement this validation.

I'm also not sure why this breaks the login flow, perhaps a login attempt (even if failed) is considered a resolution of the promise.

Hmmm, I tried the reproducer and it seems to work (no breakage), we should only show the "Welcome" message (and resolve the promise) if the token is correct anyway, otherwise it's like nothing has changed. Did you do something else in the meantime? 🤔

@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch from 4def400 to 0ef2322 Compare September 30, 2025 12:53
@EhabY EhabY requested a review from mafredri September 30, 2025 12:55
@mafredri
Copy link
Member

I think this is to provide feedback as soon as possible, VS Code allows this "validateInput" callback. If we want it on "Enter" only it might look a bit more awkward since we'd have to manually implement this validation.

I kind of get it, but the current impl. is also kind of awkward when doing anything other than copy pasting. We can put that aside for now though, it's not relevant for this PR.

Hmmm, I tried the reproducer and it seems to work (no breakage), we should only show the "Welcome" message (and resolve the promise) if the token is correct anyway, otherwise it's like nothing has changed. Did you do something else in the meantime? 🤔

I can reproduce it quite reliably (even with your latest push). And it seems it's not even a requirement to enter the wrong token first. I'm not sure of the exact cause but I've managed to reproduce in various scenarios:

  1. Enter wrong token first, then correct
  2. Enter token fast (ready in clipboard)
  3. Enter token slowly (wait a longer time before paste)

@EhabY
Copy link
Collaborator Author

EhabY commented Sep 30, 2025

Hmmmm, to me this means it's one of two things: either we have a race where the 2nd window does not read the correctly entered configurations fast enough or that the session token has not changed (the latter is impossible if you deleted the session file so we can rule it out).

Can I bother you one more time to test the latest push so we can rule out (1)? I sadly cannot reproduce so I'm not sure if this fixes it.

Also are you using Windows/Mac/Linux?

@mafredri
Copy link
Member

Thanks, I tested the new commit but there was no difference.

2nd window does not read the correctly entered configurations fast enough or that the session token has not changed (the latter is impossible if you deleted the session file so we can rule it out).

Glad you mentioned this because it seems to be exactly what's going on. I can reproduce the issue as long as I have the same token in my clipboard which I paste in, but if I grab a new token login works as expected. In either case the token is valid, it's just that in the bug scenario, the same token is used for all attempts.

Could it be that even when deleting the session file, VS Code, or our extension, has some recollection of the old value and ignores the login in other windows because the value didn't change? It seems like the value shouldn't matter, jus that if there was an event, we can try to login.

@EhabY
Copy link
Collaborator Author

EhabY commented Sep 30, 2025

Could it be that even when deleting the session file, VS Code, or our extension, has some recollection of the old value and ignores the login in other windows because the value didn't change? It seems like the value shouldn't matter, just that if there was an event, we can try to login.

Oooh I think I might know where this goes wrong now, we store the session in two different ways, once as a file for the CLI to use (this is the session that you deleted in your reproducer) and the other in the secrets (VS Code maintains that key-value pair internally). In this PR, we respond to session token secret change event since that is stored globally across different VS Code windows. In your case, the session token didn't change so there was no event, even though the CLI session file was deleted (out of sync).

I don't want us to resort to file watchers but this should somehow be unified so there's one source of truth, I'll have a think and try to find an elegant solution 🤔

@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch 2 times, most recently from 70a6c4c to bbfb3d5 Compare October 1, 2025 09:43
@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch from 2a1d50d to 12c7c98 Compare October 3, 2025 12:30
Copy link
Member

@mafredri mafredri left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Awesome work @EhabY! In use, everything is behaving as I'd expect and the UX is so much better, thank you. I flagged a couple of things but mainly for your awareness, feel free to dismiss if they are non-issues.

@EhabY EhabY force-pushed the fix-login-logout-in-multiple-windows branch from 223404c to 820cb1c Compare October 6, 2025 10:11
@EhabY EhabY merged commit 648360a into coder:main Oct 6, 2025
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Improve consistency in client-side logout experience
2 participants