Skip to content

Commit 4185ee3

Browse files
authored
Fix finding internal symbols in internals-visible-to projects (#15902)
1 parent 28cb3a3 commit 4185ee3

File tree

3 files changed

+47
-11
lines changed

3 files changed

+47
-11
lines changed

tests/FSharp.Compiler.ComponentTests/FSharpChecker/FindReferences.fs

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,36 @@ let ``Finding references in project`` (fastCheck, captureIdentifiersWhenParsing)
124124
findAllReferencesToModuleFromFile "File000" fastCheck (expectNumberOfResults 5)
125125
}
126126

127+
[<Fact>]
128+
let ``Find references to internal symbols in other projects`` () =
129+
let library = {
130+
SyntheticProject.Create("Library",
131+
{ sourceFile "Library" [] with Source = """
132+
namespace Lib
133+
134+
module internal Library =
135+
let foo x = x + 5
136+
137+
[<assembly: System.Runtime.CompilerServices.InternalsVisibleTo("FileFirst")>]
138+
do () """ })
139+
with AutoAddModules = false }
140+
141+
let project =
142+
{ SyntheticProject.Create("App",
143+
{ sourceFile "First" [] with Source = """
144+
open Lib
145+
let bar x = Library.foo x""" })
146+
with DependsOn = [library] }
147+
148+
project.Workflow {
149+
placeCursor "Library" "foo"
150+
findAllReferences (expectToFind [
151+
"FileFirst.fs", 4, 12, 23
152+
"FileLibrary.fs", 5, 8, 11
153+
])
154+
}
155+
156+
127157
[<Fact>]
128158
let ``We find back-ticked identifiers`` () =
129159
SyntheticProject.Create(

tests/FSharp.Test.Utilities/ProjectGeneration.fs

Lines changed: 11 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -441,6 +441,9 @@ let private renderFsProj (p: SyntheticProject) =
441441
let version = reference.Version |> Option.map (fun v -> $" Version=\"{v}\"") |> Option.defaultValue ""
442442
$"<PackageReference Include=\"{reference.Name}\"{version}/>"
443443

444+
for project in p.DependsOn do
445+
$"<ProjectReference Include=\"{project.ProjectFileName}\" />"
446+
444447
for f in p.SourceFiles do
445448
if f.HasSignatureFile then
446449
$"<Compile Include=\"{f.SignatureFileName}\" />"
@@ -1019,10 +1022,10 @@ type ProjectWorkflowBuilder
10191022

10201023
member this.FindSymbolUse(ctx: WorkflowContext, fileId, symbolName: string) =
10211024
async {
1022-
let file = ctx.Project.Find fileId
1023-
let fileName = ctx.Project.ProjectDir ++ file.FileName
1024-
let source = renderSourceFile ctx.Project file
1025-
let options= ctx.Project.GetProjectOptions checker
1025+
let project, file = ctx.Project.FindInAllProjects fileId
1026+
let fileName = project.ProjectDir ++ file.FileName
1027+
let source = renderSourceFile project file
1028+
let options= project.GetProjectOptions checker
10261029
return! getSymbolUse fileName source symbolName options checker
10271030
}
10281031

@@ -1072,16 +1075,17 @@ type ProjectWorkflowBuilder
10721075
member this.FindAllReferences(workflow: Async<WorkflowContext>, processResults) =
10731076
async {
10741077
let! ctx = workflow
1075-
let options = ctx.Project.GetProjectOptions checker
10761078

10771079
let symbolUse =
10781080
ctx.Cursor
10791081
|> Option.defaultWith (fun () ->
10801082
failwith $"Please place cursor at a valid location via placeCursor first")
10811083

10821084
let! results =
1083-
[ for f in options.SourceFiles do
1084-
checker.FindBackgroundReferencesInFile(f, options, symbolUse.Symbol, fastCheck = true) ]
1085+
[ for p, f in ctx.Project.GetAllFiles() do
1086+
let options = p.GetProjectOptions checker
1087+
for fileName in [getFilePath p f; if f.SignatureFile <> No then getSignatureFilePath p f] do
1088+
checker.FindBackgroundReferencesInFile(fileName, options, symbolUse.Symbol, fastCheck = true) ]
10851089
|> Async.Parallel
10861090

10871091
results |> Seq.collect id |> Seq.toList |> processResults

vsintegration/src/FSharp.Editor/LanguageService/Symbols.fs

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -24,13 +24,15 @@ type SymbolUse =
2424
type FSharpSymbol with
2525

2626
member this.IsInternalToProject =
27+
let publicOrInternal = this.Accessibility.IsPublic || this.Accessibility.IsInternal
28+
2729
match this with
2830
| :? FSharpParameter -> true
29-
| :? FSharpMemberOrFunctionOrValue as m -> not m.IsModuleValueOrMember || not m.Accessibility.IsPublic
30-
| :? FSharpEntity as m -> not m.Accessibility.IsPublic
31+
| :? FSharpMemberOrFunctionOrValue as m -> not m.IsModuleValueOrMember || not publicOrInternal
32+
| :? FSharpEntity -> not publicOrInternal
3133
| :? FSharpGenericParameter -> true
32-
| :? FSharpUnionCase as m -> not m.Accessibility.IsPublic
33-
| :? FSharpField as m -> not m.Accessibility.IsPublic
34+
| :? FSharpUnionCase -> not publicOrInternal
35+
| :? FSharpField -> not publicOrInternal
3436
| _ -> false
3537

3638
type FSharpSymbolUse with

0 commit comments

Comments
 (0)