The `as` Prop in React
Option 1:
import { Equal, Expect } from '../helpers/type-utils';
export const Wrapper = <TProps extends keyof JSX.IntrinsicElements>(
props: {
as: TProps;
} & JSX.IntrinsicElements[TProps]
) => {
const Comp = props.as as string;
return <Comp {...(props as JSX.IntrinsicElements[TProps])}></Comp>;
};
const Example1 = () => {
return (
<>
<Wrapper
as="button"
// @ts-expect-error doesNotExist is not a valid prop
doesNotExist
></Wrapper>
<Wrapper
as="button"
// e should be inferred correctly
onClick={(e) => {
type test = Expect<
Equal<typeof e, React.MouseEvent<HTMLButtonElement>>
>;
}}
></Wrapper>
</>
);
};
/**
* Should work specifying a 'div'
*/
const Example2 = () => {
return (
<>
<Wrapper
as="div"
// @ts-expect-error doesNotExist is not a valid prop
doesNotExist
></Wrapper>
<Wrapper
as="div"
// e should be inferred correctly
onClick={(e) => {
type test = Expect<Equal<typeof e, React.MouseEvent<HTMLDivElement>>>;
}}
></Wrapper>
</>
);
};
Option 2: A huge distrination union
export const Wrapper = <TAs extends keyof JSX.IntrinsicElements>(
props: {
as: TAs;
} & ComponentProps<TAs>
) => {
const Comp = props.as as string;
return <Comp {...(props as any)}></Comp>;
};
- React Typescript component Strongly typedtypescript component strongly react react typescript component strongly components typescript generics strongly typescript strongly render react typescript component generics react react typescript components propstype components typescript arguments passing typescript this type extracting components typescript custom type typescript expression error