Skip to content

WIP: Process shake restarts asynchronously#4879

Draft
crtschin wants to merge 6 commits intohaskell:masterfrom
crtschin:crtschin/deduplicate-shake-restarts
Draft

WIP: Process shake restarts asynchronously#4879
crtschin wants to merge 6 commits intohaskell:masterfrom
crtschin:crtschin/deduplicate-shake-restarts

Conversation

@crtschin
Copy link
Copy Markdown
Collaborator

@crtschin crtschin commented Mar 31, 2026

Would close #4725.

Implements the ideas from #4725 (comment). Makes the following changes:

  1. Processes notifications asynchronously keeping with the logic that notifications preceding any request, also finish before that request is processed. But does so asynchronously.
  2. The above opens up the possibility that there could be multiple shake restarts in-flight because multiple notifications arriving in quick succession. Instead of storing these restarts in a queue, accumulate all restart changes in a single slot, to be processed at once.

@crtschin crtschin requested review from fendor and wz1000 as code owners March 31, 2026 19:53
@crtschin crtschin marked this pull request as draft March 31, 2026 19:56
@crtschin crtschin force-pushed the crtschin/deduplicate-shake-restarts branch 4 times, most recently from cc251cd to 88e0f88 Compare April 1, 2026 23:22
@fendor fendor requested a review from soulomoon April 7, 2026 09:37
@crtschin crtschin force-pushed the crtschin/deduplicate-shake-restarts branch from 0a7302b to 4090ec3 Compare April 9, 2026 17:27
@crtschin
Copy link
Copy Markdown
Collaborator Author

crtschin commented Apr 9, 2026

I can't get tests to pass with notifications fully async. Kinda makes sense looking at what these notifications indicate. I thought I could get away with only LSP handling everything synchronously of the VFS-side, but it appears not.

I'm now trying out a small variant where notifications are still synchronously, but that the session restarts are initiated async, while still blocking subsequent LSP requests. So restarts still get squashed.

@crtschin crtschin force-pushed the crtschin/deduplicate-shake-restarts branch 2 times, most recently from 42b60e4 to 69e0d70 Compare April 9, 2026 22:30
@crtschin crtschin force-pushed the crtschin/deduplicate-shake-restarts branch 4 times, most recently from 0933d63 to 1dfd24e Compare May 2, 2026 21:28
@crtschin crtschin force-pushed the crtschin/deduplicate-shake-restarts branch from 1dfd24e to 5978cad Compare May 2, 2026 22:54
@soulomoon soulomoon added the performance Issues about memory consumption, responsiveness, etc. label May 3, 2026
Copy link
Copy Markdown
Collaborator

@soulomoon soulomoon left a comment

Choose a reason for hiding this comment

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

good work on the restart squash.
But if notifications are still handled synchronously, #4725 won't be close since consective typing emits consective notifications and their restarts won't be able to merge

sessionRestartTQueue <- withWorkerQueueSimple (cmapWithPrio Session.LogSessionWorkerThread recorder) "RestartTQueue"
sessionRestartTQueue <- liftIO $ newRestartSlot
sessionLoaderTQueue <- withWorkerQueueSimple (cmapWithPrio Session.LogSessionWorkerThread recorder) "SessionLoaderTQueue"
ContT $ \action -> withRestartWorker ideMVar $ action ()
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

better to extend the logic of workerThread module so it can be reused here.

there is a slight chance that downstream code would swallow the async exception and hang the shutdown. workerThread handled that by setting up a shutdown flag .

@crtschin
Copy link
Copy Markdown
Collaborator Author

crtschin commented May 4, 2026

But if notifications are still handled synchronously, #4725 won't be close since consective typing emits consective notifications and their restarts won't be able to merge

Thanks for taking a peak at the PR! The idea I'm going for now here is to still have notifications be synchronous, but that they don't wait for the shake restart to finish, unlike now. So multiple subsequent edits will issue multiple synchronous notifications which will all start asynchronous shake restarts. This allows the restarts to merge.

Note that this is still me experimenting, I'm not sure if I'm breaking preconditions. This is all quite nuancy.

@soulomoon
Copy link
Copy Markdown
Collaborator

soulomoon commented May 4, 2026

So multiple subsequent edits will issue multiple synchronous notifications which will all start asynchronous shake restarts. This allows the restarts to merge.

good idea

they don't wait for the shake restart to finish

I’ve experienced this before: if we don’t wait for Shake to fully restart, requests may observe stale state. I think we should ensure any pending restarts have completed before processing new requests but keep the notifications side of the story as you suggested, It might work.

Also it might be a good idea to go through the occurences of mkPluginNotificationHandler and find out if bug would occur.

----- update ----

Also we should move the "updatePositionMapping" in the notification handler into restart so every restart(merged or not) would see consistent mapping state ?

@crtschin crtschin changed the title Process notifications asynchronously Process shake restarts asynchronously May 4, 2026
@crtschin crtschin changed the title Process shake restarts asynchronously WIP: Process shake restarts asynchronously May 4, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

performance Issues about memory consumption, responsiveness, etc.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Reduce lag when editing by merging sequential Shake restarts

2 participants