diff --git a/.devcontainer/Dockerfile b/.devcontainer/Dockerfile
index 8bb334d1e44..e1dcf31c425 100644
--- a/.devcontainer/Dockerfile
+++ b/.devcontainer/Dockerfile
@@ -14,6 +14,7 @@ RUN apt-get update \
&& apt-get -y install --no-install-recommends apt-utils dialog 2>&1 \
# Verify bash, git, process tools, lsb-release (common in install instructions for CLIs) installed
&& apt-get -y install bash git openssh-client less iproute2 procps lsb-release \
+ && apt-get -y install gnupg \
# Clean up
&& apt-get autoremove -y \
&& apt-get clean -y \
@@ -23,4 +24,4 @@ RUN apt-get update \
ENV DEBIAN_FRONTEND=dialog
# Make sure we can build using plain dotnet
-ENV BUILDING_USING_DOTNET="true"
\ No newline at end of file
+ENV BUILDING_USING_DOTNET="true"
diff --git a/.vscode/tasks.json b/.vscode/tasks.json
index 6a15d101828..7ec6813a99c 100644
--- a/.vscode/tasks.json
+++ b/.vscode/tasks.json
@@ -20,14 +20,16 @@
"type": "shell",
"args": [
"build",
- "-c Debug",
+ "-c",
+ "Debug",
"FSharp.Compiler.Service.sln"
],
"windows": {
"command": "dotnet",
"args": [
"build",
- "-c Debug",
+ "-c",
+ "Debug",
"FSharp.Compiler.Service.sln"
],
},
@@ -40,14 +42,16 @@
"type": "shell",
"args": [
"build",
- "-c Release",
+ "-c",
+ "Release",
"FSharp.Compiler.Service.sln"
],
"windows": {
"command": "dotnet",
"args": [
"build",
- "-c Release",
+ "-c",
+ "Release",
"FSharp.Compiler.Service.sln"
],
},
diff --git a/DEVGUIDE.md b/DEVGUIDE.md
index 8e043b4dd5b..aca6b5c01d6 100644
--- a/DEVGUIDE.md
+++ b/DEVGUIDE.md
@@ -122,6 +122,12 @@ You can find all test options as separate flags. For example `build -testAll`:
Running any of the above will build the latest changes and run tests against them.
+## Using your custom compiler to build this repository
+
+By removing all the subfolders called `Proto` under `artifacts` and running the `build` script again, the proto compiler will include your changes.
+
+Once the "proto" compiler is built, it won't be built again, so you may want to perform those steps again to ensure your changes don't break building the compiler itself.
+
## Using your custom compiler to build other projects
Building the compiler using `build.cmd` or `build.sh` will output artifacts in `artifacts\bin`.
diff --git a/INTERNAL.md b/INTERNAL.md
index 41d34dbcb18..f56689e538b 100644
--- a/INTERNAL.md
+++ b/INTERNAL.md
@@ -98,29 +98,6 @@ Since github issue filtering is currently not flexible enough, that query was ge
Invoke-WebRequest -Uri "https://api.github.com/repos/dotnet/fsharp/labels?per_page=100" | ConvertFrom-Json | % { $_.name } | ? { $_.StartsWith("Area-") } | % { Write-Host -NoNewLine ('-label:"' + $_ + '" ') }
```
-## Less interesting links
-
-[FSharp.Core (Official NuGet Release)](https://dev.azure.com/dnceng/internal/_release?_a=releases&definitionId=72).
-Uploads the final `FSharp.Core` package from the specified build to NuGet. This should only be run when we know for
-certain which build produced the final offical package.
-
-[FSharp.Core (Preview NuGet Release)](https://dev.azure.com/dnceng/internal/_release?_a=releases&definitionId=92).
-Uploads the preview `FSharp.Core.*-beta.*` package from the specified build to NuGet. This should be run every time
-a new SDK preview is released.
-
-[FCS (Official NuGet Release)](https://dev.azure.com/dnceng/internal/_release?view=mine&_a=releases&definitionId=99).
-Uploads the final `FSharp.Compiler.Service` package from the specified build to NuGet. Only builds from the `release/fcs`
-branch can be selected. This should only be run when we're fairly certain that the package is complete.
-
-[FCS (Preview NuGet Release)](https://dev.azure.com/dnceng/internal/_release?view=mine&_a=releases&definitionId=98).
-Uploads the preview `FSharp.Compiler.Service.*-preview.*` package from the specified build to NuGet. Only builds from the
-`main` branch can be selected. This can be run whenever we think we're ready to preview a new FCS build.
-
-[Nightly VSIX (main) uploader](https://dev.azure.com/dnceng/internal/_release?_a=releases&definitionId=70). Uploads
-a package from every build of `main` to the [Nightly VSIX feed](README.md#using-nightly-releases-in-visual-studio).
-
-[Nightly VSIX (preview) uploader](https://dev.azure.com/dnceng/internal/_release?_a=releases&definitionId=71). Uploads
-a package from every build of the branch that corresponds to the current Visual Studio preview to the
-[Preview VSIX feed](README.md#using-nightly-releases-in-visual-studio).
+## Other links
[Internal source mirror](https://dev.azure.com/dnceng/internal/_git/dotnet-fsharp).
diff --git a/README.md b/README.md
index be1f103e9ef..58a61e349e5 100644
--- a/README.md
+++ b/README.md
@@ -75,6 +75,8 @@ Even if you find a single-character typo, we're happy to take the change! Althou
```
+**NOTE:** Official NuGet releases of FCS and FSharp.Core are synched with SDK releases (on purpose - we want to be in sync). Nightly packages release to Azure feeds on every successful insertion.
+
## Branches
These are the branches in use:
diff --git a/src/Compiler/Checking/CheckComputationExpressions.fs b/src/Compiler/Checking/CheckComputationExpressions.fs
index e27dcffc7bf..82403341f7d 100644
--- a/src/Compiler/Checking/CheckComputationExpressions.fs
+++ b/src/Compiler/Checking/CheckComputationExpressions.fs
@@ -2210,7 +2210,7 @@ let TcSequenceExpression (cenv: cenv) env tpenv comp (overallTy: OverallTy) m =
let env = { env with eContextInfo = ContextInfo.SequenceExpression genOuterTy }
- if enableImplicitYield then
+ if enableImplicitYield then
let hasTypeUnit, expr, tpenv = TryTcStmt cenv env tpenv comp
if hasTypeUnit then
Choice2Of2 expr, tpenv
@@ -2218,6 +2218,7 @@ let TcSequenceExpression (cenv: cenv) env tpenv comp (overallTy: OverallTy) m =
let genResultTy = NewInferenceType g
let mExpr = expr.Range
UnifyTypes cenv env mExpr genOuterTy (mkSeqTy cenv.g genResultTy)
+ let expr, tpenv = TcExprFlex cenv flex true genResultTy env tpenv comp
let exprTy = tyOfExpr cenv.g expr
AddCxTypeMustSubsumeType env.eContextInfo env.DisplayEnv cenv.css mExpr NoTrace genResultTy exprTy
let resExpr = mkCallSeqSingleton cenv.g mExpr genResultTy (mkCoerceExpr(expr, genResultTy, mExpr, exprTy))
diff --git a/src/Compiler/Checking/NicePrint.fs b/src/Compiler/Checking/NicePrint.fs
index 381c3789acf..c7062e058d2 100644
--- a/src/Compiler/Checking/NicePrint.fs
+++ b/src/Compiler/Checking/NicePrint.fs
@@ -38,7 +38,7 @@ module internal PrintUtilities =
let squareAngleL x = LeftL.leftBracketAngle ^^ x ^^ RightL.rightBracketAngle
- let angleL x = sepL leftAngle ^^ x ^^ rightL rightAngle
+ let angleL x = SepL.leftAngle ^^ x ^^ RightL.rightAngle
let braceL x = wordL leftBrace ^^ x ^^ wordL rightBrace
@@ -113,9 +113,9 @@ module internal PrintUtilities =
let layout =
argTyL
^^ (if idx = lastIndex then
- wordL (tagPunctuation retTyDelim)
+ wordL retTyDelim
else
- wordL (tagPunctuation "->"))
+ WordL.arrow)
isTupled, layout)
|> List.rev
@@ -486,7 +486,7 @@ module PrintTypes =
s |> tagNumericLiteral
| Const.Char c -> "'" + c.ToString() + "'" |> tagStringLiteral
| Const.String bs -> "\"" + bs + "\"" |> tagNumericLiteral
- | Const.Unit -> "()" |> tagPunctuation
+ | Const.Unit -> punctuationUnit
| Const.Decimal bs -> string bs + "M" |> tagNumericLiteral
// either "null" or "the default value for a struct"
| Const.Zero -> tagKeyword(if isRefTy g ty then "null" else "default")
@@ -555,14 +555,14 @@ module PrintTypes =
// Detect 'typeof' calls
| TypeOfExpr denv.g ty ->
- LeftL.keywordTypeof ^^ wordL (tagPunctuation "<") ^^ layoutType denv ty ^^ rightL (tagPunctuation ">")
+ LeftL.keywordTypeof ^^ WordL.leftAngle ^^ layoutType denv ty ^^ RightL.rightAngle
// Detect 'typedefof' calls
| TypeDefOfExpr denv.g ty ->
- LeftL.keywordTypedefof ^^ wordL (tagPunctuation "<") ^^ layoutType denv ty ^^ rightL (tagPunctuation ">")
+ LeftL.keywordTypedefof ^^ WordL.leftAngle ^^ layoutType denv ty ^^ RightL.rightAngle
| Expr.Op (TOp.Coerce, [tgtTy;_], [arg2], _) ->
- leftL (tagPunctuation "(") ^^ layoutAttribArg denv arg2 ^^ wordL (tagPunctuation ":>") ^^ layoutType denv tgtTy ^^ rightL (tagPunctuation ")")
+ LeftL.leftParen ^^ layoutAttribArg denv arg2 ^^ wordL (tagPunctuation ":>") ^^ layoutType denv tgtTy ^^ RightL.rightParen
| AttribBitwiseOrExpr denv.g (arg1, arg2) ->
layoutAttribArg denv arg1 ^^ wordL (tagPunctuation "|||") ^^ layoutAttribArg denv arg2
@@ -580,7 +580,7 @@ module PrintTypes =
props
|> List.map (fun (AttribNamedArg(name,_, _, AttribExpr(e1, _))) ->
wordL (tagProperty name) ^^ WordL.equals ^^ layoutAttribArg denv e1)
- sepListL (rightL (tagPunctuation ",")) (argsL @ propsL)
+ sepListL RightL.comma (argsL @ propsL)
/// Layout an attribute 'Type(arg1, ..., argN)'
and layoutAttrib denv (Attrib(tcref, _, args, props, _, _, _)) =
@@ -619,7 +619,7 @@ module PrintTypes =
wordL (tagNumericLiteral str)
| ILAttribElem.Null -> wordL (tagKeyword "null")
| ILAttribElem.Array (_, xs) ->
- leftL (tagPunctuation "[|") ^^ semiListL (List.map (layoutILAttribElement denv) xs) ^^ RightL.rightBracketBar
+ LeftL.leftBracketBar ^^ semiListL (List.map (layoutILAttribElement denv) xs) ^^ RightL.rightBracketBar
| ILAttribElem.Type (Some ty) ->
LeftL.keywordTypeof ^^ SepL.leftAngle ^^ PrintIL.layoutILType denv [] ty ^^ RightL.rightAngle
| ILAttribElem.Type None -> wordL (tagText "")
@@ -628,7 +628,7 @@ module PrintTypes =
| ILAttribElem.TypeRef None -> emptyL
and layoutILAttrib denv (ty, args) =
- let argsL = bracketL (sepListL (rightL (tagPunctuation ",")) (List.map (layoutILAttribElement denv) args))
+ let argsL = bracketL (sepListL RightL.comma (List.map (layoutILAttribElement denv) args))
PrintIL.layoutILType denv [] ty ++ argsL
/// Layout '[]' above another block
@@ -676,12 +676,12 @@ module PrintTypes =
match attrsL with
| [] -> restL
- | _ -> squareAngleL (sepListL (rightL (tagPunctuation ";")) attrsL) @@ restL
+ | _ -> squareAngleL (sepListL RightL.semicolon attrsL) @@ restL
and layoutTyparAttribs denv kind attrs restL =
match attrs, kind with
| [], TyparKind.Type -> restL
- | _, _ -> squareAngleL (sepListL (rightL (tagPunctuation ";")) ((match kind with TyparKind.Type -> [] | TyparKind.Measure -> [wordL (tagText "Measure")]) @ List.map (layoutAttrib denv) attrs)) ^^ restL
+ | _, _ -> squareAngleL (sepListL RightL.semicolon ((match kind with TyparKind.Type -> [] | TyparKind.Measure -> [wordL (tagText "Measure")]) @ List.map (layoutAttrib denv) attrs)) ^^ restL
and layoutTyparRef denv (typar: Typar) =
tagTypeParameter
@@ -744,7 +744,7 @@ module PrintTypes =
if denv.abbreviateAdditionalConstraints then
wordL (tagKeyword "when") ^^ wordL(tagText "")
elif denv.shortConstraints then
- leftL (tagPunctuation "(") ^^ wordL (tagKeyword "requires") ^^ sepListL (wordL (tagKeyword "and")) cxsL ^^ rightL (tagPunctuation ")")
+ LeftL.leftParen ^^ wordL (tagKeyword "requires") ^^ sepListL (wordL (tagKeyword "and")) cxsL ^^ RightL.rightParen
else
wordL (tagKeyword "when") ^^ sepListL (wordL (tagKeyword "and")) cxsL
@@ -765,9 +765,9 @@ module PrintTypes =
| TyparConstraint.IsEnum(ty, _) ->
if denv.shortConstraints then
- [wordL (tagKeyword "enum")]
+ [ WordL.keywordEnum ]
else
- [longConstraintPrefix (layoutTypeAppWithInfoAndPrec denv env (wordL (tagKeyword "enum")) 2 true [ty])]
+ [longConstraintPrefix (layoutTypeAppWithInfoAndPrec denv env WordL.keywordEnum 2 true [ty])]
| TyparConstraint.SupportsComparison _ ->
if denv.shortConstraints then
@@ -806,10 +806,10 @@ module PrintTypes =
if denv.shortConstraints then
[wordL (tagText "reference type")]
else
- [(wordL (tagKeyword "not") ^^ wordL(tagKeyword "struct")) |> longConstraintPrefix]
+ [(wordL (tagKeyword "not") ^^ WordL.keywordStruct) |> longConstraintPrefix]
| TyparConstraint.SimpleChoice(tys, _) ->
- [bracketL (sepListL (sepL (tagPunctuation "|")) (List.map (layoutTypeWithInfo denv env) tys)) |> longConstraintPrefix]
+ [bracketL (sepListL (sepL bar) (List.map (layoutTypeWithInfo denv env) tys)) |> longConstraintPrefix]
| TyparConstraint.RequiresDefaultConstructor _ ->
if denv.shortConstraints then
@@ -854,13 +854,13 @@ module PrintTypes =
| [] -> retTyL
| _ ->
let argTysL = layoutTypesWithInfoAndPrec denv env 2 (wordL (tagPunctuation "*")) argTys
- curriedLayoutsL "->" [argTysL] retTyL
+ curriedLayoutsL arrow [argTysL] retTyL
let getterSetterL =
match memFlags.MemberKind with
| SynMemberKind.PropertyGet when not argTys.IsEmpty ->
- wordL (tagKeyword "with") ^^ wordL (tagText "get")
+ WordL.keywordWith ^^ WordL.keywordGet
| SynMemberKind.PropertySet ->
- wordL (tagKeyword "with") ^^ wordL (tagText "set")
+ WordL.keywordWith ^^ WordL.keywordSet
| _ ->
emptyL
(tysL |> addColonL) --- bracketL (stat ++ (nameL |> addColonL) --- sigL --- getterSetterL)
@@ -881,20 +881,20 @@ module PrintTypes =
List.map (fun (c, e) -> measureToPowerL (unconL c) (NegRational e)) negcs)
match (negvs, negcs) with
| [], [] -> (match posvs, poscs with [], [] -> wordL (tagNumericLiteral "1") | _ -> prefix)
- | _ -> prefix ^^ sepL (tagPunctuation "/") ^^ (if List.length negvs + List.length negcs > 1 then sepL (tagPunctuation "(") ^^ postfix ^^ sepL (tagPunctuation ")") else postfix)
+ | _ -> prefix ^^ sepL (tagPunctuation "/") ^^ (if List.length negvs + List.length negcs > 1 then SepL.leftParen ^^ postfix ^^ SepL.rightParen else postfix)
/// Layout type arguments, either NAME or (ty, ..., ty) NAME *)
and layoutTypeAppWithInfoAndPrec denv env tcL prec prefix argTys =
if prefix then
match argTys with
| [] -> tcL
- | [argTy] -> tcL ^^ sepL (tagPunctuation "<") ^^ (layoutTypeWithInfoAndPrec denv env 4 argTy) ^^ rightL (tagPunctuation">")
- | _ -> bracketIfL (prec <= 1) (tcL ^^ angleL (layoutTypesWithInfoAndPrec denv env 2 (sepL (tagPunctuation ",")) argTys))
+ | [argTy] -> tcL ^^ SepL.leftAngle ^^ (layoutTypeWithInfoAndPrec denv env 4 argTy) ^^ RightL.rightAngle
+ | _ -> bracketIfL (prec <= 1) (tcL ^^ angleL (layoutTypesWithInfoAndPrec denv env 2 SepL.comma argTys))
else
match argTys with
| [] -> tcL
| [arg] -> layoutTypeWithInfoAndPrec denv env 2 arg ^^ tcL
- | args -> bracketIfL (prec <= 1) (bracketL (layoutTypesWithInfoAndPrec denv env 2 (sepL (tagPunctuation ",")) args) --- tcL)
+ | args -> bracketIfL (prec <= 1) (bracketL (layoutTypesWithInfoAndPrec denv env 2 SepL.comma args) --- tcL)
/// Layout a type, taking precedence into account to insert brackets where needed
and layoutTypeWithInfoAndPrec denv env prec ty =
@@ -957,7 +957,7 @@ module PrintTypes =
// Layout a tuple type
| TType_anon (anonInfo, tys) ->
- let core = sepListL (rightL (tagPunctuation ";")) (List.map2 (fun nm ty -> wordL (tagField nm) ^^ rightL (tagPunctuation ":") ^^ layoutTypeWithInfoAndPrec denv env prec ty) (Array.toList anonInfo.SortedNames) tys)
+ let core = sepListL RightL.semicolon (List.map2 (fun nm ty -> wordL (tagField nm) ^^ RightL.colon ^^ layoutTypeWithInfoAndPrec denv env prec ty) (Array.toList anonInfo.SortedNames) tys)
if evalAnonInfoIsStruct anonInfo then
WordL.keywordStruct --- braceBarL core
else
@@ -976,14 +976,14 @@ module PrintTypes =
let tauL = layoutTypeWithInfoAndPrec denv env prec tau
match tps with
| [] -> tauL
- | [h] -> layoutTyparRefWithInfo denv env h ^^ rightL (tagPunctuation ".") --- tauL
- | h :: t -> spaceListL (List.map (layoutTyparRefWithInfo denv env) (h :: t)) ^^ rightL (tagPunctuation ".") --- tauL
+ | [h] -> layoutTyparRefWithInfo denv env h ^^ rightL dot --- tauL
+ | h :: t -> spaceListL (List.map (layoutTyparRefWithInfo denv env) (h :: t)) ^^ rightL dot --- tauL
| TType_fun _ ->
let argTys, retTy = stripFunTy g ty
let retTyL = layoutTypeWithInfoAndPrec denv env 5 retTy
let argTysL = argTys |> List.map (layoutTypeWithInfoAndPrec denv env 4)
- let funcTyL = curriedLayoutsL "->" argTysL retTyL
+ let funcTyL = curriedLayoutsL arrow argTysL retTyL
bracketIfL (prec <= 4) funcTyL
// Layout a type variable .
@@ -1013,7 +1013,7 @@ module PrintTypes =
let attrsL =
[ for attr in attribs do layoutAttrib denv attr ]
- squareAngleL (sepListL (rightL (tagPunctuation ";")) attrsL)
+ squareAngleL (sepListL RightL.semicolon attrsL)
// Format each argument, including its name and type
let layoutArgInfo denv env (ty, argInfo: ArgReprInfo) =
@@ -1056,15 +1056,15 @@ module PrintTypes =
match genParamTys with
| [] -> emptyL
| _ ->
- wordL (tagPunctuation "<")
+ WordL.leftAngle
^^
(
genParamTys
|> List.map (layoutTypeWithInfoAndPrec denv env 4)
- |> sepListL (wordL (tagPunctuation ","))
+ |> sepListL (wordL comma)
)
^^
- wordL (tagPunctuation ">")
+ wordL rightAngle
/// Layout a single type used as the type of a member or value
let layoutTopType denv env argInfos retTy cxs =
@@ -1073,7 +1073,7 @@ module PrintTypes =
match argInfos with
| [] -> retTyL --- cxsL
| _ ->
- let retTyDelim = if denv.useColonForReturnType then ":" else "->"
+ let retTyDelim = if denv.useColonForReturnType then colon else arrow
let allArgsL = layoutCurriedArgInfos denv env argInfos
curriedLayoutsL retTyDelim allArgsL retTyL --- cxsL
@@ -1090,7 +1090,7 @@ module PrintTypes =
| _ ->
let tpcsL = layoutConstraintsWithInfo denv env tpcs
- let coreL = sepListL (sepL (tagPunctuation ",")) (List.map (layoutTyparRefWithInfo denv env) typars)
+ let coreL = sepListL SepL.comma (List.map (layoutTyparRefWithInfo denv env) typars)
if prefix || not (isNil tpcs) then
nmL ^^ angleL (coreL --- tpcsL)
else
@@ -1653,7 +1653,7 @@ module InfoMemberPrinting =
match methInfo with
| DefaultStructCtor _ ->
let prettyTyparInst, _ = PrettyTypes.PrettifyInst amap.g typarInst
- let resL = PrintTypes.layoutTyconRef denv methInfo.ApparentEnclosingTyconRef ^^ wordL (tagPunctuation "()")
+ let resL = PrintTypes.layoutTyconRef denv methInfo.ApparentEnclosingTyconRef ^^ wordL punctuationUnit
prettyTyparInst, resL
| FSMeth(_, _, vref, _) ->
let prettyTyparInst, resL = PrintTastMemberOrVals.prettyLayoutOfValOrMember { denv with showMemberContainers=true } infoReader typarInst vref
@@ -1676,11 +1676,11 @@ module InfoMemberPrinting =
let getterSetter =
match pinfo.HasGetter, pinfo.HasSetter with
| true, false ->
- wordL (tagKeyword "with") ^^ wordL (tagText "get")
+ WordL.keywordWith ^^ WordL.keywordGet
| false, true ->
- wordL (tagKeyword "with") ^^ wordL (tagText "set")
+ WordL.keywordWith ^^ WordL.keywordSet
| true, true ->
- wordL (tagKeyword "with") ^^ wordL (tagText "get, set")
+ WordL.keywordWith ^^ wordL (tagText "get, set")
| false, false ->
emptyL
@@ -1827,7 +1827,7 @@ module TastDefinitionPrinting =
| Some vref ->
match pinfo with
| DifferentGetterAndSetter(getValRef, setValRef) ->
- let getSuffix = if pinfo.IsIndexer then emptyL else wordL (tagKeyword "with") ^^ wordL (tagText "get")
+ let getSuffix = if pinfo.IsIndexer then emptyL else WordL.keywordWith ^^ WordL.keywordGet
[
PrintTastMemberOrVals.prettyLayoutOfValOrMemberNoInst denv infoReader getValRef ^^ getSuffix
PrintTastMemberOrVals.prettyLayoutOfValOrMemberNoInst denv infoReader setValRef
@@ -1835,7 +1835,7 @@ module TastDefinitionPrinting =
| _ ->
let propL = PrintTastMemberOrVals.prettyLayoutOfValOrMemberNoInst denv infoReader vref
if pinfo.HasGetter && pinfo.HasSetter && not pinfo.IsIndexer && isPublicGetterSetter pinfo.GetterMethod pinfo.SetterMethod then
- [ propL ^^ wordL (tagKeyword "with") ^^ wordL (tagText "get, set") ]
+ [ propL ^^ WordL.keywordWith ^^ wordL (tagText "get, set") ]
else
[ propL ]
| None ->
@@ -1928,7 +1928,7 @@ module TastDefinitionPrinting =
let iimplsLs =
iimpls
- |> List.map (fun intfTy -> wordL (tagKeyword (if isInterfaceTy g ty then "inherit" else "interface")) -* layoutType denv intfTy)
+ |> List.map (fun intfTy -> (if isInterfaceTy g ty then WordL.keywordInherit else WordL.keywordInterface) -* layoutType denv intfTy)
let props =
GetImmediateIntrinsicPropInfosOfType (None, ad) g amap m ty
@@ -2060,7 +2060,7 @@ module TastDefinitionPrinting =
let inheritsL =
inherits
- |> List.map (fun super -> wordL (tagKeyword "inherit") ^^ (layoutType denv super))
+ |> List.map (fun super -> WordL.keywordInherit ^^ (layoutType denv super))
let allDecls = inheritsL @ iimplsLs @ ctorLs @ instanceValLs @ methLs @ ilFieldsL @ propLs @ eventLs @ staticValLs @ nestedTypeLs
@@ -2300,7 +2300,7 @@ module TastDefinitionPrinting =
if mspec.IsNamespace then
// This is a container namespace. We print the header when we get to the first concrete module.
let pathL = path |> List.map (ConvertLogicalNameToDisplayLayout (tagNamespace >> wordL))
- wordL (tagKeyword "namespace") ^^ sepListL SepL.dot pathL
+ WordL.keywordNamespace ^^ sepListL SepL.dot pathL
else
// This is a module
let name = path |> List.last
@@ -2314,7 +2314,7 @@ module TastDefinitionPrinting =
let innerPathL = innerPath |> List.map (ConvertLogicalNameToDisplayLayout (tagNamespace >> wordL))
sepListL SepL.dot innerPathL ^^ SepL.dot ^^ nameL
- let modNameL = wordL (tagKeyword "module") ^^ nameL
+ let modNameL = WordL.keywordModule ^^ nameL
let modNameEqualsL = modNameL ^^ WordL.equals
let modIsEmpty =
mspec.ModuleOrNamespaceType.AllEntities |> Seq.isEmpty &&
@@ -2326,7 +2326,7 @@ module TastDefinitionPrinting =
// If so print a "module" declaration
modNameL
elif modIsEmpty then
- modNameEqualsL ^^ wordL (tagKeyword "begin") ^^ WordL.keywordEnd
+ modNameEqualsL ^^ WordL.keywordBegin ^^ WordL.keywordEnd
else
// Otherwise this is an outer module contained immediately in a namespace
// We already printed the namespace declaration earlier. So just print the
@@ -2483,7 +2483,7 @@ module InferredSigPrinting =
let basic = imdefL denv def
let attribs: Attribs = List.append mspec.Attribs moduleAttribs
let modNameL =
- wordL (tagKeyword "module") ^^ nmL
+ WordL.keywordModule ^^ nmL
|> layoutAttribs denv None false mspec.TypeOrMeasureKind attribs
let basicL = modNameL @@ basic
layoutXmlDoc denv true mspec.XmlDoc basicL
@@ -2495,7 +2495,7 @@ module InferredSigPrinting =
let pathL = innerPath |> List.map (fst >> ConvertLogicalNameToDisplayLayout (tagNamespace >> wordL))
// This is a container namespace. We print the header when we get to the first concrete module.
let headerL =
- wordL (tagKeyword "namespace") ^^ sepListL SepL.dot pathL
+ WordL.keywordNamespace ^^ sepListL SepL.dot pathL
headerL @@* basic
else
// This is a namespace that only contains namespaces. Skip the header
@@ -2511,7 +2511,7 @@ module InferredSigPrinting =
let denv = denv.AddAccessibility mspec.Accessibility
let basic = imdefL denv def
let modNameL =
- wordL (tagKeyword "module") ^^ nmL
+ WordL.keywordModule ^^ nmL
|> layoutAttribs denv None false mspec.TypeOrMeasureKind mspec.Attribs
let modNameEqualsL = modNameL ^^ WordL.equals
let isNamespace = function | Namespace _ -> true | _ -> false
@@ -2540,7 +2540,7 @@ module InferredSigPrinting =
else
// OK, this is a nested module, with indentation
if isEmptyL basic then
- modNameEqualsL ^^ wordL (tagKeyword "begin") @@* basic @@* WordL.keywordEnd
+ modNameEqualsL ^^ WordL.keywordBegin @@* basic @@* WordL.keywordEnd
else
modNameEqualsL @@* basic
layoutXmlDoc denv true mspec.XmlDoc basicL
@@ -2551,11 +2551,11 @@ module InferredSigPrinting =
let keyword =
if not mspec.IsImplicitNamespace && mspec.IsNamespace then
- "namespace"
+ WordL.keywordNamespace
else
- "module"
+ WordL.keywordModule
- wordL (tagKeyword keyword) ^^ sepListL SepL.dot pathL
+ keyword ^^ sepListL SepL.dot pathL
match expr with
| EmptyModuleOrNamespaces mspecs when showHeader ->
@@ -2575,7 +2575,7 @@ module PrintData =
match expr with
| Expr.Const (c, _, ty) ->
if isEnumTy denv.g ty then
- wordL (tagKeyword "enum") ^^ angleL (layoutType denv ty) ^^ bracketL (layoutConst denv.g ty c)
+ WordL.keywordEnum ^^ angleL (layoutType denv ty) ^^ bracketL (layoutConst denv.g ty c)
else
layoutConst denv.g ty c
@@ -2603,17 +2603,17 @@ module PrintData =
| Expr.Op (TOp.Recd (_, tc), _, xs, _) ->
let fields = tc.TrueInstanceFieldsAsList
- let lay fs x = (wordL (tagRecordField fs.rfield_id.idText) ^^ sepL (tagPunctuation "=")) --- (dataExprL denv x)
+ let lay fs x = (wordL (tagRecordField fs.rfield_id.idText) ^^ sepL equals) --- (dataExprL denv x)
braceL (semiListL (List.map2 lay fields xs))
| Expr.Op (TOp.ValFieldGet (RecdFieldRef.RecdFieldRef (tcref, name)), _, _, _) ->
- (layoutTyconRef denv tcref) ^^ sepL (tagPunctuation ".") ^^ wordL (tagField name)
+ (layoutTyconRef denv tcref) ^^ SepL.dot ^^ wordL (tagField name)
| Expr.Op (TOp.Array, [_], xs, _) ->
- leftL (tagPunctuation "[|") ^^ semiListL (dataExprsL denv xs) ^^ RightL.rightBracketBar
+ LeftL.leftBracketBar ^^ semiListL (dataExprsL denv xs) ^^ RightL.rightBracketBar
| _ ->
- wordL (tagPunctuation "?")
+ wordL questionMark
and dataExprsL denv xs = List.map (dataExprL denv) xs
diff --git a/src/Compiler/Driver/GraphChecking/TrieMapping.fs b/src/Compiler/Driver/GraphChecking/TrieMapping.fs
index bfab87f9bec..e34939abac1 100644
--- a/src/Compiler/Driver/GraphChecking/TrieMapping.fs
+++ b/src/Compiler/Driver/GraphChecking/TrieMapping.fs
@@ -70,6 +70,14 @@ let mergeTrieNodes (defaultChildSize: int) (tries: TrieNode array) =
TrieNodeInfo.Namespace (filesThatExposeTypes = otherFiles; filesDefiningNamespaceWithoutTypes = otherFilesWithoutTypes) ->
currentFilesThatExposeTypes.UnionWith otherFiles
currentFilesWithoutTypes.UnionWith otherFilesWithoutTypes
+ // Edge case scenario detected in https://github.com/dotnet/fsharp/issues/15985
+ | TrieNodeInfo.Namespace (filesThatExposeTypes = currentFilesThatExposeTypes), TrieNodeInfo.Module (_name, file) ->
+ // Keep the namespace (as it can still have nested children).
+ currentFilesThatExposeTypes.Add file |> ignore
+ | TrieNodeInfo.Module (_name, file), TrieNodeInfo.Namespace (filesThatExposeTypes = currentFilesThatExposeTypes) ->
+ currentFilesThatExposeTypes.Add file |> ignore
+ // Replace the module in favour of the namespace (which can hold nested children).
+ root.Children[ k ] <- v
| _ -> ()
for kv in v.Children do
diff --git a/src/Compiler/Facilities/TextLayoutRender.fs b/src/Compiler/Facilities/TextLayoutRender.fs
index 0768e699df1..a0b218dab77 100644
--- a/src/Compiler/Facilities/TextLayoutRender.fs
+++ b/src/Compiler/Facilities/TextLayoutRender.fs
@@ -60,6 +60,9 @@ module WordL =
let keywordOverride = wordL TaggedText.keywordOverride
let keywordEnum = wordL TaggedText.keywordEnum
let keywordInline = wordL TaggedText.keywordInline
+ let leftAngle = wordL TaggedText.leftAngle
+ let keywordModule = wordL TaggedText.keywordModule
+ let keywordNamespace = wordL TaggedText.keywordNamespace
module LeftL =
let leftParen = leftL TaggedText.leftParen
@@ -78,6 +81,7 @@ module RightL =
let rightAngle = rightL TaggedText.rightAngle
let rightBracketAngle = rightL TaggedText.rightBracketAngle
let rightBracketBar = rightL TaggedText.rightBracketBar
+ let semicolon = rightL TaggedText.semicolon
type LayoutRenderer<'a, 'b> =
abstract Start: unit -> 'b
diff --git a/src/Compiler/Facilities/TextLayoutRender.fsi b/src/Compiler/Facilities/TextLayoutRender.fsi
index 48f874a0d3b..0e52b9998f2 100644
--- a/src/Compiler/Facilities/TextLayoutRender.fsi
+++ b/src/Compiler/Facilities/TextLayoutRender.fsi
@@ -99,6 +99,9 @@ module internal WordL =
val keywordOverride: Layout
val keywordEnum: Layout
val keywordInline: Layout
+ val leftAngle: Layout
+ val keywordModule: Layout
+ val keywordNamespace: Layout
module internal LeftL =
val leftParen: Layout
@@ -117,3 +120,4 @@ module internal RightL =
val rightAngle: Layout
val rightBracketAngle: Layout
val rightBracketBar: Layout
+ val semicolon: Layout
diff --git a/src/Compiler/Utilities/sformat.fs b/src/Compiler/Utilities/sformat.fs
index 7281286dfd6..217b527f871 100644
--- a/src/Compiler/Utilities/sformat.fs
+++ b/src/Compiler/Utilities/sformat.fs
@@ -253,6 +253,9 @@ module TaggedText =
let star = tagOperator "*"
let keywordNew = tagKeyword "new"
let keywordInline = tagKeyword "inline"
+ let keywordModule = tagKeyword "module"
+ let keywordNamespace = tagKeyword "namespace"
+ let punctuationUnit = tagPunctuation "()"
#endif
[]
diff --git a/src/Compiler/Utilities/sformat.fsi b/src/Compiler/Utilities/sformat.fsi
index e4e8412495f..1c740a38dce 100644
--- a/src/Compiler/Utilities/sformat.fsi
+++ b/src/Compiler/Utilities/sformat.fsi
@@ -211,6 +211,9 @@ module internal TaggedText =
val internal star: TaggedText
val internal keywordNew: TaggedText
val internal keywordInline: TaggedText
+ val internal keywordModule: TaggedText
+ val internal keywordNamespace: TaggedText
+ val internal punctuationUnit: TaggedText
type internal IEnvironment =
/// Return to the layout-generation
diff --git a/src/FSharp.Core/ILLink.LinkAttributes.xml b/src/FSharp.Core/ILLink.LinkAttributes.xml
index e4493298d41..70eba54ff4e 100644
--- a/src/FSharp.Core/ILLink.LinkAttributes.xml
+++ b/src/FSharp.Core/ILLink.LinkAttributes.xml
@@ -122,6 +122,9 @@
+
+
+
diff --git a/tests/FSharp.Compiler.ComponentTests/ErrorMessages/TypeMismatchTests.fs b/tests/FSharp.Compiler.ComponentTests/ErrorMessages/TypeMismatchTests.fs
index 7ebec39786f..06dc7d44671 100644
--- a/tests/FSharp.Compiler.ComponentTests/ErrorMessages/TypeMismatchTests.fs
+++ b/tests/FSharp.Compiler.ComponentTests/ErrorMessages/TypeMismatchTests.fs
@@ -345,9 +345,9 @@ let f4 =
|> typecheck
|> shouldFail
|> withDiagnostics [
- (Error 193, Line 6, Col 9, Line 6, Col 16, "Type constraint mismatch. The type \n 'string' \nis not compatible with type\n 'int' \n")
- (Error 193, Line 12, Col 13, Line 12, Col 16, "Type constraint mismatch. The type \n 'string' \nis not compatible with type\n 'int' \n")
+ (Error 1, Line 6, Col 9, Line 6, Col 16, "This expression was expected to have type\n 'int' \nbut here has type\n 'string' ")
+ (Error 1, Line 12, Col 13, Line 12, Col 16, "This expression was expected to have type\n 'int' \nbut here has type\n 'string' ")
(Error 193, Line 21, Col 9, Line 21, Col 24, "Type constraint mismatch. The type \n 'int list' \nis not compatible with type\n 'string seq' \n")
- (Error 193, Line 28, Col 9, Line 28, Col 12, "Type constraint mismatch. The type \n 'float' \nis not compatible with type\n 'int64' \n")
+ (Error 1, Line 28, Col 9, Line 28, Col 12, "This expression was expected to have type\n 'int64' \nbut here has type\n 'float' ")
]
diff --git a/tests/FSharp.Compiler.ComponentTests/FSharp.Compiler.ComponentTests.fsproj b/tests/FSharp.Compiler.ComponentTests/FSharp.Compiler.ComponentTests.fsproj
index 111ba0c94e5..aefeb44cc50 100644
--- a/tests/FSharp.Compiler.ComponentTests/FSharp.Compiler.ComponentTests.fsproj
+++ b/tests/FSharp.Compiler.ComponentTests/FSharp.Compiler.ComponentTests.fsproj
@@ -226,6 +226,7 @@
+
diff --git a/tests/FSharp.Compiler.ComponentTests/Language/SequenceExpressionTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/SequenceExpressionTests.fs
index 4ad6a5cafe2..2f90f8963c6 100644
--- a/tests/FSharp.Compiler.ComponentTests/Language/SequenceExpressionTests.fs
+++ b/tests/FSharp.Compiler.ComponentTests/Language/SequenceExpressionTests.fs
@@ -414,8 +414,8 @@ let typedSeq =
|> withLangVersion80
|> typecheck
|> shouldFail
- |> withErrorCode 193
- |> withDiagnosticMessageMatches "Type constraint mismatch"
+ |> withErrorCode 1
+ |> withDiagnosticMessageMatches "This expression was expected to have type"
[]
diff --git a/tests/FSharp.Compiler.ComponentTests/TypeChecks/Graph/Scenarios.fs b/tests/FSharp.Compiler.ComponentTests/TypeChecks/Graph/Scenarios.fs
index 7931861dcfb..a60e8e7c116 100644
--- a/tests/FSharp.Compiler.ComponentTests/TypeChecks/Graph/Scenarios.fs
+++ b/tests/FSharp.Compiler.ComponentTests/TypeChecks/Graph/Scenarios.fs
@@ -688,4 +688,66 @@ module ColdTasks =
"""
(set [| 0; 2 |])
]
+ scenario
+ "ModuleSuffix clash"
+ [
+ sourceFile
+ "A.fs"
+ """
+namespace F.General
+"""
+ Set.empty
+ sourceFile
+ "B.fs"
+ """
+[]
+module F
+
+let br () = ()
+"""
+ Set.empty
+
+ sourceFile
+ "C.fs"
+ """
+module S
+
+[]
+let main _ =
+ F.br ()
+ 0
+"""
+ (set [| 1 |])
+ ]
+ scenario
+ "ModuleSuffix clash, module before namespace"
+ [
+ sourceFile
+ "A.fs"
+ """
+[]
+module F
+
+let br () = ()
+"""
+ Set.empty
+ sourceFile
+ "B.fs"
+ """
+namespace F.General
+"""
+ Set.empty
+
+ sourceFile
+ "C.fs"
+ """
+module S
+
+[]
+let main _ =
+ F.br ()
+ 0
+"""
+ (set [| 0 |])
+ ]
]
diff --git a/tests/FSharp.Compiler.ComponentTests/TypeChecks/SeqTypeCheckTests.fs b/tests/FSharp.Compiler.ComponentTests/TypeChecks/SeqTypeCheckTests.fs
new file mode 100644
index 00000000000..a0b78d83d1c
--- /dev/null
+++ b/tests/FSharp.Compiler.ComponentTests/TypeChecks/SeqTypeCheckTests.fs
@@ -0,0 +1,17 @@
+module TypeChecks.SeqTypeCheckTests
+
+open Xunit
+open FSharp.Test.Compiler
+
+[]
+let ``Seq expr with impicit yield type checks correctly when two identical record types are present`` () =
+ FSharp """
+module SeqInference
+
+type A = { X: int }
+type B = { X: int }
+
+let l: A list = [ if true then { X = 42 } ]
+"""
+ |> typecheck
+ |> shouldSucceed
\ No newline at end of file
diff --git a/tests/fsharp/typecheck/sigs/neg24.bsl b/tests/fsharp/typecheck/sigs/neg24.bsl
index 94167197aa1..f2e3feb2d54 100644
--- a/tests/fsharp/typecheck/sigs/neg24.bsl
+++ b/tests/fsharp/typecheck/sigs/neg24.bsl
@@ -21,11 +21,15 @@ neg24.fs(302,33,302,34): typecheck error FS0001: All elements of a list must be
neg24.fs(302,36,302,37): typecheck error FS0001: All elements of a list must be implicitly convertible to the type of the first element, which here is 'unit'. This element has type 'int'.
-neg24.fs(305,24,305,25): typecheck error FS0193: Type constraint mismatch. The type
- 'int'
-is not compatible with type
+neg24.fs(305,24,305,25): typecheck error FS0001: This expression was expected to have type
'unit'
+but here has type
+ 'int'
+neg24.fs(305,31,305,32): typecheck error FS0001: This expression was expected to have type
+ 'unit'
+but here has type
+ 'int'
neg24.fs(308,30,308,31): typecheck error FS0020: The result of this expression has type 'int' and is implicitly ignored. Consider using 'ignore' to discard this value explicitly, e.g. 'expr |> ignore', or 'let' to bind the result to a name, e.g. 'let result = expr'.
diff --git a/tests/fsharp/typecheck/sigs/version47/neg24.bsl b/tests/fsharp/typecheck/sigs/version47/neg24.bsl
index 4825319243d..192de09f93d 100644
--- a/tests/fsharp/typecheck/sigs/version47/neg24.bsl
+++ b/tests/fsharp/typecheck/sigs/version47/neg24.bsl
@@ -21,11 +21,15 @@ neg24.fs(302,33,302,34): typecheck error FS0001: All elements of a list must be
neg24.fs(302,36,302,37): typecheck error FS0001: All elements of a list must be implicitly convertible to the type of the first element, which here is 'unit'. This element has type 'int'.
-neg24.fs(305,24,305,25): typecheck error FS0193: Type constraint mismatch. The type
- 'int'
-is not compatible with type
+neg24.fs(305,24,305,25): typecheck error FS0001: This expression was expected to have type
'unit'
+but here has type
+ 'int'
+neg24.fs(305,31,305,32): typecheck error FS0001: This expression was expected to have type
+ 'unit'
+but here has type
+ 'int'
neg24.fs(308,30,308,31): typecheck error FS0020: The result of this expression has type 'int' and is implicitly ignored. Consider using 'ignore' to discard this value explicitly, e.g. 'expr |> ignore', or 'let' to bind the result to a name, e.g. 'let result = expr'.
diff --git a/tests/walkthroughs/sdk-script-manual-tests/README.md.txt b/tests/walkthroughs/sdk-script-manual-tests/README.md
similarity index 99%
rename from tests/walkthroughs/sdk-script-manual-tests/README.md.txt
rename to tests/walkthroughs/sdk-script-manual-tests/README.md
index 643fece6fe5..67cc030882d 100644
--- a/tests/walkthroughs/sdk-script-manual-tests/README.md.txt
+++ b/tests/walkthroughs/sdk-script-manual-tests/README.md
@@ -82,4 +82,4 @@ dotnet artifacts\bin\fsi\Debug\netcoreapp3.1\fsi.exe c:\misc\tests\neutral-scrip
dotnet artifacts\bin\fsi\Debug\netcoreapp3.1\fsi.exe c:\misc\tests\neutral-script-reference-netfx-script.fsx
dotnet artifacts\bin\fsi\Debug\netcoreapp3.1\fsi.exe c:\misc\tests\neutral-script-reference-neutral-script.fsx
-```
\ No newline at end of file
+```
diff --git a/vsintegration/src/FSharp.Editor/CodeFixes/MissingReference.fs b/vsintegration/src/FSharp.Editor/CodeFixes/MissingReference.fs
new file mode 100644
index 00000000000..eb77d13c355
--- /dev/null
+++ b/vsintegration/src/FSharp.Editor/CodeFixes/MissingReference.fs
@@ -0,0 +1,102 @@
+// Copyright (c) Microsoft Corporation. All Rights Reserved. See License.txt in the project root for license information.
+
+namespace Microsoft.VisualStudio.FSharp.Editor
+
+open System
+open System.Composition
+open System.Collections.Immutable
+open System.IO
+
+open Microsoft.CodeAnalysis
+open Microsoft.CodeAnalysis.CodeFixes
+open Microsoft.CodeAnalysis.CodeActions
+
+open CancellableTasks
+
+type private ReferenceType =
+ | AddProjectRef of ProjectReference
+ | AddMetadataRef of MetadataReference
+
+// This code fix only works for the legacy, non-SDK projects.
+// In SDK projects, transitive references do this trick.
+// See: https://github.com/dotnet/fsharp/pull/2743
+
+// Because this code fix is barely applicable anymore
+// and because it's very different from other code fixes
+// (applies to the projects files, not code itself),
+// it's not implemented via IFSharpCodeFix interfaces
+// and not tested automatically either.
+// If we happen to create similar code fixes,
+// it'd make sense to create some testing framework for them.
+[]
+type internal MissingReferenceCodeFixProvider() =
+ inherit CodeFixProvider()
+
+ let createCodeFix (title: string, context: CodeFixContext, addReference: ReferenceType) =
+ CodeAction.Create(
+ title,
+ (fun cancellationToken ->
+ cancellableTask {
+ let project = context.Document.Project
+ let solution = project.Solution
+
+ match addReference with
+ | AddProjectRef projectRef ->
+ let references = project.AllProjectReferences
+ let newReferences = references |> Seq.append [ projectRef ]
+ return solution.WithProjectReferences(project.Id, newReferences)
+
+ | AddMetadataRef metadataRef ->
+ let references = project.MetadataReferences
+ let newReferences = references |> Seq.append [ metadataRef ]
+ return solution.WithProjectMetadataReferences(project.Id, newReferences)
+ }
+ |> CancellableTask.start cancellationToken)
+ )
+
+ override _.FixableDiagnosticIds = ImmutableArray.Create "FS0074"
+
+ override _.RegisterCodeFixesAsync context =
+ cancellableTask {
+ let solution = context.Document.Project.Solution
+
+ let diagnostic = context.Diagnostics[0]
+ let message = diagnostic.GetMessage()
+ let parts = message.Split([| '\'' |], StringSplitOptions.None)
+
+ match parts with
+ | [| _; _type; _; assemblyName; _ |] ->
+
+ let exactProjectMatches =
+ solution.Projects
+ |> Seq.tryFindV (fun project ->
+ String.Compare(project.AssemblyName, assemblyName, StringComparison.OrdinalIgnoreCase) = 0)
+
+ match exactProjectMatches with
+ | ValueSome refProject ->
+ let codefix =
+ createCodeFix (
+ String.Format(SR.AddProjectReference(), refProject.Name),
+ context,
+ AddProjectRef(ProjectReference refProject.Id)
+ )
+
+ context.RegisterCodeFix(codefix, ImmutableArray.Create diagnostic)
+ | ValueNone ->
+ let metadataReferences =
+ solution.Projects
+ |> Seq.collect (fun project -> project.MetadataReferences)
+ |> Seq.tryFindV (fun ref ->
+ let referenceAssemblyName = Path.GetFileNameWithoutExtension(ref.Display)
+ String.Compare(referenceAssemblyName, assemblyName, StringComparison.OrdinalIgnoreCase) = 0)
+
+ match metadataReferences with
+ | ValueSome metadataRef ->
+ let codefix =
+ createCodeFix (String.Format(SR.AddAssemblyReference(), assemblyName), context, AddMetadataRef metadataRef)
+
+ context.RegisterCodeFix(codefix, ImmutableArray.Create diagnostic)
+ | ValueNone -> ()
+ | _ -> ()
+ }
+ |> CancellableTask.startAsTask context.CancellationToken
diff --git a/vsintegration/src/FSharp.Editor/CodeFixes/MissingReferenceCodeFixProvider.fs b/vsintegration/src/FSharp.Editor/CodeFixes/MissingReferenceCodeFixProvider.fs
deleted file mode 100644
index eabc0cd2880..00000000000
--- a/vsintegration/src/FSharp.Editor/CodeFixes/MissingReferenceCodeFixProvider.fs
+++ /dev/null
@@ -1,96 +0,0 @@
-// Copyright (c) Microsoft Corporation. All Rights Reserved. See License.txt in the project root for license information.
-
-namespace Microsoft.VisualStudio.FSharp.Editor
-
-open System
-open System.Composition
-open System.Collections.Immutable
-open System.Threading
-open System.Threading.Tasks
-open System.IO
-
-open Microsoft.CodeAnalysis
-open Microsoft.CodeAnalysis.CodeFixes
-open Microsoft.CodeAnalysis.CodeActions
-
-type private ReferenceType =
- | AddProjectRef of ProjectReference
- | AddMetadataRef of MetadataReference
-
-[]
-type internal MissingReferenceCodeFixProvider() =
- inherit CodeFixProvider()
-
- let fixableDiagnosticId = "FS0074"
-
- let createCodeFix (title: string, context: CodeFixContext, addReference: ReferenceType) =
- CodeAction.Create(
- title,
- (fun (cancellationToken: CancellationToken) ->
- async {
- let project = context.Document.Project
- let solution = project.Solution
-
- match addReference with
- | AddProjectRef projectRef ->
- let references = project.AllProjectReferences
- let newReferences = references |> Seq.append [ projectRef ]
- return solution.WithProjectReferences(project.Id, newReferences)
-
- | AddMetadataRef metadataRef ->
- let references = project.MetadataReferences
- let newReferences = references |> Seq.append [ metadataRef ]
- return solution.WithProjectMetadataReferences(project.Id, newReferences)
- }
- |> RoslynHelpers.StartAsyncAsTask(cancellationToken)),
- title
- )
-
- override _.FixableDiagnosticIds = Seq.toImmutableArray [ fixableDiagnosticId ]
-
- override _.RegisterCodeFixesAsync context : Task =
- async {
- let solution = context.Document.Project.Solution
-
- context.Diagnostics
- |> Seq.filter (fun x -> x.Id = fixableDiagnosticId)
- |> Seq.iter (fun diagnostic ->
- let message = diagnostic.GetMessage()
- let parts = message.Split([| '\'' |], StringSplitOptions.None)
-
- match parts with
- | [| _; _type; _; assemblyName; _ |] ->
-
- let exactProjectMatches =
- solution.Projects
- |> Seq.tryFindV (fun project ->
- String.Compare(project.AssemblyName, assemblyName, StringComparison.OrdinalIgnoreCase) = 0)
-
- match exactProjectMatches with
- | ValueSome refProject ->
- let codefix =
- createCodeFix (
- String.Format(SR.AddProjectReference(), refProject.Name),
- context,
- AddProjectRef(ProjectReference refProject.Id)
- )
-
- context.RegisterCodeFix(codefix, ImmutableArray.Create diagnostic)
- | ValueNone ->
- let metadataReferences =
- solution.Projects
- |> Seq.collect (fun project -> project.MetadataReferences)
- |> Seq.tryFindV (fun ref ->
- let referenceAssemblyName = Path.GetFileNameWithoutExtension(ref.Display)
- String.Compare(referenceAssemblyName, assemblyName, StringComparison.OrdinalIgnoreCase) = 0)
-
- match metadataReferences with
- | ValueSome metadataRef ->
- let codefix =
- createCodeFix (String.Format(SR.AddAssemblyReference(), assemblyName), context, AddMetadataRef metadataRef)
-
- context.RegisterCodeFix(codefix, ImmutableArray.Create diagnostic)
- | ValueNone -> ()
- | _ -> ())
- }
- |> RoslynHelpers.StartAsyncUnitAsTask(context.CancellationToken)
diff --git a/vsintegration/src/FSharp.Editor/CodeFixes/ReplaceWithSuggestion.fs b/vsintegration/src/FSharp.Editor/CodeFixes/ReplaceWithSuggestion.fs
index 31b0b84d374..1678f89c1d5 100644
--- a/vsintegration/src/FSharp.Editor/CodeFixes/ReplaceWithSuggestion.fs
+++ b/vsintegration/src/FSharp.Editor/CodeFixes/ReplaceWithSuggestion.fs
@@ -19,7 +19,7 @@ open CancellableTasks
type internal ReplaceWithSuggestionCodeFixProvider [] () =
inherit CodeFixProvider()
- override _.FixableDiagnosticIds = ImmutableArray.Create("FS0039", "FS0495")
+ override _.FixableDiagnosticIds = ImmutableArray.Create("FS0039", "FS0495", "FS1129")
override this.RegisterCodeFixesAsync context =
if context.Document.Project.IsFSharpCodeFixesSuggestNamesForErrorsEnabled then
diff --git a/vsintegration/src/FSharp.Editor/Common/Constants.fs b/vsintegration/src/FSharp.Editor/Common/Constants.fs
index d59b241b44e..8e529cf0319 100644
--- a/vsintegration/src/FSharp.Editor/Common/Constants.fs
+++ b/vsintegration/src/FSharp.Editor/Common/Constants.fs
@@ -163,6 +163,9 @@ module internal CodeFix =
[]
let MakeDeclarationMutable = "MakeDeclarationMutable"
+ []
+ let MissingReference = "MissingReference"
+
[]
let ChangePrefixNegationToInfixSubtraction =
"ChangePrefixNegationToInfixSubtraction"
diff --git a/vsintegration/src/FSharp.Editor/FSharp.Editor.fsproj b/vsintegration/src/FSharp.Editor/FSharp.Editor.fsproj
index b73a33b690d..b2a685d2347 100644
--- a/vsintegration/src/FSharp.Editor/FSharp.Editor.fsproj
+++ b/vsintegration/src/FSharp.Editor/FSharp.Editor.fsproj
@@ -133,7 +133,7 @@
-
+
diff --git a/vsintegration/src/FSharp.Editor/FSharp.Editor.resx b/vsintegration/src/FSharp.Editor/FSharp.Editor.resx
index 251cd02d780..8db6c37e401 100644
--- a/vsintegration/src/FSharp.Editor/FSharp.Editor.resx
+++ b/vsintegration/src/FSharp.Editor/FSharp.Editor.resx
@@ -211,7 +211,7 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
diff --git a/vsintegration/src/FSharp.Editor/LanguageService/LanguageService.fs b/vsintegration/src/FSharp.Editor/LanguageService/LanguageService.fs
index b8856c24259..ad5156e3082 100644
--- a/vsintegration/src/FSharp.Editor/LanguageService/LanguageService.fs
+++ b/vsintegration/src/FSharp.Editor/LanguageService/LanguageService.fs
@@ -145,10 +145,6 @@ type internal FSharpWorkspaceServiceFactory []
let enableBackgroundItemKeyStoreAndSemanticClassification =
editorOptions.LanguageServicePerformance.EnableBackgroundItemKeyStoreAndSemanticClassification
- // Default should be true
- let captureIdentifiersWhenParsing =
- editorOptions.LanguageServicePerformance.CaptureIdentifiersWhenParsing
-
// Default is false here
let solutionCrawler = editorOptions.Advanced.SolutionBackgroundAnalysis
@@ -169,7 +165,7 @@ type internal FSharpWorkspaceServiceFactory []
nameof keepAllBackgroundSymbolUses, keepAllBackgroundSymbolUses
nameof enableBackgroundItemKeyStoreAndSemanticClassification,
enableBackgroundItemKeyStoreAndSemanticClassification
- nameof captureIdentifiersWhenParsing, captureIdentifiersWhenParsing
+ "captureIdentifiersWhenParsing", enableFastFindReferences
nameof solutionCrawler, solutionCrawler
|],
TelemetryThrottlingStrategy.NoThrottling
@@ -186,7 +182,7 @@ type internal FSharpWorkspaceServiceFactory []
enableBackgroundItemKeyStoreAndSemanticClassification,
enablePartialTypeChecking = enablePartialTypeChecking,
parallelReferenceResolution = enableParallelReferenceResolution,
- captureIdentifiersWhenParsing = captureIdentifiersWhenParsing,
+ captureIdentifiersWhenParsing = enableFastFindReferences,
documentSource =
(if enableLiveBuffers then
DocumentSource.Custom getSource
diff --git a/vsintegration/src/FSharp.Editor/Navigation/GoToDefinition.fs b/vsintegration/src/FSharp.Editor/Navigation/GoToDefinition.fs
index 905919f4ce9..1199b14477d 100644
--- a/vsintegration/src/FSharp.Editor/Navigation/GoToDefinition.fs
+++ b/vsintegration/src/FSharp.Editor/Navigation/GoToDefinition.fs
@@ -252,7 +252,12 @@ type internal GoToDefinition(metadataAsSource: FSharpMetadataAsSourceService) =
|> liftAsync
let symbolUses = checkFileResults.GetUsesOfSymbolInFile targetSymbolUse.Symbol
- let! implSymbol = symbolUses |> Array.tryHead
+
+ let! implSymbol =
+ symbolUses
+ |> Array.sortByDescending (fun x -> x.IsFromDefinition)
+ |> Array.tryHead
+
return implSymbol.Range
}
diff --git a/vsintegration/src/FSharp.Editor/Options/EditorOptions.fs b/vsintegration/src/FSharp.Editor/Options/EditorOptions.fs
index fae67f36e32..5137bb8596c 100644
--- a/vsintegration/src/FSharp.Editor/Options/EditorOptions.fs
+++ b/vsintegration/src/FSharp.Editor/Options/EditorOptions.fs
@@ -88,7 +88,6 @@ type LanguageServicePerformanceOptions =
KeepAllBackgroundResolutions: bool
KeepAllBackgroundSymbolUses: bool
EnableBackgroundItemKeyStoreAndSemanticClassification: bool
- CaptureIdentifiersWhenParsing: bool
}
static member Default =
@@ -103,7 +102,6 @@ type LanguageServicePerformanceOptions =
KeepAllBackgroundResolutions = false
KeepAllBackgroundSymbolUses = false
EnableBackgroundItemKeyStoreAndSemanticClassification = true
- CaptureIdentifiersWhenParsing = true
}
[]
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.cs.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.cs.xlf
index fa6aa6fd4cc..0e588b5cd47 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.cs.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.cs.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- Možnosti výkonu projektu F# a ukládání do mezipaměti;
+ Možnosti výkonu projektu F# a ukládání do mezipaměti;
Povolit odkazy mezi projekty v paměti;
Enable_partial_type_checking;
Možnosti výkonu IntelliSense;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.de.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.de.xlf
index e3cc881854d..b276297b1b0 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.de.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.de.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- F#-Projekt- und Cacheleistungsoptionen;
+ F#-Projekt- und Cacheleistungsoptionen;
Projektübergreifende Verweise im Arbeitsspeicher aktivieren;
Enable_partial_type_checking;
IntelliSense-Leistungsoptionen;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.es.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.es.xlf
index 83074b9f703..f6bdf050f6f 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.es.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.es.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- Opciones de rendimiento de proyectos y caché de F#;
+ Opciones de rendimiento de proyectos y caché de F#;
Habilitar referencias cruzadas de proyecto en memoria;
Enable_partial_type_checking;
Opciones de rendimiento de IntelliSense;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.fr.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.fr.xlf
index 1aea7681a66..f32d4765e14 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.fr.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.fr.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- Options de performances du projet F # et de la mise en cache ;
+ Options de performances du projet F # et de la mise en cache ;
Activer les références de projets croisés en mémoire ;
Enable_partial_type_checking ;
Options de performances IntelliSense ;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.it.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.it.xlf
index 4b74d02fdf8..fcf9afb2bf2 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.it.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.it.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- Opzioni prestazioni progetto F# e memorizzazione nella cache;
+ Opzioni prestazioni progetto F# e memorizzazione nella cache;
Abilita riferimenti tra progetti in memoria;
Enable_partial_type_checking;
Opzioni prestazioni IntelliSense;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ja.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ja.xlf
index 4cfbba3fb49..893c213c3bc 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ja.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ja.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- F# プロジェクトとキャッシュのパフォーマンス オプション;
+ F# プロジェクトとキャッシュのパフォーマンス オプション;
メモリ内のプロジェクト間参照を有効にする。
Enable_partial_type_checking;
IntelliSense パフォーマンス オプション;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ko.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ko.xlf
index 6eb8c0f3ec1..ab917a9a565 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ko.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ko.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- F# 프로젝트 및 캐싱 성능 옵션;
+ F# 프로젝트 및 캐싱 성능 옵션;
메모리 내 프로젝트 간 참조 활성화;
Enable_partial_type_checking;
IntelliSense 성능 옵션;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pl.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pl.xlf
index f4d5ad66fa9..9fba8c3fd08 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pl.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pl.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- Opcje wydajności projektów i buforowania języka F#;
+ Opcje wydajności projektów i buforowania języka F#;
Włącz odwołania między projektami w pamięci;
Enable_partial_type_checking;
Opcje wydajności funkcji IntelliSense;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pt-BR.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pt-BR.xlf
index 34d03fefbe9..38c78de1849 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pt-BR.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.pt-BR.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- Opções de desempenho de projeto e cache do F#;
+ Opções de desempenho de projeto e cache do F#;
Habilitar referências de projeto cruzado na memória;
Enable_partial_type_checking;
Opções de desempenho do IntelliSense;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ru.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ru.xlf
index 97331156092..5dee3aa17ce 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ru.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.ru.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- Параметры производительности проекта F# и кэширования;
+ Параметры производительности проекта F# и кэширования;
Включить перекрестные ссылки проекта в памяти;
Enable_partial_type_checking;
Параметры производительности IntelliSense;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.tr.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.tr.xlf
index 52608a483ae..a9a33f92557 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.tr.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.tr.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- F# Proje ve Önbelleğe Alma Performans Seçenekleri;
+ F# Proje ve Önbelleğe Alma Performans Seçenekleri;
Bellek içi çapraz proje başvurularını etkinleştir;
Enable_partial_type_checking;
IntelliSense Performans Seçenekleri;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hans.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hans.xlf
index 207e0a9470b..a8b8ed8bd89 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hans.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hans.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- F# 项目和缓存性能选项;
+ F# 项目和缓存性能选项;
启用内存中的跨项目引用;
启用部分类型检查;
IntelliSense 性能选项;
diff --git a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hant.xlf b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hant.xlf
index d6cd3abe0e2..1a649a0b03a 100644
--- a/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hant.xlf
+++ b/vsintegration/src/FSharp.Editor/xlf/FSharp.Editor.zh-Hant.xlf
@@ -167,9 +167,9 @@ Time until stale results are used (in milliseconds);
Parallelization (requires restart);
Enable parallel type checking with signature files;
Enable parallel reference resolution;
-Enable fast find references & rename (experimental);
+Enable fast find references & rename (restart required);
Cache parsing results (experimental)
- F# 專案和快取效能選項;
+ F# 專案和快取效能選項;
啟用記憶體內跨專案參考;
Enable_partial_type_checking;
IntelliSense 效能選項;
diff --git a/vsintegration/src/FSharp.UIResources/LanguageServicePerformanceOptionControl.xaml b/vsintegration/src/FSharp.UIResources/LanguageServicePerformanceOptionControl.xaml
index 074bc7febc8..96b8915b80e 100644
--- a/vsintegration/src/FSharp.UIResources/LanguageServicePerformanceOptionControl.xaml
+++ b/vsintegration/src/FSharp.UIResources/LanguageServicePerformanceOptionControl.xaml
@@ -85,9 +85,6 @@
-
diff --git a/vsintegration/src/FSharp.UIResources/Strings.Designer.cs b/vsintegration/src/FSharp.UIResources/Strings.Designer.cs
index 0c8d435f87d..f3490b414a0 100644
--- a/vsintegration/src/FSharp.UIResources/Strings.Designer.cs
+++ b/vsintegration/src/FSharp.UIResources/Strings.Designer.cs
@@ -105,15 +105,6 @@ public static string Block_Structure {
}
}
- ///
- /// Looks up a localized string similar to Capture identifiers while parsing.
- ///
- public static string Capture_Identifiers_When_Parsing {
- get {
- return ResourceManager.GetString("Capture_Identifiers_When_Parsing", resourceCulture);
- }
- }
-
///
/// Looks up a localized string similar to Code Fixes.
///
diff --git a/vsintegration/src/FSharp.UIResources/Strings.resx b/vsintegration/src/FSharp.UIResources/Strings.resx
index f0ae6b60146..5bf7260f9cc 100644
--- a/vsintegration/src/FSharp.UIResources/Strings.resx
+++ b/vsintegration/src/FSharp.UIResources/Strings.resx
@@ -249,9 +249,6 @@
Keep background symbol keys
-
- Capture identifiers while parsing
-
Use live (unsaved) buffers for checking (restart required)
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.cs.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.cs.xlf
index fc6191d7055..51f813a4903 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.cs.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.cs.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.de.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.de.xlf
index c9fe10de771..6aa9e6a6686 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.de.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.de.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.es.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.es.xlf
index d2de44fb296..fc73ebc636c 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.es.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.es.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.fr.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.fr.xlf
index 03ae77ec939..7e1f700e3ea 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.fr.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.fr.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.it.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.it.xlf
index e3b948f6d8f..3b88428daa1 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.it.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.it.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.ja.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.ja.xlf
index b0ddce5658d..94126a8eef1 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.ja.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.ja.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.ko.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.ko.xlf
index 6d3d8a13a53..e5dd62c28da 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.ko.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.ko.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.pl.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.pl.xlf
index b4d2cf145ab..513d580a3b2 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.pl.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.pl.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.pt-BR.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.pt-BR.xlf
index ecd4611a48a..86629640ec9 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.pt-BR.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.pt-BR.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.ru.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.ru.xlf
index 3fcde247df6..b590dc949a2 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.ru.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.ru.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.tr.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.tr.xlf
index b1451e5a571..14a87b14ef3 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.tr.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.tr.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hans.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hans.xlf
index 1dcbb550d8e..132485ea815 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hans.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hans.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hant.xlf b/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hant.xlf
index 8f70454be10..624aefbf6cb 100644
--- a/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hant.xlf
+++ b/vsintegration/src/FSharp.UIResources/xlf/Strings.zh-Hant.xlf
@@ -22,11 +22,6 @@
Background analysis
-
- Capture identifiers while parsing
- Capture identifiers while parsing
-
-
Keep background symbol keys
Keep background symbol keys
diff --git a/vsintegration/tests/FSharp.Editor.Tests/CodeFixes/ReplaceWithSuggestionTests.fs b/vsintegration/tests/FSharp.Editor.Tests/CodeFixes/ReplaceWithSuggestionTests.fs
index 20495583a37..7f5e745b0f3 100644
--- a/vsintegration/tests/FSharp.Editor.Tests/CodeFixes/ReplaceWithSuggestionTests.fs
+++ b/vsintegration/tests/FSharp.Editor.Tests/CodeFixes/ReplaceWithSuggestionTests.fs
@@ -156,3 +156,37 @@ let song = Song(title = "Under The Milky Way")
let actual = codeFix |> multiFix code Auto
Assert.Equal(expected, actual)
+
+[]
+let ``Fixes FS1129`` () =
+ let code =
+ """
+type SomeType = { TheField : string }
+
+let f x =
+ match x with
+ | { TheField = "A" } -> true
+ | { TheFiedl = "B" } -> true
+ | _ -> false
+"""
+
+ let expected =
+ [
+ {
+ Message = "Replace with 'TheField'"
+ FixedCode =
+ """
+type SomeType = { TheField : string }
+
+let f x =
+ match x with
+ | { TheField = "A" } -> true
+ | { TheField = "B" } -> true
+ | _ -> false
+"""
+ }
+ ]
+
+ let actual = codeFix |> multiFix code Auto
+
+ Assert.Equal(expected, actual)