From e5d1bba56983314968ff7ce2086781a738ca3a3e Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Wed, 13 Mar 2024 15:15:00 +0100 Subject: [PATCH 1/4] tmp --- .../FSharp/FSharp.Common/FSharp.Common.fsproj | 1 + .../src/Checker/FcsCheckerService.fs | 83 +++++++++++++++++-- .../src/Settings/FSharpOptions.fs | 9 +- 3 files changed, 84 insertions(+), 9 deletions(-) diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj b/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj index 4e64e7f372..9c600b938a 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj @@ -12,6 +12,7 @@ true JetBrains.ReSharper.Plugins.FSharp JetBrains.ReSharper.Plugins.FSharp.Common + FS0057 diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs index 178eb0518f..a64e4c8e9c 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs @@ -25,6 +25,7 @@ open JetBrains.ReSharper.Plugins.FSharp.Shim.AssemblyReader open JetBrains.ReSharper.Plugins.FSharp.Util open JetBrains.ReSharper.Psi open JetBrains.ReSharper.Psi.CSharp +open JetBrains.ReSharper.Psi.Caches open JetBrains.ReSharper.Psi.Modules open JetBrains.ReSharper.Psi.Tree open JetBrains.ReSharper.Psi.VB @@ -36,6 +37,7 @@ module FcsCheckerService = SourceText.ofString(document.GetText()) +// add the project key? type FcsProject = { OutputPath: VirtualFileSystemPath ProjectOptions: FSharpProjectOptions @@ -74,6 +76,57 @@ type FcsProject = writer.WriteLine() +[] +type FcsSnapshotCache(fcsProjectProvider: IFcsProjectProvider, locks: IShellLocks) = + let snapshots = Dictionary() + + let remove (psiModule: IPsiModule) = + let projectKey = FcsProjectKey.Create(psiModule) + snapshots.Remove(projectKey) |> ignore + + match fcsProjectProvider.GetReferencedModule(projectKey) with + | None -> () + | Some referencedModule -> + + // todo: recursive update? + for referencingProject in referencedModule.ReferencingProjects do + snapshots.Remove(referencingProject) |> ignore + + member this.GetProjectSnapshot(projectKey: FcsProjectKey, options: FSharpProjectOptions) = + // todo: use source files in file snapshots? + lock this (fun _ -> + snapshots.GetOrCreateValue(projectKey, fun (projectKey: FcsProjectKey) -> + FSharpProjectSnapshot.FromOptions(options).RunAsTask() + ) + ) + + interface IPsiSourceFileCache with + member this.MarkAsDirty(sourceFile) = + locks.AssertWriteAccessAllowed() + remove sourceFile.PsiModule + + member this.OnDocumentChange(sourceFile, _) = + locks.AssertWriteAccessAllowed() + remove sourceFile.PsiModule + + member this.OnPsiChange(elementContainingChanges, _) = + if isNotNull elementContainingChanges then + locks.AssertWriteAccessAllowed() + remove (elementContainingChanges.GetPsiModule()) + + member this.HasDirtyFiles = false + member this.UpToDate _ = true + member this.SyncUpdate _ = () + + member this.Build(_, _) = null + member this.Drop _ = () + member this.Dump(_, _) = () + member this.Load(_, _) = null + member this.Merge(_, _) = () + member this.MergeLoaded _ = () + member this.Save(_, _) = () + + [] type FcsProjectInvalidationType = /// Used when invalidation is needed for a project still known to FCS. @@ -88,14 +141,16 @@ type FcsProjectInvalidationType = type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotifier: OnSolutionCloseNotifier, settingsStore: ISettingsStore, locks: IShellLocks, configurations: RunsProducts.ProductConfigurations) = - let checker = - Environment.SetEnvironmentVariable("FCS_CheckFileInProjectCacheSize", "20") + let settingsStoreLive = settingsStore.BindToContextLive(lifetime, ContextRange.ApplicationWide) - let settingsStoreLive = settingsStore.BindToContextLive(lifetime, ContextRange.ApplicationWide) + let getSettingProperty name = + let setting = SettingsUtil.getEntry settingsStore name + settingsStoreLive.GetValueProperty(lifetime, setting, null) - let getSettingProperty name = - let setting = SettingsUtil.getEntry settingsStore name - settingsStoreLive.GetValueProperty(lifetime, setting, null) + let useTransparentCompiler = true //(getSettingProperty "UseTransparentCompiler").Value + + let checker = + Environment.SetEnvironmentVariable("FCS_CheckFileInProjectCacheSize", "20") let skipImpl = getSettingProperty "SkipImplementationAnalysis" let analyzerProjectReferencesInParallel = getSettingProperty "ParallelProjectReferencesAnalysis" @@ -106,7 +161,8 @@ type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotif keepAllBackgroundResolutions = false, keepAllBackgroundSymbolUses = false, enablePartialTypeChecking = skipImpl.Value, - parallelReferenceResolution = analyzerProjectReferencesInParallel.Value) + parallelReferenceResolution = analyzerProjectReferencesInParallel.Value, + useTransparentCompiler = useTransparentCompiler) checker @@ -174,8 +230,19 @@ type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotif let source = FcsCheckerService.getSourceText sourceFile.Document logger.Trace("ParseAndCheckFile: start {0}, {1}", path, opName) + let getParseAndCheckResults () = + if useTransparentCompiler then + let projectKey = FcsProjectKey.Create(psiModule) + let fcsSnapshotCache = sourceFile.GetSolution().GetComponent() + let snapshot = fcsSnapshotCache.GetProjectSnapshot(projectKey, options) + match x.Checker.ParseAndCheckFileInProject(path, snapshot).RunAsTask() with + | _, FSharpCheckFileAnswer.Aborted -> None + | parseFileResults, FSharpCheckFileAnswer.Succeeded checkFileResults -> Some(parseFileResults, checkFileResults) + else + x.Checker.ParseAndCheckDocument(path, source, options, allowStaleResults, opName).RunAsTask() + // todo: don't cancel the computation when file didn't change - match x.Checker.ParseAndCheckDocument(path, source, options, allowStaleResults, opName).RunAsTask() with + match getParseAndCheckResults () with | Some (parseResults, checkResults) -> logger.Trace("ParseAndCheckFile: finish {0}, {1}", path, opName) Some { ParseResults = parseResults; CheckResults = checkResults } diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Settings/FSharpOptions.fs b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Settings/FSharpOptions.fs index f180cba49b..69f92f2da9 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Settings/FSharpOptions.fs +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Settings/FSharpOptions.fs @@ -29,6 +29,7 @@ module FSharpOptions = let [] nonFSharpProjectInMemoryReferences = "Analyze C# and VB.NET project references in-memory" let [] outOfScopeCompletion = "Enable out of scope items completion" let [] topLevelOpenCompletion = "Add 'open' declarations to top level module or namespace" + let [] useTransparentCompilerDescription = "Use TransparentCompiler" [, "FSharpOptions")>] @@ -46,7 +47,10 @@ type FSharpOptions = mutable EnableOutOfScopeCompletion: bool [] - mutable TopLevelOpenCompletion: bool } + mutable TopLevelOpenCompletion: bool + + [] + mutable UseTransparentCompiler: bool } type FantomasLocationSettings = | AutoDetected = 0 @@ -155,6 +159,9 @@ type FSharpOptionsProvider(lifetime, solution, settings, settingsSchema) = member val NonFSharpProjectInMemoryReferences = base.GetValueProperty("NonFSharpProjectInMemoryReferences").Value with get, set + member val UseTransparentCompiler = + base.GetValueProperty("UseTransparentCompiler").Value + member this.UpdateAssemblyReaderSetting() = this.NonFSharpProjectInMemoryReferences <- base.GetValueProperty("NonFSharpProjectInMemoryReferences").Value From fbd52d58a76ee713bd23e9c35f4d416abf1e4497 Mon Sep 17 00:00:00 2001 From: nojaf Date: Mon, 18 Mar 2024 10:25:53 +0100 Subject: [PATCH 2/4] Use local compiler. --- ReSharper.FSharp/Directory.Build.props | 9 +++++++++ ReSharper.FSharp/TypeProviders.Host.targets | 2 +- .../FSharp.TypeProviders.Host.NetCore.csproj | 3 +-- .../FSharp.TypeProviders.Host.csproj | 3 +-- .../src/FSharp/FSharp.Common/FSharp.Common.fsproj | 1 - .../FSharp.Common/src/Checker/FcsCheckerService.fs | 3 ++- .../FSharp.ProjectModelBase.csproj | 1 - .../FSharp/FSharp.Psi.Daemon/FSharp.Psi.Daemon.fsproj | 3 +-- .../FSharp.Psi.Features/FSharp.Psi.Features.fsproj | 3 +-- .../FSharp.Psi.Intentions/FSharp.Psi.Intentions.fsproj | 1 - .../FSharp.Psi.Services/FSharp.Psi.Services.fsproj | 3 +-- ReSharper.FSharp/src/FSharp/FSharp.Psi/FSharp.Psi.csproj | 3 +-- .../FSharp/FSharp.Tests.Host/FSharp.Tests.Host.fsproj | 1 - .../FSharp.TypeProviders.Protocol.csproj | 1 - .../src/FSharp.Common.Tests/FSharp.Common.Tests.fsproj | 1 - .../FSharp.Intentions.Tests.fsproj | 1 - .../src/FSharp.Tests.Common/FSharp.Tests.Common.fsproj | 1 - .../test/src/FSharp.Tests/FSharp.Tests.fsproj | 1 - 18 files changed, 18 insertions(+), 23 deletions(-) diff --git a/ReSharper.FSharp/Directory.Build.props b/ReSharper.FSharp/Directory.Build.props index db6c9e9455..1ec0b8c36e 100644 --- a/ReSharper.FSharp/Directory.Build.props +++ b/ReSharper.FSharp/Directory.Build.props @@ -33,5 +33,14 @@ $(Subplatform).Psi.Features_test_Framework.Props $(Subplatform).Rider_RdBackend.Common.Props $(Subplatform).Rider_Rider.Backend.Props + true + $(MSBuildThisFileDirectory)../../fsharp + + + + + + + diff --git a/ReSharper.FSharp/TypeProviders.Host.targets b/ReSharper.FSharp/TypeProviders.Host.targets index 0ab3216525..b5db342ab0 100644 --- a/ReSharper.FSharp/TypeProviders.Host.targets +++ b/ReSharper.FSharp/TypeProviders.Host.targets @@ -14,7 +14,7 @@ - + diff --git a/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.NetCore/FSharp.TypeProviders.Host.NetCore.csproj b/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.NetCore/FSharp.TypeProviders.Host.NetCore.csproj index aa48a1b6db..3f8fb7eb90 100644 --- a/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.NetCore/FSharp.TypeProviders.Host.NetCore.csproj +++ b/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.NetCore/FSharp.TypeProviders.Host.NetCore.csproj @@ -25,7 +25,6 @@ - @@ -46,4 +45,4 @@ - \ No newline at end of file + diff --git a/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.csproj b/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.csproj index 00b4dc0d6a..fe58864288 100644 --- a/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.csproj +++ b/ReSharper.FSharp/src/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host/FSharp.TypeProviders.Host.csproj @@ -26,7 +26,6 @@ - @@ -39,4 +38,4 @@ - \ No newline at end of file + diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj b/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj index 9c600b938a..1a10bb2efb 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/FSharp.Common.fsproj @@ -74,7 +74,6 @@ - diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs index a64e4c8e9c..7a2f583d40 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs @@ -276,7 +276,8 @@ type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotif member x.GetCachedScriptOptions(path) = if checker.IsValueCreated then - checker.Value.GetCachedScriptOptions(path) + None + // TODO: checker.Value.GetCachedScriptOptions(path) else None member x.InvalidateFcsProject(projectOptions: FSharpProjectOptions, invalidationType: FcsProjectInvalidationType) = diff --git a/ReSharper.FSharp/src/FSharp/FSharp.ProjectModelBase/FSharp.ProjectModelBase.csproj b/ReSharper.FSharp/src/FSharp/FSharp.ProjectModelBase/FSharp.ProjectModelBase.csproj index 8675fb00d2..34437a84d5 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.ProjectModelBase/FSharp.ProjectModelBase.csproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.ProjectModelBase/FSharp.ProjectModelBase.csproj @@ -16,7 +16,6 @@ - diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Daemon/FSharp.Psi.Daemon.fsproj b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Daemon/FSharp.Psi.Daemon.fsproj index d09f9474b0..19cda6c7ed 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Daemon/FSharp.Psi.Daemon.fsproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Daemon/FSharp.Psi.Daemon.fsproj @@ -83,7 +83,6 @@ - @@ -92,4 +91,4 @@ - \ No newline at end of file + diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Features/FSharp.Psi.Features.fsproj b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Features/FSharp.Psi.Features.fsproj index b37f139a1d..3796339eec 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Features/FSharp.Psi.Features.fsproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Features/FSharp.Psi.Features.fsproj @@ -124,7 +124,6 @@ - @@ -165,4 +164,4 @@ - \ No newline at end of file + diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Intentions/FSharp.Psi.Intentions.fsproj b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Intentions/FSharp.Psi.Intentions.fsproj index fc0dbc626e..f849ff1c12 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Intentions/FSharp.Psi.Intentions.fsproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Intentions/FSharp.Psi.Intentions.fsproj @@ -142,7 +142,6 @@ - diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Services/FSharp.Psi.Services.fsproj b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Services/FSharp.Psi.Services.fsproj index 54176c82f2..dbdbdeb6f3 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Psi.Services/FSharp.Psi.Services.fsproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Psi.Services/FSharp.Psi.Services.fsproj @@ -88,7 +88,6 @@ - @@ -97,4 +96,4 @@ - \ No newline at end of file + diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Psi/FSharp.Psi.csproj b/ReSharper.FSharp/src/FSharp/FSharp.Psi/FSharp.Psi.csproj index 8689b3c193..ff44f3d6a7 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Psi/FSharp.Psi.csproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Psi/FSharp.Psi.csproj @@ -32,7 +32,6 @@ - @@ -51,4 +50,4 @@ - \ No newline at end of file + diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Tests.Host/FSharp.Tests.Host.fsproj b/ReSharper.FSharp/src/FSharp/FSharp.Tests.Host/FSharp.Tests.Host.fsproj index 9c4ca23083..1b060eee8a 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Tests.Host/FSharp.Tests.Host.fsproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.Tests.Host/FSharp.Tests.Host.fsproj @@ -21,7 +21,6 @@ - diff --git a/ReSharper.FSharp/src/FSharp/FSharp.TypeProviders.Protocol/FSharp.TypeProviders.Protocol.csproj b/ReSharper.FSharp/src/FSharp/FSharp.TypeProviders.Protocol/FSharp.TypeProviders.Protocol.csproj index 096eb79234..b215d4fd02 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.TypeProviders.Protocol/FSharp.TypeProviders.Protocol.csproj +++ b/ReSharper.FSharp/src/FSharp/FSharp.TypeProviders.Protocol/FSharp.TypeProviders.Protocol.csproj @@ -17,7 +17,6 @@ - diff --git a/ReSharper.FSharp/test/src/FSharp.Common.Tests/FSharp.Common.Tests.fsproj b/ReSharper.FSharp/test/src/FSharp.Common.Tests/FSharp.Common.Tests.fsproj index 94e775834b..40be2ad749 100644 --- a/ReSharper.FSharp/test/src/FSharp.Common.Tests/FSharp.Common.Tests.fsproj +++ b/ReSharper.FSharp/test/src/FSharp.Common.Tests/FSharp.Common.Tests.fsproj @@ -20,7 +20,6 @@ - diff --git a/ReSharper.FSharp/test/src/FSharp.Intentions.Tests/FSharp.Intentions.Tests.fsproj b/ReSharper.FSharp/test/src/FSharp.Intentions.Tests/FSharp.Intentions.Tests.fsproj index 641af1b8a8..4b9ffb53b9 100644 --- a/ReSharper.FSharp/test/src/FSharp.Intentions.Tests/FSharp.Intentions.Tests.fsproj +++ b/ReSharper.FSharp/test/src/FSharp.Intentions.Tests/FSharp.Intentions.Tests.fsproj @@ -142,7 +142,6 @@ - diff --git a/ReSharper.FSharp/test/src/FSharp.Tests.Common/FSharp.Tests.Common.fsproj b/ReSharper.FSharp/test/src/FSharp.Tests.Common/FSharp.Tests.Common.fsproj index 844bd07cf0..f5c57209df 100644 --- a/ReSharper.FSharp/test/src/FSharp.Tests.Common/FSharp.Tests.Common.fsproj +++ b/ReSharper.FSharp/test/src/FSharp.Tests.Common/FSharp.Tests.Common.fsproj @@ -24,7 +24,6 @@ - diff --git a/ReSharper.FSharp/test/src/FSharp.Tests/FSharp.Tests.fsproj b/ReSharper.FSharp/test/src/FSharp.Tests/FSharp.Tests.fsproj index c99878c9be..c5f7b82480 100644 --- a/ReSharper.FSharp/test/src/FSharp.Tests/FSharp.Tests.fsproj +++ b/ReSharper.FSharp/test/src/FSharp.Tests/FSharp.Tests.fsproj @@ -63,7 +63,6 @@ - From fb7f5be88fa5c75f55194da11b93a31b14ecd595 Mon Sep 17 00:00:00 2001 From: nojaf Date: Mon, 18 Mar 2024 10:33:42 +0100 Subject: [PATCH 3/4] Remove references recursively. --- .../FSharp.Common/src/Checker/FcsCheckerService.fs | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs index 7a2f583d40..86a047a1eb 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs @@ -80,17 +80,19 @@ type FcsProject = type FcsSnapshotCache(fcsProjectProvider: IFcsProjectProvider, locks: IShellLocks) = let snapshots = Dictionary() - let remove (psiModule: IPsiModule) = - let projectKey = FcsProjectKey.Create(psiModule) - snapshots.Remove(projectKey) |> ignore - + let rec removeReferences (projectKey: FcsProjectKey) = match fcsProjectProvider.GetReferencedModule(projectKey) with | None -> () | Some referencedModule -> - // todo: recursive update? for referencingProject in referencedModule.ReferencingProjects do + removeReferences referencingProject snapshots.Remove(referencingProject) |> ignore + + let remove (psiModule: IPsiModule) = + let projectKey = FcsProjectKey.Create(psiModule) + snapshots.Remove(projectKey) |> ignore + removeReferences projectKey member this.GetProjectSnapshot(projectKey: FcsProjectKey, options: FSharpProjectOptions) = // todo: use source files in file snapshots? From d43e84ab0833e75a608e08febcfb2bfdad427dba Mon Sep 17 00:00:00 2001 From: nojaf Date: Mon, 18 Mar 2024 14:09:44 +0100 Subject: [PATCH 4/4] Respect useTransparentCompiler in additional FSharpChecker calls. --- .../src/Checker/FcsCheckerService.fs | 34 +++++++++++++++---- .../FSharpScriptPsiModuleFactory.fs | 8 ++++- 2 files changed, 35 insertions(+), 7 deletions(-) diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs index 86a047a1eb..af8cda3953 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/Checker/FcsCheckerService.fs @@ -149,6 +149,7 @@ type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotif let setting = SettingsUtil.getEntry settingsStore name settingsStoreLive.GetValueProperty(lifetime, setting, null) + // TODO: double check setting let useTransparentCompiler = true //(getSettingProperty "UseTransparentCompiler").Value let checker = @@ -177,6 +178,7 @@ type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotif member val AssemblyReaderShim = Unchecked.defaultof with get, set member x.Checker = checker.Value + member val UseTransparentCompiler = useTransparentCompiler member this.AssertFcsAccessThread() = () @@ -267,20 +269,34 @@ type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotif let path = file.GetLocation().FullPath logger.Trace("TryGetStaleCheckResults: start {0}, {1}", path, opName) - match x.Checker.TryGetRecentCheckResultsForFile(path, options) with - | Some (_, checkResults, _) -> + let recentCheckResults = + if not useTransparentCompiler then + x.Checker.TryGetRecentCheckResultsForFile(path, options) + |> Option.map (fun (_, checkResults, _) -> checkResults) + else + match x.FcsProjectProvider.GetFcsProject(file.PsiModule) with + | None -> None + | Some fcsProject -> + + let projectKey = FcsProjectKey.Create(file.PsiModule) + let fcsSnapshotCache = file.GetSolution().GetComponent() + let snapshot = fcsSnapshotCache.GetProjectSnapshot(projectKey, fcsProject.ProjectOptions) + x.Checker.TryGetRecentCheckResultsForFile(path, snapshot) + |> Option.map snd + + match recentCheckResults with + | Some checkResults -> logger.Trace("TryGetStaleCheckResults: finish {0}, {1}", path, opName) Some checkResults - | _ -> logger.Trace("TryGetStaleCheckResults: fail {0}, {1}", path, opName) None member x.GetCachedScriptOptions(path) = if checker.IsValueCreated then + checker.Value.GetCachedScriptOptions(path) + else None - // TODO: checker.Value.GetCachedScriptOptions(path) - else None member x.InvalidateFcsProject(projectOptions: FSharpProjectOptions, invalidationType: FcsProjectInvalidationType) = if checker.IsValueCreated then @@ -290,7 +306,13 @@ type FcsCheckerService(lifetime: Lifetime, logger: ILogger, onSolutionCloseNotif checker.Value.ClearCache(Seq.singleton projectOptions) | FcsProjectInvalidationType.Remove -> logger.Trace("Invalidate FcsProject in FCS: {0}", projectOptions.ProjectFileName) - checker.Value.InvalidateConfiguration(projectOptions) + if useTransparentCompiler then + // InvalidateConfiguration isn't required for the transparent compiler as it works differently. + // InvalidateConfiguration in the BackgroundCompiler will recreate the createBuilderNode. + // This is not required in the TransparentCompiler and so Clearing the cache would be the proper equivalent. + checker.Value.ClearCache(Seq.singleton projectOptions) + else + checker.Value.InvalidateConfiguration(projectOptions) /// Use with care: returns wrong symbol inside its non-recursive declaration, see dotnet/fsharp#7694. member x.ResolveNameAtLocation(sourceFile: IPsiSourceFile, names, coords, resolveExpr: bool, opName) = diff --git a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/ProjectModel/FSharpScriptPsiModuleFactory.fs b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/ProjectModel/FSharpScriptPsiModuleFactory.fs index 2c049d4689..9c2b8f2135 100644 --- a/ReSharper.FSharp/src/FSharp/FSharp.Common/src/ProjectModel/FSharpScriptPsiModuleFactory.fs +++ b/ReSharper.FSharp/src/FSharp/FSharp.Common/src/ProjectModel/FSharpScriptPsiModuleFactory.fs @@ -263,7 +263,13 @@ type FSharpScriptPsiModulesProvider(lifetime: Lifetime, solution: ISolution, cha |> Option.iter (fun psiModule -> match checkerService.GetCachedScriptOptions(path.FullPath) with | Some options -> checkerService.InvalidateFcsProject(options, FcsProjectInvalidationType.Remove) - | None -> () + | None -> + if checkerService.UseTransparentCompiler then + // The transparent compiler always returns GetCachedScriptOptions + // We can easily construct the project identifier (as it is done in GetProjectOptionsFromScript/GetProjectSnapshotFromScript) + // and clear the cache that way. + let projectIdentifier = ProjectSnapshot.FSharpProjectIdentifier($"%s{path.FullPath}.fsproj", "") + checkerService.Checker.ClearCache(Seq.singleton projectIdentifier) scriptsFromProjectFiles.RemoveValue(path, psiModule) |> ignore removePsiModule psiModule