πŸ’‘ This page contain affiliate links. By making a purchase through them, we may earn a commission at no extra cost to you.
Generic React Components with TypeScript

Generic React Components with TypeScript

Building React components with flexible types
Ferenc Almasi β€’ Last updated 2021 November 11 β€’ Read time 4 min read
Learn how you can build more reusable, and flexibly typed components in React using the power of generics in Typescript...
  • twitter
  • facebook
TypeScript

When building applications, we often have to think about how to create reusable components, that also have a well-defined API. These components should work on a variety of types, instead of only handling just a single one. This is what makes them so flexible.

If you are using React with TypeScript, then creating generic React components can help you better reuse your components with multiple types. But what are generic React components anyway? What are generics in the first place?


What are Generics?

Generics in TypeScript lets you define components with a special type, that can accept multiple types instead of just one. At this point, you may ask, can’t I just use any? That should work with any type, right?

Copied to clipboard!
const fn = (param: any): any => param;
any.ts

This is true. However, while doing so, you lose information about what type is passed and what is returned. If you call this function in your code, you will notice that you don’t get a clear type definition for the function call. It only tells us that it accepts any type, and we don’t know what is returned.

Using the any type in TypeScript

We might also don’t want to restrict what types this function can take. Instead of going with any, we can turn the above function into a generic using the following:

Copied to clipboard!
const fn = <T>(param: T): T => param;
generic.ts

Using T is the common way to denote generics, but you can use any name you like. You can create generics using angle brackets. Now we can see that the type definitions are inferred, and we have all information about the passed and returned types.

Using generics in TypeScript

Generics In React

Now let’s focus our attention to React, and see how generics work in them. We will take a look at how we can use it for props, hooks, and to create generic components.

Generic props

To use generic props in React, we can use the built in React.FC type β€” which accepts a generic β€” and create an interface that we can pass as the props between angle brackets. This way, you will be able to get type definitions for your props:

Copied to clipboard! Playground
interface Props {
    user: {
        name: string,
        email: Email
    }
}

const Component: React.FC<Props> = ({ user }) => {
    const { name, email } = user;

    return <div>You are logged in as {name} ({email})</div>;
};

Generic hooks

Just like props, you can also use generics with hooks. If you look into the type definitions of React, you will notice that the argument you can pass to hooks are generics. Notice in the code example below that you will get the right type definitions for the initial state:

Copied to clipboard! Playground
const Component: React.FC<Props> = ({ user }) => {
    const [state] = useState(user);
    
    // βœ”οΈ Works without an issue.
    return <div>You are logged in as {state.name}</div>;
    
    // ❌ TypeScript will throw an error as there is no fullName on the user state.
    return <div>You are logged in as {state.fullName}</div>;
};

You can also override generics by passing the type in angle brackets just before you set the initial value for the hook:

Copied to clipboard! Playground
interface InitialState {
    user: {
        fullName: string
    }
}

const Component: React.FC<Props> = ({ user }) => {
    // Pass the type explicitly before calling the hook to override.
    const [state] = useState<InitialState>(user);

    ...
}

Generics components

Lastly, in some cases, you might want to create generic components in React. This is also possible with the following syntax:

Copied to clipboard! Playground
interface Props<T> {
    items: T[]
}

const Components = <T extends InitialState>({ items }: Props<T>) => {
    
}

In this example, the interface takes in a generic with the value of T, and uses that value as the type for the items, which in this example, is an array. Also, note that you can extend generics with other types using the extends keyword, to give them a base type.

Looking to improve your skills? Master TypeScript from start to finish.
Master TypeScriptinfo Remove ads

Summary

In summary, generics (not just in React), helps us create reusable components that can work over a variety of types, without losing information about the passed types along the way. Have you worked with generics before? Don’t forget to leave your thoughts in the comments below. Thank you for reading through, happy coding!

How to Get Started With TypeScript
  • twitter
  • facebook
TypeScript
Did you find this page helpful?
πŸ“š More Webtips
Frontend Course Dashboard
Master the Art of Frontend
  • check Access 100+ interactive lessons
  • check Unlimited access to hundreds of tutorials
  • check Prepare for technical interviews
Become a Pro

Courses

Recommended

This site uses cookies We use cookies to understand visitors and create a better experience for you. By clicking on "Accept", you accept its use. To find out more, please see our privacy policy.