Open safesparrow opened 1 year ago
Some thoughts. Parsing eagerly without waiting for typecheck is conceptually equivalent to caching every parse. This is basically what #14852 do, but even more aggressive.
After #14852 We could quite easily cache awaitables. Parsing is not cancellable from what I understand, so let's say we store a backgroundTask.
Now if we don't wait for the BoundModel to request a result, but start that task eagerly in SyntaxTree
constructor, we're basically done.
One question remains, how compatible this approach is with partial checking.
So basically we could launch parsing tasks in parallel at IncrementalBuilder construction and also on every file changed notification. Cache the tasks and return Task.Result each time the builder calls for parse.
The main questions then are:
IncrementalBuilder
is constructed eagerly for all files in the project or one at a time, waiting for .Parse
to finish before proceeding to the next file (easy to verify).@safesparrow I have something that works already and shows some modest gains in benchmarks. It feels OK in the IDE, although I yet have to install it and use for a while.
Is your feature request related to a problem? Please describe.
IDE interactions in F# projects are slow and they make development experience subpar.
Describe the solution you'd like
One way to speed them up is to allow all files in a project to be parsed in parallel, when type-checking of multiple files/whole project is about to be performed.
Describe alternatives you've considered
Introducing a parsing cache of configurable size, that applies to all endpoints correctly would limit the slowdown caused by slow, sequential parsing. I raised https://github.com/dotnet/fsharp/issues/14848 for that. However:
Additional context
IncrementalBuilder
has the idea of sequential type-checking+parsing very much embedded in it (see theBoundModel
type).