diff --git a/types/react/index.d.ts b/types/react/index.d.ts
index 25f3c710ae..522a106944 100644
--- a/types/react/index.d.ts
+++ b/types/react/index.d.ts
@@ -50,7 +50,11 @@ declare namespace React {
// React Elements
// ----------------------------------------------------------------------
- type ReactType
= string | ComponentType
;
+ type ReactType
=
+ {
+ [K in keyof JSX.IntrinsicElements]: P extends JSX.IntrinsicElements[K] ? K : never
+ }[keyof JSX.IntrinsicElements] |
+ ComponentType
;
type ComponentType
= ComponentClass
| FunctionComponent
;
type Key = string | number;
@@ -713,17 +717,17 @@ declare namespace React {
* NOTE: prefer ComponentPropsWithRef, if the ref is forwarded,
* or ComponentPropsWithoutRef when refs are not supported.
*/
- type ComponentProps> =
+ type ComponentProps =
T extends ComponentType
? P
: T extends keyof JSX.IntrinsicElements
? JSX.IntrinsicElements[T]
: {};
- type ComponentPropsWithRef> =
+ type ComponentPropsWithRef =
T extends ComponentClass
? PropsWithoutRef & RefAttributes>
: PropsWithRef>;
- type ComponentPropsWithoutRef> =
+ type ComponentPropsWithoutRef =
PropsWithoutRef>;
// will show `Memo(${Component.displayName || Component.name})` in devtools by default,
diff --git a/types/react/test/tsx.tsx b/types/react/test/tsx.tsx
index f344fb2838..a8ca2ae1ea 100644
--- a/types/react/test/tsx.tsx
+++ b/types/react/test/tsx.tsx
@@ -325,3 +325,10 @@ type ImgPropsWithRefRef = ImgPropsWithRef['ref'];
type ImgPropsWithoutRef = React.ComponentPropsWithoutRef<'img'>;
// $ExpectType false
type ImgPropsHasRef = 'ref' extends keyof ImgPropsWithoutRef ? true : false;
+
+const HasClassName: React.ReactType<{ className?: string }> = 'a';
+const HasFoo: React.ReactType<{ foo: boolean }> = 'a'; // $ExpectError
+const HasFoo2: React.ReactType<{ foo: boolean }> = (props: { foo: boolean }) => null;
+const HasFoo3: React.ReactType<{ foo: boolean }> = (props: { foo: string }) => null; // $ExpectError
+const HasHref: React.ReactType<{ href?: string }> = 'a';
+const HasHref2: React.ReactType<{ href?: string }> = 'div'; // $ExpectError