From 83f87a720fbe3598885ca1f31d95a3672371be35 Mon Sep 17 00:00:00 2001 From: Steffen Forkmann Date: Sun, 24 Apr 2016 09:54:39 +0200 Subject: [PATCH] Propose compatible record labels in compiler error --- src/fsharp/CompileOps.fs | 6 +- src/fsharp/ErrorResolutionHints.fs | 29 ++ src/fsharp/FSComp.txt | 5 +- .../FSharp.Compiler-proto.fsproj | 6 + .../FSharp.Compiler/FSharp.Compiler.fsproj | 8 +- .../FSharp.LanguageService.Compiler.fsproj | 6 + src/fsharp/NameResolution.fs | 126 ++++-- src/fsharp/NameResolution.fsi | 2 +- src/fsharp/TypeChecker.fs | 7 +- src/fsharp/tast.fs | 6 +- src/utils/EditDistance.fs | 47 ++ ...VIL_PROVIDER_ResolveTypeName_Exception.bsl | 12 +- .../EVIL_PROVIDER_ResolveTypeName_Null.bsl | 12 +- tests/fsharp/typeProviders/negTests/neg1.bsl | 404 ++++++++++++++++-- tests/fsharp/typecheck/sigs/neg07.bsl | 4 +- tests/fsharp/typecheck/sigs/neg17.bsl | 28 +- .../RequireQualifiedAccess/E_OnRecord.fs | 4 +- .../Record/E_RecTypesNotMatch01.fs | 2 +- .../General/E_matrix_LetBinding01.fs | 2 +- .../Diagnostics/General/E_matrix_class01.fs | 2 +- .../General/E_matrix_interface01.fs | 4 +- .../Diagnostics/General/E_matrix_struct01.fs | 2 +- .../NameResolution/E_FieldNotInRecord.fs | 13 + .../NameResolution/E_RecordFieldProposal.fs | 13 + .../ErrorMessages/NameResolution/env.lst | 2 + tests/fsharpqa/Source/test.lst | 1 + 26 files changed, 673 insertions(+), 80 deletions(-) create mode 100644 src/fsharp/ErrorResolutionHints.fs create mode 100644 src/utils/EditDistance.fs create mode 100644 tests/fsharpqa/Source/ErrorMessages/NameResolution/E_FieldNotInRecord.fs create mode 100644 tests/fsharpqa/Source/ErrorMessages/NameResolution/E_RecordFieldProposal.fs create mode 100644 tests/fsharpqa/Source/ErrorMessages/NameResolution/env.lst diff --git a/src/fsharp/CompileOps.fs b/src/fsharp/CompileOps.fs index 0d8ea5a3fa5..d79dd8eeda1 100755 --- a/src/fsharp/CompileOps.fs +++ b/src/fsharp/CompileOps.fs @@ -742,8 +742,12 @@ let OutputPhasedErrorR (os:System.Text.StringBuilder) (err:PhasedError) = os.Append(Duplicate1E().Format (DecompileOpName s)) |> ignore else os.Append(Duplicate2E().Format k (DecompileOpName s)) |> ignore - | UndefinedName(_,k,id,_) -> + | UndefinedName(_,k,id,predictions) -> os.Append(k (DecompileOpName id.idText)) |> ignore + if Set.isEmpty predictions |> not then + let filtered = ErrorResolutionHints.FilterPredictions id.idText predictions + os.Append(ErrorResolutionHints.FormatPredictions filtered) |> ignore + | InternalUndefinedItemRef(f,smr,ccuName,s) -> let _, errs = f(smr, ccuName, s) os.Append(errs) |> ignore diff --git a/src/fsharp/ErrorResolutionHints.fs b/src/fsharp/ErrorResolutionHints.fs new file mode 100644 index 00000000000..28bb2ff2d6c --- /dev/null +++ b/src/fsharp/ErrorResolutionHints.fs @@ -0,0 +1,29 @@ +// Copyright (c) Microsoft Corporation. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +/// Functions to format error message details +module internal Microsoft.FSharp.Compiler.ErrorResolutionHints + +/// Filters predictions based on edit distance to an unknown identifier. +let FilterPredictions unknownIdent allPredictions = + let rec take n predictions = + predictions + |> Seq.mapi (fun i x -> i,x) + |> Seq.takeWhile (fun (i,_) -> i < n) + |> Seq.map snd + |> Seq.toList + + allPredictions + |> Seq.toList + |> List.distinct + |> List.sortBy (fun s -> Internal.Utilities.EditDistance.CalcEditDistance(unknownIdent,s)) + |> take 5 + +let FormatPredictions predictions = + match predictions with + | [] -> System.String.Empty + | _ -> + let predictionText = + predictions + |> Seq.map (sprintf "%s %s" System.Environment.NewLine) + |> String.concat "" + System.Environment.NewLine + FSComp.SR.undefinedNameRecordLabelDetails() + predictionText diff --git a/src/fsharp/FSComp.txt b/src/fsharp/FSComp.txt index b05aaca7ae0..5575d29959f 100644 --- a/src/fsharp/FSComp.txt +++ b/src/fsharp/FSComp.txt @@ -9,8 +9,10 @@ undefinedNameValueOfConstructor,"The value or constructor '%s' is not defined" undefinedNameValueNamespaceTypeOrModule,"The value, namespace, type or module '%s' is not defined" undefinedNameConstructorModuleOrNamespace,"The constructor, module or namespace '%s' is not defined" undefinedNameType,"The type '%s' is not defined" +undefinedNameTypeIn,"The type '%s' is not defined in '%s'." undefinedNameRecordLabelOrNamespace,"The record label or namespace '%s' is not defined" -undefinedNameRecordLabel,"The record label '%s' is not defined" +undefinedNameRecordLabel,"The record label '%s' is not defined." +undefinedNameRecordLabelDetails,"Maybe you want one of the following:" undefinedNameTypeParameter,"The type parameter '%s' is not defined" undefinedNamePatternDiscriminator,"The pattern discriminator '%s' is not defined" missingElseBranch,"The 'if' expression is missing an 'else' branch. The 'then' branch has type '%s'. Because 'if' is an expression, and not a statement, add an 'else' branch which returns a value of the same type." @@ -951,6 +953,7 @@ lexfltSeparatorTokensOfPatternMatchMisaligned,"The '|' tokens separating rules o 1127,nrIsNotConstructorOrLiteral,"This is not a constructor or literal, or a constructor is being used incorrectly" 1128,nrUnexpectedEmptyLongId,"Unexpected empty long identifier" 1129,nrTypeDoesNotContainSuchField,"The type '%s' does not contain a field '%s'" +1129,nrRecordDoesNotContainSuchLabel,"The record type '%s' does not contain a label '%s'." 1130,nrInvalidFieldLabel,"Invalid field label" 1132,nrInvalidExpression,"Invalid expression '%s'" 1133,nrNoConstructorsAvailableForType,"No constructors are available for the type '%s'" diff --git a/src/fsharp/FSharp.Compiler-proto/FSharp.Compiler-proto.fsproj b/src/fsharp/FSharp.Compiler-proto/FSharp.Compiler-proto.fsproj index 9731adc082c..7eb20114970 100644 --- a/src/fsharp/FSharp.Compiler-proto/FSharp.Compiler-proto.fsproj +++ b/src/fsharp/FSharp.Compiler-proto/FSharp.Compiler-proto.fsproj @@ -98,6 +98,9 @@ HashMultiMap.fs + + Utilities\EditDistance.fs + TaggedCollections.fsi @@ -211,6 +214,9 @@ ErrorLogger.fs + + ErrorResolutionHints.fs + InternalCollections.fsi diff --git a/src/fsharp/FSharp.Compiler/FSharp.Compiler.fsproj b/src/fsharp/FSharp.Compiler/FSharp.Compiler.fsproj index 9ff448d299e..9ba9ef50d9f 100644 --- a/src/fsharp/FSharp.Compiler/FSharp.Compiler.fsproj +++ b/src/fsharp/FSharp.Compiler/FSharp.Compiler.fsproj @@ -1,4 +1,4 @@ - + @@ -84,6 +84,9 @@ Utilities\HashMultiMap.fs + + Utilities\EditDistance.fs + Utilities\TaggedCollections.fsi @@ -159,6 +162,9 @@ ErrorLogging\ErrorLogger.fs + + ErrorLogging\ErrorResolutionHints.fs + ReferenceResolution\ReferenceResolution.fsi diff --git a/src/fsharp/FSharp.LanguageService.Compiler/FSharp.LanguageService.Compiler.fsproj b/src/fsharp/FSharp.LanguageService.Compiler/FSharp.LanguageService.Compiler.fsproj index 2ab989865f6..eae4ab21a55 100644 --- a/src/fsharp/FSharp.LanguageService.Compiler/FSharp.LanguageService.Compiler.fsproj +++ b/src/fsharp/FSharp.LanguageService.Compiler/FSharp.LanguageService.Compiler.fsproj @@ -80,6 +80,9 @@ Utilities\HashMultiMap.fs + + Utilities\EditDistance.fs + Utilities\TaggedCollections.fsi @@ -152,6 +155,9 @@ ErrorLogging\ErrorLogger.fs + + ErrorLogging\ErrorResolutionHints.fs + ReferenceResolution\ReferenceResolution.fsi diff --git a/src/fsharp/NameResolution.fs b/src/fsharp/NameResolution.fs index 8c5b65ebd89..2dc05d9dc23 100755 --- a/src/fsharp/NameResolution.fs +++ b/src/fsharp/NameResolution.fs @@ -801,8 +801,11 @@ let AddResults res1 res2 = | Result x,Result l -> Result (x @ l) | Exception _,Result l -> Result l | Result x,Exception _ -> Result x + // This prefers error messages with more predictions + | Exception (UndefinedName(n1,_,_,predictions1) as e1),Exception (UndefinedName(n2,_,_,predictions2) as e2) when n1 = n2 -> + if Set.count predictions1 < Set.count predictions2 then Exception e2 else Exception e1 // This prefers error messages coming from deeper failing long identifier paths - | Exception (UndefinedName(n1,_,_,_) as e1),Exception (UndefinedName(n2,_,_,_) as e2) -> + | Exception (UndefinedName(n1,_,_,_) as e1),Exception (UndefinedName(n2,_,_,_) as e2) -> if n1 < n2 then Exception e2 else Exception e1 // Prefer more concrete errors about things being undefined | Exception (UndefinedName _ as e1),Exception (Error _) -> Exception e1 @@ -1610,15 +1613,15 @@ let rec ResolveLongIndentAsModuleOrNamespace amap m fullyQualified (nenv:NameRes | Some mspec when IsEntityAccessible amap m ad (modref.NestedTyconRef mspec) -> let subref = modref.NestedTyconRef mspec look (depth+1) subref mspec.ModuleOrNamespaceType rest - | _ -> raze (UndefinedName(depth,FSComp.SR.undefinedNameNamespace,id,[])) + | _ -> raze (UndefinedName(depth,FSComp.SR.undefinedNameNamespace,id,NoPredictions)) modrefs |> CollectResults (fun modref -> if IsEntityAccessible amap m ad modref then look 1 modref modref.ModuleOrNamespaceType rest else - raze (UndefinedName(0,FSComp.SR.undefinedNameNamespaceOrModule,id,[]))) + raze (UndefinedName(0,FSComp.SR.undefinedNameNamespaceOrModule,id,NoPredictions))) | None -> - raze (UndefinedName(0,FSComp.SR.undefinedNameNamespaceOrModule,id,[])) + raze (UndefinedName(0,FSComp.SR.undefinedNameNamespaceOrModule,id,NoPredictions)) let ResolveLongIndentAsModuleOrNamespaceThen amap m fullyQualified (nenv:NameResolutionEnv) ad lid f = @@ -1858,7 +1861,7 @@ let rec ResolveLongIdentInTypePrim (ncenv:NameResolver) nenv lookupKind (resInfo // since later on this logic is used when giving preference to intrinsic definitions match DecodeFSharpEvent (pinfos@extensionPropInfos) ad g ncenv m with | Some x -> success (resInfo, x, rest) - | None-> raze (UndefinedName (depth,FSComp.SR.undefinedNameFieldConstructorOrMember, id,[])) + | None -> raze (UndefinedName (depth,FSComp.SR.undefinedNameFieldConstructorOrMember, id,NoPredictions)) | Some(MethodItem msets) when (match lookupKind with LookupKind.Expr -> true | _ -> false) -> let minfos = msets |> ExcludeHiddenOfMethInfos g ncenv.amap m @@ -1883,7 +1886,7 @@ let rec ResolveLongIdentInTypePrim (ncenv:NameResolver) nenv lookupKind (resInfo success (resInfo,Item.MakeMethGroup (nm,minfos),rest) elif isTyparTy g typ then raze (IndeterminateType(unionRanges m id.idRange)) - else raze (UndefinedName (depth,FSComp.SR.undefinedNameFieldConstructorOrMember, id,[])) + else raze (UndefinedName (depth,FSComp.SR.undefinedNameFieldConstructorOrMember, id,NoPredictions)) let nestedSearchAccessible = let nestedTypes = GetNestedTypesOfType (ad, ncenv, Some nm, (if isNil rest then typeNameResInfo.StaticArgsInfo else TypeNameResolutionStaticArgsInfo.Indefinite), true, m) typ @@ -1995,7 +1998,7 @@ let rec ResolveExprLongIdentInModuleOrNamespace (ncenv:NameResolver) nenv (typeN else NoResultsOrUsefulErrors - AtMostOneResult id.idRange ( tyconSearch +++ moduleSearch +++ raze (UndefinedName(depth,FSComp.SR.undefinedNameValueConstructorNamespaceOrType,id,[]))) + AtMostOneResult id.idRange ( tyconSearch +++ moduleSearch +++ raze (UndefinedName(depth,FSComp.SR.undefinedNameValueConstructorNamespaceOrType,id,NoPredictions))) /// An identifier has resolved to a type name in an expression (corresponding to one or more TyconRefs). @@ -2076,7 +2079,7 @@ let rec ResolveExprLongIdentPrim sink (ncenv:NameResolver) fullyQualified m ad n success [(resInfo,Item.ImplicitOp(id, ref None),[])] else NoResultsOrUsefulErrors - let failingCase = raze (UndefinedName(0,FSComp.SR.undefinedNameValueOfConstructor,id,[])) + let failingCase = raze (UndefinedName(0,FSComp.SR.undefinedNameValueOfConstructor,id,NoPredictions)) let search = ctorSearch +++ implicitOpSearch +++ failingCase let resInfo,item,rest = ForceRaise (AtMostOneResult m search) ResolutionInfo.SendToSink(sink,ncenv,nenv,ItemOccurence.Use,ad,resInfo,ResultTyparChecker(fun () -> CheckAllTyparsInferrable ncenv.amap m item)); @@ -2133,7 +2136,7 @@ let rec ResolveExprLongIdentPrim sink (ncenv:NameResolver) fullyQualified m ad n | Result _ as res -> ForceRaise res | _ -> - let failingCase = raze (UndefinedName(0,FSComp.SR.undefinedNameValueNamespaceTypeOrModule,id,[])) + let failingCase = raze (UndefinedName(0,FSComp.SR.undefinedNameValueNamespaceTypeOrModule,id,NoPredictions)) ForceRaise (AtMostOneResult m (search +++ moduleSearch AccessibleFromSomeFSharpCode +++ tyconSearch AccessibleFromSomeFSharpCode +++ failingCase)) ResolutionInfo.SendToSink(sink,ncenv,nenv,ItemOccurence.Use,ad,resInfo,ResultTyparChecker(fun () -> CheckAllTyparsInferrable ncenv.amap m item)); item,rest @@ -2200,7 +2203,7 @@ let rec ResolvePatternLongIdentInModuleOrNamespace (ncenv:NameResolver) nenv num | _ -> NoResultsOrUsefulErrors else NoResultsOrUsefulErrors - let res = AtMostOneResult id.idRange ( tyconSearch +++ ctorSearch +++ moduleSearch +++ raze (UndefinedName(depth,FSComp.SR.undefinedNameConstructorModuleOrNamespace,id,[]))) + let res = AtMostOneResult id.idRange ( tyconSearch +++ ctorSearch +++ moduleSearch +++ raze (UndefinedName(depth,FSComp.SR.undefinedNameConstructorModuleOrNamespace,id,NoPredictions))) res /// Used to report a warning condition for the use of upper-case identifiers in patterns @@ -2296,7 +2299,7 @@ let rec ResolveTypeLongIdentInTyconRefPrim (ncenv:NameResolver) (typeNameResInfo let tcrefs = CheckForTypeLegitimacyAndMultipleGenericTypeAmbiguities (tcrefs, typeNameResInfo, genOk, m) match tcrefs with | tcref :: _ -> success tcref - | [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,[])) + | [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,NoPredictions)) | id::rest -> #if EXTENSIONTYPING // No dotting through type generators to get to a nested type! @@ -2310,7 +2313,7 @@ let rec ResolveTypeLongIdentInTyconRefPrim (ncenv:NameResolver) (typeNameResInfo let tcrefs = CheckForTypeLegitimacyAndMultipleGenericTypeAmbiguities (tcrefs, typeNameResInfo.DropStaticArgsInfo, genOk, m) match tcrefs with | _ :: _ -> tcrefs |> CollectResults (fun (resInfo,tcref) -> ResolveTypeLongIdentInTyconRefPrim ncenv typeNameResInfo ad resInfo genOk (depth+1) m tcref rest) - | [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,[])) + | [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,NoPredictions)) AtMostOneResult m tyconSearch @@ -2322,6 +2325,15 @@ let ResolveTypeLongIdentInTyconRef sink (ncenv:NameResolver) nenv typeNameResInf CallNameResolutionSink sink (rangeOfLid lid,nenv,item,item,ItemOccurence.UseInType,nenv.eDisplayEnv,ad) tcref +/// Create an UndefinedName error with details +let SuggestTypeLongIdentInModuleOrNamespace depth (modref:ModuleOrNamespaceRef) (id:Ident) = + let predictedPossibleTypes = + modref.ModuleOrNamespaceType.AllEntities + |> Seq.map (fun e -> e.DisplayName) + |> Set.ofSeq + + let errorTextF s = FSComp.SR.undefinedNameTypeIn(s,fullDisplayTextOfModRef modref) + UndefinedName(depth,errorTextF,id,predictedPossibleTypes) /// Resolve a long identifier representing a type in a module or namespace let rec private ResolveTypeLongIdentInModuleOrNamespace (ncenv:NameResolver) (typeNameResInfo: TypeNameResolutionInfo) ad genOk (resInfo:ResolutionInfo) depth m modref _mty (lid: Ident list) = @@ -2332,7 +2344,7 @@ let rec private ResolveTypeLongIdentInModuleOrNamespace (ncenv:NameResolver) (ty let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, typeNameResInfo.StaticArgsInfo, modref) match tcrefs with | _ :: _ -> tcrefs |> CollectResults (fun tcref -> success(resInfo,tcref)) - | [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,[])) + | [] -> raze (SuggestTypeLongIdentInModuleOrNamespace depth modref id) | id::rest -> let m = unionRanges m id.idRange let modulSearch = @@ -2341,12 +2353,12 @@ let rec private ResolveTypeLongIdentInModuleOrNamespace (ncenv:NameResolver) (ty let resInfo = resInfo.AddEntity(id.idRange,submodref) ResolveTypeLongIdentInModuleOrNamespace ncenv typeNameResInfo ad genOk resInfo (depth+1) m submodref submodref.ModuleOrNamespaceType rest | _ -> - raze (UndefinedName(depth,FSComp.SR.undefinedNameNamespaceOrModule,id,[])) + raze (UndefinedName(depth,FSComp.SR.undefinedNameNamespaceOrModule,id,NoPredictions)) let tyconSearch = let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, modref) match tcrefs with | _ :: _ -> tcrefs |> CollectResults (fun tcref -> ResolveTypeLongIdentInTyconRefPrim ncenv typeNameResInfo ad resInfo genOk (depth+1) m tcref rest) - | [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,[])) + | [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,NoPredictions)) tyconSearch +++ modulSearch /// Resolve a long identifier representing a type @@ -2376,7 +2388,7 @@ let rec ResolveTypeLongIdentPrim (ncenv:NameResolver) fullyQualified m nenv ad ( //CheckForTypeLegitimacyAndMultipleGenericTypeAmbiguities tcref rest typeNameResInfo m; success(ResolutionInfo.Empty,tcref) | [] -> - raze (UndefinedName(0,FSComp.SR.undefinedNameType,id,[])) + raze (UndefinedName(0,FSComp.SR.undefinedNameType,id,NoPredictions)) | id::rest -> let m = unionRanges m id.idRange @@ -2440,14 +2452,13 @@ let rec ResolveFieldInModuleOrNamespace (ncenv:NameResolver) nenv ad (resInfo:Re match lid with | id::rest -> let m = unionRanges m id.idRange - let error = raze (UndefinedName(depth,FSComp.SR.undefinedNameRecordLabelOrNamespace,id,[])) // search for module-qualified names, e.g. { Microsoft.FSharp.Core.contents = 1 } let modulScopedFieldNames = match TryFindTypeWithRecdField modref id with | Some tycon when IsEntityAccessible ncenv.amap m ad (modref.NestedTyconRef tycon) -> let showDeprecated = HasFSharpAttribute ncenv.g ncenv.g.attrib_RequireQualifiedAccessAttribute tycon.Attribs success(resInfo, FieldResolution(modref.RecdFieldRefInNestedTycon tycon id,showDeprecated), rest) - | _ -> error + | _ -> raze (UndefinedName(depth,FSComp.SR.undefinedNameRecordLabelOrNamespace,id,NoPredictions)) // search for type-qualified names, e.g. { Microsoft.FSharp.Core.Ref.contents = 1 } let tyconSearch = match lid with @@ -2467,15 +2478,69 @@ let rec ResolveFieldInModuleOrNamespace (ncenv:NameResolver) nenv ad (resInfo:Re | Some(AccessibleEntityRef ncenv.amap m ad modref submodref) -> let resInfo = resInfo.AddEntity(id.idRange,submodref) ResolveFieldInModuleOrNamespace ncenv nenv ad resInfo (depth+1) m submodref submodref.ModuleOrNamespaceType rest - | _ -> - error - else error + | _ -> raze (UndefinedName(depth,FSComp.SR.undefinedNameRecordLabelOrNamespace,id,NoPredictions)) + else raze (UndefinedName(depth,FSComp.SR.undefinedNameRecordLabelOrNamespace,id,NoPredictions)) AtMostOneResult m (OneResult modulScopedFieldNames +++ tyconSearch +++ OneResult modulSearch) | [] -> error(InternalError("ResolveFieldInModuleOrNamespace",m)) +/// Suggest other labels of the same record +let SuggestOtherLabelsOfSameRecordType (nenv:NameResolutionEnv) typeName (id:Ident) (allFields:Ident list) = + let labelsOfPossibleRecord = + nenv.eFieldLabels + |> Seq.filter (fun kv -> + kv.Value + |> List.map (fun r -> r.TyconRef.DisplayName) + |> List.exists ((=) typeName)) + |> Seq.map (fun kv -> kv.Key) + |> Set.ofSeq + + let givenFields = + allFields + |> List.map (fun fld -> fld.idText) + |> List.filter ((<>) id.idText) + |> Set.ofList + + let predictedLabels = Set.difference labelsOfPossibleRecord givenFields + let predictions = ErrorResolutionHints.FilterPredictions id.idText predictedLabels + + let errorCode,text = FSComp.SR.nrRecordDoesNotContainSuchLabel(typeName, id.idText) + errorCode,text + ErrorResolutionHints.FormatPredictions predictions + + +let SuggestLabelsOfRelatedRecords (nenv:NameResolutionEnv) (id:Ident) (allFields:Ident list) = + let predictedLabels = + let givenFields = allFields |> List.map (fun fld -> fld.idText) |> List.filter ((<>) id.idText) |> Set.ofList + if Set.isEmpty givenFields then + // return labels from all records + NameMap.domainL nenv.eFieldLabels |> Set.ofList |> Set.remove "contents" + else + let possibleRecords = + [for fld in givenFields do + match Map.tryFind fld nenv.eFieldLabels with + | None -> () + | Some recordTypes -> yield! (recordTypes |> List.map (fun r -> r.TyconRef.DisplayName, fld)) ] + |> List.groupBy fst + |> List.map (fun (r,fields) -> r, fields |> List.map snd |> Set.ofList) + |> List.filter (fun (_,fields) -> Set.isSubset givenFields fields) + |> List.map fst + |> Set.ofList + + let labelsOfPossibleRecords = + nenv.eFieldLabels + |> Seq.filter (fun kv -> + kv.Value + |> List.map (fun r -> r.TyconRef.DisplayName) + |> List.exists possibleRecords.Contains) + |> Seq.map (fun kv -> kv.Key) + |> Set.ofSeq + + Set.difference labelsOfPossibleRecords givenFields + + UndefinedName(0,FSComp.SR.undefinedNameRecordLabel, id, predictedLabels) + /// Resolve a long identifier representing a record field -let ResolveFieldPrim (ncenv:NameResolver) nenv ad typ (mp,id:Ident) = +let ResolveFieldPrim (ncenv:NameResolver) nenv ad typ (mp,id:Ident) allFields = let typeNameResInfo = TypeNameResolutionInfo.Default let g = ncenv.g let m = id.idRange @@ -2484,11 +2549,20 @@ let ResolveFieldPrim (ncenv:NameResolver) nenv ad typ (mp,id:Ident) = if isAppTy g typ then match ncenv.InfoReader.TryFindRecdOrClassFieldInfoOfType(id.idText,m,typ) with | Some (RecdFieldInfo(_,rfref)) -> [ResolutionInfo.Empty, FieldResolution(rfref,false)] - | None -> error(Error(FSComp.SR.nrTypeDoesNotContainSuchField((NicePrint.minimalStringOfType nenv.eDisplayEnv typ), id.idText),m)) + | None -> + let typeName = NicePrint.minimalStringOfType nenv.eDisplayEnv typ + if isRecdTy g typ then + // record label doesn't belong to record type -> predict other labels of same record + error(Error(SuggestOtherLabelsOfSameRecordType nenv typeName id allFields,m)) + else + error(Error(FSComp.SR.nrTypeDoesNotContainSuchField(typeName, id.idText),m)) else let frefs = try Map.find id.idText nenv.eFieldLabels - with :? KeyNotFoundException -> error (UndefinedName(0,FSComp.SR.undefinedNameRecordLabel,id,NameMap.domainL nenv.eFieldLabels)) + with :? KeyNotFoundException -> + // record label is unknown -> predict related labels and give a hint to the user + error(SuggestLabelsOfRelatedRecords nenv id allFields) + // Eliminate duplicates arising from multiple 'open' frefs |> ListSet.setify (fun fref1 fref2 -> tyconRefEq g fref1.TyconRef fref2.TyconRef) @@ -2514,8 +2588,8 @@ let ResolveFieldPrim (ncenv:NameResolver) nenv ad typ (mp,id:Ident) = if nonNil rest then errorR(Error(FSComp.SR.nrInvalidFieldLabel(),(List.head rest).idRange)); [(resInfo,item)] -let ResolveField sink ncenv nenv ad typ (mp,id) = - let res = ResolveFieldPrim ncenv nenv ad typ (mp,id) +let ResolveField sink ncenv nenv ad typ (mp,id) allFields = + let res = ResolveFieldPrim ncenv nenv ad typ (mp,id) allFields // Register the results of any field paths "Module.Type" in "Module.Type.field" as a name resolution. (Note, the path resolution // info is only non-empty if there was a unique resolution of the field) for (resInfo,_rfref) in res do diff --git a/src/fsharp/NameResolution.fsi b/src/fsharp/NameResolution.fsi index ccad006c207..590f8a07016 100755 --- a/src/fsharp/NameResolution.fsi +++ b/src/fsharp/NameResolution.fsi @@ -366,7 +366,7 @@ val internal ResolveTypeLongIdentInTyconRef : TcResultsSink -> NameResol val internal ResolveTypeLongIdent : TcResultsSink -> NameResolver -> ItemOccurence -> FullyQualifiedFlag -> NameResolutionEnv -> AccessorDomain -> Ident list -> TypeNameResolutionStaticArgsInfo -> PermitDirectReferenceToGeneratedType -> ResultOrException /// Resolve a long identifier to a field -val internal ResolveField : TcResultsSink -> NameResolver -> NameResolutionEnv -> AccessorDomain -> TType -> Ident list * Ident -> FieldResolution list +val internal ResolveField : TcResultsSink -> NameResolver -> NameResolutionEnv -> AccessorDomain -> TType -> Ident list * Ident -> Ident list -> FieldResolution list /// Resolve a long identifier occurring in an expression position val internal ResolveExprLongIdent : TcResultsSink -> NameResolver -> range -> AccessorDomain -> NameResolutionEnv -> TypeNameResolutionInfo -> Ident list -> Item * Ident list diff --git a/src/fsharp/TypeChecker.fs b/src/fsharp/TypeChecker.fs index ddcffab75a4..1229f890ee5 100755 --- a/src/fsharp/TypeChecker.fs +++ b/src/fsharp/TypeChecker.fs @@ -1855,8 +1855,9 @@ let BuildFieldMap cenv env isPartial ty flds m = if isNil flds then invalidArg "flds" "BuildFieldMap" let frefSets = + let allFields = flds |> List.map (fun ((_,ident),_) -> ident) flds |> List.map (fun (fld,fldExpr) -> - let frefSet = ResolveField cenv.tcSink cenv.nameResolver env.eNameResEnv ad ty fld + let frefSet = ResolveField cenv.tcSink cenv.nameResolver env.eNameResEnv ad ty fld allFields fld,frefSet, fldExpr) let relevantTypeSets = frefSets |> List.map (fun (_,frefSet,_) -> frefSet |> List.choose (fun (FieldResolution(rfref,_)) -> Some rfref.TyconRef)) @@ -4146,7 +4147,7 @@ and TcTyparOrMeasurePar optKind cenv (env:TcEnv) newOk tpenv (Typar(id,_,_) as t match TryFindUnscopedTypar key tpenv with | Some res -> checkRes res | None -> - if newOk = NoNewTypars then error (UndefinedName(0,FSComp.SR.undefinedNameTypeParameter,id,[""])) + if newOk = NoNewTypars then error (UndefinedName(0,FSComp.SR.undefinedNameTypeParameter,id,NoPredictions)) // OK, this is an implicit declaration of a type parameter // The kind defaults to Type let tp' = NewTypar ((match optKind with None -> TyparKind.Type | Some kind -> kind), TyparRigidity.WarnIfNotRigid,tp,false,TyparDynamicReq.Yes,[],false,false) @@ -4858,7 +4859,7 @@ and TcPat warnOnUpper cenv env topValInfo vFlags (tpenv,names,takenNames) ty pat match args with | SynConstructorArgs.Pats [] | SynConstructorArgs.NamePatPairs ([], _)-> TcPat warnOnUpperForId cenv env topValInfo vFlags (tpenv,names,takenNames) ty (mkSynPatVar vis id) - | _ -> error (UndefinedName(0,FSComp.SR.undefinedNamePatternDiscriminator,id,[])) + | _ -> error (UndefinedName(0,FSComp.SR.undefinedNamePatternDiscriminator,id,NoPredictions)) | Item.ActivePatternCase(APElemRef(apinfo,vref,idx)) as item -> let args = match args with SynConstructorArgs.Pats args -> args | _ -> failwith "impossible" diff --git a/src/fsharp/tast.fs b/src/fsharp/tast.fs index ad1f15cb268..e11004ab29b 100755 --- a/src/fsharp/tast.fs +++ b/src/fsharp/tast.fs @@ -384,7 +384,11 @@ assert (sizeof = 4) let unassignedTyparName = "?" -exception UndefinedName of int * (* error func that expects identifier name *)(string -> string) * Ident * string list +type Predictions = Set + +let NoPredictions = Set.empty + +exception UndefinedName of int * (* error func that expects identifier name *)(string -> string) * Ident * Predictions exception InternalUndefinedItemRef of (string * string * string -> int * string) * string * string * string let KeyTyconByDemangledNameAndArity nm (typars: _ list) x = diff --git a/src/utils/EditDistance.fs b/src/utils/EditDistance.fs new file mode 100644 index 00000000000..b1271f1b76e --- /dev/null +++ b/src/utils/EditDistance.fs @@ -0,0 +1,47 @@ +// Copyright (c) Microsoft Corporation. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +/// Functions to compute the edit distance between two strings +module internal Internal.Utilities.EditDistance + +/// Computes the DamerauLevenstein distance +/// - read more at https://en.wikipedia.org/wiki/Damerau%E2%80%93Levenshtein_distance +/// - Implementation taken from http://www.navision-blog.de/2008/11/01/damerau-levenshtein-distance-in-fsharp-part-ii/ +let private calcDamerauLevenshtein (a:string, b:string) = + let m = b.Length + 1 + let mutable lastLine = Array.init m (fun i -> i) + let mutable lastLastLine = Array.create m 0 + let mutable actLine = Array.create m 0 + + for i in [1..a.Length] do + actLine.[0] <- i + for j in [1..b.Length] do + let cost = if a.[i-1] = b.[j-1] then 0 else 1 + let deletion = lastLine.[j] + 1 + let insertion = actLine.[j-1] + 1 + let substitution = lastLine.[j-1] + cost + actLine.[j] <- + deletion + |> min insertion + |> min substitution + + if i > 1 && j > 1 then + if a.[i-1] = b.[j-2] && a.[i-2] = b.[j-1] then + let transposition = lastLastLine.[j-2] + cost + actLine.[j] <- min actLine.[j] transposition + + // swap lines + let temp = lastLastLine + lastLastLine <- lastLine + lastLine <- actLine + actLine <- temp + + lastLine.[b.Length] + +/// Calculates the edit distance between two strings. +/// The edit distance is a metric that allows to measure the amount of difference between two strings +/// and shows how many edit operations (insert, delete, substitution) are needed to transform one string into the other. +let CalcEditDistance(a:string, b:string) = + if a.Length > b.Length then + calcDamerauLevenshtein(a, b) + else + calcDamerauLevenshtein(b, a) \ No newline at end of file diff --git a/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Exception.bsl b/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Exception.bsl index d5c920e5f4b..4d1aed83136 100644 --- a/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Exception.bsl +++ b/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Exception.bsl @@ -7,7 +7,11 @@ EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS3033: EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS3033: The type provider 'Provider.EvilProviderWhereResolveTypeNameRaisesException' reported an error: deliberate error for testing purposes -EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined +EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined in 'FSharp.EvilProviderWhereResolveTypeNameRaisesException'. + +Maybe you want one of the following: + + TheType EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS3033: The type provider 'Provider.EvilProviderWhereResolveTypeNameRaisesException' reported an error: deliberate error for testing purposes @@ -17,4 +21,8 @@ EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS3033: EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS3033: The type provider 'Provider.EvilProviderWhereResolveTypeNameRaisesException' reported an error: deliberate error for testing purposes -EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined +EVIL_PROVIDER_ResolveTypeName_Exception.fsx(7,73,7,96): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined in 'FSharp.EvilProviderWhereResolveTypeNameRaisesException'. + +Maybe you want one of the following: + + TheType diff --git a/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Null.bsl b/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Null.bsl index 03beeb13246..b299ed7e461 100644 --- a/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Null.bsl +++ b/tests/fsharp/typeProviders/negTests/EVIL_PROVIDER_ResolveTypeName_Null.bsl @@ -1,4 +1,12 @@ -EVIL_PROVIDER_ResolveTypeName_Null.fsx(7,69,7,92): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined +EVIL_PROVIDER_ResolveTypeName_Null.fsx(7,69,7,92): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined in 'FSharp.EvilProviderWhereResolveTypeNameReturnsNull'. -EVIL_PROVIDER_ResolveTypeName_Null.fsx(7,69,7,92): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined +Maybe you want one of the following: + + TheType + +EVIL_PROVIDER_ResolveTypeName_Null.fsx(7,69,7,92): typecheck error FS0039: The type 'SomeNameThatDoesntExist' is not defined in 'FSharp.EvilProviderWhereResolveTypeNameReturnsNull'. + +Maybe you want one of the following: + + TheType diff --git a/tests/fsharp/typeProviders/negTests/neg1.bsl b/tests/fsharp/typeProviders/negTests/neg1.bsl index 07d2d8a4da1..64fd3e58aef 100644 --- a/tests/fsharp/typeProviders/negTests/neg1.bsl +++ b/tests/fsharp/typeProviders/negTests/neg1.bsl @@ -28,7 +28,15 @@ neg1.fsx(11,38,11,66): typecheck error FS3072: The type provider 'Provider.EvilP neg1.fsx(11,38,11,66): typecheck error FS3072: The type provider 'Provider.EvilProvider' reported an error: An exception occurred when accessing the 'Name' of a provided type: deliberate error for testing purposes -neg1.fsx(11,38,11,66): typecheck error FS0039: The type 'TypeWhereNameRaisesException' is not defined +neg1.fsx(11,38,11,66): typecheck error FS0039: The type 'TypeWhereNameRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsArrayTypeRaisesException + + TheType + + IsArrayTypeReturnsTrue neg1.fsx(11,38,11,66): typecheck error FS3072: The type provider 'Provider.EvilProvider' reported an error: An exception occurred when accessing the 'Name' of a provided type: deliberate error for testing purposes @@ -38,7 +46,15 @@ neg1.fsx(11,38,11,66): typecheck error FS3072: The type provider 'Provider.EvilP neg1.fsx(11,38,11,66): typecheck error FS3072: The type provider 'Provider.EvilProvider' reported an error: An exception occurred when accessing the 'Name' of a provided type: deliberate error for testing purposes -neg1.fsx(11,38,11,66): typecheck error FS0039: The type 'TypeWhereNameRaisesException' is not defined +neg1.fsx(11,38,11,66): typecheck error FS0039: The type 'TypeWhereNameRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsArrayTypeRaisesException + + TheType + + IsArrayTypeReturnsTrue neg1.fsx(12,38,12,62): typecheck error FS3073: The type provider 'Provider.EvilProvider' reported an error: The 'Name' of a provided type was null or empty. @@ -48,7 +64,15 @@ neg1.fsx(12,38,12,62): typecheck error FS3073: The type provider 'Provider.EvilP neg1.fsx(12,38,12,62): typecheck error FS3073: The type provider 'Provider.EvilProvider' reported an error: The 'Name' of a provided type was null or empty. -neg1.fsx(12,38,12,62): typecheck error FS0039: The type 'TypeWhereNameReturnsNull' is not defined +neg1.fsx(12,38,12,62): typecheck error FS0039: The type 'TypeWhereNameReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsArrayTypeReturnsTrue + + TheType + + IsArrayTypeRaisesException neg1.fsx(12,38,12,62): typecheck error FS3073: The type provider 'Provider.EvilProvider' reported an error: The 'Name' of a provided type was null or empty. @@ -58,7 +82,15 @@ neg1.fsx(12,38,12,62): typecheck error FS3073: The type provider 'Provider.EvilP neg1.fsx(12,38,12,62): typecheck error FS3073: The type provider 'Provider.EvilProvider' reported an error: The 'Name' of a provided type was null or empty. -neg1.fsx(12,38,12,62): typecheck error FS0039: The type 'TypeWhereNameReturnsNull' is not defined +neg1.fsx(12,38,12,62): typecheck error FS0039: The type 'TypeWhereNameReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsArrayTypeReturnsTrue + + TheType + + IsArrayTypeRaisesException neg1.fsx(13,38,13,66): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.IsGenericTypeRaisesException' member 'IsGenericType': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -92,7 +124,19 @@ neg1.fsx(15,38,15,70): typecheck error FS3021: Unexpected exception from provide neg1.fsx(15,38,15,70): typecheck error FS3072: The type provider 'Provider.EvilProvider' reported an error: An exception occurred when accessing the 'FullName' of a provided type: deliberate error for testing purposes -neg1.fsx(15,38,15,70): typecheck error FS0039: The type 'TypeWhereFullNameRaisesException' is not defined +neg1.fsx(15,38,15,70): typecheck error FS0039: The type 'TypeWhereFullNameRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(15,38,15,70): typecheck error FS3021: Unexpected exception from provided type 'TypeWhereFullNameRaisesException' member 'FullName': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -110,7 +154,19 @@ neg1.fsx(15,38,15,70): typecheck error FS3021: Unexpected exception from provide neg1.fsx(15,38,15,70): typecheck error FS3072: The type provider 'Provider.EvilProvider' reported an error: An exception occurred when accessing the 'FullName' of a provided type: deliberate error for testing purposes -neg1.fsx(15,38,15,70): typecheck error FS0039: The type 'TypeWhereFullNameRaisesException' is not defined +neg1.fsx(15,38,15,70): typecheck error FS0039: The type 'TypeWhereFullNameRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(16,38,16,66): typecheck error FS3042: Unexpected 'null' return value from provided type 'TypeWhereFullNameReturnsNull' member 'FullName' @@ -128,7 +184,19 @@ neg1.fsx(16,38,16,66): typecheck error FS3042: Unexpected 'null' return value fr neg1.fsx(16,38,16,66): typecheck error FS3073: The type provider 'Provider.EvilProvider' reported an error: The 'FullName' of a provided type was null or empty. -neg1.fsx(16,38,16,66): typecheck error FS0039: The type 'TypeWhereFullNameReturnsNull' is not defined +neg1.fsx(16,38,16,66): typecheck error FS0039: The type 'TypeWhereFullNameReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException neg1.fsx(16,38,16,66): typecheck error FS3042: Unexpected 'null' return value from provided type 'TypeWhereFullNameReturnsNull' member 'FullName' @@ -146,7 +214,19 @@ neg1.fsx(16,38,16,66): typecheck error FS3042: Unexpected 'null' return value fr neg1.fsx(16,38,16,66): typecheck error FS3073: The type provider 'Provider.EvilProvider' reported an error: The 'FullName' of a provided type was null or empty. -neg1.fsx(16,38,16,66): typecheck error FS0039: The type 'TypeWhereFullNameReturnsNull' is not defined +neg1.fsx(16,38,16,66): typecheck error FS0039: The type 'TypeWhereFullNameReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException neg1.fsx(17,38,17,71): typecheck error FS3021: Unexpected exception from provided type 'TypeWhereNamespaceRaisesException' member 'Namespace': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -184,9 +264,33 @@ neg1.fsx(17,38,17,71): typecheck error FS3004: The provided type 'FSharp.EvilPro neg1.fsx(17,38,17,71): typecheck error FS3033: The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(18,39,18,68): typecheck error FS0039: The type 'TypeWhereNamespaceReturnsNull' is not defined +neg1.fsx(18,39,18,68): typecheck error FS0039: The type 'TypeWhereNamespaceReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue -neg1.fsx(18,39,18,68): typecheck error FS0039: The type 'TypeWhereNamespaceReturnsNull' is not defined + IsArrayTypeRaisesException + + IsGenericTypeRaisesException + + TheType + +neg1.fsx(18,39,18,68): typecheck error FS0039: The type 'TypeWhereNamespaceReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + IsArrayTypeRaisesException + + IsGenericTypeRaisesException + + TheType neg1.fsx(19,39,19,67): typecheck error FS3021: Unexpected exception from provided type 'DeclaringTypeRaisesException' member 'DeclaringType': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -216,7 +320,19 @@ neg1.fsx(20,39,20,73): typecheck error FS3021: Unexpected exception from provide neg1.fsx(20,39,20,73): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetMethodsRaisesException' member 'GetMethods': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(20,39,20,73): typecheck error FS0039: The type 'TypeWhereGetMethodsRaisesException' is not defined +neg1.fsx(20,39,20,73): typecheck error FS0039: The type 'TypeWhereGetMethodsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(20,39,20,73): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetMethodsRaisesException' member 'GetMethods': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -226,7 +342,19 @@ neg1.fsx(20,39,20,73): typecheck error FS3021: Unexpected exception from provide neg1.fsx(20,39,20,73): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetMethodsRaisesException' member 'GetMethods': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(20,39,20,73): typecheck error FS0039: The type 'TypeWhereGetMethodsRaisesException' is not defined +neg1.fsx(20,39,20,73): typecheck error FS0039: The type 'TypeWhereGetMethodsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(21,39,21,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsRaisesException' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -236,7 +364,19 @@ neg1.fsx(21,39,21,72): typecheck error FS3021: Unexpected exception from provide neg1.fsx(21,39,21,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsRaisesException' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(21,39,21,72): typecheck error FS0039: The type 'TypeWhereGetEventsRaisesException' is not defined +neg1.fsx(21,39,21,72): typecheck error FS0039: The type 'TypeWhereGetEventsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(21,39,21,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsRaisesException' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -246,7 +386,19 @@ neg1.fsx(21,39,21,72): typecheck error FS3021: Unexpected exception from provide neg1.fsx(21,39,21,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsRaisesException' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(21,39,21,72): typecheck error FS0039: The type 'TypeWhereGetEventsRaisesException' is not defined +neg1.fsx(21,39,21,72): typecheck error FS0039: The type 'TypeWhereGetEventsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(22,39,22,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsRaisesException' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -256,7 +408,19 @@ neg1.fsx(22,39,22,72): typecheck error FS3021: Unexpected exception from provide neg1.fsx(22,39,22,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsRaisesException' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(22,39,22,72): typecheck error FS0039: The type 'TypeWhereGetFieldsRaisesException' is not defined +neg1.fsx(22,39,22,72): typecheck error FS0039: The type 'TypeWhereGetFieldsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(22,39,22,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsRaisesException' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -266,7 +430,19 @@ neg1.fsx(22,39,22,72): typecheck error FS3021: Unexpected exception from provide neg1.fsx(22,39,22,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsRaisesException' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(22,39,22,72): typecheck error FS0039: The type 'TypeWhereGetFieldsRaisesException' is not defined +neg1.fsx(22,39,22,72): typecheck error FS0039: The type 'TypeWhereGetFieldsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(23,39,23,76): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesRaisesException' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -276,7 +452,19 @@ neg1.fsx(23,39,23,76): typecheck error FS3021: Unexpected exception from provide neg1.fsx(23,39,23,76): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesRaisesException' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(23,39,23,76): typecheck error FS0039: The type 'TypeWhereGetPropertiesRaisesException' is not defined +neg1.fsx(23,39,23,76): typecheck error FS0039: The type 'TypeWhereGetPropertiesRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(23,39,23,76): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesRaisesException' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -286,7 +474,19 @@ neg1.fsx(23,39,23,76): typecheck error FS3021: Unexpected exception from provide neg1.fsx(23,39,23,76): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesRaisesException' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(23,39,23,76): typecheck error FS0039: The type 'TypeWhereGetPropertiesRaisesException' is not defined +neg1.fsx(23,39,23,76): typecheck error FS0039: The type 'TypeWhereGetPropertiesRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TheType neg1.fsx(24,39,24,77): typecheck error FS3004: The provided type 'FSharp.EvilProvider.TypeWhereGetNestedTypesRaisesException' has member 'Boo' which has declaring type 'FSharp.EvilProvider.TheType'. Expected declaring type to be the same as provided type. @@ -300,7 +500,19 @@ neg1.fsx(25,39,25,78): typecheck error FS3021: Unexpected exception from provide neg1.fsx(25,39,25,78): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetConstructorsRaisesException' member 'GetConstructors': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(25,39,25,78): typecheck error FS0039: The type 'TypeWhereGetConstructorsRaisesException' is not defined +neg1.fsx(25,39,25,78): typecheck error FS0039: The type 'TypeWhereGetConstructorsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue neg1.fsx(25,39,25,78): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetConstructorsRaisesException' member 'GetConstructors': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes @@ -310,7 +522,19 @@ neg1.fsx(25,39,25,78): typecheck error FS3021: Unexpected exception from provide neg1.fsx(25,39,25,78): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetConstructorsRaisesException' member 'GetConstructors': The type provider 'Provider.EvilProvider' reported an error: deliberate error for testing purposes -neg1.fsx(25,39,25,78): typecheck error FS0039: The type 'TypeWhereGetConstructorsRaisesException' is not defined +neg1.fsx(25,39,25,78): typecheck error FS0039: The type 'TypeWhereGetConstructorsRaisesException' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue neg1.fsx(27,39,27,69): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetMethodsReturnsNull' member 'GetMethods': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetMethods' @@ -320,7 +544,19 @@ neg1.fsx(27,39,27,69): typecheck error FS3021: Unexpected exception from provide neg1.fsx(27,39,27,69): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetMethodsReturnsNull' member 'GetMethods': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetMethods' -neg1.fsx(27,39,27,69): typecheck error FS0039: The type 'TypeWhereGetMethodsReturnsNull' is not defined +neg1.fsx(27,39,27,69): typecheck error FS0039: The type 'TypeWhereGetMethodsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeRaisesException + + TheType neg1.fsx(27,39,27,69): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetMethodsReturnsNull' member 'GetMethods': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetMethods' @@ -330,7 +566,19 @@ neg1.fsx(27,39,27,69): typecheck error FS3021: Unexpected exception from provide neg1.fsx(27,39,27,69): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetMethodsReturnsNull' member 'GetMethods': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetMethods' -neg1.fsx(27,39,27,69): typecheck error FS0039: The type 'TypeWhereGetMethodsReturnsNull' is not defined +neg1.fsx(27,39,27,69): typecheck error FS0039: The type 'TypeWhereGetMethodsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeRaisesException + + TheType neg1.fsx(28,39,28,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsReturnsNull' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetEvents' @@ -340,7 +588,19 @@ neg1.fsx(28,39,28,68): typecheck error FS3021: Unexpected exception from provide neg1.fsx(28,39,28,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsReturnsNull' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetEvents' -neg1.fsx(28,39,28,68): typecheck error FS0039: The type 'TypeWhereGetEventsReturnsNull' is not defined +neg1.fsx(28,39,28,68): typecheck error FS0039: The type 'TypeWhereGetEventsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeRaisesException + + TheType neg1.fsx(28,39,28,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsReturnsNull' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetEvents' @@ -350,7 +610,19 @@ neg1.fsx(28,39,28,68): typecheck error FS3021: Unexpected exception from provide neg1.fsx(28,39,28,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetEventsReturnsNull' member 'GetEvents': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetEvents' -neg1.fsx(28,39,28,68): typecheck error FS0039: The type 'TypeWhereGetEventsReturnsNull' is not defined +neg1.fsx(28,39,28,68): typecheck error FS0039: The type 'TypeWhereGetEventsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeRaisesException + + TheType neg1.fsx(29,39,29,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsReturnsNull' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetFields' @@ -360,7 +632,19 @@ neg1.fsx(29,39,29,68): typecheck error FS3021: Unexpected exception from provide neg1.fsx(29,39,29,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsReturnsNull' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetFields' -neg1.fsx(29,39,29,68): typecheck error FS0039: The type 'TypeWhereGetFieldsReturnsNull' is not defined +neg1.fsx(29,39,29,68): typecheck error FS0039: The type 'TypeWhereGetFieldsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeRaisesException neg1.fsx(29,39,29,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsReturnsNull' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetFields' @@ -370,7 +654,19 @@ neg1.fsx(29,39,29,68): typecheck error FS3021: Unexpected exception from provide neg1.fsx(29,39,29,68): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetFieldsReturnsNull' member 'GetFields': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetFields' -neg1.fsx(29,39,29,68): typecheck error FS0039: The type 'TypeWhereGetFieldsReturnsNull' is not defined +neg1.fsx(29,39,29,68): typecheck error FS0039: The type 'TypeWhereGetFieldsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsArrayTypeRaisesException + + IsGenericTypeRaisesException neg1.fsx(30,39,30,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesReturnsNull' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetProperties' @@ -380,7 +676,19 @@ neg1.fsx(30,39,30,72): typecheck error FS3021: Unexpected exception from provide neg1.fsx(30,39,30,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesReturnsNull' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetProperties' -neg1.fsx(30,39,30,72): typecheck error FS0039: The type 'TypeWhereGetPropertiesReturnsNull' is not defined +neg1.fsx(30,39,30,72): typecheck error FS0039: The type 'TypeWhereGetPropertiesReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsArrayTypeReturnsTrue + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException neg1.fsx(30,39,30,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesReturnsNull' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetProperties' @@ -390,7 +698,19 @@ neg1.fsx(30,39,30,72): typecheck error FS3021: Unexpected exception from provide neg1.fsx(30,39,30,72): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetPropertiesReturnsNull' member 'GetProperties': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetProperties' -neg1.fsx(30,39,30,72): typecheck error FS0039: The type 'TypeWhereGetPropertiesReturnsNull' is not defined +neg1.fsx(30,39,30,72): typecheck error FS0039: The type 'TypeWhereGetPropertiesReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + IsGenericTypeReturnsTrue + + TypeWhereGetNestedTypesRaisesException + + IsArrayTypeReturnsTrue + + IsGenericTypeRaisesException + + IsArrayTypeRaisesException neg1.fsx(31,39,31,73): typecheck error FS3004: The provided type 'FSharp.EvilProvider.TypeWhereGetNestedTypesReturnsNull' has member 'Boo' which has declaring type 'FSharp.EvilProvider.TheType'. Expected declaring type to be the same as provided type. @@ -404,7 +724,19 @@ neg1.fsx(32,39,32,74): typecheck error FS3021: Unexpected exception from provide neg1.fsx(32,39,32,74): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetConstructorsReturnsNull' member 'GetConstructors': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetConstructors' -neg1.fsx(32,39,32,74): typecheck error FS0039: The type 'TypeWhereGetConstructorsReturnsNull' is not defined +neg1.fsx(32,39,32,74): typecheck error FS0039: The type 'TypeWhereGetConstructorsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + TypeWhereGetNestedTypesReturnsNull + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + IsGenericTypeRaisesException neg1.fsx(32,39,32,74): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetConstructorsReturnsNull' member 'GetConstructors': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetConstructors' @@ -414,7 +746,19 @@ neg1.fsx(32,39,32,74): typecheck error FS3021: Unexpected exception from provide neg1.fsx(32,39,32,74): typecheck error FS3021: Unexpected exception from provided type 'FSharp.EvilProvider.TypeWhereGetConstructorsReturnsNull' member 'GetConstructors': The type provider 'Provider.EvilProvider' reported an error: The type provider returned 'null', which is not a valid return value from 'GetConstructors' -neg1.fsx(32,39,32,74): typecheck error FS0039: The type 'TypeWhereGetConstructorsReturnsNull' is not defined +neg1.fsx(32,39,32,74): typecheck error FS0039: The type 'TypeWhereGetConstructorsReturnsNull' is not defined in 'FSharp.EvilProvider'. + +Maybe you want one of the following: + + TypeWhereGetNestedTypesReturnsNull + + TypeWhereGetNestedTypesRaisesException + + IsGenericTypeReturnsTrue + + IsArrayTypeReturnsTrue + + IsGenericTypeRaisesException neg1.fsx(33,39,33,72): typecheck error FS3042: Unexpected 'null' return value from provided type 'FSharp.EvilProvider.TypeWhereGetInterfacesReturnsNull' member 'GetInterfaces' diff --git a/tests/fsharp/typecheck/sigs/neg07.bsl b/tests/fsharp/typecheck/sigs/neg07.bsl index 4551e7a9487..a040fd5bc56 100644 --- a/tests/fsharp/typecheck/sigs/neg07.bsl +++ b/tests/fsharp/typecheck/sigs/neg07.bsl @@ -19,9 +19,9 @@ neg07.fs(36,11,36,21): typecheck error FS0049: Uppercase variable identifiers sh neg07.fs(36,11,36,21): typecheck error FS0026: This rule will never be matched -neg07.fs(46,15,46,27): typecheck error FS0039: The record label 'RecordLabel1' is not defined +neg07.fs(46,15,46,27): typecheck error FS0039: The record label 'RecordLabel1' is not defined. -neg07.fs(47,19,47,31): typecheck error FS0039: The record label 'RecordLabel1' is not defined +neg07.fs(47,19,47,31): typecheck error FS0039: The record label 'RecordLabel1' is not defined. neg07.fs(57,10,57,17): typecheck error FS1196: The 'UseNullAsTrueValue' attribute flag may only be used with union types that have one nullary case and at least one non-nullary case diff --git a/tests/fsharp/typecheck/sigs/neg17.bsl b/tests/fsharp/typecheck/sigs/neg17.bsl index 66590123741..a74ee616628 100644 --- a/tests/fsharp/typecheck/sigs/neg17.bsl +++ b/tests/fsharp/typecheck/sigs/neg17.bsl @@ -27,10 +27,34 @@ neg17b.fs(29,31,29,61): typecheck error FS0072: Lookup on object of indeterminat neg17b.fs(30,31,30,84): typecheck error FS0072: Lookup on object of indeterminate type based on information prior to this program point. A type annotation may be needed prior to this program point to constrain the type of the object. This may allow the lookup to be resolved. -neg17b.fs(32,24,32,50): typecheck error FS0039: The type 'RecordTypeWithPrivateField' is not defined +neg17b.fs(32,24,32,50): typecheck error FS0039: The type 'RecordTypeWithPrivateField' is not defined in 'Neg17.M'. + +Maybe you want one of the following: + + RecordTypeWithPrivateRepresentation + + UnionTypeWithPrivateRepresentation + + InternalRecordType + + PrivateRecordType + + PrivateUnionType neg17b.fs(43,30,43,60): typecheck error FS0072: Lookup on object of indeterminate type based on information prior to this program point. A type annotation may be needed prior to this program point to constrain the type of the object. This may allow the lookup to be resolved. -neg17b.fs(45,23,45,49): typecheck error FS0039: The type 'RecordTypeWithPrivateField' is not defined +neg17b.fs(45,23,45,49): typecheck error FS0039: The type 'RecordTypeWithPrivateField' is not defined in 'Neg17.M'. + +Maybe you want one of the following: + + RecordTypeWithPrivateRepresentation + + UnionTypeWithPrivateRepresentation + + InternalRecordType + + PrivateRecordType + + PrivateUnionType neg17b.fs(54,20,54,50): typecheck error FS0072: Lookup on object of indeterminate type based on information prior to this program point. A type annotation may be needed prior to this program point to constrain the type of the object. This may allow the lookup to be resolved. diff --git a/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/RequireQualifiedAccess/E_OnRecord.fs b/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/RequireQualifiedAccess/E_OnRecord.fs index 85282204720..fa7973cdf0d 100644 --- a/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/RequireQualifiedAccess/E_OnRecord.fs +++ b/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/RequireQualifiedAccess/E_OnRecord.fs @@ -2,8 +2,8 @@ // Verify error when not fully qualifying a record field when it // has the RequireQualifiedAccess attribute. -//The record label 'Field1' is not defined$ -//The record label 'Field1' is not defined$ +//The record label 'Field1' is not defined\.$ +//The record label 'Field1' is not defined\.$ [] type R = { Field1 : int; Field2 : string } diff --git a/tests/fsharpqa/Source/Conformance/PatternMatching/Record/E_RecTypesNotMatch01.fs b/tests/fsharpqa/Source/Conformance/PatternMatching/Record/E_RecTypesNotMatch01.fs index fb7527d54ce..9297cb34285 100644 --- a/tests/fsharpqa/Source/Conformance/PatternMatching/Record/E_RecTypesNotMatch01.fs +++ b/tests/fsharpqa/Source/Conformance/PatternMatching/Record/E_RecTypesNotMatch01.fs @@ -1,7 +1,7 @@ // #Regression #Conformance #PatternMatching #Records // Verify error if two record types in a pattern match don't match // Verify error if type of a record field is incorrect. -//The type 'R1' does not contain a field 'A' +//The record type 'R1' does not contain a label 'A'\. type R1 = { X : int; Y : int } diff --git a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_LetBinding01.fs b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_LetBinding01.fs index 63af47e7f92..86fd6bc7b85 100644 --- a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_LetBinding01.fs +++ b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_LetBinding01.fs @@ -1,6 +1,6 @@ // #Regression #Diagnostics // Regression test for FSHARP1.0:3175 -//The type 'matrix' is not defined$ +//The type 'matrix' is not defined in 'Microsoft.FSharp.Math'\.$ let f ( m : Math.matrix) = 12 diff --git a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_class01.fs b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_class01.fs index afa10b64e17..806c444041d 100644 --- a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_class01.fs +++ b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_class01.fs @@ -1,6 +1,6 @@ // #Regression #Diagnostics // Regression test for FSHARP1.0:3175 -//The type 'matrix' is not defined$ +//The type 'matrix' is not defined in 'Microsoft.FSharp.Math'\.$ type C = class diff --git a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_interface01.fs b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_interface01.fs index eb6df520402..59b2c81ed70 100644 --- a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_interface01.fs +++ b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_interface01.fs @@ -1,7 +1,7 @@ // #Regression #Diagnostics // Regression test for FSHARP1.0:3175 -//The type 'matrix' is not defined$ -//The type 'matrix' is not defined$ +//The type 'matrix' is not defined in 'Microsoft.FSharp.Math'\.$ +//The type 'matrix' is not defined in 'Microsoft.FSharp.Math'\.$ type I = interface diff --git a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_struct01.fs b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_struct01.fs index e9938175d2a..b7b48288559 100644 --- a/tests/fsharpqa/Source/Diagnostics/General/E_matrix_struct01.fs +++ b/tests/fsharpqa/Source/Diagnostics/General/E_matrix_struct01.fs @@ -1,6 +1,6 @@ // #Regression #Diagnostics // Regression test for FSHARP1.0:3175 -//The type 'matrix' is not defined$ +//The type 'matrix' is not defined in 'Microsoft.FSharp.Math'\.$ type S = struct val a : Math.matrix diff --git a/tests/fsharpqa/Source/ErrorMessages/NameResolution/E_FieldNotInRecord.fs b/tests/fsharpqa/Source/ErrorMessages/NameResolution/E_FieldNotInRecord.fs new file mode 100644 index 00000000000..4a5361f8f67 --- /dev/null +++ b/tests/fsharpqa/Source/ErrorMessages/NameResolution/E_FieldNotInRecord.fs @@ -0,0 +1,13 @@ +// #ErrorMessages #NameResolution +//The record type 'F' does not contain a label 'Wall'\. + +type A = { Hello:string; World:string } +type B = { Size:int; Height:int } +type C = { Wheels:int } +type D = { Size:int; Height:int; Walls:int } +type E = { Unknown:string } +type F = { Wallis:int; Size:int; Height:int; } + +let r:F = { Size=3; Height=4; Wall=1 } + +exit 0 diff --git a/tests/fsharpqa/Source/ErrorMessages/NameResolution/E_RecordFieldProposal.fs b/tests/fsharpqa/Source/ErrorMessages/NameResolution/E_RecordFieldProposal.fs new file mode 100644 index 00000000000..ca73d5c1e54 --- /dev/null +++ b/tests/fsharpqa/Source/ErrorMessages/NameResolution/E_RecordFieldProposal.fs @@ -0,0 +1,13 @@ +// #ErrorMessages #NameResolution +//The record label 'Wall' is not defined\. + +type A = { Hello:string; World:string } +type B = { Size:int; Height:int } +type C = { Wheels:int } +type D = { Size:int; Height:int; Walls:int } +type E = { Unknown:string } +type F = { Wallis:int; Size:int; Height:int; } + +let r = { Size=3; Height=4; Wall=1 } + +exit 0 diff --git a/tests/fsharpqa/Source/ErrorMessages/NameResolution/env.lst b/tests/fsharpqa/Source/ErrorMessages/NameResolution/env.lst new file mode 100644 index 00000000000..435fb96c42b --- /dev/null +++ b/tests/fsharpqa/Source/ErrorMessages/NameResolution/env.lst @@ -0,0 +1,2 @@ + SOURCE=E_RecordFieldProposal.fs # E_RecordFieldProposal + SOURCE=E_FieldNotInRecord.fs # E_FieldNotInRecord \ No newline at end of file diff --git a/tests/fsharpqa/Source/test.lst b/tests/fsharpqa/Source/test.lst index 5072d02cac3..b9391dc0801 100644 --- a/tests/fsharpqa/Source/test.lst +++ b/tests/fsharpqa/Source/test.lst @@ -258,6 +258,7 @@ Misc01 Libraries\Core\Operators Misc01 Libraries\Core\Reflection Misc01 Libraries\Core\Unchecked Misc01 Warnings +Misc01 ErrorMessages\NameResolution Misc02 Libraries\Portable Misc02 Misc