Skip to content

Commit f04d28d

Browse files
committed
Recursively check union type of react components for constructor/call
1 parent 0795c8d commit f04d28d

File tree

1 file changed

+33
-10
lines changed

1 file changed

+33
-10
lines changed

src/compiler/checker.ts

Lines changed: 33 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -9499,6 +9499,34 @@ namespace ts {
94999499
return links.resolvedSymbol;
95009500
}
95019501

9502+
/**
9503+
* Given a type, resolve its constructor signatures.
9504+
* If no construct signatures, call signatures are resolved.
9505+
* If the type is a union type, recursively resolve the signatures using
9506+
* the same method.
9507+
* Return collected construct/call signature.
9508+
*/
9509+
function getConstructOrCallSignature(type: Type): Signature[] {
9510+
if (type.flags & TypeFlags.Union) {
9511+
let signatures: Signature[] = [];
9512+
forEach((<UnionOrIntersectionType> type).types, (childType) => {
9513+
let childSignatures = getConstructOrCallSignature(childType);
9514+
forEach(childSignatures, (signature) => {
9515+
signatures.push(signature);
9516+
})
9517+
})
9518+
return signatures;
9519+
} else {
9520+
let signatures = getSignaturesOfType(type, SignatureKind.Construct);
9521+
if (signatures.length === 0) {
9522+
// No construct signatures, try call signatures
9523+
return getSignaturesOfType(type, SignatureKind.Call);
9524+
} else {
9525+
return signatures;
9526+
}
9527+
}
9528+
}
9529+
95029530
/**
95039531
* Given a JSX element that is a class element, finds the Element Instance Type. If the
95049532
* element is not a class element, or the class element type cannot be determined, returns 'undefined'.
@@ -9512,17 +9540,12 @@ namespace ts {
95129540
return anyType;
95139541
}
95149542

9515-
// Resolve the signatures, preferring constructors
9516-
let signatures = getSignaturesOfType(valueType, SignatureKind.Construct);
9543+
// Resolve the signatures
9544+
let signatures = getConstructOrCallSignature(valueType);
95179545
if (signatures.length === 0) {
9518-
// No construct signatures, try call signatures
9519-
signatures = getSignaturesOfType(valueType, SignatureKind.Call);
9520-
9521-
if (signatures.length === 0) {
9522-
// We found no signatures at all, which is an error
9523-
error(node.tagName, Diagnostics.JSX_element_type_0_does_not_have_any_construct_or_call_signatures, getTextOfNode(node.tagName));
9524-
return unknownType;
9525-
}
9546+
// We found no signatures at all, which is an error
9547+
error(node.tagName, Diagnostics.JSX_element_type_0_does_not_have_any_construct_or_call_signatures, getTextOfNode(node.tagName));
9548+
return unknownType;
95269549
}
95279550

95289551
return getUnionType(signatures.map(getReturnTypeOfSignature));

0 commit comments

Comments
 (0)