mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-02-15 11:35:42 -06:00
Use immediate constraint instead of base constraint in T[K] relations
This commit is contained in:
parent
0fb415ac61
commit
014aeb3fd3
@ -3973,7 +3973,7 @@ namespace ts {
|
||||
return true;
|
||||
}
|
||||
if (type.flags & TypeFlags.TypeVariable) {
|
||||
const constraint = getBaseConstraintOfType(<TypeVariable>type);
|
||||
const constraint = getBaseConstraintOfType(type);
|
||||
return constraint && isValidBaseType(constraint) && isMixinConstructorType(constraint);
|
||||
}
|
||||
return false;
|
||||
@ -4989,16 +4989,32 @@ namespace ts {
|
||||
}
|
||||
|
||||
function getConstraintOfType(type: TypeVariable | UnionOrIntersectionType): Type {
|
||||
return type.flags & TypeFlags.TypeParameter ? getConstraintOfTypeParameter(<TypeParameter>type) : getBaseConstraintOfType(type);
|
||||
return type.flags & TypeFlags.TypeParameter ? getConstraintOfTypeParameter(<TypeParameter>type) :
|
||||
type.flags & TypeFlags.IndexedAccess ? getConstraintOfIndexedAccess(<IndexedAccessType>type) :
|
||||
getBaseConstraintOfType(type);
|
||||
}
|
||||
|
||||
function getConstraintOfTypeParameter(typeParameter: TypeParameter): Type {
|
||||
return hasNonCircularBaseConstraint(typeParameter) ? getConstraintFromTypeParameter(typeParameter) : undefined;
|
||||
}
|
||||
|
||||
function getBaseConstraintOfType(type: TypeVariable | UnionOrIntersectionType): Type {
|
||||
const constraint = getResolvedBaseConstraint(type);
|
||||
return constraint !== noConstraintType && constraint !== circularConstraintType ? constraint : undefined;
|
||||
function getConstraintOfIndexedAccess(type: IndexedAccessType) {
|
||||
const baseObjectType = getBaseConstraintOfType(type.objectType);
|
||||
const baseIndexType = getBaseConstraintOfType(type.indexType);
|
||||
return baseObjectType || baseIndexType ? getIndexedAccessType(baseObjectType || type.objectType, baseIndexType || type.indexType) : undefined;
|
||||
}
|
||||
|
||||
function getBaseConstraintOfType(type: Type): Type {
|
||||
if (type.flags & (TypeFlags.TypeVariable | TypeFlags.UnionOrIntersection)) {
|
||||
const constraint = getResolvedBaseConstraint(<TypeVariable | UnionOrIntersectionType>type);
|
||||
if (constraint !== noConstraintType && constraint !== circularConstraintType) {
|
||||
return constraint;
|
||||
}
|
||||
}
|
||||
else if (type.flags & TypeFlags.Index) {
|
||||
return stringType;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
function hasNonCircularBaseConstraint(type: TypeVariable): boolean {
|
||||
@ -5096,7 +5112,7 @@ namespace ts {
|
||||
* type itself. Note that the apparent type of a union type is the union type itself.
|
||||
*/
|
||||
function getApparentType(type: Type): Type {
|
||||
const t = type.flags & TypeFlags.TypeVariable ? getBaseConstraintOfType(<TypeVariable>type) || emptyObjectType : type;
|
||||
const t = type.flags & TypeFlags.TypeVariable ? getBaseConstraintOfType(type) || emptyObjectType : type;
|
||||
return t.flags & TypeFlags.Intersection ? getApparentTypeOfIntersectionType(<IntersectionType>t) :
|
||||
t.flags & TypeFlags.StringLike ? globalStringType :
|
||||
t.flags & TypeFlags.NumberLike ? globalNumberType :
|
||||
@ -7921,7 +7937,7 @@ namespace ts {
|
||||
}
|
||||
// A type S is related to a type T[K] if S is related to A[K], where K is string-like and
|
||||
// A is the apparent type of S.
|
||||
const constraint = getBaseConstraintOfType(<IndexedAccessType>target);
|
||||
const constraint = getBaseConstraintOfType(target);
|
||||
if (constraint) {
|
||||
if (result = isRelatedTo(source, constraint, reportErrors)) {
|
||||
errorInfo = saveErrorInfo;
|
||||
@ -7961,7 +7977,7 @@ namespace ts {
|
||||
else if (source.flags & TypeFlags.IndexedAccess) {
|
||||
// A type S[K] is related to a type T if A[K] is related to T, where K is string-like and
|
||||
// A is the apparent type of S.
|
||||
const constraint = getBaseConstraintOfType(<IndexedAccessType>source);
|
||||
const constraint = getConstraintOfType(<IndexedAccessType>source);
|
||||
if (constraint) {
|
||||
if (result = isRelatedTo(constraint, target, reportErrors)) {
|
||||
errorInfo = saveErrorInfo;
|
||||
@ -9874,7 +9890,7 @@ namespace ts {
|
||||
return strictNullChecks ? TypeFacts.ObjectStrictFacts : TypeFacts.ObjectFacts;
|
||||
}
|
||||
if (flags & TypeFlags.TypeVariable) {
|
||||
return getTypeFacts(getBaseConstraintOfType(<TypeVariable>type) || emptyObjectType);
|
||||
return getTypeFacts(getBaseConstraintOfType(type) || emptyObjectType);
|
||||
}
|
||||
if (flags & TypeFlags.UnionOrIntersection) {
|
||||
return getTypeFactsOfTypes((<UnionOrIntersectionType>type).types);
|
||||
@ -10686,7 +10702,7 @@ namespace ts {
|
||||
return targetType;
|
||||
}
|
||||
if (type.flags & TypeFlags.TypeVariable) {
|
||||
const constraint = getBaseConstraintOfType(<TypeVariable>type) || anyType;
|
||||
const constraint = getBaseConstraintOfType(type) || anyType;
|
||||
if (isTypeSubtypeOf(targetType, constraint)) {
|
||||
return getIntersectionType([type, targetType]);
|
||||
}
|
||||
@ -16234,7 +16250,7 @@ namespace ts {
|
||||
function isLiteralContextualType(contextualType: Type) {
|
||||
if (contextualType) {
|
||||
if (contextualType.flags & TypeFlags.TypeVariable) {
|
||||
const constraint = getBaseConstraintOfType(<TypeVariable>contextualType) || emptyObjectType;
|
||||
const constraint = getBaseConstraintOfType(contextualType) || emptyObjectType;
|
||||
// If the type parameter is constrained to the base primitive type we're checking for,
|
||||
// consider this a literal context. For example, given a type parameter 'T extends string',
|
||||
// this causes us to infer string literal types for T.
|
||||
@ -17124,7 +17140,7 @@ namespace ts {
|
||||
// Check if we're indexing with a numeric type and the object type is a generic
|
||||
// type with a constraint that has a numeric index signature.
|
||||
if (maybeTypeOfKind(objectType, TypeFlags.TypeVariable) && isTypeOfKind(indexType, TypeFlags.NumberLike)) {
|
||||
const constraint = getBaseConstraintOfType(<TypeVariable | UnionOrIntersectionType>objectType);
|
||||
const constraint = getBaseConstraintOfType(objectType);
|
||||
if (constraint && getIndexInfoOfType(constraint, IndexKind.Number)) {
|
||||
return type;
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user