Skip to content

Instantly share code, notes, and snippets.

@danielkcz
Last active May 28, 2024 17:41
Show Gist options
  • Save danielkcz/3aba908bb0894b83dc25cf1a02d1928d to your computer and use it in GitHub Desktop.
Save danielkcz/3aba908bb0894b83dc25cf1a02d1928d to your computer and use it in GitHub Desktop.
Children handling with React FC
const NoChildrenAllowed: ReactFC<NoChildren> = () => null
const RequireSingleChild: ReactFC<Required<SingleChild>> = () => null
type TProps = Required<SomeChildren> & {
otherProp: number
}
const RequireMoreChildrenAndOtherProps: ReactFC<TProps> = () => null
const SomeChildrenCanBeReturned: ReactFC<Required<SomeChildren>> = ({ children }) => {
return children
}
const OptionalStringChildren: ReactFC<WithChildren<string>> = ({ children }) => {
return children ?? 'default'
}
/**
* Stricter variant of React.FC for type checking return value
* and to require one of variant of Children type to be specified
* If no children are expected, use `NoChildren`.
*/
declare type ReactFC<P extends WithChildren<any>> = {
(props: P): ReactNode
displayName?: string
}
/**
* Single React element (not a component).
*/
declare type ReactNode = null | string | number | React.ReactElement<any>
/**
* Single or multiple React elements.
*/
declare type ReactNodes = ReactNode | ReactNode[]
/**
* Extend props with specific type for children, eg. string.
* Use Required<WithChildren<T>> if children are required.
*/
declare type WithChildren<T> = {
children?: T
}
/**
* Extend props to forbid any child to be passed to component.
*
* Most components don't do anything with children. It's a good
* practice to inform consumer about it to avoid confusion of children
* not rendered.
*/
declare type NoChildren = WithChildren<never>
/**
* Extend props to allow only single react element as child.
*
* On rare occasions only a single child might be relevant and component
* should inform about it to avoid accidental ignoration of multiple children.
*
* Use `Required<SingleChild>` if child is required.
*/
declare type SingleChild = WithChildren<ReactNode>
/**
* Extend props to allow for single, multiple or none react elements as children.
*
* Most common to use when children are utilized and passed down to nested components.
* For advanced patterns like render prop, the `WithChildren<T>` is more appropriate.
*
* Use `Required<SomeChildren>` if children are required.
*/
declare type SomeChildren = WithChildren<ReactNodes>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment