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

noDts project resolutions verification and updates for incremental behaviour #56016

Merged
merged 13 commits into from
Oct 10, 2023

Conversation

sheetalkamat
Copy link
Member

@sheetalkamat sheetalkamat commented Oct 6, 2023

When resolving module specifier for finding implementation file, we were using module resolution cache which means that it was possible to reuse existing module resolution and add more failed lookup locations to it. Which means that when we release that resolution as part of program update/close, we will try to release more locations than being watched.
Fixed this by marking module resolution cache as read-only after construction of program, which indicates module resolution algorithm to not update the cache or resolution. (instead of freezing internal maps, went ahead with at usage mode approach to avoid having to deal with invalidation logic eg for package json info before program construction) 1b6c9a8

Also updated some of the other noDts project related things:

  • Project gets updates root files only if the requested file changes 2d40a69
  • Add isBackgroundProject so we can ensure all the updates where we need to skip things for background project are handled correctly fe7f068
  • Earlier if the js file was not part of project it would use it only if it was at any point used and cached in services. Instead of that, now it's always added to project to search for implementation from. 0efe4ee

Added coverage for some of the missing cases like

  • when module specifier resolved from file is not already in the file: d552636
  • file is added to project after project construction for the first time based on imports present in existing file 43720b9
  • repeated query shouldn't change project: 5ef80a9
  • resolution is reused that was done from some sibling folder 8538100
  • incremental verification for resolveSingleModuleNameWithoutWatching to ensure it does not impact state: a49de0e

@typescript-bot typescript-bot added Author: Team For Uncommitted Bug PR for untriaged, rejected, closed or missing bug labels Oct 9, 2023
@sheetalkamat sheetalkamat marked this pull request as ready for review October 9, 2023 21:24
@sheetalkamat sheetalkamat changed the title [wip] noDts project resolutions verification and updates for incremental behaviour noDts project resolutions verification and updates for incremental behaviour Oct 9, 2023
@jakebailey
Copy link
Member

I'm not entirely sure how these types are used in public, but is the readonly flag something that should be exported so that external consumers know to use the API in the right way, or is it unlikely to matter?

@sheetalkamat
Copy link
Member Author

I think we only care about resolution cache we created and are using so i am not sure if it matters. But also while investigating i was wondering Project::getModuleResolutionCache should have been internal and i was going to mark it that way and forgot. Will do that.

@typescript-bot
Copy link
Collaborator

Looks like you're introducing a change to the public API surface area. If this includes breaking changes, please document them on our wiki's API Breaking Changes page.

Also, please make sure @DanielRosenwasser and @RyanCavanaugh are aware of the changes, just as a heads up.

@@ -3354,7 +3354,6 @@ declare namespace ts {
readFile(fileName: string): string | undefined;
writeFile(fileName: string, content: string): void;
fileExists(file: string): boolean;
getModuleResolutionCache(): ModuleResolutionCache | undefined;
Copy link
Member

Choose a reason for hiding this comment

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

Copy link
Member Author

Choose a reason for hiding this comment

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

They shouldnt have been. Gitlens went in loops but couldnt figure out when and why this was exposed but from looks of it, it should not be exposed at all

Copy link
Member

Choose a reason for hiding this comment

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

It was added in #47388, it seems. @andrewbranch

Copy link
Member

Choose a reason for hiding this comment

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

Wait, but it's internal there. Hm, one sec.

Copy link
Member

Choose a reason for hiding this comment

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

It’s internal on LanguageServiceHost, but not on Project 😕

Copy link
Member

Choose a reason for hiding this comment

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

Ah, yeah, I just discovered that. I guess it should just be dropped?

Copy link
Member

Choose a reason for hiding this comment

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

(To be clear I'm not trying to actually blame anyone, moreso just trying to do the forensics so we know if there was a reason to have it 😅)

resultFromCache.affectingLocations = updateResolutionField(resultFromCache.affectingLocations, affectingLocations);
resultFromCache.resolutionDiagnostics = updateResolutionField(resultFromCache.resolutionDiagnostics, diagnostics);
return resultFromCache;
if (!cache?.isReadonly) {
Copy link
Member

Choose a reason for hiding this comment

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

My only concern is it seems somewhat easy to miss this check if someone were adding new code that interacts with the cache, and it seems like there still are no compile-time or runtime checks preventing you from mutating the contents at a time when it could cause problems. Would it be worth changing ResolvedModuleWithFailedLookupLocations etc. to have readonly properties that can only be changed by a method on the cache, which could check isReadonly to ensure it’s not being violated?

Copy link
Member Author

Choose a reason for hiding this comment

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

i can do that, but frankly I dont see point in that since I think we want this method to be that one. Which ensures the resolutionWithFailedLookupLocation is created correctly.

@sheetalkamat sheetalkamat merged commit 9473195 into main Oct 10, 2023
@sheetalkamat sheetalkamat deleted the sourceDefChanges branch October 10, 2023 17:24
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Author: Team For Uncommitted Bug PR for untriaged, rejected, closed or missing bug
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants