Let’s say I have a <Button />
component that can take two sets of props:
type CommonProps = {
disabled?: boolean
// ... other “normal” props here
}
type Props =
| (CommonProps & { action: () => void })
| (CommonProps & { href: string })
So Button
can be used either like <Button action={() => {}} />
or <Button href="..." />
(each time with an optional disabled
prop).
const Button = ({ action, disabled, href }) => {
return // ...
}
Written like this, TypeScript complains about the destructured props in the component function argument, because action
and href
never co-occur. Understandable. But written like this:
type Props =
| (CommonProps & { action: () => void; href: void })
| (CommonProps & { action: void; href: string })
TS would complain about the <Button /* ... */ />
component not being passed an action={undefined}
or href={undefined}
prop.
So how would one go about typing a component with props that must not co-occur? What I’m looking for is something like
type Props = {
action?: () => void
href?: string
}
but without the possibility of both props being null or non-null at the same time, so that we can write for example <Button href="..." />
but not <Button action={() => {}} href="..." />
.
Thanks for your advice!