Filter symbol property names out of index signature assignability checks (#22398)
This commit is contained in:
parent
55bffba5fd
commit
95862880fb
6 changed files with 124 additions and 2 deletions
|
@ -8008,10 +8008,10 @@ namespace ts {
|
|||
}
|
||||
|
||||
function getLiteralTypeFromPropertyName(prop: Symbol) {
|
||||
const links = getSymbolLinks(prop);
|
||||
const links = getSymbolLinks(getLateBoundSymbol(prop));
|
||||
if (!links.nameType) {
|
||||
if (links.target) {
|
||||
Debug.assert(links.target.escapedName === prop.escapedName, "Target symbol and symbol do not have the same name");
|
||||
Debug.assert(links.target.escapedName === prop.escapedName || links.target.escapedName === InternalSymbolName.Computed, "Target symbol and symbol do not have the same name");
|
||||
links.nameType = getLiteralTypeFromPropertyName(links.target);
|
||||
}
|
||||
else {
|
||||
|
@ -10558,6 +10558,11 @@ namespace ts {
|
|||
if (isIgnoredJsxProperty(source, prop, /*targetMemberType*/ undefined)) {
|
||||
continue;
|
||||
}
|
||||
// Skip over symbol-named members
|
||||
const nameType = getLiteralTypeFromPropertyName(prop);
|
||||
if (nameType !== undefined && !(isRelatedTo(nameType, stringType) || isRelatedTo(nameType, numberType))) {
|
||||
continue;
|
||||
}
|
||||
if (kind === IndexKind.String || isNumericLiteralName(prop.escapedName)) {
|
||||
const related = isRelatedTo(getTypeOfSymbol(prop), target, reportErrors);
|
||||
if (!related) {
|
||||
|
|
|
@ -0,0 +1,21 @@
|
|||
tests/cases/compiler/uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts(10,5): error TS2322: Type '{ [SYM]: "str"; }' is not assignable to type 'I'.
|
||||
Types of property '[SYM]' are incompatible.
|
||||
Type '"str"' is not assignable to type '"sym"'.
|
||||
|
||||
|
||||
==== tests/cases/compiler/uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts (1 errors) ====
|
||||
// https://github.com/Microsoft/TypeScript/issues/21962
|
||||
export const SYM = Symbol('a unique symbol');
|
||||
|
||||
export interface I {
|
||||
[SYM]: 'sym';
|
||||
[x: string]: 'str';
|
||||
}
|
||||
|
||||
let a: I = {[SYM]: 'sym'}; // Expect ok
|
||||
let b: I = {[SYM]: 'str'}; // Expect error
|
||||
~
|
||||
!!! error TS2322: Type '{ [SYM]: "str"; }' is not assignable to type 'I'.
|
||||
!!! error TS2322: Types of property '[SYM]' are incompatible.
|
||||
!!! error TS2322: Type '"str"' is not assignable to type '"sym"'.
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
//// [uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts]
|
||||
// https://github.com/Microsoft/TypeScript/issues/21962
|
||||
export const SYM = Symbol('a unique symbol');
|
||||
|
||||
export interface I {
|
||||
[SYM]: 'sym';
|
||||
[x: string]: 'str';
|
||||
}
|
||||
|
||||
let a: I = {[SYM]: 'sym'}; // Expect ok
|
||||
let b: I = {[SYM]: 'str'}; // Expect error
|
||||
|
||||
|
||||
//// [uniqueSymbolAllowsIndexInObjectWithIndexSignature.js]
|
||||
"use strict";
|
||||
exports.__esModule = true;
|
||||
// https://github.com/Microsoft/TypeScript/issues/21962
|
||||
exports.SYM = Symbol('a unique symbol');
|
||||
var a = (_a = {}, _a[exports.SYM] = 'sym', _a); // Expect ok
|
||||
var b = (_b = {}, _b[exports.SYM] = 'str', _b); // Expect error
|
||||
var _a, _b;
|
|
@ -0,0 +1,29 @@
|
|||
=== tests/cases/compiler/uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts ===
|
||||
// https://github.com/Microsoft/TypeScript/issues/21962
|
||||
export const SYM = Symbol('a unique symbol');
|
||||
>SYM : Symbol(SYM, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 1, 12))
|
||||
>Symbol : Symbol(Symbol, Decl(lib.es2015.symbol.wellknown.d.ts, --, --), Decl(lib.es2015.symbol.d.ts, --, --), Decl(lib.es2015.symbol.d.ts, --, --))
|
||||
|
||||
export interface I {
|
||||
>I : Symbol(I, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 1, 45))
|
||||
|
||||
[SYM]: 'sym';
|
||||
>[SYM] : Symbol(I[SYM], Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 3, 20))
|
||||
>SYM : Symbol(SYM, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 1, 12))
|
||||
|
||||
[x: string]: 'str';
|
||||
>x : Symbol(x, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 5, 3))
|
||||
}
|
||||
|
||||
let a: I = {[SYM]: 'sym'}; // Expect ok
|
||||
>a : Symbol(a, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 8, 3))
|
||||
>I : Symbol(I, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 1, 45))
|
||||
>[SYM] : Symbol([SYM], Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 8, 12))
|
||||
>SYM : Symbol(SYM, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 1, 12))
|
||||
|
||||
let b: I = {[SYM]: 'str'}; // Expect error
|
||||
>b : Symbol(b, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 9, 3))
|
||||
>I : Symbol(I, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 1, 45))
|
||||
>[SYM] : Symbol([SYM], Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 9, 12))
|
||||
>SYM : Symbol(SYM, Decl(uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts, 1, 12))
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
=== tests/cases/compiler/uniqueSymbolAllowsIndexInObjectWithIndexSignature.ts ===
|
||||
// https://github.com/Microsoft/TypeScript/issues/21962
|
||||
export const SYM = Symbol('a unique symbol');
|
||||
>SYM : unique symbol
|
||||
>Symbol('a unique symbol') : unique symbol
|
||||
>Symbol : SymbolConstructor
|
||||
>'a unique symbol' : "a unique symbol"
|
||||
|
||||
export interface I {
|
||||
>I : I
|
||||
|
||||
[SYM]: 'sym';
|
||||
>[SYM] : "sym"
|
||||
>SYM : unique symbol
|
||||
|
||||
[x: string]: 'str';
|
||||
>x : string
|
||||
}
|
||||
|
||||
let a: I = {[SYM]: 'sym'}; // Expect ok
|
||||
>a : I
|
||||
>I : I
|
||||
>{[SYM]: 'sym'} : { [SYM]: "sym"; }
|
||||
>[SYM] : "sym"
|
||||
>SYM : unique symbol
|
||||
>'sym' : "sym"
|
||||
|
||||
let b: I = {[SYM]: 'str'}; // Expect error
|
||||
>b : I
|
||||
>I : I
|
||||
>{[SYM]: 'str'} : { [SYM]: "str"; }
|
||||
>[SYM] : "str"
|
||||
>SYM : unique symbol
|
||||
>'str' : "str"
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
// @lib: es6
|
||||
// https://github.com/Microsoft/TypeScript/issues/21962
|
||||
export const SYM = Symbol('a unique symbol');
|
||||
|
||||
export interface I {
|
||||
[SYM]: 'sym';
|
||||
[x: string]: 'str';
|
||||
}
|
||||
|
||||
let a: I = {[SYM]: 'sym'}; // Expect ok
|
||||
let b: I = {[SYM]: 'str'}; // Expect error
|
Loading…
Reference in a new issue