mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-02-13 06:20:23 -06:00
Associate type alias names with union, intersection and literal types
This commit is contained in:
parent
7d1c2fcf70
commit
a17bd026e5
@ -2133,6 +2133,10 @@ namespace ts {
|
||||
else if (type.flags & TypeFlags.Tuple) {
|
||||
writeTupleType(<TupleType>type);
|
||||
}
|
||||
else if (type.flags & (TypeFlags.Anonymous | TypeFlags.UnionOrIntersection) && type.aliasSymbol) {
|
||||
const typeArguments = type.aliasTypeArguments;
|
||||
writeSymbolTypeReference(type.aliasSymbol, typeArguments, 0, typeArguments ? typeArguments.length : 0, flags);
|
||||
}
|
||||
else if (type.flags & TypeFlags.UnionOrIntersection) {
|
||||
writeUnionOrIntersectionType(<UnionOrIntersectionType>type, flags);
|
||||
}
|
||||
@ -3704,8 +3708,9 @@ namespace ts {
|
||||
return unknownType;
|
||||
}
|
||||
|
||||
let type: Type;
|
||||
const typeParameters = getLocalTypeParametersOfClassOrInterfaceOrTypeAlias(symbol);
|
||||
let declaration: JSDocTypedefTag | TypeAliasDeclaration = <JSDocTypedefTag>getDeclarationOfKind(symbol, SyntaxKind.JSDocTypedefTag);
|
||||
let type: Type;
|
||||
if (declaration) {
|
||||
if (declaration.jsDocTypeLiteral) {
|
||||
type = getTypeFromTypeNode(declaration.jsDocTypeLiteral);
|
||||
@ -3716,12 +3721,12 @@ namespace ts {
|
||||
}
|
||||
else {
|
||||
declaration = <TypeAliasDeclaration>getDeclarationOfKind(symbol, SyntaxKind.TypeAliasDeclaration);
|
||||
type = getTypeFromTypeNode(declaration.type);
|
||||
type = getTypeFromTypeNode(declaration.type, symbol, typeParameters);
|
||||
}
|
||||
|
||||
if (popTypeResolution()) {
|
||||
links.typeParameters = getLocalTypeParametersOfClassOrInterfaceOrTypeAlias(symbol);
|
||||
if (links.typeParameters) {
|
||||
links.typeParameters = typeParameters;
|
||||
if (typeParameters) {
|
||||
// Initialize the instantiation cache for generic type aliases. The declared type corresponds to
|
||||
// an instantiation of the type alias with the type parameters supplied as type arguments.
|
||||
links.instantiations = {};
|
||||
@ -5226,7 +5231,7 @@ namespace ts {
|
||||
// literals and the || and ?: operators). Named types can circularly reference themselves and therefore
|
||||
// cannot be deduplicated during their declaration. For example, "type Item = string | (() => Item" is
|
||||
// a named type that circularly references itself.
|
||||
function getUnionType(types: Type[], noSubtypeReduction?: boolean): Type {
|
||||
function getUnionType(types: Type[], noSubtypeReduction?: boolean, aliasSymbol?: Symbol, aliasTypeArguments?: Type[]): Type {
|
||||
if (types.length === 0) {
|
||||
return neverType;
|
||||
}
|
||||
@ -5260,14 +5265,16 @@ namespace ts {
|
||||
const propagatedFlags = getPropagatingFlagsOfTypes(typeSet, /*excludeKinds*/ TypeFlags.Nullable);
|
||||
type = unionTypes[id] = <UnionType>createObjectType(TypeFlags.Union | propagatedFlags);
|
||||
type.types = typeSet;
|
||||
type.aliasSymbol = aliasSymbol;
|
||||
type.aliasTypeArguments = aliasTypeArguments;
|
||||
}
|
||||
return type;
|
||||
}
|
||||
|
||||
function getTypeFromUnionTypeNode(node: UnionTypeNode): Type {
|
||||
function getTypeFromUnionTypeNode(node: UnionTypeNode, aliasSymbol?: Symbol, aliasTypeArguments?: Type[]): Type {
|
||||
const links = getNodeLinks(node);
|
||||
if (!links.resolvedType) {
|
||||
links.resolvedType = getUnionType(map(node.types, getTypeFromTypeNode), /*noSubtypeReduction*/ true);
|
||||
links.resolvedType = getUnionType(map(node.types, getTypeFromTypeNode), /*noSubtypeReduction*/ true, aliasSymbol, aliasTypeArguments);
|
||||
}
|
||||
return links.resolvedType;
|
||||
}
|
||||
@ -5277,7 +5284,7 @@ namespace ts {
|
||||
// a type alias of the form "type List<T> = T & { next: List<T> }" cannot be reduced during its declaration.
|
||||
// Also, unlike union types, the order of the constituent types is preserved in order that overload resolution
|
||||
// for intersections of types with signatures can be deterministic.
|
||||
function getIntersectionType(types: Type[]): Type {
|
||||
function getIntersectionType(types: Type[], aliasSymbol?: Symbol, aliasTypeArguments?: Type[]): Type {
|
||||
if (types.length === 0) {
|
||||
return emptyObjectType;
|
||||
}
|
||||
@ -5299,23 +5306,28 @@ namespace ts {
|
||||
const propagatedFlags = getPropagatingFlagsOfTypes(typeSet, /*excludeKinds*/ TypeFlags.Nullable);
|
||||
type = intersectionTypes[id] = <IntersectionType>createObjectType(TypeFlags.Intersection | propagatedFlags);
|
||||
type.types = typeSet;
|
||||
type.aliasSymbol = aliasSymbol;
|
||||
type.aliasTypeArguments = aliasTypeArguments;
|
||||
}
|
||||
return type;
|
||||
}
|
||||
|
||||
function getTypeFromIntersectionTypeNode(node: IntersectionTypeNode): Type {
|
||||
function getTypeFromIntersectionTypeNode(node: IntersectionTypeNode, aliasSymbol?: Symbol, aliasTypeArguments?: Type[]): Type {
|
||||
const links = getNodeLinks(node);
|
||||
if (!links.resolvedType) {
|
||||
links.resolvedType = getIntersectionType(map(node.types, getTypeFromTypeNode));
|
||||
links.resolvedType = getIntersectionType(map(node.types, getTypeFromTypeNode), aliasSymbol, aliasTypeArguments);
|
||||
}
|
||||
return links.resolvedType;
|
||||
}
|
||||
|
||||
function getTypeFromTypeLiteralOrFunctionOrConstructorTypeNode(node: Node): Type {
|
||||
function getTypeFromTypeLiteralOrFunctionOrConstructorTypeNode(node: Node, aliasSymbol?: Symbol, aliasTypeArguments?: Type[]): Type {
|
||||
const links = getNodeLinks(node);
|
||||
if (!links.resolvedType) {
|
||||
// Deferred resolution of members is handled by resolveObjectTypeMembers
|
||||
links.resolvedType = createObjectType(TypeFlags.Anonymous, node.symbol);
|
||||
const type = createObjectType(TypeFlags.Anonymous, node.symbol);
|
||||
type.aliasSymbol = aliasSymbol;
|
||||
type.aliasTypeArguments = aliasTypeArguments;
|
||||
links.resolvedType = type;
|
||||
}
|
||||
return links.resolvedType;
|
||||
}
|
||||
@ -5378,7 +5390,7 @@ namespace ts {
|
||||
return links.resolvedType;
|
||||
}
|
||||
|
||||
function getTypeFromTypeNode(node: TypeNode): Type {
|
||||
function getTypeFromTypeNode(node: TypeNode, aliasSymbol?: Symbol, aliasTypeArguments?: Type[]): Type {
|
||||
switch (node.kind) {
|
||||
case SyntaxKind.AnyKeyword:
|
||||
case SyntaxKind.JSDocAllType:
|
||||
@ -5421,9 +5433,9 @@ namespace ts {
|
||||
return getTypeFromTupleTypeNode(<TupleTypeNode>node);
|
||||
case SyntaxKind.UnionType:
|
||||
case SyntaxKind.JSDocUnionType:
|
||||
return getTypeFromUnionTypeNode(<UnionTypeNode>node);
|
||||
return getTypeFromUnionTypeNode(<UnionTypeNode>node, aliasSymbol, aliasTypeArguments);
|
||||
case SyntaxKind.IntersectionType:
|
||||
return getTypeFromIntersectionTypeNode(<IntersectionTypeNode>node);
|
||||
return getTypeFromIntersectionTypeNode(<IntersectionTypeNode>node, aliasSymbol, aliasTypeArguments);
|
||||
case SyntaxKind.ParenthesizedType:
|
||||
case SyntaxKind.JSDocNullableType:
|
||||
case SyntaxKind.JSDocNonNullableType:
|
||||
@ -5437,7 +5449,7 @@ namespace ts {
|
||||
case SyntaxKind.JSDocTypeLiteral:
|
||||
case SyntaxKind.JSDocFunctionType:
|
||||
case SyntaxKind.JSDocRecordType:
|
||||
return getTypeFromTypeLiteralOrFunctionOrConstructorTypeNode(node);
|
||||
return getTypeFromTypeLiteralOrFunctionOrConstructorTypeNode(node, aliasSymbol, aliasTypeArguments);
|
||||
// This function assumes that an identifier or qualified name is a type expression
|
||||
// Callers should first ensure this by calling isTypeNode
|
||||
case SyntaxKind.Identifier:
|
||||
@ -5490,6 +5502,7 @@ namespace ts {
|
||||
count == 2 ? createBinaryTypeMapper(sources[0], targets ? targets[0] : anyType, sources[1], targets ? targets[1] : anyType) :
|
||||
createArrayTypeMapper(sources, targets);
|
||||
mapper.mappedTypes = sources;
|
||||
mapper.targetTypes = targets;
|
||||
return mapper;
|
||||
}
|
||||
|
||||
@ -5615,6 +5628,8 @@ namespace ts {
|
||||
const result = <AnonymousType>createObjectType(TypeFlags.Anonymous | TypeFlags.Instantiated, type.symbol);
|
||||
result.target = type;
|
||||
result.mapper = mapper;
|
||||
result.aliasSymbol = type.aliasSymbol;
|
||||
result.aliasTypeArguments = mapper.targetTypes;
|
||||
mapper.instantiations[type.id] = result;
|
||||
return result;
|
||||
}
|
||||
@ -5692,10 +5707,10 @@ namespace ts {
|
||||
return createTupleType(instantiateList((<TupleType>type).elementTypes, mapper, instantiateType));
|
||||
}
|
||||
if (type.flags & TypeFlags.Union && !(type.flags & TypeFlags.Primitive)) {
|
||||
return getUnionType(instantiateList((<UnionType>type).types, mapper, instantiateType), /*noSubtypeReduction*/ true);
|
||||
return getUnionType(instantiateList((<UnionType>type).types, mapper, instantiateType), /*noSubtypeReduction*/ true, type.aliasSymbol, mapper.targetTypes);
|
||||
}
|
||||
if (type.flags & TypeFlags.Intersection) {
|
||||
return getIntersectionType(instantiateList((<IntersectionType>type).types, mapper, instantiateType));
|
||||
return getIntersectionType(instantiateList((<IntersectionType>type).types, mapper, instantiateType), type.aliasSymbol, mapper.targetTypes);
|
||||
}
|
||||
}
|
||||
return type;
|
||||
|
||||
@ -2283,6 +2283,8 @@ namespace ts {
|
||||
/* @internal */ id: number; // Unique ID
|
||||
symbol?: Symbol; // Symbol associated with type (if any)
|
||||
pattern?: DestructuringPattern; // Destructuring pattern represented by type (if any)
|
||||
aliasSymbol?: Symbol; // Alias associated with type
|
||||
aliasTypeArguments?: Type[]; // Alias type arguments (if any)
|
||||
}
|
||||
|
||||
/* @internal */
|
||||
@ -2446,6 +2448,7 @@ namespace ts {
|
||||
export interface TypeMapper {
|
||||
(t: TypeParameter): Type;
|
||||
mappedTypes?: Type[]; // Types mapped by this mapper
|
||||
targetTypes?: Type[]; // Types substituted for mapped types
|
||||
instantiations?: Type[]; // Cache of instantiations created using this type mapper.
|
||||
context?: InferenceContext; // The inference context this mapper was created from.
|
||||
// Only inference mappers have this set (in createInferenceMapper).
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user