From 26b3665f70e05117fb320e8e10cf22148f0a4993 Mon Sep 17 00:00:00 2001 From: Wesley Wigham Date: Tue, 5 Jun 2018 12:03:38 -0700 Subject: [PATCH 1/4] Check destructuring validity the same way element accesses and indexed accesses are checked --- src/compiler/checker.ts | 99 +++++++------------ .../reference/ES5For-of27.errors.txt | 8 +- .../reference/ES5For-of29.errors.txt | 8 +- .../reference/ES5For-of35.errors.txt | 8 +- ...blockScopedBindingUsedBeforeDef.errors.txt | 13 ++- ...putedPropertiesInDestructuring1.errors.txt | 32 +++++- ...dPropertiesInDestructuring1_ES6.errors.txt | 32 +++++- ...putedPropertiesInDestructuring2.errors.txt | 8 ++ ...dPropertiesInDestructuring2_ES6.errors.txt | 8 ++ ...pertiesInES5ShouldBeTransformed.errors.txt | 7 ++ .../declarationsAndAssignments.errors.txt | 8 +- ...niteAssignmentOfDestructuredVariable.types | 14 +-- ...redLateBoundNameHasCorrectTypes.errors.txt | 6 +- ...structuredMaappedTypeIsNotImplicitlyAny.js | 16 +++ ...turedMaappedTypeIsNotImplicitlyAny.symbols | 24 +++++ ...ucturedMaappedTypeIsNotImplicitlyAny.types | 25 +++++ ...ectBindingPatternAndAssignment3.errors.txt | 8 +- ...structuringParameterProperties5.errors.txt | 12 +-- ...structuringVariableDeclaration2.errors.txt | 8 +- .../reference/downlevelLetConst16.errors.txt | 8 +- .../for-inStatementsDestructuring2.errors.txt | 8 +- .../reference/jsdocParamTag2.errors.txt | 8 +- ...ndDestructuringImplicitAnyError.errors.txt | 36 +++---- ...teBoundDestructuringImplicitAnyError.types | 8 +- .../nonPrimitiveAccessProperty.errors.txt | 4 +- ...eIndexingWithForInNoImplicitAny.errors.txt | 4 +- .../baselines/reference/objectRest.errors.txt | 62 ++++++++++++ tests/baselines/reference/objectRest.types | 4 +- .../restElementWithBindingPattern2.errors.txt | 4 +- ...structuredMaappedTypeIsNotImplicitlyAny.ts | 8 ++ 30 files changed, 351 insertions(+), 147 deletions(-) create mode 100644 tests/baselines/reference/computedPropertiesInDestructuring2.errors.txt create mode 100644 tests/baselines/reference/computedPropertiesInDestructuring2_ES6.errors.txt create mode 100644 tests/baselines/reference/computerPropertiesInES5ShouldBeTransformed.errors.txt create mode 100644 tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.js create mode 100644 tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.symbols create mode 100644 tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.types create mode 100644 tests/baselines/reference/objectRest.errors.txt create mode 100644 tests/cases/compiler/destructuredMaappedTypeIsNotImplicitlyAny.ts diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 62607797679ea..77ce14e7014c9 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -4418,6 +4418,10 @@ namespace ts { if (isTypeAny(parentType)) { return parentType; } + // Relax null check on ambient destructuring parameters, since the parameters have no implementation and are just documentation + if (strictNullChecks && declaration.flags & NodeFlags.Ambient && isParameterDeclaration(declaration)) { + parentType = getNonNullableType(parentType); + } let type: Type | undefined; if (pattern.kind === SyntaxKind.ObjectBindingPattern) { @@ -4437,53 +4441,13 @@ namespace ts { else { // Use explicitly specified property name ({ p: xxx } form), or otherwise the implied name ({ p } form) const name = declaration.propertyName || declaration.name; - const isLate = isLateBindableName(name); - const isWellKnown = isComputedPropertyName(name) && isWellKnownSymbolSyntactically(name.expression); - if (!isLate && !isWellKnown && isComputedNonLiteralName(name)) { - const exprType = checkExpression((name as ComputedPropertyName).expression); - if (isTypeAssignableToKind(exprType, TypeFlags.ESSymbolLike)) { - if (noImplicitAny) { - error(declaration, Diagnostics.Type_0_cannot_be_used_to_index_type_1, typeToString(exprType), typeToString(parentType)); - } - return anyType; - } - const indexerType = isTypeAssignableToKind(exprType, TypeFlags.NumberLike) && getIndexTypeOfType(parentType, IndexKind.Number) || getIndexTypeOfType(parentType, IndexKind.String); - if (!indexerType && noImplicitAny && !compilerOptions.suppressImplicitAnyIndexErrors) { - if (getIndexTypeOfType(parentType, IndexKind.Number)) { - error(declaration, Diagnostics.Element_implicitly_has_an_any_type_because_index_expression_is_not_of_type_number); - } - else { - error(declaration, Diagnostics.Element_implicitly_has_an_any_type_because_type_0_has_no_index_signature, typeToString(parentType)); - } - } - return indexerType || anyType; - } - - // Use type of the specified property, or otherwise, for a numeric name, the type of the numeric index signature, - // or otherwise the type of the string index signature. - const nameType = isLate ? checkComputedPropertyName(name as ComputedPropertyName) as LiteralType | UniqueESSymbolType : undefined; - const text = isLate ? getLateBoundNameFromType(nameType!) : - isWellKnown ? getPropertyNameForKnownSymbolName(idText(((name as ComputedPropertyName).expression as PropertyAccessExpression).name)) : - getTextOfPropertyName(name); - - // Relax null check on ambient destructuring parameters, since the parameters have no implementation and are just documentation - if (strictNullChecks && declaration.flags & NodeFlags.Ambient && isParameterDeclaration(declaration)) { - parentType = getNonNullableType(parentType); - } - if (isLate && nameType && !getPropertyOfType(parentType, text) && isTypeAssignableToKind(nameType, TypeFlags.ESSymbolLike)) { - if (noImplicitAny) { - error(declaration, Diagnostics.Type_0_cannot_be_used_to_index_type_1, typeToString(nameType), typeToString(parentType)); - } - return anyType; - } - const declaredType = getConstraintForLocation(getTypeOfPropertyOfType(parentType, text), declaration.name); - type = declaredType && getFlowTypeOfReference(declaration, declaredType) || - isNumericLiteralName(text) && getIndexTypeOfType(parentType, IndexKind.Number) || - getIndexTypeOfType(parentType, IndexKind.String); - if (!type) { - error(name, Diagnostics.Type_0_has_no_property_1_and_no_string_index_signature, typeToString(parentType), declarationNameToString(name)); - return errorType; - } + const exprType = isComputedPropertyName(name) + ? checkExpression(name.expression) + : isIdentifier(name) + ? getLiteralType(unescapeLeadingUnderscores(name.escapedText)) + : checkExpression(name); + const declaredType = checkIndexedAccessIndexType(getIndexedAccessType(parentType, exprType, name, /*useApparentObjectType*/ true), name, /*useApparentObjectType*/ true); + type = getFlowTypeOfReference(declaration, getConstraintForLocation(declaredType, declaration.name)); } } else { @@ -8777,12 +8741,16 @@ namespace ts { return type; } - function getPropertyTypeForIndexType(objectType: Type, indexType: Type, accessNode: ElementAccessExpression | IndexedAccessTypeNode | undefined, cacheSymbol: boolean) { + function getPropertyTypeForIndexType(objectType: Type, indexType: Type, accessNode: ElementAccessExpression | IndexedAccessTypeNode | PropertyName | undefined, cacheSymbol: boolean) { const accessExpression = accessNode && accessNode.kind === SyntaxKind.ElementAccessExpression ? accessNode : undefined; - const propName = isTypeUsableAsLateBoundName(indexType) ? getLateBoundNameFromType(indexType) : - accessExpression && checkThatExpressionIsProperSymbolReference(accessExpression.argumentExpression, indexType, /*reportError*/ false) ? - getPropertyNameForKnownSymbolName(idText((accessExpression.argumentExpression).name)) : - undefined; + const propName = isTypeUsableAsLateBoundName(indexType) + ? getLateBoundNameFromType(indexType) + : accessExpression && checkThatExpressionIsProperSymbolReference(accessExpression.argumentExpression, indexType, /*reportError*/ false) + ? getPropertyNameForKnownSymbolName(idText((accessExpression.argumentExpression).name)) + : accessNode && isPropertyName(accessNode) + // late bound names are handled in the first branch, so here we only need to handle normal names + ? getPropertyNameForPropertyNameNode(accessNode) + : undefined; if (propName !== undefined) { const prop = getPropertyOfType(objectType, propName); if (prop) { @@ -8808,7 +8776,7 @@ namespace ts { undefined; if (indexInfo) { if (accessNode && !isTypeAssignableToKind(indexType, TypeFlags.String | TypeFlags.Number)) { - const indexNode = accessNode.kind === SyntaxKind.ElementAccessExpression ? accessNode.argumentExpression : accessNode.indexType; + const indexNode = getIndexNodeForAccessExpression(accessNode); error(indexNode, Diagnostics.Type_0_cannot_be_used_as_an_index_type, typeToString(indexType)); } else if (accessExpression && indexInfo.isReadonly && (isAssignmentTarget(accessExpression) || isDeleteTarget(accessExpression))) { @@ -8832,7 +8800,7 @@ namespace ts { } } if (accessNode) { - const indexNode = accessNode.kind === SyntaxKind.ElementAccessExpression ? accessNode.argumentExpression : accessNode.indexType; + const indexNode = getIndexNodeForAccessExpression(accessNode); if (indexType.flags & (TypeFlags.StringLiteral | TypeFlags.NumberLiteral)) { error(indexNode, Diagnostics.Property_0_does_not_exist_on_type_1, "" + (indexType).value, typeToString(objectType)); } @@ -8846,6 +8814,16 @@ namespace ts { return errorType; } + function getIndexNodeForAccessExpression(accessNode: ElementAccessExpression | IndexedAccessTypeNode | PropertyName) { + return accessNode.kind === SyntaxKind.ElementAccessExpression + ? accessNode.argumentExpression + : accessNode.kind === SyntaxKind.IndexedAccessType + ? accessNode.indexType + : accessNode.kind === SyntaxKind.ComputedPropertyName + ? accessNode.expression + : accessNode; + } + function isGenericObjectType(type: Type): boolean { return maybeTypeOfKind(type, TypeFlags.InstantiableNonPrimitive | TypeFlags.GenericMappedType); } @@ -8936,7 +8914,7 @@ namespace ts { return instantiateType(getTemplateTypeFromMappedType(objectType), templateMapper); } - function getIndexedAccessType(objectType: Type, indexType: Type, accessNode?: ElementAccessExpression | IndexedAccessTypeNode): Type { + function getIndexedAccessType(objectType: Type, indexType: Type, accessNode?: ElementAccessExpression | IndexedAccessTypeNode | PropertyName, useApparentObjectType?: boolean): Type { if (objectType === wildcardType || indexType === wildcardType) { return wildcardType; } @@ -8945,7 +8923,7 @@ namespace ts { // object type. Note that for a generic T and a non-generic K, we eagerly resolve T[K] if it originates in // an expression. This is to preserve backwards compatibility. For example, an element access 'this["foo"]' // has always been resolved eagerly using the constraint type of 'this' at the given location. - if (isGenericIndexType(indexType) || !(accessNode && accessNode.kind === SyntaxKind.ElementAccessExpression) && isGenericObjectType(objectType)) { + if (isGenericIndexType(indexType) || !(accessNode && accessNode.kind === SyntaxKind.ElementAccessExpression) && isGenericObjectType(useApparentObjectType ? getApparentType(objectType) : objectType)) { if (objectType.flags & TypeFlags.AnyOrUnknown) { return objectType; } @@ -8960,11 +8938,10 @@ namespace ts { // In the following we resolve T[K] to the type of the property in T selected by K. // We treat boolean as different from other unions to improve errors; // skipping straight to getPropertyTypeForIndexType gives errors with 'boolean' instead of 'true'. - const apparentObjectType = getApparentType(objectType); if (indexType.flags & TypeFlags.Union && !(indexType.flags & TypeFlags.Boolean)) { const propTypes: Type[] = []; for (const t of (indexType).types) { - const propType = getPropertyTypeForIndexType(apparentObjectType, t, accessNode, /*cacheSymbol*/ false); + const propType = getPropertyTypeForIndexType(objectType, t, accessNode, /*cacheSymbol*/ false); if (propType === errorType) { return errorType; } @@ -8972,7 +8949,7 @@ namespace ts { } return getUnionType(propTypes); } - return getPropertyTypeForIndexType(apparentObjectType, indexType, accessNode, /*cacheSymbol*/ true); + return getPropertyTypeForIndexType(objectType, indexType, accessNode, /*cacheSymbol*/ true); } function getTypeFromIndexedAccessTypeNode(node: IndexedAccessTypeNode) { @@ -21663,14 +21640,14 @@ namespace ts { forEach(node.types, checkSourceElement); } - function checkIndexedAccessIndexType(type: Type, accessNode: ElementAccessExpression | IndexedAccessTypeNode) { + function checkIndexedAccessIndexType(type: Type, accessNode: Node, useApparentObjectType?: boolean) { if (!(type.flags & TypeFlags.IndexedAccess)) { return type; } // Check if the index type is assignable to 'keyof T' for the object type. const objectType = (type).objectType; const indexType = (type).indexType; - if (isTypeAssignableTo(indexType, getIndexType(objectType, /*stringsOnly*/ false))) { + if (isTypeAssignableTo(indexType, getIndexType(useApparentObjectType ? getApparentType(objectType) : objectType, /*stringsOnly*/ false))) { if (accessNode.kind === SyntaxKind.ElementAccessExpression && isAssignmentTarget(accessNode) && getObjectFlags(objectType) & ObjectFlags.Mapped && getMappedTypeModifiers(objectType) & MappedTypeModifiers.IncludeReadonly) { error(accessNode, Diagnostics.Index_signature_in_type_0_only_permits_reading, typeToString(objectType)); diff --git a/tests/baselines/reference/ES5For-of27.errors.txt b/tests/baselines/reference/ES5For-of27.errors.txt index 0c83985993069..d64baaa1aa75c 100644 --- a/tests/baselines/reference/ES5For-of27.errors.txt +++ b/tests/baselines/reference/ES5For-of27.errors.txt @@ -1,13 +1,13 @@ -tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,11): error TS2459: Type 'number' has no property 'x' and no string index signature. -tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,21): error TS2459: Type 'number' has no property 'y' and no string index signature. +tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,11): error TS2339: Property 'x' does not exist on type 'number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,21): error TS2339: Property 'y' does not exist on type 'number'. ==== tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts (2 errors) ==== for (var {x: a = 0, y: b = 1} of [2, 3]) { ~ -!!! error TS2459: Type 'number' has no property 'x' and no string index signature. +!!! error TS2339: Property 'x' does not exist on type 'number'. ~ -!!! error TS2459: Type 'number' has no property 'y' and no string index signature. +!!! error TS2339: Property 'y' does not exist on type 'number'. a; b; } \ No newline at end of file diff --git a/tests/baselines/reference/ES5For-of29.errors.txt b/tests/baselines/reference/ES5For-of29.errors.txt index e669b070222e1..1ab9c84d284d2 100644 --- a/tests/baselines/reference/ES5For-of29.errors.txt +++ b/tests/baselines/reference/ES5For-of29.errors.txt @@ -1,13 +1,13 @@ -tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,13): error TS2459: Type 'number' has no property 'x' and no string index signature. -tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,23): error TS2459: Type 'number' has no property 'y' and no string index signature. +tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,13): error TS2339: Property 'x' does not exist on type 'number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,23): error TS2339: Property 'y' does not exist on type 'number'. ==== tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts (2 errors) ==== for (const {x: a = 0, y: b = 1} of [2, 3]) { ~ -!!! error TS2459: Type 'number' has no property 'x' and no string index signature. +!!! error TS2339: Property 'x' does not exist on type 'number'. ~ -!!! error TS2459: Type 'number' has no property 'y' and no string index signature. +!!! error TS2339: Property 'y' does not exist on type 'number'. a; b; } \ No newline at end of file diff --git a/tests/baselines/reference/ES5For-of35.errors.txt b/tests/baselines/reference/ES5For-of35.errors.txt index 8c43d9598888d..2670f6285d599 100644 --- a/tests/baselines/reference/ES5For-of35.errors.txt +++ b/tests/baselines/reference/ES5For-of35.errors.txt @@ -1,13 +1,13 @@ -tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,13): error TS2459: Type 'number' has no property 'x' and no string index signature. -tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,23): error TS2459: Type 'number' has no property 'y' and no string index signature. +tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,13): error TS2339: Property 'x' does not exist on type 'number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,23): error TS2339: Property 'y' does not exist on type 'number'. ==== tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts (2 errors) ==== for (const {x: a = 0, y: b = 1} of [2, 3]) { ~ -!!! error TS2459: Type 'number' has no property 'x' and no string index signature. +!!! error TS2339: Property 'x' does not exist on type 'number'. ~ -!!! error TS2459: Type 'number' has no property 'y' and no string index signature. +!!! error TS2339: Property 'y' does not exist on type 'number'. a; b; } \ No newline at end of file diff --git a/tests/baselines/reference/blockScopedBindingUsedBeforeDef.errors.txt b/tests/baselines/reference/blockScopedBindingUsedBeforeDef.errors.txt index 3a55ebbfded50..7bd7cd2013b3c 100644 --- a/tests/baselines/reference/blockScopedBindingUsedBeforeDef.errors.txt +++ b/tests/baselines/reference/blockScopedBindingUsedBeforeDef.errors.txt @@ -1,20 +1,29 @@ tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts(2,12): error TS2448: Block-scoped variable 'a' used before its declaration. +tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts(2,12): error TS2538: Type 'any' cannot be used as an index type. tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts(5,12): error TS2448: Block-scoped variable 'a' used before its declaration. +tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts(5,12): error TS2538: Type 'any' cannot be used as an index type. tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts(8,7): error TS2448: Block-scoped variable 'b' used before its declaration. +tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts(8,7): error TS2538: Type 'any' cannot be used as an index type. -==== tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts (3 errors) ==== +==== tests/cases/compiler/blockScopedBindingUsedBeforeDef.ts (6 errors) ==== // 1: for (let {[a]: a} of [{ }]) continue; ~ !!! error TS2448: Block-scoped variable 'a' used before its declaration. + ~ +!!! error TS2538: Type 'any' cannot be used as an index type. // 2: for (let {[a]: a} = { }; false; ) continue; ~ !!! error TS2448: Block-scoped variable 'a' used before its declaration. + ~ +!!! error TS2538: Type 'any' cannot be used as an index type. // 3: let {[b]: b} = { }; ~ -!!! error TS2448: Block-scoped variable 'b' used before its declaration. \ No newline at end of file +!!! error TS2448: Block-scoped variable 'b' used before its declaration. + ~ +!!! error TS2538: Type 'any' cannot be used as an index type. \ No newline at end of file diff --git a/tests/baselines/reference/computedPropertiesInDestructuring1.errors.txt b/tests/baselines/reference/computedPropertiesInDestructuring1.errors.txt index d2d63a4817498..31b938fb3fb3e 100644 --- a/tests/baselines/reference/computedPropertiesInDestructuring1.errors.txt +++ b/tests/baselines/reference/computedPropertiesInDestructuring1.errors.txt @@ -1,33 +1,63 @@ +tests/cases/compiler/computedPropertiesInDestructuring1.ts(3,7): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(8,7): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(10,8): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(11,8): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(14,15): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(15,15): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(16,16): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(17,16): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. tests/cases/compiler/computedPropertiesInDestructuring1.ts(20,8): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type 'String' has no compatible call signatures. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(20,8): error TS2538: Type 'any' cannot be used as an index type. +tests/cases/compiler/computedPropertiesInDestructuring1.ts(21,8): error TS2538: Type 'any' cannot be used as an index type. tests/cases/compiler/computedPropertiesInDestructuring1.ts(21,12): error TS2339: Property 'toExponential' does not exist on type 'string'. tests/cases/compiler/computedPropertiesInDestructuring1.ts(33,4): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type 'String' has no compatible call signatures. tests/cases/compiler/computedPropertiesInDestructuring1.ts(34,5): error TS2365: Operator '+' cannot be applied to types '1' and '{}'. -==== tests/cases/compiler/computedPropertiesInDestructuring1.ts (4 errors) ==== +==== tests/cases/compiler/computedPropertiesInDestructuring1.ts (14 errors) ==== // destructuring in variable declarations let foo = "bar"; let {[foo]: bar} = {bar: "bar"}; + ~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. let {["bar"]: bar2} = {bar: "bar"}; let foo2 = () => "bar"; let {[foo2()]: bar3} = {bar: "bar"}; + ~~~~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. let [{[foo]: bar4}] = [{bar: "bar"}]; + ~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. let [{[foo2()]: bar5}] = [{bar: "bar"}]; + ~~~~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. function f1({["bar"]: x}: { bar: number }) {} function f2({[foo]: x}: { bar: number }) {} + ~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. function f3({[foo2()]: x}: { bar: number }) {} + ~~~~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. function f4([{[foo]: x}]: [{ bar: number }]) {} + ~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. function f5([{[foo2()]: x}]: [{ bar: number }]) {} + ~~~~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. // report errors on type errors in computed properties used in destructuring let [{[foo()]: bar6}] = [{bar: "bar"}]; ~~~~~ !!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type 'String' has no compatible call signatures. + ~~~~~ +!!! error TS2538: Type 'any' cannot be used as an index type. let [{[foo.toExponential()]: bar7}] = [{bar: "bar"}]; + ~~~~~~~~~~~~~~~~~~~ +!!! error TS2538: Type 'any' cannot be used as an index type. ~~~~~~~~~~~~~ !!! error TS2339: Property 'toExponential' does not exist on type 'string'. diff --git a/tests/baselines/reference/computedPropertiesInDestructuring1_ES6.errors.txt b/tests/baselines/reference/computedPropertiesInDestructuring1_ES6.errors.txt index fa4d29cf42653..610b8e56ab3da 100644 --- a/tests/baselines/reference/computedPropertiesInDestructuring1_ES6.errors.txt +++ b/tests/baselines/reference/computedPropertiesInDestructuring1_ES6.errors.txt @@ -1,34 +1,64 @@ +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(3,7): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(9,7): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(11,8): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(12,8): error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(15,15): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(16,15): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(17,16): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(18,16): error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(21,8): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type 'String' has no compatible call signatures. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(21,8): error TS2538: Type 'any' cannot be used as an index type. +tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(22,8): error TS2538: Type 'any' cannot be used as an index type. tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(22,12): error TS2339: Property 'toExponential' does not exist on type 'string'. tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(34,4): error TS2349: Cannot invoke an expression whose type lacks a call signature. Type 'String' has no compatible call signatures. tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts(35,5): error TS2365: Operator '+' cannot be applied to types '1' and '{}'. -==== tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts (4 errors) ==== +==== tests/cases/compiler/computedPropertiesInDestructuring1_ES6.ts (14 errors) ==== // destructuring in variable declarations let foo = "bar"; let {[foo]: bar} = {bar: "bar"}; + ~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. let {["bar"]: bar2} = {bar: "bar"}; let {[11]: bar2_1} = {11: "bar"}; let foo2 = () => "bar"; let {[foo2()]: bar3} = {bar: "bar"}; + ~~~~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. let [{[foo]: bar4}] = [{bar: "bar"}]; + ~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. let [{[foo2()]: bar5}] = [{bar: "bar"}]; + ~~~~~~ +!!! error TS2537: Type '{ bar: string; }' has no matching index signature for type 'string'. function f1({["bar"]: x}: { bar: number }) {} function f2({[foo]: x}: { bar: number }) {} + ~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. function f3({[foo2()]: x}: { bar: number }) {} + ~~~~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. function f4([{[foo]: x}]: [{ bar: number }]) {} + ~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. function f5([{[foo2()]: x}]: [{ bar: number }]) {} + ~~~~~~ +!!! error TS2537: Type '{ bar: number; }' has no matching index signature for type 'string'. // report errors on type errors in computed properties used in destructuring let [{[foo()]: bar6}] = [{bar: "bar"}]; ~~~~~ !!! error TS2349: Cannot invoke an expression whose type lacks a call signature. Type 'String' has no compatible call signatures. + ~~~~~ +!!! error TS2538: Type 'any' cannot be used as an index type. let [{[foo.toExponential()]: bar7}] = [{bar: "bar"}]; + ~~~~~~~~~~~~~~~~~~~ +!!! error TS2538: Type 'any' cannot be used as an index type. ~~~~~~~~~~~~~ !!! error TS2339: Property 'toExponential' does not exist on type 'string'. diff --git a/tests/baselines/reference/computedPropertiesInDestructuring2.errors.txt b/tests/baselines/reference/computedPropertiesInDestructuring2.errors.txt new file mode 100644 index 0000000000000..da858e47c892d --- /dev/null +++ b/tests/baselines/reference/computedPropertiesInDestructuring2.errors.txt @@ -0,0 +1,8 @@ +tests/cases/compiler/computedPropertiesInDestructuring2.ts(2,7): error TS2537: Type '{}' has no matching index signature for type 'string'. + + +==== tests/cases/compiler/computedPropertiesInDestructuring2.ts (1 errors) ==== + let foo2 = () => "bar"; + let {[foo2()]: bar3} = {}; + ~~~~~~ +!!! error TS2537: Type '{}' has no matching index signature for type 'string'. \ No newline at end of file diff --git a/tests/baselines/reference/computedPropertiesInDestructuring2_ES6.errors.txt b/tests/baselines/reference/computedPropertiesInDestructuring2_ES6.errors.txt new file mode 100644 index 0000000000000..529cc2ebef82a --- /dev/null +++ b/tests/baselines/reference/computedPropertiesInDestructuring2_ES6.errors.txt @@ -0,0 +1,8 @@ +tests/cases/compiler/computedPropertiesInDestructuring2_ES6.ts(2,7): error TS2537: Type '{}' has no matching index signature for type 'string'. + + +==== tests/cases/compiler/computedPropertiesInDestructuring2_ES6.ts (1 errors) ==== + let foo2 = () => "bar"; + let {[foo2()]: bar3} = {}; + ~~~~~~ +!!! error TS2537: Type '{}' has no matching index signature for type 'string'. \ No newline at end of file diff --git a/tests/baselines/reference/computerPropertiesInES5ShouldBeTransformed.errors.txt b/tests/baselines/reference/computerPropertiesInES5ShouldBeTransformed.errors.txt new file mode 100644 index 0000000000000..7a0069ec03f80 --- /dev/null +++ b/tests/baselines/reference/computerPropertiesInES5ShouldBeTransformed.errors.txt @@ -0,0 +1,7 @@ +tests/cases/compiler/computerPropertiesInES5ShouldBeTransformed.ts(1,15): error TS2339: Property 'key' does not exist on type '{}'. + + +==== tests/cases/compiler/computerPropertiesInES5ShouldBeTransformed.ts (1 errors) ==== + const b = ({ [`key`]: renamed }) => renamed; + ~~~~~ +!!! error TS2339: Property 'key' does not exist on type '{}'. \ No newline at end of file diff --git a/tests/baselines/reference/declarationsAndAssignments.errors.txt b/tests/baselines/reference/declarationsAndAssignments.errors.txt index 64bd8d7e57825..f592df63d9227 100644 --- a/tests/baselines/reference/declarationsAndAssignments.errors.txt +++ b/tests/baselines/reference/declarationsAndAssignments.errors.txt @@ -15,8 +15,8 @@ tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(67,9): e tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(68,9): error TS2461: Type '{ 0: number; 1: number; }' is not an array type. tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(73,11): error TS2525: Initializer provides no value for this binding element and the binding element has no default value. tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(73,14): error TS2525: Initializer provides no value for this binding element and the binding element has no default value. -tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(74,11): error TS2459: Type 'undefined[]' has no property 'a' and no string index signature. -tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(74,14): error TS2459: Type 'undefined[]' has no property 'b' and no string index signature. +tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(74,11): error TS2339: Property 'a' does not exist on type 'undefined[]'. +tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(74,14): error TS2339: Property 'b' does not exist on type 'undefined[]'. tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(106,5): error TS2345: Argument of type '[number, [string, { y: false; }]]' is not assignable to parameter of type '[number, [string, { x: any; y?: boolean; }]]'. Type '[string, { y: false; }]' is not assignable to type '[string, { x: any; y?: boolean; }]'. Type '{ y: false; }' is not assignable to type '{ x: any; y?: boolean; }'. @@ -135,9 +135,9 @@ tests/cases/conformance/es6/destructuring/declarationsAndAssignments.ts(138,9): !!! error TS2525: Initializer provides no value for this binding element and the binding element has no default value. var { a, b } = []; // Error ~ -!!! error TS2459: Type 'undefined[]' has no property 'a' and no string index signature. +!!! error TS2339: Property 'a' does not exist on type 'undefined[]'. ~ -!!! error TS2459: Type 'undefined[]' has no property 'b' and no string index signature. +!!! error TS2339: Property 'b' does not exist on type 'undefined[]'. } function f11() { diff --git a/tests/baselines/reference/definiteAssignmentOfDestructuredVariable.types b/tests/baselines/reference/definiteAssignmentOfDestructuredVariable.types index 36ff5028305a1..f8337bdaac73f 100644 --- a/tests/baselines/reference/definiteAssignmentOfDestructuredVariable.types +++ b/tests/baselines/reference/definiteAssignmentOfDestructuredVariable.types @@ -26,20 +26,20 @@ class C { >method : () => void let { a, b } = this.foo; ->a : T["a"] ->b : T["b"] +>a : { [P in keyof T]: T[P]; }["a"] +>b : { [P in keyof T]: T[P]; }["b"] >this.foo : { [P in keyof T]: T[P]; } >this : this >foo : { [P in keyof T]: T[P]; } !(a && b); >!(a && b) : false ->(a && b) : T["b"] ->a && b : T["b"] ->a : T["a"] ->b : T["b"] +>(a && b) : { [P in keyof T]: T[P]; }["b"] +>a && b : { [P in keyof T]: T[P]; }["b"] +>a : { [P in keyof T]: T[P]; }["a"] +>b : { [P in keyof T]: T[P]; }["b"] a; ->a : T["a"] +>a : { [P in keyof T]: T[P]; }["a"] } } diff --git a/tests/baselines/reference/destructuredLateBoundNameHasCorrectTypes.errors.txt b/tests/baselines/reference/destructuredLateBoundNameHasCorrectTypes.errors.txt index 6a5c50021db04..100ce2d9a0879 100644 --- a/tests/baselines/reference/destructuredLateBoundNameHasCorrectTypes.errors.txt +++ b/tests/baselines/reference/destructuredLateBoundNameHasCorrectTypes.errors.txt @@ -1,4 +1,4 @@ -tests/cases/compiler/destructuredLateBoundNameHasCorrectTypes.ts(11,7): error TS2459: Type '{ prop: string; }' has no property '[notPresent]' and no string index signature. +tests/cases/compiler/destructuredLateBoundNameHasCorrectTypes.ts(11,8): error TS2339: Property 'prop2' does not exist on type '{ prop: string; }'. ==== tests/cases/compiler/destructuredLateBoundNameHasCorrectTypes.ts (1 errors) ==== @@ -13,6 +13,6 @@ tests/cases/compiler/destructuredLateBoundNameHasCorrectTypes.ts(11,7): error TS const notPresent = "prop2"; let { [notPresent]: computed2 } = { prop: "b" }; - ~~~~~~~~~~~~ -!!! error TS2459: Type '{ prop: string; }' has no property '[notPresent]' and no string index signature. + ~~~~~~~~~~ +!!! error TS2339: Property 'prop2' does not exist on type '{ prop: string; }'. \ No newline at end of file diff --git a/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.js b/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.js new file mode 100644 index 0000000000000..3fe1f2febcc26 --- /dev/null +++ b/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.js @@ -0,0 +1,16 @@ +//// [destructuredMaappedTypeIsNotImplicitlyAny.ts] +function foo(key: T, obj: { [_ in T]: number }) { + const { [key]: bar } = obj; // Element implicitly has an 'any' type because type '{ [_ in T]: number; }' has no index signature. + bar; // bar : any + + // Note: this does work: + const lorem = obj[key]; +} + +//// [destructuredMaappedTypeIsNotImplicitlyAny.js] +function foo(key, obj) { + var _a = key, bar = obj[_a]; // Element implicitly has an 'any' type because type '{ [_ in T]: number; }' has no index signature. + bar; // bar : any + // Note: this does work: + var lorem = obj[key]; +} diff --git a/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.symbols b/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.symbols new file mode 100644 index 0000000000000..93bd2be6638b4 --- /dev/null +++ b/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.symbols @@ -0,0 +1,24 @@ +=== tests/cases/compiler/destructuredMaappedTypeIsNotImplicitlyAny.ts === +function foo(key: T, obj: { [_ in T]: number }) { +>foo : Symbol(foo, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 0)) +>T : Symbol(T, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 13)) +>key : Symbol(key, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 31)) +>T : Symbol(T, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 13)) +>obj : Symbol(obj, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 38)) +>_ : Symbol(_, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 47)) +>T : Symbol(T, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 13)) + + const { [key]: bar } = obj; // Element implicitly has an 'any' type because type '{ [_ in T]: number; }' has no index signature. +>key : Symbol(key, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 31)) +>bar : Symbol(bar, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 1, 11)) +>obj : Symbol(obj, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 38)) + + bar; // bar : any +>bar : Symbol(bar, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 1, 11)) + + // Note: this does work: + const lorem = obj[key]; +>lorem : Symbol(lorem, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 5, 9)) +>obj : Symbol(obj, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 38)) +>key : Symbol(key, Decl(destructuredMaappedTypeIsNotImplicitlyAny.ts, 0, 31)) +} diff --git a/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.types b/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.types new file mode 100644 index 0000000000000..1f5cc38bfdb26 --- /dev/null +++ b/tests/baselines/reference/destructuredMaappedTypeIsNotImplicitlyAny.types @@ -0,0 +1,25 @@ +=== tests/cases/compiler/destructuredMaappedTypeIsNotImplicitlyAny.ts === +function foo(key: T, obj: { [_ in T]: number }) { +>foo : (key: T, obj: { [_ in T]: number; }) => void +>T : T +>key : T +>T : T +>obj : { [_ in T]: number; } +>_ : _ +>T : T + + const { [key]: bar } = obj; // Element implicitly has an 'any' type because type '{ [_ in T]: number; }' has no index signature. +>key : T +>bar : { [_ in T]: number; }[T] +>obj : { [_ in T]: number; } + + bar; // bar : any +>bar : { [_ in T]: number; }[T] + + // Note: this does work: + const lorem = obj[key]; +>lorem : { [_ in T]: number; }[T] +>obj[key] : { [_ in T]: number; }[T] +>obj : { [_ in T]: number; } +>key : T +} diff --git a/tests/baselines/reference/destructuringObjectBindingPatternAndAssignment3.errors.txt b/tests/baselines/reference/destructuringObjectBindingPatternAndAssignment3.errors.txt index 33344b9b5eb00..5a906d7d43e5e 100644 --- a/tests/baselines/reference/destructuringObjectBindingPatternAndAssignment3.errors.txt +++ b/tests/baselines/reference/destructuringObjectBindingPatternAndAssignment3.errors.txt @@ -1,8 +1,8 @@ tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(2,7): error TS1005: ',' expected. tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(3,5): error TS2322: Type '{ i: number; }' is not assignable to type 'string | number'. Type '{ i: number; }' is not assignable to type 'number'. -tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(3,6): error TS2459: Type 'string | number' has no property 'i' and no string index signature. -tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(4,6): error TS2459: Type 'string | number | {}' has no property 'i1' and no string index signature. +tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(3,6): error TS2339: Property 'i' does not exist on type 'string | number'. +tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(4,6): error TS2339: Property 'i1' does not exist on type 'string | number | {}'. tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(5,12): error TS2525: Initializer provides no value for this binding element and the binding element has no default value. tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(5,21): error TS2353: Object literal may only specify known properties, and 'f212' does not exist in type '{ f21: any; }'. tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAssignment3.ts(6,7): error TS1005: ':' expected. @@ -20,10 +20,10 @@ tests/cases/conformance/es6/destructuring/destructuringObjectBindingPatternAndAs !!! error TS2322: Type '{ i: number; }' is not assignable to type 'string | number'. !!! error TS2322: Type '{ i: number; }' is not assignable to type 'number'. ~ -!!! error TS2459: Type 'string | number' has no property 'i' and no string index signature. +!!! error TS2339: Property 'i' does not exist on type 'string | number'. var {i1}: string | number| {} = { i1: 2 }; ~~ -!!! error TS2459: Type 'string | number | {}' has no property 'i1' and no string index signature. +!!! error TS2339: Property 'i1' does not exist on type 'string | number | {}'. var { f2: {f21} = { f212: "string" } }: any = undefined; ~~~ !!! error TS2525: Initializer provides no value for this binding element and the binding element has no default value. diff --git a/tests/baselines/reference/destructuringParameterProperties5.errors.txt b/tests/baselines/reference/destructuringParameterProperties5.errors.txt index e0540240b61c4..5c6032112d509 100644 --- a/tests/baselines/reference/destructuringParameterProperties5.errors.txt +++ b/tests/baselines/reference/destructuringParameterProperties5.errors.txt @@ -1,7 +1,7 @@ tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(5,17): error TS1187: A parameter property may not be declared using a binding pattern. -tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(5,27): error TS2459: Type 'ObjType1' has no property 'x1' and no string index signature. -tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(5,31): error TS2459: Type 'ObjType1' has no property 'x2' and no string index signature. -tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(5,35): error TS2459: Type 'ObjType1' has no property 'x3' and no string index signature. +tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(5,27): error TS2339: Property 'x1' does not exist on type 'ObjType1'. +tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(5,31): error TS2339: Property 'x2' does not exist on type 'ObjType1'. +tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(5,35): error TS2339: Property 'x3' does not exist on type 'ObjType1'. tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(7,29): error TS2339: Property 'x1' does not exist on type 'C1'. tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(7,40): error TS2339: Property 'x2' does not exist on type 'C1'. tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(7,51): error TS2339: Property 'x3' does not exist on type 'C1'. @@ -21,11 +21,11 @@ tests/cases/conformance/es6/destructuring/destructuringParameterProperties5.ts(1 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ !!! error TS1187: A parameter property may not be declared using a binding pattern. ~~ -!!! error TS2459: Type 'ObjType1' has no property 'x1' and no string index signature. +!!! error TS2339: Property 'x1' does not exist on type 'ObjType1'. ~~ -!!! error TS2459: Type 'ObjType1' has no property 'x2' and no string index signature. +!!! error TS2339: Property 'x2' does not exist on type 'ObjType1'. ~~ -!!! error TS2459: Type 'ObjType1' has no property 'x3' and no string index signature. +!!! error TS2339: Property 'x3' does not exist on type 'ObjType1'. var foo: any = x1 || x2 || x3 || y || z; var bar: any = this.x1 || this.x2 || this.x3 || this.y || this.z; ~~ diff --git a/tests/baselines/reference/destructuringVariableDeclaration2.errors.txt b/tests/baselines/reference/destructuringVariableDeclaration2.errors.txt index c831b10a467fb..3d686c492fcd4 100644 --- a/tests/baselines/reference/destructuringVariableDeclaration2.errors.txt +++ b/tests/baselines/reference/destructuringVariableDeclaration2.errors.txt @@ -5,8 +5,8 @@ tests/cases/conformance/es6/destructuring/destructuringVariableDeclaration2.ts(4 Type '[[boolean]]' is not assignable to type '[[string]]'. Type '[boolean]' is not assignable to type '[string]'. Type 'boolean' is not assignable to type 'string'. -tests/cases/conformance/es6/destructuring/destructuringVariableDeclaration2.ts(14,16): error TS2459: Type 'number | { c3: number; c5: number; }' has no property 'c3' and no string index signature. -tests/cases/conformance/es6/destructuring/destructuringVariableDeclaration2.ts(14,24): error TS2459: Type 'number | { c3: number; c5: number; }' has no property 'c5' and no string index signature. +tests/cases/conformance/es6/destructuring/destructuringVariableDeclaration2.ts(14,16): error TS2339: Property 'c3' does not exist on type 'number | { c3: number; c5: number; }'. +tests/cases/conformance/es6/destructuring/destructuringVariableDeclaration2.ts(14,24): error TS2339: Property 'c5' does not exist on type 'number | { c3: number; c5: number; }'. ==== tests/cases/conformance/es6/destructuring/destructuringVariableDeclaration2.ts (4 errors) ==== @@ -34,9 +34,9 @@ tests/cases/conformance/es6/destructuring/destructuringVariableDeclaration2.ts(1 // an element type E, where E is the type of the numeric index signature of S. var [c1, c2, { c3: c4, c5 }, , ...c6] = [1, 2, { c3: 4, c5: 0 }]; // Error ~~ -!!! error TS2459: Type 'number | { c3: number; c5: number; }' has no property 'c3' and no string index signature. +!!! error TS2339: Property 'c3' does not exist on type 'number | { c3: number; c5: number; }'. ~~ -!!! error TS2459: Type 'number | { c3: number; c5: number; }' has no property 'c5' and no string index signature. +!!! error TS2339: Property 'c5' does not exist on type 'number | { c3: number; c5: number; }'. // When a destructuring variable declaration, binding property, or binding element specifies // an initializer expression, the type of the initializer expression is required to be assignable diff --git a/tests/baselines/reference/downlevelLetConst16.errors.txt b/tests/baselines/reference/downlevelLetConst16.errors.txt index 905d1a607e81d..955c79378fe30 100644 --- a/tests/baselines/reference/downlevelLetConst16.errors.txt +++ b/tests/baselines/reference/downlevelLetConst16.errors.txt @@ -1,9 +1,9 @@ tests/cases/compiler/downlevelLetConst16.ts(151,15): error TS2525: Initializer provides no value for this binding element and the binding element has no default value. tests/cases/compiler/downlevelLetConst16.ts(164,17): error TS2525: Initializer provides no value for this binding element and the binding element has no default value. tests/cases/compiler/downlevelLetConst16.ts(195,14): error TS2461: Type 'undefined' is not an array type. -tests/cases/compiler/downlevelLetConst16.ts(202,15): error TS2459: Type 'undefined' has no property 'a' and no string index signature. +tests/cases/compiler/downlevelLetConst16.ts(202,15): error TS2339: Property 'a' does not exist on type 'undefined'. tests/cases/compiler/downlevelLetConst16.ts(216,16): error TS2461: Type 'undefined' is not an array type. -tests/cases/compiler/downlevelLetConst16.ts(223,17): error TS2459: Type 'undefined' has no property 'a' and no string index signature. +tests/cases/compiler/downlevelLetConst16.ts(223,17): error TS2339: Property 'a' does not exist on type 'undefined'. ==== tests/cases/compiler/downlevelLetConst16.ts (6 errors) ==== @@ -216,7 +216,7 @@ tests/cases/compiler/downlevelLetConst16.ts(223,17): error TS2459: Type 'undefin function foo9() { for (let {a: x} of []) { ~ -!!! error TS2459: Type 'undefined' has no property 'a' and no string index signature. +!!! error TS2339: Property 'a' does not exist on type 'undefined'. use(x); } use(x); @@ -241,7 +241,7 @@ tests/cases/compiler/downlevelLetConst16.ts(223,17): error TS2459: Type 'undefin function foo12() { for (const {a: x} of []) { ~ -!!! error TS2459: Type 'undefined' has no property 'a' and no string index signature. +!!! error TS2339: Property 'a' does not exist on type 'undefined'. use(x); } use(x); diff --git a/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt b/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt index 7589610a64e35..9a5a498dc0daf 100644 --- a/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt +++ b/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt @@ -1,6 +1,6 @@ tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,10): error TS2491: The left-hand side of a 'for...in' statement cannot be a destructuring pattern. -tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,11): error TS2459: Type 'string' has no property 'a' and no string index signature. -tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,14): error TS2459: Type 'string' has no property 'b' and no string index signature. +tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,11): error TS2339: Property 'a' does not exist on type 'string'. +tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,14): error TS2339: Property 'b' does not exist on type 'string'. ==== tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts (3 errors) ==== @@ -8,6 +8,6 @@ tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructurin ~~~~~~ !!! error TS2491: The left-hand side of a 'for...in' statement cannot be a destructuring pattern. ~ -!!! error TS2459: Type 'string' has no property 'a' and no string index signature. +!!! error TS2339: Property 'a' does not exist on type 'string'. ~ -!!! error TS2459: Type 'string' has no property 'b' and no string index signature. \ No newline at end of file +!!! error TS2339: Property 'b' does not exist on type 'string'. \ No newline at end of file diff --git a/tests/baselines/reference/jsdocParamTag2.errors.txt b/tests/baselines/reference/jsdocParamTag2.errors.txt index e19140b3f9deb..287846cc0a121 100644 --- a/tests/baselines/reference/jsdocParamTag2.errors.txt +++ b/tests/baselines/reference/jsdocParamTag2.errors.txt @@ -1,6 +1,6 @@ tests/cases/conformance/jsdoc/0.js(56,20): error TS8024: JSDoc '@param' tag has name 'obj', but there is no parameter with that name. -tests/cases/conformance/jsdoc/0.js(61,19): error TS2459: Type 'string' has no property 'a' and no string index signature. -tests/cases/conformance/jsdoc/0.js(61,22): error TS2459: Type 'string' has no property 'b' and no string index signature. +tests/cases/conformance/jsdoc/0.js(61,19): error TS2339: Property 'a' does not exist on type 'string'. +tests/cases/conformance/jsdoc/0.js(61,22): error TS2339: Property 'b' does not exist on type 'string'. tests/cases/conformance/jsdoc/0.js(63,20): error TS8024: JSDoc '@param' tag has name 'y', but there is no parameter with that name. @@ -69,9 +69,9 @@ tests/cases/conformance/jsdoc/0.js(63,20): error TS8024: JSDoc '@param' tag has */ function bad1(x, {a, b}) {} ~ -!!! error TS2459: Type 'string' has no property 'a' and no string index signature. +!!! error TS2339: Property 'a' does not exist on type 'string'. ~ -!!! error TS2459: Type 'string' has no property 'b' and no string index signature. +!!! error TS2339: Property 'b' does not exist on type 'string'. /** * @param {string} y - here, y's type gets ignored but obj's is fine ~ diff --git a/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.errors.txt b/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.errors.txt index 2e926ac1b83d3..edba02d293927 100644 --- a/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.errors.txt +++ b/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.errors.txt @@ -1,16 +1,16 @@ -tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(2,15): error TS7017: Element implicitly has an 'any' type because type '{ prop: string; }' has no index signature. -tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(13,15): error TS7015: Element implicitly has an 'any' type because index expression is not of type 'number'. -tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(21,15): error TS2536: Type 'unique symbol' cannot be used to index type '{ [idx: number]: string; }'. -tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(23,15): error TS2536: Type 'unique symbol' cannot be used to index type '{ [idx: string]: string; }'. -tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(25,16): error TS2536: Type 'symbol' cannot be used to index type '{ [idx: number]: string; }'. -tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(27,16): error TS2536: Type 'symbol' cannot be used to index type '{ [idx: string]: string; }'. +tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(2,7): error TS2537: Type '{ prop: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(13,7): error TS2537: Type '{ [idx: number]: string; }' has no matching index signature for type 'string'. +tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(21,7): error TS2538: Type 'unique symbol' cannot be used as an index type. +tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(23,7): error TS2538: Type 'unique symbol' cannot be used as an index type. +tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(25,7): error TS2538: Type 'symbol' cannot be used as an index type. +tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(27,7): error TS2538: Type 'symbol' cannot be used as an index type. ==== tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts (6 errors) ==== let named = "foo"; let {[named]: prop} = {prop: "foo"}; - ~~~~ -!!! error TS7017: Element implicitly has an 'any' type because type '{ prop: string; }' has no index signature. + ~~~~~ +!!! error TS2537: Type '{ prop: string; }' has no matching index signature for type 'string'. void prop; const numIndexed: {[idx: number]: string} = null as any; @@ -22,8 +22,8 @@ tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(27,16): error TS2 let symed2 = Symbol(); let {[named]: prop2} = numIndexed; - ~~~~~ -!!! error TS7015: Element implicitly has an 'any' type because index expression is not of type 'number'. + ~~~~~ +!!! error TS2537: Type '{ [idx: number]: string; }' has no matching index signature for type 'string'. void prop2; let {[numed]: prop3} = numIndexed; void prop3; @@ -32,18 +32,18 @@ tests/cases/compiler/lateBoundDestructuringImplicitAnyError.ts(27,16): error TS2 let {[numed]: prop5} = strIndexed; void prop5; let {[symed]: prop6} = numIndexed; - ~~~~~ -!!! error TS2536: Type 'unique symbol' cannot be used to index type '{ [idx: number]: string; }'. + ~~~~~ +!!! error TS2538: Type 'unique symbol' cannot be used as an index type. void prop6; let {[symed]: prop7} = strIndexed; - ~~~~~ -!!! error TS2536: Type 'unique symbol' cannot be used to index type '{ [idx: string]: string; }'. + ~~~~~ +!!! error TS2538: Type 'unique symbol' cannot be used as an index type. void prop7; let {[symed2]: prop8} = numIndexed; - ~~~~~ -!!! error TS2536: Type 'symbol' cannot be used to index type '{ [idx: number]: string; }'. + ~~~~~~ +!!! error TS2538: Type 'symbol' cannot be used as an index type. void prop8; let {[symed2]: prop9} = strIndexed; - ~~~~~ -!!! error TS2536: Type 'symbol' cannot be used to index type '{ [idx: string]: string; }'. + ~~~~~~ +!!! error TS2538: Type 'symbol' cannot be used as an index type. void prop9; \ No newline at end of file diff --git a/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.types b/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.types index 92d2c4c662c4b..60c220095adb3 100644 --- a/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.types +++ b/tests/baselines/reference/lateBoundDestructuringImplicitAnyError.types @@ -87,12 +87,12 @@ void prop6; let {[symed]: prop7} = strIndexed; >symed : unique symbol ->prop7 : any +>prop7 : string >strIndexed : { [idx: string]: string; } void prop7; >void prop7 : undefined ->prop7 : any +>prop7 : string let {[symed2]: prop8} = numIndexed; >symed2 : symbol @@ -105,10 +105,10 @@ void prop8; let {[symed2]: prop9} = strIndexed; >symed2 : symbol ->prop9 : any +>prop9 : string >strIndexed : { [idx: string]: string; } void prop9; >void prop9 : undefined ->prop9 : any +>prop9 : string diff --git a/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt b/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt index 0a6dfa66b86b2..13acc44c39758 100644 --- a/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt +++ b/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt @@ -1,5 +1,5 @@ tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(3,3): error TS2339: Property 'nonExist' does not exist on type 'object'. -tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(5,7): error TS2459: Type 'object' has no property 'destructuring' and no string index signature. +tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(5,7): error TS2339: Property 'destructuring' does not exist on type 'object'. ==== tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts (2 errors) ==== @@ -11,6 +11,6 @@ tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(5,7): e var { destructuring } = a; // error ~~~~~~~~~~~~~ -!!! error TS2459: Type 'object' has no property 'destructuring' and no string index signature. +!!! error TS2339: Property 'destructuring' does not exist on type 'object'. var { ...rest } = a; // ok \ No newline at end of file diff --git a/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt b/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt index f7f2ee3db16d5..d9b229e2e9f8b 100644 --- a/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt +++ b/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt @@ -1,4 +1,4 @@ -tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplicitAny.ts(4,17): error TS7017: Element implicitly has an 'any' type because type '{}' has no index signature. +tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplicitAny.ts(4,17): error TS7017: Element implicitly has an 'any' type because type 'object' has no index signature. ==== tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplicitAny.ts (1 errors) ==== @@ -7,6 +7,6 @@ tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplic for (var key in a) { var value = a[key]; // error ~~~~~~ -!!! error TS7017: Element implicitly has an 'any' type because type '{}' has no index signature. +!!! error TS7017: Element implicitly has an 'any' type because type 'object' has no index signature. } \ No newline at end of file diff --git a/tests/baselines/reference/objectRest.errors.txt b/tests/baselines/reference/objectRest.errors.txt new file mode 100644 index 0000000000000..f1505bb3ea56f --- /dev/null +++ b/tests/baselines/reference/objectRest.errors.txt @@ -0,0 +1,62 @@ +tests/cases/conformance/types/rest/objectRest.ts(7,12): error TS2339: Property '0' does not exist on type 'string'. +tests/cases/conformance/types/rest/objectRest.ts(7,20): error TS2339: Property '1' does not exist on type 'string'. +tests/cases/conformance/types/rest/objectRest.ts(43,8): error TS2537: Type '{ a: number; b: string; }' has no matching index signature for type 'string'. +tests/cases/conformance/types/rest/objectRest.ts(43,35): error TS2537: Type '{ a: number; b: string; }' has no matching index signature for type 'string'. + + +==== tests/cases/conformance/types/rest/objectRest.ts (4 errors) ==== + var o = { a: 1, b: 'no' } + var { ...clone } = o; + var { a, ...justB } = o; + var { a, b: renamed, ...empty } = o; + var { ['b']: renamed, ...justA } = o; + var { 'b': renamed, ...justA } = o; + var { b: { '0': n, '1': oooo }, ...justA } = o; + ~~~ +!!! error TS2339: Property '0' does not exist on type 'string'. + ~~~ +!!! error TS2339: Property '1' does not exist on type 'string'. + + let o2 = { c: 'terrible idea?', d: 'yes' }; + var { d: renamed, ...d } = o2; + + let nestedrest: { x: number, n1: { y: number, n2: { z: number, n3: { n4: number } } }, rest: number, restrest: number }; + var { x, n1: { y, n2: { z, n3: { ...nr } } }, ...restrest } = nestedrest; + + let complex: { x: { ka, ki }, y: number }; + var { x: { ka, ...nested }, y: other, ...rest } = complex; + ({x: { ka, ...nested }, y: other, ...rest} = complex); + var { x, ...fresh } = { x: 1, y: 2 }; + ({ x, ...fresh } = { x: 1, y: 2 }); + + class Removable { + private x: number; + protected y: number; + set z(value: number) { } + get both(): number { return 12 } + set both(value: number) { } + m() { } + removed: string; + remainder: string; + } + interface I { + m(): void; + removed: string; + remainder: string; + } + var removable = new Removable(); + var { removed, ...removableRest } = removable; + var i: I = removable; + var { removed, ...removableRest2 } = i; + + let computed = 'b'; + let computed2 = 'a'; + var { [computed]: stillNotGreat, [computed2]: soSo, ...o } = o; + ~~~~~~~~ +!!! error TS2537: Type '{ a: number; b: string; }' has no matching index signature for type 'string'. + ~~~~~~~~~ +!!! error TS2537: Type '{ a: number; b: string; }' has no matching index signature for type 'string'. + ({ [computed]: stillNotGreat, [computed2]: soSo, ...o } = o); + + var noContextualType = ({ aNumber = 12, ...notEmptyObject }) => aNumber + notEmptyObject.anythingGoes; + \ No newline at end of file diff --git a/tests/baselines/reference/objectRest.types b/tests/baselines/reference/objectRest.types index d4ca309608555..3fe0cd35e9f58 100644 --- a/tests/baselines/reference/objectRest.types +++ b/tests/baselines/reference/objectRest.types @@ -36,8 +36,8 @@ var { 'b': renamed, ...justA } = o; var { b: { '0': n, '1': oooo }, ...justA } = o; >b : any ->n : string ->oooo : string +>n : any +>oooo : any >justA : { a: number; } >o : { a: number; b: string; } diff --git a/tests/baselines/reference/restElementWithBindingPattern2.errors.txt b/tests/baselines/reference/restElementWithBindingPattern2.errors.txt index 9645a028a4ebf..02cac652a223f 100644 --- a/tests/baselines/reference/restElementWithBindingPattern2.errors.txt +++ b/tests/baselines/reference/restElementWithBindingPattern2.errors.txt @@ -1,5 +1,5 @@ tests/cases/conformance/es6/destructuring/restElementWithBindingPattern2.ts(1,9): error TS2501: A rest element cannot contain a binding pattern. -tests/cases/conformance/es6/destructuring/restElementWithBindingPattern2.ts(1,16): error TS2459: Type 'number[]' has no property 'b' and no string index signature. +tests/cases/conformance/es6/destructuring/restElementWithBindingPattern2.ts(1,16): error TS2339: Property 'b' does not exist on type 'number[]'. ==== tests/cases/conformance/es6/destructuring/restElementWithBindingPattern2.ts (2 errors) ==== @@ -7,4 +7,4 @@ tests/cases/conformance/es6/destructuring/restElementWithBindingPattern2.ts(1,16 ~~~~~~~~~~ !!! error TS2501: A rest element cannot contain a binding pattern. ~ -!!! error TS2459: Type 'number[]' has no property 'b' and no string index signature. \ No newline at end of file +!!! error TS2339: Property 'b' does not exist on type 'number[]'. \ No newline at end of file diff --git a/tests/cases/compiler/destructuredMaappedTypeIsNotImplicitlyAny.ts b/tests/cases/compiler/destructuredMaappedTypeIsNotImplicitlyAny.ts new file mode 100644 index 0000000000000..4fd88fd5c8e68 --- /dev/null +++ b/tests/cases/compiler/destructuredMaappedTypeIsNotImplicitlyAny.ts @@ -0,0 +1,8 @@ +// @noImplicitAny: true +function foo(key: T, obj: { [_ in T]: number }) { + const { [key]: bar } = obj; // Element implicitly has an 'any' type because type '{ [_ in T]: number; }' has no index signature. + bar; // bar : any + + // Note: this does work: + const lorem = obj[key]; +} \ No newline at end of file From d9338129351f6146e70ecf986074fce764e76d8c Mon Sep 17 00:00:00 2001 From: Wesley Wigham Date: Wed, 31 Oct 2018 13:39:52 -0700 Subject: [PATCH 2/4] Accept updated test baseline --- .../parameterInitializersForwardReferencing1_es6.errors.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/tests/baselines/reference/parameterInitializersForwardReferencing1_es6.errors.txt b/tests/baselines/reference/parameterInitializersForwardReferencing1_es6.errors.txt index 59280d2006a01..c65f327161ebe 100644 --- a/tests/baselines/reference/parameterInitializersForwardReferencing1_es6.errors.txt +++ b/tests/baselines/reference/parameterInitializersForwardReferencing1_es6.errors.txt @@ -1,9 +1,10 @@ tests/cases/conformance/functions/parameterInitializersForwardReferencing1_es6.ts(13,20): error TS2373: Initializer of parameter 'bar' cannot reference identifier 'foo' declared after it. tests/cases/conformance/functions/parameterInitializersForwardReferencing1_es6.ts(21,18): error TS2372: Parameter 'a' cannot be referenced in its initializer. tests/cases/conformance/functions/parameterInitializersForwardReferencing1_es6.ts(25,22): error TS2372: Parameter 'async' cannot be referenced in its initializer. +tests/cases/conformance/functions/parameterInitializersForwardReferencing1_es6.ts(29,15): error TS2537: Type 'any[]' has no matching index signature for type 'string'. -==== tests/cases/conformance/functions/parameterInitializersForwardReferencing1_es6.ts (3 errors) ==== +==== tests/cases/conformance/functions/parameterInitializersForwardReferencing1_es6.ts (4 errors) ==== let foo: string = ""; function f1 (bar = foo) { // unexpected compiler error; works at runtime @@ -39,6 +40,8 @@ tests/cases/conformance/functions/parameterInitializersForwardReferencing1_es6.t } function f7({[foo]: bar}: any[]) { + ~~~ +!!! error TS2537: Type 'any[]' has no matching index signature for type 'string'. let foo: number = 2; } From 8250384320a0c39cec234861aa8fb33744453be7 Mon Sep 17 00:00:00 2001 From: Wesley Wigham Date: Wed, 31 Oct 2018 15:10:34 -0700 Subject: [PATCH 3/4] Use raw apparent type instead of passing in flag to sometimes make one --- src/compiler/checker.ts | 23 ++++++++++--------- .../reference/ES5For-of27.errors.txt | 8 +++---- .../reference/ES5For-of29.errors.txt | 8 +++---- .../reference/ES5For-of35.errors.txt | 8 +++---- .../for-inStatementsDestructuring2.errors.txt | 8 +++---- .../reference/jsdocParamTag2.errors.txt | 8 +++---- .../nonPrimitiveAccessProperty.errors.txt | 4 ++-- ...eIndexingWithForInNoImplicitAny.errors.txt | 4 ++-- .../baselines/reference/objectRest.errors.txt | 8 +++---- 9 files changed, 40 insertions(+), 39 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index cb3daa48c29bc..5b10aceca9ed4 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -4663,7 +4663,7 @@ namespace ts { : isIdentifier(name) ? getLiteralType(unescapeLeadingUnderscores(name.escapedText)) : checkExpression(name); - const declaredType = checkIndexedAccessIndexType(getIndexedAccessType(parentType, exprType, name, /*useApparentObjectType*/ true), name, /*useApparentObjectType*/ true); + const declaredType = checkIndexedAccessIndexType(getIndexedAccessType(getApparentType(parentType), exprType, name), name); type = getFlowTypeOfReference(declaration, getConstraintForLocation(declaredType, declaration.name)); } } @@ -7037,7 +7037,7 @@ namespace ts { function getConstraintOfIndexedAccess(type: IndexedAccessType) { const objectType = getConstraintOfType(type.objectType) || type.objectType; if (objectType !== type.objectType) { - const constraint = getIndexedAccessType(objectType, type.indexType, /*accessNode*/ undefined, /*useApparentObjectType*/ false, errorType); + const constraint = getIndexedAccessType(objectType, type.indexType, /*accessNode*/ undefined, errorType); if (constraint && constraint !== errorType) { return constraint; } @@ -7209,7 +7209,7 @@ namespace ts { if (t.flags & TypeFlags.IndexedAccess) { const baseObjectType = getBaseConstraint((t).objectType); const baseIndexType = getBaseConstraint((t).indexType); - const baseIndexedAccess = baseObjectType && baseIndexType ? getIndexedAccessType(baseObjectType, baseIndexType, /*accessNode*/ undefined, /*useApparentObjectType*/ false, errorType) : undefined; + const baseIndexedAccess = baseObjectType && baseIndexType ? getIndexedAccessType(baseObjectType, baseIndexType, /*accessNode*/ undefined, errorType) : undefined; return baseIndexedAccess && baseIndexedAccess !== errorType ? getBaseConstraint(baseIndexedAccess) : undefined; } if (t.flags & TypeFlags.Conditional) { @@ -9499,7 +9499,7 @@ namespace ts { return instantiateType(getTemplateTypeFromMappedType(objectType), templateMapper); } - function getIndexedAccessType(objectType: Type, indexType: Type, accessNode?: ElementAccessExpression | IndexedAccessTypeNode | PropertyName, useApparentObjectType?: boolean, missingType = accessNode ? errorType : unknownType): Type { + function getIndexedAccessType(objectType: Type, indexType: Type, accessNode?: ElementAccessExpression | IndexedAccessTypeNode | PropertyName, missingType = accessNode ? errorType : unknownType): Type { if (objectType === wildcardType || indexType === wildcardType) { return wildcardType; } @@ -9508,7 +9508,7 @@ namespace ts { // object type. Note that for a generic T and a non-generic K, we eagerly resolve T[K] if it originates in // an expression. This is to preserve backwards compatibility. For example, an element access 'this["foo"]' // has always been resolved eagerly using the constraint type of 'this' at the given location. - if (isGenericIndexType(indexType) || !(accessNode && accessNode.kind === SyntaxKind.ElementAccessExpression) && isGenericObjectType(useApparentObjectType ? getApparentType(objectType) : objectType)) { + if (isGenericIndexType(indexType) || !(accessNode && accessNode.kind === SyntaxKind.ElementAccessExpression) && isGenericObjectType(objectType)) { if (objectType.flags & TypeFlags.AnyOrUnknown) { return objectType; } @@ -9523,11 +9523,12 @@ namespace ts { // In the following we resolve T[K] to the type of the property in T selected by K. // We treat boolean as different from other unions to improve errors; // skipping straight to getPropertyTypeForIndexType gives errors with 'boolean' instead of 'true'. + const apparentObjectType = getApparentType(objectType); if (indexType.flags & TypeFlags.Union && !(indexType.flags & TypeFlags.Boolean)) { const propTypes: Type[] = []; let wasMissingProp = false; for (const t of (indexType).types) { - const propType = getPropertyTypeForIndexType(objectType, t, accessNode, /*cacheSymbol*/ false, missingType); + const propType = getPropertyTypeForIndexType(apparentObjectType, t, accessNode, /*cacheSymbol*/ false, missingType); if (propType === missingType) { if (!accessNode) { // If there's no error node, we can immeditely stop, since error reporting is off @@ -9545,7 +9546,7 @@ namespace ts { } return getUnionType(propTypes); } - return getPropertyTypeForIndexType(objectType, indexType, accessNode, /*cacheSymbol*/ true, missingType); + return getPropertyTypeForIndexType(apparentObjectType, indexType, accessNode, /*cacheSymbol*/ true, missingType); } function getTypeFromIndexedAccessTypeNode(node: IndexedAccessTypeNode) { @@ -10860,8 +10861,8 @@ namespace ts { let reportedError = false; for (let status = iterator.next(); !status.done; status = iterator.next()) { const { errorNode: prop, innerExpression: next, nameType, errorMessage } = status.value; - const sourcePropType = getIndexedAccessType(source, nameType, /*accessNode*/ undefined, /*useApparentObjectType*/ false, errorType); - const targetPropType = getIndexedAccessType(target, nameType, /*accessNode*/ undefined, /*useApparentObjectType*/ false, errorType); + const sourcePropType = getIndexedAccessType(source, nameType, /*accessNode*/ undefined, errorType); + const targetPropType = getIndexedAccessType(target, nameType, /*accessNode*/ undefined, errorType); if (sourcePropType !== errorType && targetPropType !== errorType && !checkTypeRelatedTo(sourcePropType, targetPropType, relation, /*errorNode*/ undefined)) { const elaborated = next && elaborateError(next, sourcePropType, targetPropType, relation, /*headMessage*/ undefined); if (elaborated) { @@ -23182,14 +23183,14 @@ namespace ts { forEach(node.types, checkSourceElement); } - function checkIndexedAccessIndexType(type: Type, accessNode: Node, useApparentObjectType?: boolean) { + function checkIndexedAccessIndexType(type: Type, accessNode: Node) { if (!(type.flags & TypeFlags.IndexedAccess)) { return type; } // Check if the index type is assignable to 'keyof T' for the object type. const objectType = (type).objectType; const indexType = (type).indexType; - if (isTypeAssignableTo(indexType, getIndexType(useApparentObjectType ? getApparentType(objectType) : objectType, /*stringsOnly*/ false))) { + if (isTypeAssignableTo(indexType, getIndexType(objectType, /*stringsOnly*/ false))) { if (accessNode.kind === SyntaxKind.ElementAccessExpression && isAssignmentTarget(accessNode) && getObjectFlags(objectType) & ObjectFlags.Mapped && getMappedTypeModifiers(objectType) & MappedTypeModifiers.IncludeReadonly) { error(accessNode, Diagnostics.Index_signature_in_type_0_only_permits_reading, typeToString(objectType)); diff --git a/tests/baselines/reference/ES5For-of27.errors.txt b/tests/baselines/reference/ES5For-of27.errors.txt index d64baaa1aa75c..837a11cf7ee89 100644 --- a/tests/baselines/reference/ES5For-of27.errors.txt +++ b/tests/baselines/reference/ES5For-of27.errors.txt @@ -1,13 +1,13 @@ -tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,11): error TS2339: Property 'x' does not exist on type 'number'. -tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,21): error TS2339: Property 'y' does not exist on type 'number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,11): error TS2339: Property 'x' does not exist on type 'Number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts(1,21): error TS2339: Property 'y' does not exist on type 'Number'. ==== tests/cases/conformance/statements/for-ofStatements/ES5For-of27.ts (2 errors) ==== for (var {x: a = 0, y: b = 1} of [2, 3]) { ~ -!!! error TS2339: Property 'x' does not exist on type 'number'. +!!! error TS2339: Property 'x' does not exist on type 'Number'. ~ -!!! error TS2339: Property 'y' does not exist on type 'number'. +!!! error TS2339: Property 'y' does not exist on type 'Number'. a; b; } \ No newline at end of file diff --git a/tests/baselines/reference/ES5For-of29.errors.txt b/tests/baselines/reference/ES5For-of29.errors.txt index 1ab9c84d284d2..c23ff1af21171 100644 --- a/tests/baselines/reference/ES5For-of29.errors.txt +++ b/tests/baselines/reference/ES5For-of29.errors.txt @@ -1,13 +1,13 @@ -tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,13): error TS2339: Property 'x' does not exist on type 'number'. -tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,23): error TS2339: Property 'y' does not exist on type 'number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,13): error TS2339: Property 'x' does not exist on type 'Number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts(1,23): error TS2339: Property 'y' does not exist on type 'Number'. ==== tests/cases/conformance/statements/for-ofStatements/ES5For-of29.ts (2 errors) ==== for (const {x: a = 0, y: b = 1} of [2, 3]) { ~ -!!! error TS2339: Property 'x' does not exist on type 'number'. +!!! error TS2339: Property 'x' does not exist on type 'Number'. ~ -!!! error TS2339: Property 'y' does not exist on type 'number'. +!!! error TS2339: Property 'y' does not exist on type 'Number'. a; b; } \ No newline at end of file diff --git a/tests/baselines/reference/ES5For-of35.errors.txt b/tests/baselines/reference/ES5For-of35.errors.txt index 2670f6285d599..c22dc96e42dce 100644 --- a/tests/baselines/reference/ES5For-of35.errors.txt +++ b/tests/baselines/reference/ES5For-of35.errors.txt @@ -1,13 +1,13 @@ -tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,13): error TS2339: Property 'x' does not exist on type 'number'. -tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,23): error TS2339: Property 'y' does not exist on type 'number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,13): error TS2339: Property 'x' does not exist on type 'Number'. +tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts(1,23): error TS2339: Property 'y' does not exist on type 'Number'. ==== tests/cases/conformance/statements/for-ofStatements/ES5For-of35.ts (2 errors) ==== for (const {x: a = 0, y: b = 1} of [2, 3]) { ~ -!!! error TS2339: Property 'x' does not exist on type 'number'. +!!! error TS2339: Property 'x' does not exist on type 'Number'. ~ -!!! error TS2339: Property 'y' does not exist on type 'number'. +!!! error TS2339: Property 'y' does not exist on type 'Number'. a; b; } \ No newline at end of file diff --git a/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt b/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt index 9a5a498dc0daf..5d80cf26ebc2c 100644 --- a/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt +++ b/tests/baselines/reference/for-inStatementsDestructuring2.errors.txt @@ -1,6 +1,6 @@ tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,10): error TS2491: The left-hand side of a 'for...in' statement cannot be a destructuring pattern. -tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,11): error TS2339: Property 'a' does not exist on type 'string'. -tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,14): error TS2339: Property 'b' does not exist on type 'string'. +tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,11): error TS2339: Property 'a' does not exist on type 'String'. +tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts(1,14): error TS2339: Property 'b' does not exist on type 'String'. ==== tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructuring2.ts (3 errors) ==== @@ -8,6 +8,6 @@ tests/cases/conformance/statements/for-inStatements/for-inStatementsDestructurin ~~~~~~ !!! error TS2491: The left-hand side of a 'for...in' statement cannot be a destructuring pattern. ~ -!!! error TS2339: Property 'a' does not exist on type 'string'. +!!! error TS2339: Property 'a' does not exist on type 'String'. ~ -!!! error TS2339: Property 'b' does not exist on type 'string'. \ No newline at end of file +!!! error TS2339: Property 'b' does not exist on type 'String'. \ No newline at end of file diff --git a/tests/baselines/reference/jsdocParamTag2.errors.txt b/tests/baselines/reference/jsdocParamTag2.errors.txt index 287846cc0a121..cbf6140ee7d86 100644 --- a/tests/baselines/reference/jsdocParamTag2.errors.txt +++ b/tests/baselines/reference/jsdocParamTag2.errors.txt @@ -1,6 +1,6 @@ tests/cases/conformance/jsdoc/0.js(56,20): error TS8024: JSDoc '@param' tag has name 'obj', but there is no parameter with that name. -tests/cases/conformance/jsdoc/0.js(61,19): error TS2339: Property 'a' does not exist on type 'string'. -tests/cases/conformance/jsdoc/0.js(61,22): error TS2339: Property 'b' does not exist on type 'string'. +tests/cases/conformance/jsdoc/0.js(61,19): error TS2339: Property 'a' does not exist on type 'String'. +tests/cases/conformance/jsdoc/0.js(61,22): error TS2339: Property 'b' does not exist on type 'String'. tests/cases/conformance/jsdoc/0.js(63,20): error TS8024: JSDoc '@param' tag has name 'y', but there is no parameter with that name. @@ -69,9 +69,9 @@ tests/cases/conformance/jsdoc/0.js(63,20): error TS8024: JSDoc '@param' tag has */ function bad1(x, {a, b}) {} ~ -!!! error TS2339: Property 'a' does not exist on type 'string'. +!!! error TS2339: Property 'a' does not exist on type 'String'. ~ -!!! error TS2339: Property 'b' does not exist on type 'string'. +!!! error TS2339: Property 'b' does not exist on type 'String'. /** * @param {string} y - here, y's type gets ignored but obj's is fine ~ diff --git a/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt b/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt index 13acc44c39758..c584dba6462f2 100644 --- a/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt +++ b/tests/baselines/reference/nonPrimitiveAccessProperty.errors.txt @@ -1,5 +1,5 @@ tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(3,3): error TS2339: Property 'nonExist' does not exist on type 'object'. -tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(5,7): error TS2339: Property 'destructuring' does not exist on type 'object'. +tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(5,7): error TS2339: Property 'destructuring' does not exist on type '{}'. ==== tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts (2 errors) ==== @@ -11,6 +11,6 @@ tests/cases/conformance/types/nonPrimitive/nonPrimitiveAccessProperty.ts(5,7): e var { destructuring } = a; // error ~~~~~~~~~~~~~ -!!! error TS2339: Property 'destructuring' does not exist on type 'object'. +!!! error TS2339: Property 'destructuring' does not exist on type '{}'. var { ...rest } = a; // ok \ No newline at end of file diff --git a/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt b/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt index d9b229e2e9f8b..f7f2ee3db16d5 100644 --- a/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt +++ b/tests/baselines/reference/nonPrimitiveIndexingWithForInNoImplicitAny.errors.txt @@ -1,4 +1,4 @@ -tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplicitAny.ts(4,17): error TS7017: Element implicitly has an 'any' type because type 'object' has no index signature. +tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplicitAny.ts(4,17): error TS7017: Element implicitly has an 'any' type because type '{}' has no index signature. ==== tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplicitAny.ts (1 errors) ==== @@ -7,6 +7,6 @@ tests/cases/conformance/types/nonPrimitive/nonPrimitiveIndexingWithForInNoImplic for (var key in a) { var value = a[key]; // error ~~~~~~ -!!! error TS7017: Element implicitly has an 'any' type because type 'object' has no index signature. +!!! error TS7017: Element implicitly has an 'any' type because type '{}' has no index signature. } \ No newline at end of file diff --git a/tests/baselines/reference/objectRest.errors.txt b/tests/baselines/reference/objectRest.errors.txt index f1505bb3ea56f..709a2d3cdd6c7 100644 --- a/tests/baselines/reference/objectRest.errors.txt +++ b/tests/baselines/reference/objectRest.errors.txt @@ -1,5 +1,5 @@ -tests/cases/conformance/types/rest/objectRest.ts(7,12): error TS2339: Property '0' does not exist on type 'string'. -tests/cases/conformance/types/rest/objectRest.ts(7,20): error TS2339: Property '1' does not exist on type 'string'. +tests/cases/conformance/types/rest/objectRest.ts(7,12): error TS2339: Property '0' does not exist on type 'String'. +tests/cases/conformance/types/rest/objectRest.ts(7,20): error TS2339: Property '1' does not exist on type 'String'. tests/cases/conformance/types/rest/objectRest.ts(43,8): error TS2537: Type '{ a: number; b: string; }' has no matching index signature for type 'string'. tests/cases/conformance/types/rest/objectRest.ts(43,35): error TS2537: Type '{ a: number; b: string; }' has no matching index signature for type 'string'. @@ -13,9 +13,9 @@ tests/cases/conformance/types/rest/objectRest.ts(43,35): error TS2537: Type '{ a var { 'b': renamed, ...justA } = o; var { b: { '0': n, '1': oooo }, ...justA } = o; ~~~ -!!! error TS2339: Property '0' does not exist on type 'string'. +!!! error TS2339: Property '0' does not exist on type 'String'. ~~~ -!!! error TS2339: Property '1' does not exist on type 'string'. +!!! error TS2339: Property '1' does not exist on type 'String'. let o2 = { c: 'terrible idea?', d: 'yes' }; var { d: renamed, ...d } = o2; From 96ad54c44827e6e789b664f710cf36624f7b5775 Mon Sep 17 00:00:00 2001 From: Wesley Wigham Date: Thu, 1 Nov 2018 13:25:03 -0700 Subject: [PATCH 4/4] Use `checkComputedPropertyName` --- src/compiler/checker.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 5b10aceca9ed4..3f071569e9315 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -4659,7 +4659,7 @@ namespace ts { // Use explicitly specified property name ({ p: xxx } form), or otherwise the implied name ({ p } form) const name = declaration.propertyName || declaration.name; const exprType = isComputedPropertyName(name) - ? checkExpression(name.expression) + ? checkComputedPropertyName(name) : isIdentifier(name) ? getLiteralType(unescapeLeadingUnderscores(name.escapedText)) : checkExpression(name);