diff --git a/_packages/native-preview/src/enums/objectFlags.enum.ts b/_packages/native-preview/src/enums/objectFlags.enum.ts index 414e4d012e8..8a508ff7309 100644 --- a/_packages/native-preview/src/enums/objectFlags.enum.ts +++ b/_packages/native-preview/src/enums/objectFlags.enum.ts @@ -37,6 +37,7 @@ export enum ObjectFlags { IdenticalBaseTypeCalculated = 1 << 27, IdenticalBaseTypeExists = 1 << 28, UnresolvedMembers = 1 << 29, + FromTypeNode = 1 << 30, IsGenericTypeComputed = 1 << 22, IsGenericObjectType = 1 << 23, IsGenericIndexType = 1 << 24, diff --git a/_packages/native-preview/src/enums/objectFlags.ts b/_packages/native-preview/src/enums/objectFlags.ts index 9e81863658c..9882e266a60 100644 --- a/_packages/native-preview/src/enums/objectFlags.ts +++ b/_packages/native-preview/src/enums/objectFlags.ts @@ -37,6 +37,7 @@ export var ObjectFlags: any; ObjectFlags[ObjectFlags["IdenticalBaseTypeCalculated"] = 134217728] = "IdenticalBaseTypeCalculated"; ObjectFlags[ObjectFlags["IdenticalBaseTypeExists"] = 268435456] = "IdenticalBaseTypeExists"; ObjectFlags[ObjectFlags["UnresolvedMembers"] = 536870912] = "UnresolvedMembers"; + ObjectFlags[ObjectFlags["FromTypeNode"] = 1073741824] = "FromTypeNode"; ObjectFlags[ObjectFlags["IsGenericTypeComputed"] = 4194304] = "IsGenericTypeComputed"; ObjectFlags[ObjectFlags["IsGenericObjectType"] = 8388608] = "IsGenericObjectType"; ObjectFlags[ObjectFlags["IsGenericIndexType"] = 16777216] = "IsGenericIndexType"; diff --git a/internal/checker/checker.go b/internal/checker/checker.go index fb7db6ec85e..2dc7581b4aa 100644 --- a/internal/checker/checker.go +++ b/internal/checker/checker.go @@ -22741,7 +22741,7 @@ func (c *Checker) getTypeFromClassOrInterfaceReference(node *ast.Node, symbol *a // of the class or interface. localTypeArguments := c.fillMissingTypeArguments(c.getTypeArgumentsFromNode(node), typeParameters, minTypeArgumentCount, isJs) typeArguments := append(d.OuterTypeParameters(), localTypeArguments...) - return c.createTypeReference(t, typeArguments) + return c.createTypeReferenceEx(t, typeArguments, ObjectFlagsFromTypeNode) } if c.checkNoTypeArguments(node, symbol) { return t @@ -22836,11 +22836,11 @@ func (c *Checker) createNormalizedTypeReference(target *Type, typeArguments []*T return c.createTypeReference(target, typeArguments) } -func (c *Checker) createNormalizedTupleType(target *Type, elementTypes []*Type) *Type { +func (c *Checker) createNormalizedTupleTypeEx(target *Type, elementTypes []*Type, objectFlags ObjectFlags) *Type { d := target.AsTupleType() if d.combinedFlags&ElementFlagsNonRequired == 0 { // No need to normalize when we only have regular required elements - return c.createTypeReference(target, elementTypes) + return c.createTypeReferenceEx(target, elementTypes, objectFlags) } if d.combinedFlags&ElementFlagsVariadic != 0 { for i, e := range elementTypes { @@ -22854,7 +22854,7 @@ func (c *Checker) createNormalizedTupleType(target *Type, elementTypes []*Type) }) if c.checkCrossProductUnion(checkTypes) { return c.mapType(e, func(t *Type) *Type { - return c.createNormalizedTupleType(target, core.ReplaceElement(elementTypes, i, t)) + return c.createNormalizedTupleTypeEx(target, core.ReplaceElement(elementTypes, i, t), objectFlags) }) } } @@ -22879,11 +22879,15 @@ func (c *Checker) createNormalizedTupleType(target *Type, elementTypes []*Type) case tupleTarget == c.emptyGenericType: return c.emptyObjectType case len(n.types) != 0: - return c.createTypeReference(tupleTarget, n.types) + return c.createTypeReferenceEx(tupleTarget, n.types, objectFlags) } return tupleTarget } +func (c *Checker) createNormalizedTupleType(target *Type, elementTypes []*Type) *Type { + return c.createNormalizedTupleTypeEx(target, elementTypes, ObjectFlagsNone) +} + type TupleNormalizer struct { c *Checker types []*Type @@ -23662,7 +23666,11 @@ func (c *Checker) getTypeFromArrayOrTupleTypeNode(node *ast.Node) *Type { } else { elementTypes = core.Map(node.Elements(), c.getTypeFromTypeNode) } - links.resolvedType = c.createNormalizedTypeReference(target, elementTypes) + if target.objectFlags&ObjectFlagsTuple != 0 { + links.resolvedType = c.createNormalizedTupleTypeEx(target, elementTypes, ObjectFlagsFromTypeNode) + } else { + links.resolvedType = c.createTypeReferenceEx(target, elementTypes, ObjectFlagsFromTypeNode) + } } } return links.resolvedType @@ -24625,13 +24633,16 @@ func (c *Checker) tryCreateTypeReference(target *Type, typeArguments []*Type) *T } func (c *Checker) createTypeReference(target *Type, typeArguments []*Type) *Type { + return c.createTypeReferenceEx(target, typeArguments, ObjectFlagsNone) +} + +func (c *Checker) createTypeReferenceEx(target *Type, typeArguments []*Type, objectFlags ObjectFlags) *Type { id := getTypeListKey(typeArguments) intf := target.AsInterfaceType() if t, ok := intf.instantiations[id]; ok { return t } - t := c.newObjectType(ObjectFlagsReference, target.symbol) - t.objectFlags |= c.getPropagatingFlagsOfTypes(typeArguments, TypeFlagsNone) + t := c.newObjectType(ObjectFlagsReference|objectFlags|c.getPropagatingFlagsOfTypes(typeArguments, TypeFlagsNone), target.symbol) d := t.AsTypeReference() d.target = target d.resolvedTypeArguments = typeArguments diff --git a/internal/checker/relater.go b/internal/checker/relater.go index f5b0b751ed8..3009811efaf 100644 --- a/internal/checker/relater.go +++ b/internal/checker/relater.go @@ -839,12 +839,14 @@ func getRecursionIdentity(t *Type) RecursionId { // unique AST node. return asRecursionId(t.AsTypeReference().node) } - if t.symbol != nil && !(t.objectFlags&ObjectFlagsAnonymous != 0 && t.symbol.Flags&ast.SymbolFlagsClass != 0) { + if t.symbol != nil && !(t.objectFlags&ObjectFlagsAnonymous != 0 && t.symbol.Flags&ast.SymbolFlagsClass != 0) && t.objectFlags&ObjectFlagsFromTypeNode == 0 { // We track object types that have a symbol by that symbol (representing the origin of the type), but - // exclude the static side of a class since it shares its symbol with the instance side. + // exclude the static sides of classes (since they share their symbols with the instance sides) and type + // references that originate in resolution of AST type nodes (since such type nodes cannot be the source + // of generative recursion without first being instantiated). return asRecursionId(t.symbol) } - if isTupleType(t) { + if isTupleType(t) && t.objectFlags&ObjectFlagsFromTypeNode == 0 { return asRecursionId(t.Target()) } } diff --git a/internal/checker/types.go b/internal/checker/types.go index af5aadb63cf..6a9ec658777 100644 --- a/internal/checker/types.go +++ b/internal/checker/types.go @@ -498,6 +498,7 @@ const ( ObjectFlagsIdenticalBaseTypeCalculated = 1 << 27 // has had `getSingleBaseForNonAugmentingSubtype` invoked on it already ObjectFlagsIdenticalBaseTypeExists = 1 << 28 // has a defined cachedEquivalentBaseType member ObjectFlagsUnresolvedMembers = 1 << 29 // Member resolution in process + ObjectFlagsFromTypeNode = 1 << 30 // Originates in resolution of AST type node // Flags that require TypeFlags.UnionOrIntersection or TypeFlags.Substitution ObjectFlagsIsGenericTypeComputed = 1 << 22 // IsGenericObjectType flag has been computed ObjectFlagsIsGenericObjectType = 1 << 23 // Union or intersection contains generic object type diff --git a/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.errors.txt b/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.errors.txt new file mode 100644 index 00000000000..cfc396b8667 --- /dev/null +++ b/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.errors.txt @@ -0,0 +1,64 @@ +deeplyNestedArrayTypes.ts(34,5): error TS2322: Type 'B.Outer' is not assignable to type 'A.Outer'. + Types of property 'inners' are incompatible. + Type 'B.Inner[]' is not assignable to type 'A.Inner[]'. + Type 'B.Inner' is not assignable to type 'A.Inner'. + Types of property 'mids' are incompatible. + Type 'B.Mid[]' is not assignable to type 'A.Mid[]'. + Type 'B.Mid' is not assignable to type 'A.Mid'. + Types of property 'leaves' are incompatible. + Type 'B.Leaf[]' is not assignable to type 'A.Leaf[]'. + Type 'B.Leaf' is not assignable to type 'A.Leaf'. + Types of property 'id' are incompatible. + Type 'number' is not assignable to type 'string'. + + +==== deeplyNestedArrayTypes.ts (1 errors) ==== + // https://github.com/microsoft/typescript-go/issues/3426 + + namespace A { + export type Outer = { + inners: Inner[]; + } + export type Inner = { + mids: Mid[]; + } + export type Mid = { + leaves: Leaf[]; + } + export type Leaf = { + id: string; + } + } + + namespace B { + export type Outer = { + inners: Inner[]; + } + export type Inner = { + mids: Mid[]; + } + export type Mid = { + leaves: Leaf[]; + } + export type Leaf = { + id: number; + } + } + + function test(a: A.Outer, b: B.Outer) { + a = b + ~ +!!! error TS2322: Type 'B.Outer' is not assignable to type 'A.Outer'. +!!! error TS2322: Types of property 'inners' are incompatible. +!!! error TS2322: Type 'B.Inner[]' is not assignable to type 'A.Inner[]'. +!!! error TS2322: Type 'B.Inner' is not assignable to type 'A.Inner'. +!!! error TS2322: Types of property 'mids' are incompatible. +!!! error TS2322: Type 'B.Mid[]' is not assignable to type 'A.Mid[]'. +!!! error TS2322: Type 'B.Mid' is not assignable to type 'A.Mid'. +!!! error TS2322: Types of property 'leaves' are incompatible. +!!! error TS2322: Type 'B.Leaf[]' is not assignable to type 'A.Leaf[]'. +!!! error TS2322: Type 'B.Leaf' is not assignable to type 'A.Leaf'. +!!! error TS2322: Types of property 'id' are incompatible. +!!! error TS2322: Type 'number' is not assignable to type 'string'. + } + \ No newline at end of file diff --git a/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.symbols b/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.symbols new file mode 100644 index 00000000000..d52544ad6d4 --- /dev/null +++ b/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.symbols @@ -0,0 +1,83 @@ +//// [tests/cases/compiler/deeplyNestedArrayTypes.ts] //// + +=== deeplyNestedArrayTypes.ts === +// https://github.com/microsoft/typescript-go/issues/3426 + +namespace A { +>A : Symbol(A, Decl(deeplyNestedArrayTypes.ts, 0, 0)) + + export type Outer = { +>Outer : Symbol(Outer, Decl(deeplyNestedArrayTypes.ts, 2, 13)) + + inners: Inner[]; +>inners : Symbol(inners, Decl(deeplyNestedArrayTypes.ts, 3, 25)) +>Inner : Symbol(Inner, Decl(deeplyNestedArrayTypes.ts, 5, 5)) + } + export type Inner = { +>Inner : Symbol(Inner, Decl(deeplyNestedArrayTypes.ts, 5, 5)) + + mids: Mid[]; +>mids : Symbol(mids, Decl(deeplyNestedArrayTypes.ts, 6, 25)) +>Mid : Symbol(Mid, Decl(deeplyNestedArrayTypes.ts, 8, 5)) + } + export type Mid = { +>Mid : Symbol(Mid, Decl(deeplyNestedArrayTypes.ts, 8, 5)) + + leaves: Leaf[]; +>leaves : Symbol(leaves, Decl(deeplyNestedArrayTypes.ts, 9, 23)) +>Leaf : Symbol(Leaf, Decl(deeplyNestedArrayTypes.ts, 11, 5)) + } + export type Leaf = { +>Leaf : Symbol(Leaf, Decl(deeplyNestedArrayTypes.ts, 11, 5)) + + id: string; +>id : Symbol(id, Decl(deeplyNestedArrayTypes.ts, 12, 24)) + } +} + +namespace B { +>B : Symbol(B, Decl(deeplyNestedArrayTypes.ts, 15, 1)) + + export type Outer = { +>Outer : Symbol(Outer, Decl(deeplyNestedArrayTypes.ts, 17, 13)) + + inners: Inner[]; +>inners : Symbol(inners, Decl(deeplyNestedArrayTypes.ts, 18, 25)) +>Inner : Symbol(Inner, Decl(deeplyNestedArrayTypes.ts, 20, 5)) + } + export type Inner = { +>Inner : Symbol(Inner, Decl(deeplyNestedArrayTypes.ts, 20, 5)) + + mids: Mid[]; +>mids : Symbol(mids, Decl(deeplyNestedArrayTypes.ts, 21, 25)) +>Mid : Symbol(Mid, Decl(deeplyNestedArrayTypes.ts, 23, 5)) + } + export type Mid = { +>Mid : Symbol(Mid, Decl(deeplyNestedArrayTypes.ts, 23, 5)) + + leaves: Leaf[]; +>leaves : Symbol(leaves, Decl(deeplyNestedArrayTypes.ts, 24, 23)) +>Leaf : Symbol(Leaf, Decl(deeplyNestedArrayTypes.ts, 26, 5)) + } + export type Leaf = { +>Leaf : Symbol(Leaf, Decl(deeplyNestedArrayTypes.ts, 26, 5)) + + id: number; +>id : Symbol(id, Decl(deeplyNestedArrayTypes.ts, 27, 24)) + } +} + +function test(a: A.Outer, b: B.Outer) { +>test : Symbol(test, Decl(deeplyNestedArrayTypes.ts, 30, 1)) +>a : Symbol(a, Decl(deeplyNestedArrayTypes.ts, 32, 14)) +>A : Symbol(A, Decl(deeplyNestedArrayTypes.ts, 0, 0)) +>Outer : Symbol(A.Outer, Decl(deeplyNestedArrayTypes.ts, 2, 13)) +>b : Symbol(b, Decl(deeplyNestedArrayTypes.ts, 32, 25)) +>B : Symbol(B, Decl(deeplyNestedArrayTypes.ts, 15, 1)) +>Outer : Symbol(B.Outer, Decl(deeplyNestedArrayTypes.ts, 17, 13)) + + a = b +>a : Symbol(a, Decl(deeplyNestedArrayTypes.ts, 32, 14)) +>b : Symbol(b, Decl(deeplyNestedArrayTypes.ts, 32, 25)) +} + diff --git a/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.types b/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.types new file mode 100644 index 00000000000..34130aeda3d --- /dev/null +++ b/testdata/baselines/reference/compiler/deeplyNestedArrayTypes.types @@ -0,0 +1,72 @@ +//// [tests/cases/compiler/deeplyNestedArrayTypes.ts] //// + +=== deeplyNestedArrayTypes.ts === +// https://github.com/microsoft/typescript-go/issues/3426 + +namespace A { + export type Outer = { +>Outer : Outer + + inners: Inner[]; +>inners : Inner[] + } + export type Inner = { +>Inner : Inner + + mids: Mid[]; +>mids : Mid[] + } + export type Mid = { +>Mid : Mid + + leaves: Leaf[]; +>leaves : Leaf[] + } + export type Leaf = { +>Leaf : Leaf + + id: string; +>id : string + } +} + +namespace B { + export type Outer = { +>Outer : Outer + + inners: Inner[]; +>inners : Inner[] + } + export type Inner = { +>Inner : Inner + + mids: Mid[]; +>mids : Mid[] + } + export type Mid = { +>Mid : Mid + + leaves: Leaf[]; +>leaves : Leaf[] + } + export type Leaf = { +>Leaf : Leaf + + id: number; +>id : number + } +} + +function test(a: A.Outer, b: B.Outer) { +>test : (a: A.Outer, b: B.Outer) => void +>a : A.Outer +>A : any +>b : B.Outer +>B : any + + a = b +>a = b : B.Outer +>a : A.Outer +>b : B.Outer +} + diff --git a/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.errors.txt b/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.errors.txt new file mode 100644 index 00000000000..bbd96493822 --- /dev/null +++ b/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.errors.txt @@ -0,0 +1,64 @@ +deeplyNestedTupleTypes.ts(34,3): error TS2322: Type 'B.Outer' is not assignable to type 'A.Outer'. + Types of property 'inners' are incompatible. + Type '[B.Inner]' is not assignable to type '[A.Inner]'. + Type 'B.Inner' is not assignable to type 'A.Inner'. + Types of property 'mids' are incompatible. + Type '[B.Mid]' is not assignable to type '[A.Mid]'. + Type 'B.Mid' is not assignable to type 'A.Mid'. + Types of property 'leaves' are incompatible. + Type '[B.Leaf]' is not assignable to type '[A.Leaf]'. + Type 'B.Leaf' is not assignable to type 'A.Leaf'. + Types of property 'id' are incompatible. + Type 'number' is not assignable to type 'string'. + + +==== deeplyNestedTupleTypes.ts (1 errors) ==== + // https://github.com/microsoft/typescript-go/issues/3426 + + namespace A { + export type Outer = { + inners: [Inner]; + }; + export type Inner = { + mids: [Mid]; + }; + export type Mid = { + leaves: [Leaf]; + }; + export type Leaf = { + id: string; + }; + } + + namespace B { + export type Outer = { + inners: [Inner]; + }; + export type Inner = { + mids: [Mid]; + }; + export type Mid = { + leaves: [Leaf]; + }; + export type Leaf = { + id: number; + }; + } + + function test(a: A.Outer, b: B.Outer) { + a = b; + ~ +!!! error TS2322: Type 'B.Outer' is not assignable to type 'A.Outer'. +!!! error TS2322: Types of property 'inners' are incompatible. +!!! error TS2322: Type '[B.Inner]' is not assignable to type '[A.Inner]'. +!!! error TS2322: Type 'B.Inner' is not assignable to type 'A.Inner'. +!!! error TS2322: Types of property 'mids' are incompatible. +!!! error TS2322: Type '[B.Mid]' is not assignable to type '[A.Mid]'. +!!! error TS2322: Type 'B.Mid' is not assignable to type 'A.Mid'. +!!! error TS2322: Types of property 'leaves' are incompatible. +!!! error TS2322: Type '[B.Leaf]' is not assignable to type '[A.Leaf]'. +!!! error TS2322: Type 'B.Leaf' is not assignable to type 'A.Leaf'. +!!! error TS2322: Types of property 'id' are incompatible. +!!! error TS2322: Type 'number' is not assignable to type 'string'. + } + \ No newline at end of file diff --git a/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.symbols b/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.symbols new file mode 100644 index 00000000000..705db6769f0 --- /dev/null +++ b/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.symbols @@ -0,0 +1,91 @@ +//// [tests/cases/compiler/deeplyNestedTupleTypes.ts] //// + +=== deeplyNestedTupleTypes.ts === +// https://github.com/microsoft/typescript-go/issues/3426 + +namespace A { +>A : Symbol(A, Decl(deeplyNestedTupleTypes.ts, 0, 0)) + + export type Outer = { +>Outer : Symbol(Outer, Decl(deeplyNestedTupleTypes.ts, 2, 13)) + + inners: [Inner]; +>inners : Symbol(inners, Decl(deeplyNestedTupleTypes.ts, 3, 23)) +>Inner : Symbol(Inner, Decl(deeplyNestedTupleTypes.ts, 5, 4)) + + }; + export type Inner = { +>Inner : Symbol(Inner, Decl(deeplyNestedTupleTypes.ts, 5, 4)) + + mids: [Mid]; +>mids : Symbol(mids, Decl(deeplyNestedTupleTypes.ts, 6, 23)) +>Mid : Symbol(Mid, Decl(deeplyNestedTupleTypes.ts, 8, 4)) + + }; + export type Mid = { +>Mid : Symbol(Mid, Decl(deeplyNestedTupleTypes.ts, 8, 4)) + + leaves: [Leaf]; +>leaves : Symbol(leaves, Decl(deeplyNestedTupleTypes.ts, 9, 21)) +>Leaf : Symbol(Leaf, Decl(deeplyNestedTupleTypes.ts, 11, 4)) + + }; + export type Leaf = { +>Leaf : Symbol(Leaf, Decl(deeplyNestedTupleTypes.ts, 11, 4)) + + id: string; +>id : Symbol(id, Decl(deeplyNestedTupleTypes.ts, 12, 22)) + + }; +} + +namespace B { +>B : Symbol(B, Decl(deeplyNestedTupleTypes.ts, 15, 1)) + + export type Outer = { +>Outer : Symbol(Outer, Decl(deeplyNestedTupleTypes.ts, 17, 13)) + + inners: [Inner]; +>inners : Symbol(inners, Decl(deeplyNestedTupleTypes.ts, 18, 23)) +>Inner : Symbol(Inner, Decl(deeplyNestedTupleTypes.ts, 20, 4)) + + }; + export type Inner = { +>Inner : Symbol(Inner, Decl(deeplyNestedTupleTypes.ts, 20, 4)) + + mids: [Mid]; +>mids : Symbol(mids, Decl(deeplyNestedTupleTypes.ts, 21, 23)) +>Mid : Symbol(Mid, Decl(deeplyNestedTupleTypes.ts, 23, 4)) + + }; + export type Mid = { +>Mid : Symbol(Mid, Decl(deeplyNestedTupleTypes.ts, 23, 4)) + + leaves: [Leaf]; +>leaves : Symbol(leaves, Decl(deeplyNestedTupleTypes.ts, 24, 21)) +>Leaf : Symbol(Leaf, Decl(deeplyNestedTupleTypes.ts, 26, 4)) + + }; + export type Leaf = { +>Leaf : Symbol(Leaf, Decl(deeplyNestedTupleTypes.ts, 26, 4)) + + id: number; +>id : Symbol(id, Decl(deeplyNestedTupleTypes.ts, 27, 22)) + + }; +} + +function test(a: A.Outer, b: B.Outer) { +>test : Symbol(test, Decl(deeplyNestedTupleTypes.ts, 30, 1)) +>a : Symbol(a, Decl(deeplyNestedTupleTypes.ts, 32, 14)) +>A : Symbol(A, Decl(deeplyNestedTupleTypes.ts, 0, 0)) +>Outer : Symbol(A.Outer, Decl(deeplyNestedTupleTypes.ts, 2, 13)) +>b : Symbol(b, Decl(deeplyNestedTupleTypes.ts, 32, 25)) +>B : Symbol(B, Decl(deeplyNestedTupleTypes.ts, 15, 1)) +>Outer : Symbol(B.Outer, Decl(deeplyNestedTupleTypes.ts, 17, 13)) + + a = b; +>a : Symbol(a, Decl(deeplyNestedTupleTypes.ts, 32, 14)) +>b : Symbol(b, Decl(deeplyNestedTupleTypes.ts, 32, 25)) +} + diff --git a/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.types b/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.types new file mode 100644 index 00000000000..6b37971bf35 --- /dev/null +++ b/testdata/baselines/reference/compiler/deeplyNestedTupleTypes.types @@ -0,0 +1,80 @@ +//// [tests/cases/compiler/deeplyNestedTupleTypes.ts] //// + +=== deeplyNestedTupleTypes.ts === +// https://github.com/microsoft/typescript-go/issues/3426 + +namespace A { + export type Outer = { +>Outer : Outer + + inners: [Inner]; +>inners : [Inner] + + }; + export type Inner = { +>Inner : Inner + + mids: [Mid]; +>mids : [Mid] + + }; + export type Mid = { +>Mid : Mid + + leaves: [Leaf]; +>leaves : [Leaf] + + }; + export type Leaf = { +>Leaf : Leaf + + id: string; +>id : string + + }; +} + +namespace B { + export type Outer = { +>Outer : Outer + + inners: [Inner]; +>inners : [Inner] + + }; + export type Inner = { +>Inner : Inner + + mids: [Mid]; +>mids : [Mid] + + }; + export type Mid = { +>Mid : Mid + + leaves: [Leaf]; +>leaves : [Leaf] + + }; + export type Leaf = { +>Leaf : Leaf + + id: number; +>id : number + + }; +} + +function test(a: A.Outer, b: B.Outer) { +>test : (a: A.Outer, b: B.Outer) => void +>a : A.Outer +>A : any +>b : B.Outer +>B : any + + a = b; +>a = b : B.Outer +>a : A.Outer +>b : B.Outer +} + diff --git a/testdata/tests/cases/compiler/deeplyNestedArrayTypes.ts b/testdata/tests/cases/compiler/deeplyNestedArrayTypes.ts new file mode 100644 index 00000000000..d8bb95e7155 --- /dev/null +++ b/testdata/tests/cases/compiler/deeplyNestedArrayTypes.ts @@ -0,0 +1,37 @@ +// @noEmit: true + +// https://github.com/microsoft/typescript-go/issues/3426 + +namespace A { + export type Outer = { + inners: Inner[]; + } + export type Inner = { + mids: Mid[]; + } + export type Mid = { + leaves: Leaf[]; + } + export type Leaf = { + id: string; + } +} + +namespace B { + export type Outer = { + inners: Inner[]; + } + export type Inner = { + mids: Mid[]; + } + export type Mid = { + leaves: Leaf[]; + } + export type Leaf = { + id: number; + } +} + +function test(a: A.Outer, b: B.Outer) { + a = b +} diff --git a/testdata/tests/cases/compiler/deeplyNestedTupleTypes.ts b/testdata/tests/cases/compiler/deeplyNestedTupleTypes.ts new file mode 100644 index 00000000000..e2265e3e9f8 --- /dev/null +++ b/testdata/tests/cases/compiler/deeplyNestedTupleTypes.ts @@ -0,0 +1,37 @@ +// @noEmit: true + +// https://github.com/microsoft/typescript-go/issues/3426 + +namespace A { + export type Outer = { + inners: [Inner]; + }; + export type Inner = { + mids: [Mid]; + }; + export type Mid = { + leaves: [Leaf]; + }; + export type Leaf = { + id: string; + }; +} + +namespace B { + export type Outer = { + inners: [Inner]; + }; + export type Inner = { + mids: [Mid]; + }; + export type Mid = { + leaves: [Leaf]; + }; + export type Leaf = { + id: number; + }; +} + +function test(a: A.Outer, b: B.Outer) { + a = b; +}