Skip to content

Commit

Permalink
use the normalized ranges to fetch text spans
Browse files Browse the repository at this point in the history
  • Loading branch information
baronfel committed May 30, 2022
1 parent ea795cc commit 61f6aea
Show file tree
Hide file tree
Showing 2 changed files with 36 additions and 52 deletions.
59 changes: 7 additions & 52 deletions src/FsAutoComplete.Core/Commands.fs
Original file line number Diff line number Diff line change
Expand Up @@ -1168,28 +1168,8 @@ type Commands(checker: FSharpCompilerServiceChecker, state: State, hasAnalyzers:

| SymbolDeclarationLocation.Projects (projects, isInternalToProject) ->
let symbolUseRanges = ImmutableArray.CreateBuilder()

// the checker gives us back wacky ranges sometimes, so what we're going to do is check if the text of the triggering
// symbol use is in each of the ranges we plan to rename, and if we're looking at a range that is _longer_ than our rename range,
// do some splicing to find just the range we need to replace.
// TODO: figure out where the caps are coming from in the compilation, maybe something wrong in the
let symbolFile, symbolRange =
let symbolRange = symbol.DefinitionRange

if System.Char.IsUpper(symbolRange.FileName[0]) then
// we've got a case where the compiler is reading things from the file system that we'd rather it not -
// if we're adjusting the range's filename, we need to construct a whole new range or else indexing won't work
//
let fileName =
UMX.tag (
string (System.Char.ToLowerInvariant symbolRange.FileName[0])
+ (symbolRange.FileName.Substring(1))
)

let newRange = Range.mkRange fileName symbolRange.Start symbolRange.End
UMX.tag fileName, newRange
else
UMX.tag symbolRange.FileName, symbolRange
let symbolRange = symbol.DefinitionRange.NormalizeDriveLetterCasing()
let symbolFile = symbolRange.TaggedFileName

let symbolFileText =
state.TryGetFileSource(symbolFile)
Expand All @@ -1215,26 +1195,8 @@ type Commands(checker: FSharpCompilerServiceChecker, state: State, hasAnalyzers:

let onFound (symbolUseRange: range) =
async {
// the checker gives us back wacky ranges sometimes, so what we're going to do is check if the text of the triggering
// symbol use is in each of the ranges we plan to rename, and if we're looking at a range that is _longer_ than our rename range,
// do some splicing to find just the range we need to replace.
// TODO: figure out where the caps are coming from in the compilation, maybe something wrong in the
let symbolFile, symbolRange =
if System.Char.IsUpper(symbolUseRange.FileName[0]) then
// we've got a case where the compiler is reading things from the file system that we'd rather it not -
// if we're adjusting the range's filename, we need to construct a whole new range or else indexing won't work
//
let fileName =
UMX.tag (
string (System.Char.ToLowerInvariant symbolRange.FileName[0])
+ (symbolRange.FileName.Substring(1))
)

let newRange = Range.mkRange fileName symbolRange.Start symbolRange.End
UMX.tag fileName, newRange
else
UMX.tag symbolRange.FileName, symbolRange

let symbolUseRange = symbolUseRange.NormalizeDriveLetterCasing()
let symbolFile = symbolUseRange.TaggedFileName
let targetText = state.TryGetFileSource(symbolFile)

match targetText with
Expand All @@ -1257,11 +1219,8 @@ type Commands(checker: FSharpCompilerServiceChecker, state: State, hasAnalyzers:
| -1 -> ()
| n ->
if sourceSpan.Length >= n + symbolText.Length then
let startPos =
Position.mkPos symbolUseRange.StartLine (symbolUseRange.StartColumn + n)

let endPos =
Position.mkPos symbolUseRange.StartLine (symbolUseRange.StartColumn + n + symbolText.Length)
let startPos = symbolUseRange.Start.IncColumn n
let endPos = symbolUseRange.Start.IncColumn(n + symbolText.Length)

let actualUseRange = Range.mkRange symbolUseRange.FileName startPos endPos
symbolUseRanges.Add actualUseRange
Expand Down Expand Up @@ -1534,11 +1493,7 @@ type Commands(checker: FSharpCompilerServiceChecker, state: State, hasAnalyzers:
| Some (recordEpr, (Some recordDefinition), insertionPos) ->
if shouldGenerateRecordStub recordEpr recordDefinition then
let result = formatRecord insertionPos "$1" recordDefinition recordEpr.FieldExprList

let pos =
Position.mkPos insertionPos.InsertionPos.Line insertionPos.InsertionPos.Column

return CoreResponse.Res(result, pos)
return CoreResponse.Res(result, insertionPos.InsertionPos)
else
return CoreResponse.InfoRes "Record at position not found"
| _ -> return CoreResponse.InfoRes "Record at position not found"
Expand Down
29 changes: 29 additions & 0 deletions src/FsAutoComplete.Core/FileSystem.fs
Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,38 @@ module PositionExtensions =

member x.IncLine() = Position.mkPos (x.Line + 1) x.Column
member x.DecLine() = Position.mkPos (x.Line - 1) x.Column
member x.IncColumn() = Position.mkPos x.Line (x.Column + 1)
member x.IncColumn n = Position.mkPos x.Line (x.Column + n)


let inline (|Pos|) (p: FSharp.Compiler.Text.Position) = p.Line, p.Column

[<AutoOpen>]
module RangeExtensions =
type FSharp.Compiler.Text.Range with
member x.WithFileName(fileName: string) = Range.mkRange fileName x.Start x.End

/// the checker gives us back wacky ranges sometimes, so what we're going to do is check if the text of the triggering
/// symbol use is in each of the ranges we plan to rename, and if we're looking at a range that is _longer_ than our rename range,
/// do some splicing to find just the range we need to replace.
/// TODO: figure out where the caps are coming from in the compilation, maybe something wrong in the
member x.NormalizeDriveLetterCasing() =
if System.Char.IsUpper(x.FileName[0]) then
// we've got a case where the compiler is reading things from the file system that we'd rather it not -
// if we're adjusting the range's filename, we need to construct a whole new range or else indexing won't work
let fileName =
string (System.Char.ToLowerInvariant x.FileName[0])
+ (x.FileName.Substring(1))

let newRange = Range.mkRange fileName x.Start x.End
newRange
else
x

/// utility method to get the tagged filename for use in our state storage
/// TODO: should we enforce this/use the Path members for normalization?
member x.TaggedFileName: string<LocalPath> = UMX.tag x.FileName

/// A copy of the StringText type from F#.Compiler.Text, which is private.
/// Adds a UOM-typed filename to make range manipulation easier, as well as
/// safer traversals
Expand Down

0 comments on commit 61f6aea

Please sign in to comment.