Type-checking React and Redux (+Thunk) with Flow — Part 1

Satyajit Sahoo

blog content

Need help with Performance Optimization? 
hire us
Need help with Super app development
hire us
Need help with React Native?
hire us
Need help with migration to React Native?
hire us
Our React Native EU Conference is back
register nowlearn more

If you don’t know what Flow is, it’s a static type-checker for JavaScript. I love it because it detects errors in my code even before I run it and provides awesome autocomplete experience.

Now, I’m obsessed with always type-checking my code, and I’ve come across many roadblocks when doing that, because there aren’t always examples available. I’ll share what I’ve learned during my usage of Flow with React, and hopefully it’ll improve your experience with Flow with React code.

type check all the things

I’m assuming you’ve already followed the guide on flow’s website and know about basic usage. If you’ve not, go read it and then come back to this article.

Let’s get started, shall we?

Stateless Function Components

Type-checking stateless function components is just like type-checking plain functions. A stateless function component takes the props object as its argument. So we just have to specify the type for it.

For example:

Simple, right? Now when you don’t pass the correct props, flow warns:

Flow warning


You can also type-check the children prop. For example:

For normal components accepting children, this should be fine. However, you may add a more specific type definition if you need.

If you want to use React’s default props, flow doesn’t understand them with function components, so you need to use the default parameters syntax. For example:

Also note the | character at the beginning and end of the type definition. This is the exact object type syntax. Using it will make sure that you don’t pass any extra props to the component that it doesn’t receive. You could leave it out, but it is nice to have because it can catch typos etc.

Class Components

A class component can have props and state, so we need to specify types for a bit more.

Now, when we forget to pass a prop, Flow warns:

Flow warning

This is a bit confusing since it warns in the component we’re passing the props to rather than where we’re passing the props, but if you run Flow from CLI or have CI setup in your repo, you can catch this error.

Note that here we’re not passing a time prop, but since it’s in the defaultProps, Flow understands that and doesn’t warn.

Since we’ve declared the type of state here, if you forget to declare a property, declare wrong type or do setState with wrong type, flow will warn you.

Flow warning - wrong type

Note that the caveat mentioned about children props above still apply here.

If your component doesn’t accept props, you can define it as just {}(empty object). If it doesn’t have state, you can leave it out:

Transferring Props

Sometimes we have components which consume one or more props, and transfer rest of the props to another component using the spread operator. The intermediate component could be a simple wrapper which does something like data fetching and passes a prop to underlying component, or just changes some behaviour.

For example:

It is not clear how to avoid having to declare all the prop types again in the intermediate component. But fear not, it’s possible.

Flow has a feature called generics, which lets you declare an abstract type without having to know what’s inside. Check the docs on the Flow website to know more about it. Flow also has another feature where you can specify the type as * to let flow infer the type. We can combine both to achieve what we want.

For example, say we have an Article component, and a wrapper IntermediateArticle component, and we want to avoid declaring all the prop types again in IntermediateArticle component. We can do something like this:

Notice the line: function IntermediateArticle<T: *>(props: IntermediateArticleProps<T>)

Here, we’re declaring an abstract type, and by saying T: *, we’re telling flow to infer it. So Flow basically infers the rest of the props and we don’t have to declare the prop types of Article again.

Flow still gives us error when we forget to pass some props:

For class components, we need to do some modifications:

And flow will warn us when we forget to pass props:

Flow warning props pass 2


Higher Order Components

HOCs are common pattern in React where we have a function which takes a React component, adds some functionality, and then returns an enhanced component.

Sometimes we inject a new prop to the wrapped component. To type-check such an HOC, we can annotate it as follows:

Here we take advantage of abstract types as well as generics.

Static type-checking in JavaScript is pretty new, and there’s so much to explore and improve. Even though flow is pretty good at inferring types, it’s not always obvious how to type-check your code. I hope this article was a good starting point for you to start introducing flow to your React codebase. If you have any tips or improvements, please let me know.This is the first part of a two part series and only covers React. If you want to read about type-checking Redux, see part 2.

Satyajit Sahoo
Satya is in the 2016 Facebook’s TOP 5 external contributors list. You can find him everywhere. Satya is also a React & React Native ninja that will make your apps to stand above the others.
arrow icon
MORE posts from this author

Bundle React Native apps using Webpack features

Discover Re.Pack – a Webpack-based toolkit that allows you to build a React Native app with the full support of the Webpack ecosystem.

learn more

More posts from this category

Ensure your React components perform as intended as your app grows

Discover Reassure - our open-source library that allows you to run performance tests measuring the average rendering time of the in-app components.

business benefits

Performance Optimization

To stay competitive, you need a high-performing app. Improving React Native performance can bring your company many business and tech benefits. To learn more about it, check the page entirely dedicated to React Native Performance Optimization. Discover a real-life example of React Native optimization we performed for Aaqua, a Singaporean platform that enables global users to share their passion through groups.

Bundle React Native apps using Webpack features

Discover Re.Pack – a Webpack-based toolkit that allows you to build a React Native app with the full support of the Webpack ecosystem.

business benefits

Why React Native?

Building an all-in-one platform can bring your company a lot of business and tech benefits like seamless UX experience, global reach, brand growth just to name a few. To learn more about the benefits of using React Native to develop super apps, check out the MoMo case study. Where we helped improve app's performance by migrating architecture to Re.Pack.

stay tuned

Subscribe to our newsletter

You may unsubscribe from these communications at any time. For details see the Privacy Policy.