From 3d366361dbfb0585db5d4285501052d889588e00 Mon Sep 17 00:00:00 2001 From: nosami Date: Mon, 11 Dec 2017 13:17:22 +0000 Subject: [PATCH 1/4] Update GetDeclarationListSymbols to add getAllEntities --- src/fsharp/service/service.fs | 13 +++++++------ src/fsharp/service/service.fsi | 2 +- tests/service/EditorTests.fs | 6 +++--- 3 files changed, 11 insertions(+), 10 deletions(-) diff --git a/src/fsharp/service/service.fs b/src/fsharp/service/service.fs index 80b55834f02..0325b3fed16 100644 --- a/src/fsharp/service/service.fs +++ b/src/fsharp/service/service.fs @@ -950,11 +950,11 @@ type TypeCheckInfo FSharpDeclarationListInfo.Error msg) /// Get the symbols for auto-complete items at a location - member __.GetDeclarationListSymbols (ctok, parseResultsOpt, line, lineStr, partialName, hasTextChangedSinceLastTypecheck) = + member __.GetDeclarationListSymbols (ctok, parseResultsOpt, line, lineStr, partialName, getAllSymbols, hasTextChangedSinceLastTypecheck) = let isInterfaceFile = SourceFileImpl.IsInterfaceFile mainInputFileName ErrorScope.Protect Range.range0 (fun () -> - match GetDeclItemsForNamesAtPosition(ctok, parseResultsOpt, Some partialName.QualifyingIdents, Some partialName.PartialIdent, partialName.LastDotPos, line, lineStr, partialName.EndColumn + 1, ResolveTypeNamesToCtors, ResolveOverloads.Yes, (fun () -> []), hasTextChangedSinceLastTypecheck) with + match GetDeclItemsForNamesAtPosition(ctok, parseResultsOpt, Some partialName.QualifyingIdents, Some partialName.PartialIdent, partialName.LastDotPos, line, lineStr, partialName.EndColumn + 1, ResolveTypeNamesToCtors, ResolveOverloads.Yes, getAllSymbols, hasTextChangedSinceLastTypecheck) with | None -> List.Empty | Some (items, denv, _, m) -> let items = if isInterfaceFile then items |> List.filter (fun x -> IsValidSignatureFileItem x.Item) else items @@ -966,7 +966,7 @@ type TypeCheckInfo // - show types with fewer generic parameters first // - show types before over other related items - they usually have very useful XmlDocs let items = - items |> List.sortBy (fun d -> + items |> List.sortBy (fun d -> let n = match d.Item with | Item.Types (_,(TType_app(tcref,_) :: _)) -> 1 + tcref.TyparsNoRange.Length @@ -982,7 +982,8 @@ type TypeCheckInfo let items = items |> RemoveDuplicateCompletionItems g // Group by display name - let items = items |> List.groupBy (fun d -> d.Item.DisplayName) + let items = + items |> List.groupBy (fun d -> d.Item.DisplayName) // Filter out operators (and list) let items = @@ -1925,10 +1926,10 @@ type FSharpCheckFileResults(filename: string, errors: FSharpErrorInfo[], scopeOp reactorOp userOpName "GetDeclarations" FSharpDeclarationListInfo.Empty (fun ctok scope -> scope.GetDeclarations(ctok, parseResultsOpt, line, lineStr, partialName, getAllEntities, hasTextChangedSinceLastTypecheck)) - member info.GetDeclarationListSymbols(parseResultsOpt, line, lineStr, partialName, ?hasTextChangedSinceLastTypecheck, ?userOpName: string) = + member info.GetDeclarationListSymbols(parseResultsOpt, line, lineStr, partialName, getAllEntities, ?hasTextChangedSinceLastTypecheck, ?userOpName: string) = let userOpName = defaultArg userOpName "Unknown" let hasTextChangedSinceLastTypecheck = defaultArg hasTextChangedSinceLastTypecheck (fun _ -> false) - reactorOp userOpName "GetDeclarationListSymbols" List.empty (fun ctok scope -> scope.GetDeclarationListSymbols(ctok, parseResultsOpt, line, lineStr, partialName, hasTextChangedSinceLastTypecheck)) + reactorOp userOpName "GetDeclarationListSymbols" List.empty (fun ctok scope -> scope.GetDeclarationListSymbols(ctok, parseResultsOpt, line, lineStr, partialName, getAllEntities, hasTextChangedSinceLastTypecheck)) /// Resolve the names at the given location to give a data tip member info.GetStructuredToolTipText(line, colAtEndOfNames, lineStr, names, tokenTag, ?userOpName: string) = diff --git a/src/fsharp/service/service.fsi b/src/fsharp/service/service.fsi index 61ac7e1fb2d..e5d4640d164 100755 --- a/src/fsharp/service/service.fsi +++ b/src/fsharp/service/service.fsi @@ -154,7 +154,7 @@ type public FSharpCheckFileResults = /// and assume that we're going to repeat the operation later on. /// /// An optional string used for tracing compiler operations associated with this request. - member GetDeclarationListSymbols : ParsedFileResultsOpt:FSharpParseFileResults option * line: int * lineText:string * partialName: PartialLongName * ?hasTextChangedSinceLastTypecheck: (obj * range -> bool) * ?userOpName: string -> Async + member GetDeclarationListSymbols : ParsedFileResultsOpt:FSharpParseFileResults option * line: int * lineText:string * partialName: PartialLongName * getAllSymbols: (unit -> AssemblySymbol list) * ?hasTextChangedSinceLastTypecheck: (obj * range -> bool) * ?userOpName: string -> Async /// Compute a formatted tooltip for the given location diff --git a/tests/service/EditorTests.fs b/tests/service/EditorTests.fs index d3e7c724509..424201a493e 100644 --- a/tests/service/EditorTests.fs +++ b/tests/service/EditorTests.fs @@ -357,7 +357,7 @@ type Test() = let file = "/home/user/Test.fsx" let parseResult, typeCheckResults = parseAndCheckScript(file, input) - let decls = typeCheckResults.GetDeclarationListSymbols(Some parseResult, 4, inputLines.[3], PartialLongName.Empty(20), fun _ -> false)|> Async.RunSynchronously + let decls = typeCheckResults.GetDeclarationListSymbols(Some parseResult, 4, inputLines.[3], PartialLongName.Empty(20), (fun () -> []), fun _ -> false)|> Async.RunSynchronously //decls |> List.map (fun d -> d.Head.Symbol.DisplayName) |> printfn "---> decls = %A" decls |> Seq.exists (fun d -> d.Head.Symbol.DisplayName = "abc") |> shouldEqual true @@ -374,7 +374,7 @@ type Test() = let file = "/home/user/Test.fsx" let parseResult, typeCheckResults = parseAndCheckScript(file, input) - let decls = typeCheckResults.GetDeclarationListSymbols(Some parseResult, 4, inputLines.[3], PartialLongName.Empty(21), fun _ -> false)|> Async.RunSynchronously + let decls = typeCheckResults.GetDeclarationListSymbols(Some parseResult, 4, inputLines.[3], PartialLongName.Empty(21), (fun () -> []), fun _ -> false)|> Async.RunSynchronously //decls |> List.map (fun d -> d.Head.Symbol.DisplayName) |> printfn "---> decls = %A" decls |> Seq.exists (fun d -> d.Head.Symbol.DisplayName = "abc") |> shouldEqual true @@ -391,7 +391,7 @@ type Test() = let file = "/home/user/Test.fsx" let parseResult, typeCheckResults = parseAndCheckScript(file, input) - let decls = typeCheckResults.GetDeclarationListSymbols(Some parseResult, 4, inputLines.[3], PartialLongName.Empty(14), fun _ -> false)|> Async.RunSynchronously + let decls = typeCheckResults.GetDeclarationListSymbols(Some parseResult, 4, inputLines.[3], PartialLongName.Empty(14), (fun () -> []), fun _ -> false)|> Async.RunSynchronously //decls |> List.map (fun d -> d.Head.Symbol.DisplayName) |> printfn "---> decls = %A" decls |> Seq.exists (fun d -> d.Head.Symbol.DisplayName = "abc") |> shouldEqual true From 94f426866adcdd5f01ddb3706ed3e9ae8a71c18c Mon Sep 17 00:00:00 2001 From: nosami Date: Mon, 11 Dec 2017 13:26:05 +0000 Subject: [PATCH 2/4] Don't group types with the same display name as function overloads. Now that we can include all entities for top level completions, the grouping function can incorrectly group types with the same display name as function overloads. Use the compiled name instead as this includes the namespace. --- src/fsharp/service/service.fs | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/src/fsharp/service/service.fs b/src/fsharp/service/service.fs index 0325b3fed16..9be84041c6e 100644 --- a/src/fsharp/service/service.fs +++ b/src/fsharp/service/service.fs @@ -981,9 +981,16 @@ type TypeCheckInfo // Remove all duplicates. We've put the types first, so this removes the DelegateCtor and DefaultStructCtor's. let items = items |> RemoveDuplicateCompletionItems g - // Group by display name + // Group by compiled name for types, display name for functions + // (We don't want types with the same display name to be grouped as overloads) let items = - items |> List.groupBy (fun d -> d.Item.DisplayName) + items |> List.groupBy (fun d -> + match d.Item with + | Item.Types (_,(TType_app(tcref,_) :: _)) + | Item.FakeInterfaceCtor (TType_app(tcref,_)) + | Item.DelegateCtor (TType_app(tcref,_)) -> tcref.CompiledName + | Item.CtorGroup (_, (cinfo :: _)) -> (tcrefOfAppTy g cinfo.EnclosingType).CompiledName + | _ -> d.Item.DisplayName) // Filter out operators (and list) let items = From 21993cbc0278611ace9505ed45c9fc2e145b425f Mon Sep 17 00:00:00 2001 From: nosami Date: Mon, 15 Jan 2018 11:38:23 +0000 Subject: [PATCH 3/4] Get logical name from ExnCase --- src/fsharp/service/service.fs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/fsharp/service/service.fs b/src/fsharp/service/service.fs index 9be84041c6e..65e98b78d9f 100644 --- a/src/fsharp/service/service.fs +++ b/src/fsharp/service/service.fs @@ -987,6 +987,8 @@ type TypeCheckInfo items |> List.groupBy (fun d -> match d.Item with | Item.Types (_,(TType_app(tcref,_) :: _)) + | Item.ExnCase tcref -> tcref.LogicalName + | Item.UnqualifiedType(tcref :: _) | Item.FakeInterfaceCtor (TType_app(tcref,_)) | Item.DelegateCtor (TType_app(tcref,_)) -> tcref.CompiledName | Item.CtorGroup (_, (cinfo :: _)) -> (tcrefOfAppTy g cinfo.EnclosingType).CompiledName From 361359fcc1a13dd59c0cb6e165f1cec1fee5ac73 Mon Sep 17 00:00:00 2001 From: nosami Date: Tue, 16 Jan 2018 20:21:02 +0000 Subject: [PATCH 4/4] Make getAllEntities optional Also renamed getAllSymbols to getAllEntities everywhere for consistency --- src/fsharp/service/service.fs | 14 ++++++++------ src/fsharp/service/service.fsi | 12 ++++++------ 2 files changed, 14 insertions(+), 12 deletions(-) diff --git a/src/fsharp/service/service.fs b/src/fsharp/service/service.fs index 65e98b78d9f..488534f4a79 100644 --- a/src/fsharp/service/service.fs +++ b/src/fsharp/service/service.fs @@ -930,11 +930,11 @@ type TypeCheckInfo scope.IsRelativeNameResolvable(cursorPos, plid, symbol.Item) /// Get the auto-complete items at a location - member __.GetDeclarations (ctok, parseResultsOpt, line, lineStr, partialName, getAllSymbols, hasTextChangedSinceLastTypecheck) = + member __.GetDeclarations (ctok, parseResultsOpt, line, lineStr, partialName, getAllEntities, hasTextChangedSinceLastTypecheck) = let isInterfaceFile = SourceFileImpl.IsInterfaceFile mainInputFileName ErrorScope.Protect Range.range0 (fun () -> - match GetDeclItemsForNamesAtPosition(ctok, parseResultsOpt, Some partialName.QualifyingIdents, Some partialName.PartialIdent, partialName.LastDotPos, line, lineStr, partialName.EndColumn + 1, ResolveTypeNamesToCtors, ResolveOverloads.Yes, getAllSymbols, hasTextChangedSinceLastTypecheck) with + match GetDeclItemsForNamesAtPosition(ctok, parseResultsOpt, Some partialName.QualifyingIdents, Some partialName.PartialIdent, partialName.LastDotPos, line, lineStr, partialName.EndColumn + 1, ResolveTypeNamesToCtors, ResolveOverloads.Yes, getAllEntities, hasTextChangedSinceLastTypecheck) with | None -> FSharpDeclarationListInfo.Empty | Some (items, denv, ctx, m) -> let items = if isInterfaceFile then items |> List.filter (fun x -> IsValidSignatureFileItem x.Item) else items @@ -950,11 +950,11 @@ type TypeCheckInfo FSharpDeclarationListInfo.Error msg) /// Get the symbols for auto-complete items at a location - member __.GetDeclarationListSymbols (ctok, parseResultsOpt, line, lineStr, partialName, getAllSymbols, hasTextChangedSinceLastTypecheck) = + member __.GetDeclarationListSymbols (ctok, parseResultsOpt, line, lineStr, partialName, getAllEntities, hasTextChangedSinceLastTypecheck) = let isInterfaceFile = SourceFileImpl.IsInterfaceFile mainInputFileName ErrorScope.Protect Range.range0 (fun () -> - match GetDeclItemsForNamesAtPosition(ctok, parseResultsOpt, Some partialName.QualifyingIdents, Some partialName.PartialIdent, partialName.LastDotPos, line, lineStr, partialName.EndColumn + 1, ResolveTypeNamesToCtors, ResolveOverloads.Yes, getAllSymbols, hasTextChangedSinceLastTypecheck) with + match GetDeclItemsForNamesAtPosition(ctok, parseResultsOpt, Some partialName.QualifyingIdents, Some partialName.PartialIdent, partialName.LastDotPos, line, lineStr, partialName.EndColumn + 1, ResolveTypeNamesToCtors, ResolveOverloads.Yes, getAllEntities, hasTextChangedSinceLastTypecheck) with | None -> List.Empty | Some (items, denv, _, m) -> let items = if isInterfaceFile then items |> List.filter (fun x -> IsValidSignatureFileItem x.Item) else items @@ -1929,15 +1929,17 @@ type FSharpCheckFileResults(filename: string, errors: FSharpErrorInfo[], scopeOp member info.HasFullTypeCheckInfo = details.IsSome /// Intellisense autocompletions - member info.GetDeclarationListInfo(parseResultsOpt, line, lineStr, partialName, getAllEntities, ?hasTextChangedSinceLastTypecheck, ?userOpName: string) = + member info.GetDeclarationListInfo(parseResultsOpt, line, lineStr, partialName, ?getAllEntities, ?hasTextChangedSinceLastTypecheck, ?userOpName: string) = let userOpName = defaultArg userOpName "Unknown" + let getAllEntities = defaultArg getAllEntities (fun() -> []) let hasTextChangedSinceLastTypecheck = defaultArg hasTextChangedSinceLastTypecheck (fun _ -> false) reactorOp userOpName "GetDeclarations" FSharpDeclarationListInfo.Empty (fun ctok scope -> scope.GetDeclarations(ctok, parseResultsOpt, line, lineStr, partialName, getAllEntities, hasTextChangedSinceLastTypecheck)) - member info.GetDeclarationListSymbols(parseResultsOpt, line, lineStr, partialName, getAllEntities, ?hasTextChangedSinceLastTypecheck, ?userOpName: string) = + member info.GetDeclarationListSymbols(parseResultsOpt, line, lineStr, partialName, ?getAllEntities, ?hasTextChangedSinceLastTypecheck, ?userOpName: string) = let userOpName = defaultArg userOpName "Unknown" let hasTextChangedSinceLastTypecheck = defaultArg hasTextChangedSinceLastTypecheck (fun _ -> false) + let getAllEntities = defaultArg getAllEntities (fun() -> []) reactorOp userOpName "GetDeclarationListSymbols" List.empty (fun ctok scope -> scope.GetDeclarationListSymbols(ctok, parseResultsOpt, line, lineStr, partialName, getAllEntities, hasTextChangedSinceLastTypecheck)) /// Resolve the names at the given location to give a data tip diff --git a/src/fsharp/service/service.fsi b/src/fsharp/service/service.fsi index e5d4640d164..31bf8efb977 100755 --- a/src/fsharp/service/service.fsi +++ b/src/fsharp/service/service.fsi @@ -119,8 +119,8 @@ type public FSharpCheckFileResults = /// The text of the line where the completion is happening. This is only used to make a couple /// of adhoc corrections to completion accuracy (e.g. checking for "..") /// - /// - /// Function that returns all symbols from current and referenced assemblies. + /// + /// Function that returns all entities from current and referenced assemblies. /// /// /// If text has been used from a captured name resolution from the typecheck, then @@ -128,7 +128,7 @@ type public FSharpCheckFileResults = /// and assume that we're going to repeat the operation later on. /// /// An optional string used for tracing compiler operations associated with this request. - member GetDeclarationListInfo : ParsedFileResultsOpt:FSharpParseFileResults option * line: int * lineText:string * partialName: PartialLongName * getAllSymbols: (unit -> AssemblySymbol list) * ?hasTextChangedSinceLastTypecheck: (obj * range -> bool) * ?userOpName: string -> Async + member GetDeclarationListInfo : ParsedFileResultsOpt:FSharpParseFileResults option * line: int * lineText:string * partialName: PartialLongName * ?getAllEntities: (unit -> AssemblySymbol list) * ?hasTextChangedSinceLastTypecheck: (obj * range -> bool) * ?userOpName: string -> Async /// Get the items for a declaration list in FSharpSymbol format /// @@ -145,8 +145,8 @@ type public FSharpCheckFileResults = /// The text of the line where the completion is happening. This is only used to make a couple /// of adhoc corrections to completion accuracy (e.g. checking for "..") /// - /// - /// Function that returns all symbols from current and referenced assemblies. + /// + /// Function that returns all entities from current and referenced assemblies. /// /// /// If text has been used from a captured name resolution from the typecheck, then @@ -154,7 +154,7 @@ type public FSharpCheckFileResults = /// and assume that we're going to repeat the operation later on. /// /// An optional string used for tracing compiler operations associated with this request. - member GetDeclarationListSymbols : ParsedFileResultsOpt:FSharpParseFileResults option * line: int * lineText:string * partialName: PartialLongName * getAllSymbols: (unit -> AssemblySymbol list) * ?hasTextChangedSinceLastTypecheck: (obj * range -> bool) * ?userOpName: string -> Async + member GetDeclarationListSymbols : ParsedFileResultsOpt:FSharpParseFileResults option * line: int * lineText:string * partialName: PartialLongName * ?getAllEntities: (unit -> AssemblySymbol list) * ?hasTextChangedSinceLastTypecheck: (obj * range -> bool) * ?userOpName: string -> Async /// Compute a formatted tooltip for the given location