From 7b40895b2943c9e93647869da2fc4f62bf6eaed9 Mon Sep 17 00:00:00 2001 From: Andrew Casey Date: Fri, 21 Aug 2020 17:39:03 -0700 Subject: [PATCH] Record the recursion ID of each type, if available --- src/compiler/checker.ts | 1 + src/compiler/tracing.ts | 15 +++++++++++++++ src/compiler/types.ts | 1 + 3 files changed, 17 insertions(+) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 45ad4e1f2e5..ff7e456cb6c 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -377,6 +377,7 @@ namespace ts { getMergedSymbol, getDiagnostics, getGlobalDiagnostics, + getRecursionIdentity, getTypeOfSymbolAtLocation: (symbol, locationIn) => { const location = getParseTreeNode(locationIn); return location ? getTypeOfSymbolAtLocation(symbol, location) : errorType; diff --git a/src/compiler/tracing.ts b/src/compiler/tracing.ts index c7f2add068a..cabbb6c810c 100644 --- a/src/compiler/tracing.ts +++ b/src/compiler/tracing.ts @@ -127,6 +127,8 @@ namespace ts.tracing { const typesPath = legend[legend.length - 1].typesPath!; const typesFd = fs.openSync(typesPath, "w"); + const recursionIdentityMap = new Map(); + // Cleverness: no line break here so that the type ID will match the line number fs.writeSync(typesFd, "["); @@ -178,10 +180,23 @@ namespace ts.tracing { }; } + // We can't print out an arbitrary object, so just assign each one a unique number. + // Don't call it an "id" so people don't treat it as a type id. + let recursionToken: number | undefined; + const recursionIdentity = type.checker.getRecursionIdentity(type); + if (recursionIdentity) { + recursionToken = recursionIdentityMap.get(recursionIdentity); + if (!recursionToken) { + recursionToken = recursionIdentityMap.size; + recursionIdentityMap.set(recursionIdentity, recursionToken); + } + } + const descriptor = { id: type.id, intrinsicName: (type as any).intrinsicName, symbolName: symbol?.escapedName && unescapeLeadingUnderscores(symbol.escapedName), + recursionId: recursionToken, unionTypes: (type.flags & TypeFlags.Union) ? (type as UnionType).types?.map(t => t.id) : undefined, intersectionTypes: (type.flags & TypeFlags.Intersection) ? (type as IntersectionType).types.map(t => t.id) : undefined, aliasTypeArguments: type.aliasTypeArguments?.map(t => t.id), diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 5e8ba2786a5..2bfc8e5a5cf 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -4073,6 +4073,7 @@ namespace ts { /* @internal */ getTypeCount(): number; /* @internal */ getInstantiationCount(): number; /* @internal */ getRelationCacheSizes(): { assignable: number, identity: number, subtype: number, strictSubtype: number }; + /* @internal */ getRecursionIdentity(type: Type): object | undefined; /* @internal */ isArrayType(type: Type): boolean; /* @internal */ isTupleType(type: Type): boolean;