Skip to content

Instantly share code, notes, and snippets.

@Andarist
Created September 22, 2021 07:25
Show Gist options
  • Save Andarist/f4271f3988a652488f9c9b22c7d56a55 to your computer and use it in GitHub Desktop.
Save Andarist/f4271f3988a652488f9c9b22c7d56a55 to your computer and use it in GitHub Desktop.
simple script to decode TS type flags
// source
524288; // {"basics":["Object"],"composites":["StructuredType","StructuredOrInstantiable","ObjectFlagsType","Narrowable","NotPrimitiveUnion","IncludesMask"]}
// target
8388608; // {"basics":["IndexedAccess"],"composites":["TypeVariable","InstantiableNonPrimitive","Instantiable","StructuredOrInstantiable","Simplifiable","Narrowable","NotPrimitiveUnion","IncludesWildcard"]}
var flags = {
Any: 1 << 0,
Unknown: 1 << 1,
String: 1 << 2,
Number: 1 << 3,
Boolean: 1 << 4,
Enum: 1 << 5,
BigInt: 1 << 6,
StringLiteral: 1 << 7,
NumberLiteral: 1 << 8,
BooleanLiteral: 1 << 9,
EnumLiteral: 1 << 10, // Always combined with StringLiteral, NumberLiteral, or Union
BigIntLiteral: 1 << 11,
ESSymbol: 1 << 12, // Type of symbol primitive introduced in ES6
UniqueESSymbol: 1 << 13, // unique symbol
Void: 1 << 14,
Undefined: 1 << 15,
Null: 1 << 16,
Never: 1 << 17, // Never type
TypeParameter: 1 << 18, // Type parameter
Object: 1 << 19, // Object type
Union: 1 << 20, // Union (flags.T | U)
Intersection: 1 << 21, // Intersection (T & U)
Index: 1 << 22, // keyof T
IndexedAccess: 1 << 23, // T[K]
Conditional: 1 << 24, // T extends U ? X : Y
Substitution: 1 << 25, // Type parameter substitution
NonPrimitive: 1 << 26, // intrinsic object type
TemplateLiteral: 1 << 27, // Template literal type
StringMapping: 1 << 28, // Uppercase/Lowercase type
};
flags.AnyOrUnknown = flags.Any | flags.Unknown;
/* @internal */
flags.Nullable = flags.Undefined | flags.Null;
flags.Literal =
flags.StringLiteral |
flags.NumberLiteral |
flags.BigIntLiteral |
flags.BooleanLiteral;
flags.Unit = flags.Literal | flags.UniqueESSymbol | flags.Nullable;
flags.StringOrNumberLiteral = flags.StringLiteral | flags.NumberLiteral;
/* @internal */
flags.StringOrNumberLiteralOrUnique =
flags.StringLiteral | flags.NumberLiteral | flags.UniqueESSymbol;
/* @internal */
flags.DefinitelyFalsy =
flags.StringLiteral |
flags.NumberLiteral |
flags.BigIntLiteral |
flags.BooleanLiteral |
flags.Void |
flags.Undefined |
flags.Null;
flags.PossiblyFalsy =
flags.DefinitelyFalsy |
flags.String |
flags.Number |
flags.BigInt |
flags.Boolean;
/* @internal */
flags.Intrinsic =
flags.Any |
flags.Unknown |
flags.String |
flags.Number |
flags.BigInt |
flags.Boolean |
flags.BooleanLiteral |
flags.ESSymbol |
flags.Void |
flags.Undefined |
flags.Null |
flags.Never |
flags.NonPrimitive;
/* @internal */
flags.Primitive =
flags.String |
flags.Number |
flags.BigInt |
flags.Boolean |
flags.Enum |
flags.EnumLiteral |
flags.ESSymbol |
flags.Void |
flags.Undefined |
flags.Null |
flags.Literal |
flags.UniqueESSymbol;
flags.StringLike =
flags.String |
flags.StringLiteral |
flags.TemplateLiteral |
flags.StringMapping;
flags.NumberLike = flags.Number | flags.NumberLiteral | flags.Enum;
flags.BigIntLike = flags.BigInt | flags.BigIntLiteral;
flags.BooleanLike = flags.Boolean | flags.BooleanLiteral;
flags.EnumLike = flags.Enum | flags.EnumLiteral;
flags.ESSymbolLike = flags.ESSymbol | flags.UniqueESSymbol;
flags.VoidLike = flags.Void | flags.Undefined;
/* @internal */
flags.DisjointDomains =
flags.NonPrimitive |
flags.StringLike |
flags.NumberLike |
flags.BigIntLike |
flags.BooleanLike |
flags.ESSymbolLike |
flags.VoidLike |
flags.Null;
flags.UnionOrIntersection = flags.Union | flags.Intersection;
flags.StructuredType = flags.Object | flags.Union | flags.Intersection;
flags.TypeVariable = flags.TypeParameter | flags.IndexedAccess;
flags.InstantiableNonPrimitive =
flags.TypeVariable | flags.Conditional | flags.Substitution;
flags.InstantiablePrimitive =
flags.Index | flags.TemplateLiteral | flags.StringMapping;
flags.Instantiable =
flags.InstantiableNonPrimitive | flags.InstantiablePrimitive;
flags.StructuredOrInstantiable = flags.StructuredType | flags.Instantiable;
/* @internal */
flags.ObjectFlagsType =
flags.Any |
flags.Nullable |
flags.Never |
flags.Object |
flags.Union |
flags.Intersection;
/* @internal */
flags.Simplifiable = flags.IndexedAccess | flags.Conditional;
/* @internal */
flags.Singleton =
flags.Any |
flags.Unknown |
flags.String |
flags.Number |
flags.Boolean |
flags.BigInt |
flags.ESSymbol |
flags.Void |
flags.Undefined |
flags.Null |
flags.Never |
flags.NonPrimitive;
// 'Narrowable' types are types where narrowing actually narrows.
// This *should* be every type other than null, undefined, void, and never
flags.Narrowable =
flags.Any |
flags.Unknown |
flags.StructuredOrInstantiable |
flags.StringLike |
flags.NumberLike |
flags.BigIntLike |
flags.BooleanLike |
flags.ESSymbol |
flags.UniqueESSymbol |
flags.NonPrimitive;
/* @internal */
flags.NotPrimitiveUnion =
flags.Any |
flags.Unknown |
flags.Enum |
flags.Void |
flags.Never |
flags.Object |
flags.Intersection |
flags.Instantiable;
// The following flags are aggregated during union and intersection type construction
/* @internal */
flags.IncludesMask =
flags.Any |
flags.Unknown |
flags.Primitive |
flags.Never |
flags.Object |
flags.Union |
flags.Intersection |
flags.NonPrimitive |
flags.TemplateLiteral;
// The following flags are used for different purposes during union and intersection type construction
/* @internal */
flags.IncludesStructuredOrInstantiable = flags.TypeParameter;
/* @internal */
flags.IncludesNonWideningType = flags.Index;
/* @internal */
flags.IncludesWildcard = flags.IndexedAccess;
/* @internal */
flags.IncludesEmptyObject = flags.Conditional;
function decode(inputFlags) {
const basics = {
Any: flags.Any & inputFlags,
Unknown: flags.Unknown & inputFlags,
String: flags.String & inputFlags,
Number: flags.Number & inputFlags,
Boolean: flags.Boolean & inputFlags,
Enum: flags.Enum & inputFlags,
BigInt: flags.BigInt & inputFlags,
StringLiteral: flags.StringLiteral & inputFlags,
NumberLiteral: flags.NumberLiteral & inputFlags,
BooleanLiteral: flags.BooleanLiteral & inputFlags,
EnumLiteral: flags.EnumLiteral & inputFlags,
BigIntLiteral: flags.BigIntLiteral & inputFlags,
ESSymbol: flags.ESSymbol & inputFlags,
UniqueESSymbol: flags.UniqueESSymbol & inputFlags,
Void: flags.Void & inputFlags,
Undefined: flags.Undefined & inputFlags,
Null: flags.Null & inputFlags,
Never: flags.Never & inputFlags,
TypeParameter: flags.TypeParameter & inputFlags,
Object: flags.Object & inputFlags,
Union: flags.Union & inputFlags,
Intersection: flags.Intersection & inputFlags,
Index: flags.Index & inputFlags,
IndexedAccess: flags.IndexedAccess & inputFlags,
Conditional: flags.Conditional & inputFlags,
Substitution: flags.Substitution & inputFlags,
NonPrimitive: flags.NonPrimitive & inputFlags,
TemplateLiteral: flags.TemplateLiteral & inputFlags,
StringMapping: flags.StringMapping & inputFlags,
};
const composites = {
AnyOrUnknown: flags.AnyOrUnknown & inputFlags,
Nullable: flags.Nullable & inputFlags,
Literal: flags.Literal & inputFlags,
Unit: flags.Unit & inputFlags,
StringOrNumberLiteral: flags.StringOrNumberLiteral & inputFlags,
StringOrNumberLiteralOrUnique: flags.StringOrNumberLiteralOrUnique & inputFlags,
DefinitelyFalsy: flags.DefinitelyFalsy & inputFlags,
PossiblyFalsy: flags.PossiblyFalsy & inputFlags,
Intrinsic: flags.Intrinsic & inputFlags,
Primitive: flags.Primitive & inputFlags,
StringLike: flags.StringLike & inputFlags,
NumberLike: flags.NumberLike & inputFlags,
BigIntLike: flags.BigIntLike & inputFlags,
BooleanLike: flags.BooleanLike & inputFlags,
EnumLike: flags.EnumLike & inputFlags,
ESSymbolLike: flags.ESSymbolLike & inputFlags,
VoidLike: flags.VoidLike & inputFlags,
DisjointDomains: flags.DisjointDomains & inputFlags,
UnionOrIntersection: flags.UnionOrIntersection & inputFlags,
StructuredType: flags.StructuredType & inputFlags,
TypeVariable: flags.TypeVariable & inputFlags,
InstantiableNonPrimitive: flags.InstantiableNonPrimitive & inputFlags,
InstantiablePrimitive: flags.InstantiablePrimitive & inputFlags,
Instantiable: flags.Instantiable & inputFlags,
StructuredOrInstantiable: flags.StructuredOrInstantiable & inputFlags,
ObjectFlagsType: flags.ObjectFlagsType & inputFlags,
Simplifiable: flags.Simplifiable & inputFlags,
Singleton: flags.Singleton & inputFlags,
Narrowable: flags.Narrowable & inputFlags,
NotPrimitiveUnion: flags.NotPrimitiveUnion & inputFlags,
IncludesMask: flags.IncludesMask & inputFlags,
IncludesStructuredOrInstantiable:
flags.IncludesStructuredOrInstantiable & inputFlags,
IncludesNonWideningType: flags.IncludesNonWideningType & inputFlags,
IncludesWildcard: flags.IncludesWildcard & inputFlags,
IncludesEmptyObject: flags.IncludesEmptyObject & inputFlags,
};
const dump = (map) => Object.keys(map).filter((k) => !!map[k]);
return {
basics: dump(basics),
composites: dump(composites),
};
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment