Using React with TypeScript
In this page:
interface ComponentProps {
name: string;
count?: number;
}
function Component({ name, count = 0 }: ComponentProps) {
const [value, setValue] = useState<string>("");
const handleChange = (e: React.ChangeEvent<HTMLInputElement>) => setValue(e.target.value);
return <input value={value} onChange={handleChange} />;
}
Typing Component Props
Defining an interface (or type alias) describing a component's expected props, then using it as the type for the props parameter, lets TypeScript catch mistakes like a missing required prop or a value of the wrong type at compile time, before the code ever runs.
Example: Typing Component Props
// Run in your local React project (npm install required)
interface GreetingProps {
name: string;
age?: number; // optional
}
function Greeting({ name, age }: GreetingProps) {
return <p>Hello, {name}{age ? ` (${age})` : ''}</p>;
}
Typing useState
TypeScript usually infers a useState hook's type automatically from its initial value, like useState(0) being inferred as number. When the initial value doesn't fully capture the intended type (like an empty array that will later hold strings), you specify the type explicitly with a generic.
Example: Typing useState
// Run in your local React project (npm install required)
function TodoList() {
const [todos, setTodos] = useState<string[]>([]);
const addTodo = (text: string) => setTodos([...todos, text]);
return <button onClick={() => addTodo('New task')}>Add ({todos.length})</button>;
}
Typing Event Handlers
React's built-in TypeScript types include specific event types, like React.ChangeEvent<HTMLInputElement> for an input's onChange handler, giving you correct autocomplete and type-checking on properties like event.target.value.
Example: Typing Event Handlers
// Run in your local React project (npm install required)
function SearchBox() {
const [query, setQuery] = useState('');
const handleChange = (e: React.ChangeEvent<HTMLInputElement>) => {
setQuery(e.target.value);
};
return <input value={query} onChange={handleChange} />;
}
- Typing a component's props as any, which defeats the entire purpose of adding TypeScript.
- Forgetting the React import needed for JSX.Element or React.FC return types in some TS configurations.
- Not typing useState's generic when the initial value doesn't clearly imply the full type (like starting a list with an empty array).
- TypeScript adds static type-checking to React, catching many prop/state mismatches before runtime.
- A component's props are typically typed with an interface or type alias for its props object.
- useState<Type>(initialValue) lets you specify a hook's type explicitly when it can't be inferred correctly.
- TypeScript integrates directly into React's existing patterns — components, hooks, and props all get typed, not replaced.
Requires a TypeScript-aware build setup (Vite/Next.js templates support it out of the box); works with any React version.
Chapter Quiz — Complete all 14 topics to unlock
0/14 topics done
Complete these topics first:
- Error Boundaries
- React Portals
- Modals using Portals (practical use)
- React Suspense
- Code Splitting with React.lazy
- Introduction to Server Components
- Introduction to Next.js (server-side React)
- Using React with TypeScript
- Scalable Folder Architecture
- Common React Design Patterns
- Component Documentation with Storybook
- Accessibility (a11y) in React
- i18n with react-i18next
- React Security Best Practices