diff --git a/docs/release-notes/.FSharp.Compiler.Service/9.0.200.md b/docs/release-notes/.FSharp.Compiler.Service/9.0.200.md index a2a0f964f7f..ce187cb8421 100644 --- a/docs/release-notes/.FSharp.Compiler.Service/9.0.200.md +++ b/docs/release-notes/.FSharp.Compiler.Service/9.0.200.md @@ -7,5 +7,6 @@ ### Changed * Make ILTypeDef interface impls calculation lazy. ([PR #17392](https://github.com/dotnet/fsharp/pull/17392)) +* Better ranges for CE `let!` and `use!` error reporting. ([PR #17712](https://github.com/dotnet/fsharp/pull/17712)) ### Breaking Changes diff --git a/src/Compiler/Checking/Expressions/CheckComputationExpressions.fs b/src/Compiler/Checking/Expressions/CheckComputationExpressions.fs index 3a3682fbf53..5d9f3562ed9 100644 --- a/src/Compiler/Checking/Expressions/CheckComputationExpressions.fs +++ b/src/Compiler/Checking/Expressions/CheckComputationExpressions.fs @@ -1589,10 +1589,10 @@ let rec TryTranslateComputationExpression Some(TranslateComputationExpression ceenv CompExprTranslationPass.Initial q varSpace innerComp2 translatedCtxt) else - if ceenv.isQuery && not (innerComp1.IsArbExprAndThusAlreadyReportedError) then match innerComp1 with - | SynExpr.JoinIn _ -> () // an error will be reported later when we process innerComp1 as a sequential + | SynExpr.JoinIn _ -> () + | SynExpr.DoBang(range = m) -> errorR (Error(FSComp.SR.tcBindMayNotBeUsedInQueries (), m)) | _ -> errorR (Error(FSComp.SR.tcUnrecognizedQueryOperator (), innerComp1.RangeOfFirstPortion)) match @@ -1854,12 +1854,14 @@ let rec TryTranslateComputationExpression // or // --> build.BindReturn(e1, (fun _argN -> match _argN with pat -> expr-without-return)) | SynExpr.LetOrUseBang( - bindDebugPoint = spBind; isUse = false; isFromSource = isFromSource; pat = pat; rhs = rhsExpr; andBangs = []; body = innerComp) -> - - let mBind = - match spBind with - | DebugPointAtBinding.Yes m -> m - | _ -> rhsExpr.Range + bindDebugPoint = spBind + isUse = false + isFromSource = isFromSource + pat = pat + rhs = rhsExpr + andBangs = [] + body = innerComp + trivia = { LetOrUseBangKeyword = mBind }) -> if ceenv.isQuery then error (Error(FSComp.SR.tcBindMayNotBeUsedInQueries (), mBind)) @@ -1900,7 +1902,8 @@ let rec TryTranslateComputationExpression pat = SynPat.Named(ident = SynIdent(id, _); isThisVal = false) as pat rhs = rhsExpr andBangs = [] - body = innerComp) + body = innerComp + trivia = { LetOrUseBangKeyword = mBind }) | SynExpr.LetOrUseBang( bindDebugPoint = spBind isUse = true @@ -1908,12 +1911,8 @@ let rec TryTranslateComputationExpression pat = SynPat.LongIdent(longDotId = SynLongIdent(id = [ id ])) as pat rhs = rhsExpr andBangs = [] - body = innerComp) -> - - let mBind = - match spBind with - | DebugPointAtBinding.Yes m -> m - | _ -> rhsExpr.Range + body = innerComp + trivia = { LetOrUseBangKeyword = mBind }) -> if ceenv.isQuery then error (Error(FSComp.SR.tcBindMayNotBeUsedInQueries (), mBind)) @@ -1988,9 +1987,9 @@ let rec TryTranslateComputationExpression Some(translatedCtxt bindExpr) // 'use! pat = e1 ... in e2' where 'pat' is not a simple name -> error - | SynExpr.LetOrUseBang(isUse = true; pat = pat; andBangs = andBangs) -> + | SynExpr.LetOrUseBang(isUse = true; andBangs = andBangs; trivia = { LetOrUseBangKeyword = mBind }) -> if isNil andBangs then - error (Error(FSComp.SR.tcInvalidUseBangBinding (), pat.Range)) + error (Error(FSComp.SR.tcInvalidUseBangBinding (), mBind)) else let m = match andBangs with @@ -2013,17 +2012,17 @@ let rec TryTranslateComputationExpression rhs = letRhsExpr andBangs = andBangBindings body = innerComp - range = letBindRange) -> + trivia = { LetOrUseBangKeyword = mBind }) -> if not (cenv.g.langVersion.SupportsFeature LanguageFeature.AndBang) then - error (Error(FSComp.SR.tcAndBangNotSupported (), comp.Range)) + let andBangRange = + match andBangBindings with + | [] -> comp.Range + | h :: _ -> h.Trivia.AndBangKeyword - if ceenv.isQuery then - error (Error(FSComp.SR.tcBindMayNotBeUsedInQueries (), letBindRange)) + error (Error(FSComp.SR.tcAndBangNotSupported (), andBangRange)) - let mBind = - match spBind with - | DebugPointAtBinding.Yes m -> m - | _ -> letRhsExpr.Range + if ceenv.isQuery then + error (Error(FSComp.SR.tcBindMayNotBeUsedInQueries (), mBind)) let sources = (letRhsExpr diff --git a/src/Compiler/SyntaxTree/SyntaxTrivia.fs b/src/Compiler/SyntaxTree/SyntaxTrivia.fs index 0932befd7c1..bbc5f8ea0ce 100644 --- a/src/Compiler/SyntaxTree/SyntaxTrivia.fs +++ b/src/Compiler/SyntaxTree/SyntaxTrivia.fs @@ -93,10 +93,15 @@ type SynExprLetOrUseTrivia = [] type SynExprLetOrUseBangTrivia = { + LetOrUseBangKeyword: range EqualsRange: range option } - static member Zero: SynExprLetOrUseBangTrivia = { EqualsRange = None } + static member Zero: SynExprLetOrUseBangTrivia = + { + LetOrUseBangKeyword = Range.Zero + EqualsRange = None + } [] type SynExprMatchTrivia = diff --git a/src/Compiler/SyntaxTree/SyntaxTrivia.fsi b/src/Compiler/SyntaxTree/SyntaxTrivia.fsi index 24bfc1b7a52..08f8228c3bc 100644 --- a/src/Compiler/SyntaxTree/SyntaxTrivia.fsi +++ b/src/Compiler/SyntaxTree/SyntaxTrivia.fsi @@ -139,6 +139,8 @@ type SynExprLetOrUseTrivia = [] type SynExprLetOrUseBangTrivia = { + /// The syntax range of the `let!` or `use!` keyword. + LetOrUseBangKeyword: range /// The syntax range of the `=` token. EqualsRange: range option } diff --git a/src/Compiler/pars.fsy b/src/Compiler/pars.fsy index 2794edf560e..c930398b24b 100644 --- a/src/Compiler/pars.fsy +++ b/src/Compiler/pars.fsy @@ -4419,7 +4419,7 @@ declExpr: { let spBind = DebugPointAtBinding.Yes(rhs2 parseState 1 5) let mEquals = rhs parseState 3 let m = unionRanges (rhs parseState 1) $8.Range - let trivia: SynExprLetOrUseBangTrivia = { EqualsRange = Some mEquals } + let trivia: SynExprLetOrUseBangTrivia = { LetOrUseBangKeyword = rhs parseState 1 ; EqualsRange = Some mEquals } SynExpr.LetOrUseBang(spBind, ($1 = "use"), true, $2, $4, $7, $8, m, trivia) } | OBINDER headBindingPattern EQUALS typedSequentialExprBlock hardwhiteDefnBindingsTerminator opt_OBLOCKSEP moreBinders typedSequentialExprBlock %prec expr_let @@ -4428,7 +4428,7 @@ declExpr: let spBind = DebugPointAtBinding.Yes(unionRanges (rhs parseState 1) $4.Range) let mEquals = rhs parseState 3 let m = unionRanges (rhs parseState 1) $8.Range - let trivia: SynExprLetOrUseBangTrivia = { EqualsRange = Some mEquals } + let trivia: SynExprLetOrUseBangTrivia = { LetOrUseBangKeyword = rhs parseState 1 ; EqualsRange = Some mEquals } SynExpr.LetOrUseBang(spBind, ($1 = "use"), true, $2, $4, $7, $8, m, trivia) } | OBINDER headBindingPattern EQUALS typedSequentialExprBlock hardwhiteDefnBindingsTerminator opt_OBLOCKSEP error %prec expr_let @@ -4437,12 +4437,12 @@ declExpr: let mEquals = rhs parseState 3 let mAll = unionRanges (rhs parseState 1) (rhs parseState 7) let m = $4.Range.EndRange // zero-width range - let trivia: SynExprLetOrUseBangTrivia = { EqualsRange = Some mEquals } + let trivia: SynExprLetOrUseBangTrivia = { LetOrUseBangKeyword = rhs parseState 1 ; EqualsRange = Some mEquals } SynExpr.LetOrUseBang(spBind, ($1 = "use"), true, $2, $4, [], SynExpr.ImplicitZero m, mAll, trivia) } | DO_BANG typedSequentialExpr IN opt_OBLOCKSEP typedSequentialExprBlock %prec expr_let { let spBind = DebugPointAtBinding.NoneAtDo - let trivia: SynExprLetOrUseBangTrivia = { EqualsRange = None } + let trivia: SynExprLetOrUseBangTrivia = { LetOrUseBangKeyword = Range.Zero; EqualsRange = None } SynExpr.LetOrUseBang(spBind, false, true, SynPat.Const(SynConst.Unit, $2.Range), $2, [], $5, unionRanges (rhs parseState 1) $5.Range, trivia) } | ODO_BANG typedSequentialExprBlock hardwhiteDefnBindingsTerminator %prec expr_let diff --git a/tests/FSharp.Compiler.ComponentTests/Language/ComputationExpressionTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/ComputationExpressionTests.fs index d5c6a5a0a63..8333657e699 100644 --- a/tests/FSharp.Compiler.ComponentTests/Language/ComputationExpressionTests.fs +++ b/tests/FSharp.Compiler.ComponentTests/Language/ComputationExpressionTests.fs @@ -246,4 +246,200 @@ let run r2 r3 = |> shouldFail |> withDiagnostics [ (Error 3345, Line 22, Col 9, Line 22, Col 13, "use! may not be combined with and!") + ] + + [] + let ``This control construct may only be used if the computation expression builder defines a 'Bind' method`` () = + Fsx """ +module Result = + let zip x1 x2 = + match x1,x2 with + | Ok x1res, Ok x2res -> Ok (x1res, x2res) + | Error e, _ -> Error e + | _, Error e -> Error e + +type ResultBuilder() = + member _.MergeSources(t1: Result<'T,'U>, t2: Result<'T1,'U>) = Result.zip t1 t2 + member _.BindReturn(x: Result<'T,'U>, f) = Result.map f x + member _.Delay(f) = f() + + member _.TryWith(r: Result<'T,'U>, f) = + match r with + | Ok x -> Ok x + | Error e -> f e + +let result = ResultBuilder() + +let run r2 r3 = + result { + let! a = r2 + return! a + } + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 708, Line 23, Col 9, Line 23, Col 13, "This control construct may only be used if the computation expression builder defines a 'Bind' method") + ] + + [] + let ``This control construct may only be used if the computation expression builder defines a 'Using' method`` () = + Fsx """ +module Result = + let zip x1 x2 = + match x1,x2 with + | Ok x1res, Ok x2res -> Ok (x1res, x2res) + | Error e, _ -> Error e + | _, Error e -> Error e + +type ResultBuilder() = + member _.MergeSources(t1: Result<'T,'U>, t2: Result<'T1,'U>) = Result.zip t1 t2 + member _.BindReturn(x: Result<'T,'U>, f) = Result.map f x + member _.Delay(f) = f() + + member _.TryWith(r: Result<'T,'U>, f) = + match r with + | Ok x -> Ok x + | Error e -> f e + +let result = ResultBuilder() + +let run r2 r3 = + result { + use! a = r2 + return! a + } + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 708, Line 23, Col 9, Line 23, Col 13, "This control construct may only be used if the computation expression builder defines a 'Using' method") + ] + + [] + let ``do! expressions may not be used in queries`` () = + Fsx """ +query { + do! failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 3, Col 5, Line 3, Col 20, "'let!', 'use!' and 'do!' expressions may not be used in queries") + ] + + [] + let ``let! expressions may not be used in queries`` () = + Fsx """ +query { + let! x = failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 3, Col 5, Line 3, Col 9, "'let!', 'use!' and 'do!' expressions may not be used in queries") + ] + + [] + let ``let!, and! expressions may not be used in queries`` () = + Fsx """ +query { + let! x = failwith "" + and! y = failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 3, Col 5, Line 3, Col 9, "'let!', 'use!' and 'do!' expressions may not be used in queries") + ] + + [] + let ``use! expressions may not be used in queries`` () = + Fsx """ +query { + use! x = failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 3, Col 5, Line 3, Col 9, "'let!', 'use!' and 'do!' expressions may not be used in queries") + ] + + [] + let ``do! expressions may not be used in queries(SynExpr.Sequential)`` () = + Fsx """ +query { + for c in [1..10] do + do! failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 4, Col 5, Line 4, Col 20, "'let!', 'use!' and 'do!' expressions may not be used in queries") + ] + + [] + let ``let! expressions may not be used in queries(SynExpr.Sequential)`` () = + Fsx """ +query { + for c in [1..10] do + let! x = failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 4, Col 5, Line 4, Col 9, "'let!', 'use!' and 'do!' expressions may not be used in queries") + ] + + [] + let ``let!, and! expressions may not be used in queries(SynExpr.Sequential)`` () = + Fsx """ +query { + for c in [1..10] do + let! x = failwith "" + and! y = failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 4, Col 5, Line 4, Col 9, "'let!', 'use!' and 'do!' expressions may not be used in queries") + ] + + [] + let ``use! expressions may not be used in queries(SynExpr.Sequential)`` () = + Fsx """ +query { + for c in [1..10] do + use! x = failwith "" + yield 1 +} + """ + |> ignoreWarnings + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 3143, Line 4, Col 5, Line 4, Col 9, "'let!', 'use!' and 'do!' expressions may not be used in queries") ] \ No newline at end of file diff --git a/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.debug.bsl b/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.debug.bsl index 543c92ef5cc..c41cdbbea96 100644 --- a/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.debug.bsl +++ b/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.debug.bsl @@ -10203,7 +10203,9 @@ FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: FSharp.Compiler.SyntaxTr FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range] EqualsRange FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range] get_EqualsRange() FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: System.String ToString() -FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Void .ctor(Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range]) +FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: FSharp.Compiler.Text.Range LetOrUseBangKeyword +FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: FSharp.Compiler.Text.Range get_LetOrUseBangKeyword() +FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Void .ctor(FSharp.Compiler.Text.Range, Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range]) FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia: FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia Zero FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia: FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia get_Zero() FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia: Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range] InKeyword diff --git a/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.release.bsl b/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.release.bsl index 543c92ef5cc..c41cdbbea96 100644 --- a/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.release.bsl +++ b/tests/FSharp.Compiler.Service.Tests/FSharp.Compiler.Service.SurfaceArea.netstandard20.release.bsl @@ -10203,7 +10203,9 @@ FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: FSharp.Compiler.SyntaxTr FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range] EqualsRange FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range] get_EqualsRange() FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: System.String ToString() -FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Void .ctor(Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range]) +FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: FSharp.Compiler.Text.Range LetOrUseBangKeyword +FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: FSharp.Compiler.Text.Range get_LetOrUseBangKeyword() +FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseBangTrivia: Void .ctor(FSharp.Compiler.Text.Range, Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range]) FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia: FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia Zero FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia: FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia get_Zero() FSharp.Compiler.SyntaxTrivia.SynExprLetOrUseTrivia: Microsoft.FSharp.Core.FSharpOption`1[FSharp.Compiler.Text.Range] InKeyword diff --git a/tests/fsharp/Compiler/Conformance/DataExpressions/ComputationExpressions.fs b/tests/fsharp/Compiler/Conformance/DataExpressions/ComputationExpressions.fs index 715a1e060a1..c6269705d17 100644 --- a/tests/fsharp/Compiler/Conformance/DataExpressions/ComputationExpressions.fs +++ b/tests/fsharp/Compiler/Conformance/DataExpressions/ComputationExpressions.fs @@ -281,7 +281,7 @@ let ceResult : Trace = return if y then x else -1 } """ - [| FSharpDiagnosticSeverity.Error, 3344, (6, 9, 8, 35), "This feature is not supported in this version of F#. You may need to add /langversion:preview to use this feature." |] + [| FSharpDiagnosticSeverity.Error, 3344, (7, 9, 7, 13), "This feature is not supported in this version of F#. You may need to add /langversion:preview to use this feature." |] [] let ``AndBang TraceMultiBindingMonoid`` () = @@ -582,7 +582,7 @@ let _ = return x + y } """ - [|(FSharpDiagnosticSeverity.Error, 3343, (6, 9, 6, 25), "The 'let! ... and! ...' construct may only be used if the computation expression builder defines either a 'Bind2' method or appropriate 'MergeSources' and 'Bind' methods")|] + [|(FSharpDiagnosticSeverity.Error, 3343, (6, 9, 6, 13), "The 'let! ... and! ...' construct may only be used if the computation expression builder defines either a 'Bind2' method or appropriate 'MergeSources' and 'Bind' methods")|] [] let ``AndBang Negative TraceApplicative missing Bind and BindReturn`` () = @@ -596,7 +596,7 @@ let _ = return x + y } """ - [|(FSharpDiagnosticSeverity.Error, 708, (6, 9, 6, 25), "This control construct may only be used if the computation expression builder defines a 'Bind' method")|] + [|(FSharpDiagnosticSeverity.Error, 708, (6, 9, 6, 13), "This control construct may only be used if the computation expression builder defines a 'Bind' method")|] [] @@ -612,7 +612,7 @@ let _ = return x + y } """ - [| FSharpDiagnosticSeverity.Error, 708, (7, 9, 7, 25), "This control construct may only be used if the computation expression builder defines a 'Bind' method" |] + [| FSharpDiagnosticSeverity.Error, 708, (7, 9, 7, 13), "This control construct may only be used if the computation expression builder defines a 'Bind' method" |] [] let ``AndBang TraceApplicative with do-bang`` () = diff --git a/tests/fsharp/typecheck/sigs/neg61.bsl b/tests/fsharp/typecheck/sigs/neg61.bsl index e0b2fb5eafb..8a8bd79e168 100644 --- a/tests/fsharp/typecheck/sigs/neg61.bsl +++ b/tests/fsharp/typecheck/sigs/neg61.bsl @@ -59,9 +59,7 @@ neg61.fs(86,13,86,16): typecheck error FS3141: 'try/finally' expressions may not neg61.fs(92,13,92,70): typecheck error FS3142: 'use' expressions may not be used in queries -neg61.fs(97,13,97,33): typecheck error FS3143: 'let!', 'use!' and 'do!' expressions may not be used in queries - -neg61.fs(102,13,102,28): typecheck error FS3145: This is not a known query operator. Query operators are identifiers such as 'select', 'where', 'sortBy', 'thenBy', 'groupBy', 'groupValBy', 'join', 'groupJoin', 'sumBy' and 'averageBy', defined using corresponding methods on the 'QueryBuilder' type. +neg61.fs(97,13,97,17): typecheck error FS3143: 'let!', 'use!' and 'do!' expressions may not be used in queries neg61.fs(102,13,102,28): typecheck error FS3143: 'let!', 'use!' and 'do!' expressions may not be used in queries diff --git a/tests/service/data/SyntaxTree/ComputationExpression/MultipleSynExprAndBangHaveRangeThatStartsAtAndAndEndsAfterExpression.fs.bsl b/tests/service/data/SyntaxTree/ComputationExpression/MultipleSynExprAndBangHaveRangeThatStartsAtAndAndEndsAfterExpression.fs.bsl index 2c7ca108bc8..72f8528c23f 100644 --- a/tests/service/data/SyntaxTree/ComputationExpression/MultipleSynExprAndBangHaveRangeThatStartsAtAndAndEndsAfterExpression.fs.bsl +++ b/tests/service/data/SyntaxTree/ComputationExpression/MultipleSynExprAndBangHaveRangeThatStartsAtAndAndEndsAfterExpression.fs.bsl @@ -40,7 +40,8 @@ ImplFile EqualsRange = (5,13--5,14) InKeyword = None })], YieldOrReturn ((false, true), Ident bar, (6,4--6,14)), - (3,4--6,14), { EqualsRange = Some (3,13--3,14) }), + (3,4--6,14), { LetOrUseBangKeyword = (3,4--3,8) + EqualsRange = Some (3,13--3,14) }), (2,6--7,1)), (2,0--7,1)), (2,0--7,1))], PreXmlDocEmpty, [], None, (2,0--7,1), { LeadingKeyword = None })], (true, true), { ConditionalDirectives = [] diff --git a/tests/service/data/SyntaxTree/ComputationExpression/SynExprAndBangRangeStartsAtAndAndEndsAfterExpression.fs.bsl b/tests/service/data/SyntaxTree/ComputationExpression/SynExprAndBangRangeStartsAtAndAndEndsAfterExpression.fs.bsl index 105a94f5b46..d0dd3083e64 100644 --- a/tests/service/data/SyntaxTree/ComputationExpression/SynExprAndBangRangeStartsAtAndAndEndsAfterExpression.fs.bsl +++ b/tests/service/data/SyntaxTree/ComputationExpression/SynExprAndBangRangeStartsAtAndAndEndsAfterExpression.fs.bsl @@ -29,7 +29,8 @@ ImplFile EqualsRange = (5,13--5,14) InKeyword = None })], YieldOrReturn ((false, true), Ident bar, (7,4--7,14)), - (3,4--7,14), { EqualsRange = Some (3,13--3,14) }), + (3,4--7,14), { LetOrUseBangKeyword = (3,4--3,8) + EqualsRange = Some (3,13--3,14) }), (2,6--8,1)), (2,0--8,1)), (2,0--8,1))], PreXmlDocEmpty, [], None, (2,0--8,1), { LeadingKeyword = None })], (true, true), { ConditionalDirectives = [] diff --git a/tests/service/data/SyntaxTree/Expression/SynExprLetOrUseBangContainsTheRangeOfTheEqualsSign.fs.bsl b/tests/service/data/SyntaxTree/Expression/SynExprLetOrUseBangContainsTheRangeOfTheEqualsSign.fs.bsl index 7dfd05fc1ad..a0f54029820 100644 --- a/tests/service/data/SyntaxTree/Expression/SynExprLetOrUseBangContainsTheRangeOfTheEqualsSign.fs.bsl +++ b/tests/service/data/SyntaxTree/Expression/SynExprLetOrUseBangContainsTheRangeOfTheEqualsSign.fs.bsl @@ -27,7 +27,8 @@ ImplFile InKeyword = None })], YieldOrReturn ((false, true), Const (Unit, (5,11--5,13)), (5,4--5,13)), - (3,4--5,13), { EqualsRange = Some (3,11--3,12) }), + (3,4--5,13), { LetOrUseBangKeyword = (3,4--3,8) + EqualsRange = Some (3,11--3,12) }), (2,5--6,1)), (2,0--6,1)), (2,0--6,1))], PreXmlDocEmpty, [], None, (2,0--6,1), { LeadingKeyword = None })], (true, true), { ConditionalDirectives = []