Building forms with React Hook Form and TypeScript

JavaScript React TypeScript

Handling forms manually is not difficult in React. Keeping all of the code consistent in your project might be quite a hassle, though. There are many ways in which we can tackle the state of our forms and validation. We can expect the approach of our teammates to differ slightly. To manage our forms better, we look into the React Hook Form library that has gained quite a lot of traction lately.

In the past, we’ve covered Formik on this blog. We’ve also done it with the help of hooks API. This time, we look into how we can do similar things with React Hook Form. The knowledge from using Formik will come in handy because this time, we also use Yup for validation. We also point out some similarities and differences between Formik and React Hook Form.

Introducing React Hook Form

To start, we need to install the library. Since both Formik and React Hook Form are built with TypeScript, we don’t need any additional packages.

When creating forms with TypeScript, the first thing is to create an interface describing our data. Although we could omit it, we would lose many benefits that React Hook Form has to offer.

There a few notable things happening above. The most important is the function. With it, we can register inputs and let the React Hook Form handle them. For it to be successful, we need to make sure that the names of our inputs match our interface.

The second crucial thing is the method. Let’s look under the hood of the React Hook Form and inspect it closely.

Above there are quite a few generic types. If you want to know more about them, check out TypeScript Generics. Discussing naming conventions and More advanced types with TypeScript generics

We can see that as an argument, expects a function that handles the data of the form. Once the user submits the form, React Hook Form calls our submit handler.

Striving for clean code, I suggest creating custom React hooks. If you want to read more about it, check out JavaScript design patterns #3. The Facade pattern and applying it to React Hooks.

Moving the logic of the form into a custom hook helps us to get closer to the separation of concerns.

Validation with Yup

By default, the React Hook Form library utilizes the native HTML form validation. For a variety of reasons, we might want to implement something fancier. Both React Hook Form and Formik encourage the use of the Yup library.

There are a lot of possibilities when it comes to the Yup library. For a full list, check out the documentation.

As long as there are some errors, the React Hook Form library does not call the handler. We can also access the error messages through the object.

Accessing the context of the form

For more advanced forms, we might need to access the form properties outside of the submit handler. The returns the , but passing it through the component props might not be the cleanest approach.

The solution to the above issue is the and the .

After we inject the context using the , we can start using it with the hook.

To watch the value in real-time, we need to use the method provided by the React Hook Form library.

Providing default values

An important aspect of managing forms is handling the initial state. When dealing with initial values that are known on the first render, we can use the property.

A very common case is when we want to use data pulled from the API as the initial values of our form. In the documentation, we can find that the is cached at the first render within the custom hook. If you want to reset the , you should use the .

The above means that we need to use the function provided by React Hook Form to use the initial values that we access asynchronously.

I like to keep data fetching somewhat separate from the form management. To achieve that, we might pass a callback to our hook that deals with the data fetching.

To separate the logic of the form, I also create a custom hook for it.

We could also call the hook in to listen for the incoming data. This way, we wouldn’t have to pass a callback to .

One important thing is to somehow handle the variable. In this simple example, we hide the form until we finish fetching the necessary data.

On the contrary, Formik has the property and can automatically reinitialize the form when it changes.


In this article, we’ve learned quite a few things about how to use React Hook Form with TypeScript. Aside from the bare basics, we’ve learned how to validate the form using the Yup library. We’ve also learned how to deal with the initial value of the form with asynchronous data. Another thing that might come in handy is accessing the context of the form through the hook.

What’s your view on the React Hook Form library? Would you use it instead of Formik?

Notify of
1 Comment
Newest Most Voted
Inline Feedbacks
View all comments
Paulo Silva
Paulo Silva
3 years ago

thank you very much.. I’ve been using custom hook and since I decided test it for the first time I realized that was an amazing decision. The code achieves the approach of separation of concerns and looks like more elegant and easy to test.