@typescript/analyze-trace
Version:
Analyze the output of tsc --generatetrace
201 lines • 9.02 kB
JavaScript
"use strict";
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
function simplifyType(type) {
const processed = simplifyTypeHelper(Object.assign({}, type));
// Normalize the property order
const result = {
id: processed.id,
kind: processed.kind,
name: processed.name,
aliasTypeArguments: processed.aliasTypeArguments,
instantiatedType: processed.instantiatedType,
typeArguments: processed.typeArguments,
};
for (const prop in processed) {
if (!result[prop] && prop !== "location" && prop !== "display") {
result[prop] = processed[prop];
}
}
result["location"] = processed.location;
result["display"] = processed.display;
return result;
}
function simplifyTypeHelper(type) {
var _a, _b, _c, _d, _e, _f, _g;
type.name = type.symbolName;
type.symbolName = undefined;
const isDestructuring = !!type.destructuringPattern;
const node = (_b = (_a = type.destructuringPattern) !== null && _a !== void 0 ? _a : type.referenceLocation) !== null && _b !== void 0 ? _b : type.firstDeclaration;
type.destructuringPattern = undefined;
type.referenceLocation = undefined;
type.firstDeclaration = undefined;
type.location = node && {
path: node.path,
line: (_c = node.start) === null || _c === void 0 ? void 0 : _c.line,
char: (_d = node.start) === null || _d === void 0 ? void 0 : _d.character,
};
const flags = getTypeFlags(type);
type.flags = undefined;
const display = type.display;
type.display = undefined;
type.recursionId = undefined;
if (type.intrinsicName) {
return Object.assign(Object.assign({ kind: "Intrinsic" }, type), { name: type.intrinsicName, intrinsicName: undefined });
}
if (type.unionTypes) {
return Object.assign(Object.assign({ kind: makeAliasedKindIfNamed(type, "Union"), count: type.unionTypes.length, types: type.unionTypes }, type), { unionTypes: undefined });
}
if (type.intersectionTypes) {
return Object.assign(Object.assign({ kind: makeAliasedKindIfNamed(type, "Intersection"), count: type.intersectionTypes.length, types: type.intersectionTypes }, type), { intersectionTypes: undefined });
}
if (type.indexedAccessObjectType) {
return Object.assign({ kind: makeAliasedKindIfNamed(type, "IndexedAccess") }, type);
}
if (type.keyofType) {
return Object.assign({ kind: makeAliasedKindIfNamed(type, "IndexType") }, type);
}
if (type.isTuple) {
return Object.assign(Object.assign({ kind: makeAliasedKindIfNamed(type, "Tuple") }, type), { isTuple: undefined });
}
if (type.conditionalCheckType) {
return Object.assign(Object.assign({ kind: makeAliasedKindIfNamed(type, "ConditionalType") }, type), { conditionalTrueType: type.conditionalTrueType < 0 ? undefined : type.conditionalTrueType, conditionalFalseType: type.conditionalFalseType < 0 ? undefined : type.conditionalFalseType });
}
if (type.substitutionBaseType) {
return Object.assign(Object.assign({ kind: makeAliasedKindIfNamed(type, "SubstitutionType"), originalType: type.substitutionBaseType }, type), { substitutionBaseType: undefined });
}
if (type.reverseMappedSourceType) {
return Object.assign(Object.assign({ kind: makeAliasedKindIfNamed(type, "ReverseMappedType"), sourceType: type.reverseMappedSourceType, mappedType: type.reverseMappedMappedType, constraintType: type.reverseMappedConstraintType }, type), { reverseMappedSourceType: undefined, reverseMappedMappedType: undefined, reverseMappedConstraintType: undefined });
}
if (type.aliasTypeArguments) {
return Object.assign(Object.assign({ kind: "GenericTypeAlias" }, type), { instantiatedType: undefined, aliasedType: type.instantiatedType, aliasedTypeTypeArguments: type.typeArguments });
}
if (type.instantiatedType && ((_e = type.typeArguments) === null || _e === void 0 ? void 0 : _e.length)) {
const instantiatedIsSelf = type.instantiatedType === type.id;
return Object.assign(Object.assign({ kind: instantiatedIsSelf ? "GenericType" : "GenericInstantiation" }, type), { instantiatedType: instantiatedIsSelf ? undefined : type.instantiatedType });
}
if (isDestructuring) {
return Object.assign({ kind: "Destructuring" }, type);
}
if (flags.includes("StringLiteral")) {
return Object.assign({ kind: "StringLiteral", value: display }, type);
}
if (flags.includes("NumberLiteral")) {
return Object.assign({ kind: "NumberLiteral", value: display }, type);
}
if (flags.includes("BigIntLiteral")) {
return Object.assign({ kind: "BigIntLiteral", value: display }, type);
}
if (flags.includes("TypeParameter")) {
return Object.assign({ kind: "TypeParameter" }, type);
}
if (flags.includes("UniqueESSymbol")) {
return Object.assign({ kind: "Unique" }, type);
}
if ((_f = type.name) === null || _f === void 0 ? void 0 : _f.startsWith("__@")) {
const match = /^__@([^@]+)@\d+$/.exec(type.name);
return Object.assign(Object.assign({ kind: "KnownSymbol" }, type), { name: match ? match[1] : type.name });
}
if (type.name === "__function" ||
type.name === "__type" ||
type.name === "__class" ||
type.name === "__object") {
return makeAnonymous(type);
}
if (type.name === "__jsxAttributes") {
return makeAnonymous(type, "JsxAttributesType");
}
// This is less specific than the name checks
if (flags.includes("Object") && type.name) {
// Unclear why this happens - known instances are non-generic classes or interfaces
if (type.instantiatedType === type.id && ((_g = type.typeArguments) === null || _g === void 0 ? void 0 : _g.length) === 0) {
type.instantiatedType = undefined;
type.typeArguments = undefined;
}
return Object.assign({ kind: "Object" }, type);
}
// This goes at the end because it's a guess and depends on other interpretations having been checked previously
if (display && display.startsWith("(props:") && display.endsWith("=> Element")) {
return Object.assign(Object.assign({ kind: "JsxElementSignature" }, type), { display });
}
return Object.assign(Object.assign({ kind: "Other" }, type), { display });
function makeAnonymous(type, kind) {
return Object.assign(Object.assign({ kind: kind !== null && kind !== void 0 ? kind : "Anonymous" + firstToUpper(type.name.replace(/^__/, "")) }, type), { display: type.location ? undefined : display, name: undefined });
}
function makeAliasedKindIfNamed(type, kind) {
return type.name ? "Aliased" + kind : kind;
}
}
function firstToUpper(name) {
return name[0].toUpperCase() + name.substring(1);
}
function expandTypeFlags41(flags41) {
const flags = [];
if (flags41 & 1 << 0)
flags.push("Any");
if (flags41 & 1 << 1)
flags.push("Unknown");
if (flags41 & 1 << 2)
flags.push("String");
if (flags41 & 1 << 3)
flags.push("Number");
if (flags41 & 1 << 4)
flags.push("Boolean");
if (flags41 & 1 << 5)
flags.push("Enum");
if (flags41 & 1 << 6)
flags.push("BigInt");
if (flags41 & 1 << 7)
flags.push("StringLiteral");
if (flags41 & 1 << 8)
flags.push("NumberLiteral");
if (flags41 & 1 << 9)
flags.push("BooleanLiteral");
if (flags41 & 1 << 10)
flags.push("EnumLiteral");
if (flags41 & 1 << 11)
flags.push("BigIntLiteral");
if (flags41 & 1 << 12)
flags.push("ESSymbol");
if (flags41 & 1 << 13)
flags.push("UniqueESSymbol");
if (flags41 & 1 << 14)
flags.push("Void");
if (flags41 & 1 << 15)
flags.push("Undefined");
if (flags41 & 1 << 16)
flags.push("Null");
if (flags41 & 1 << 17)
flags.push("Never");
if (flags41 & 1 << 18)
flags.push("TypeParameter");
if (flags41 & 1 << 19)
flags.push("Object");
if (flags41 & 1 << 20)
flags.push("Union");
if (flags41 & 1 << 21)
flags.push("Intersection");
if (flags41 & 1 << 22)
flags.push("Index");
if (flags41 & 1 << 23)
flags.push("IndexedAccess");
if (flags41 & 1 << 24)
flags.push("Conditional");
if (flags41 & 1 << 25)
flags.push("Substitution");
if (flags41 & 1 << 26)
flags.push("NonPrimitive");
if (flags41 & 1 << 27)
flags.push("TemplateLiteral");
if (flags41 & 1 << 28)
flags.push("StringMapping");
return flags;
}
function getTypeFlags({ flags }) {
// Traces from TS 4.1 contained numeric flags, rather than their string equivalents
return flags.length === 1 && /^\d+$/.test(flags[0])
? expandTypeFlags41(+flags[0])
: flags;
}
module.exports = simplifyType;
//# sourceMappingURL=simplify-type.js.map