React PropTypes header image of a coast guard

Validating Props easily with React PropTypes

React PropTypes are a good way to help you catching bugs by validating data types of values passed through props. They also offer possibilities to flag props as mandatory or set default values. They provide a great benefit with little effort. 

Header Photo by Fré Sonneveld on Unsplash

Introduction

If you want to pass any value to a component, you won’t get around props. They are the component’s interface to get data passed down the component tree. When your application got bigger and more complex, you or one of your colleagues may want to reuse some existing components. Maybe you wrote the component a long time ago, so you have to find out, how to use it and which props are required.

To find that out, you have a look the source code of said component and have a look at all occurrences of this.props. You can imagine that this can take some time, depending on the component. But now that you know which props are mandatory, you can start – but wait, do you know what to pass down? Is it just a string or is an object required? You see, it’s not that easy. But there is a solution for that: React PropTypes.

What the heck are React PropTypes?

PropTypes not only help you to catch bugs, but also serve as a handy documentation on how a component has to be used in terms of passing props. Let’s have a look at a small example:

import React from 'react';
import PropTypes from 'prop-types';

const Person = (props) => <div> 
  <h1>{props.firstName} {props.lastName}</h1>
  {props.country ? <p>Country: {props.country}</p> : null}
</div>;

Person.propTypes = {
  firstName:PropTypes.string,
  lastName:PropTypes.string,
  country:PropTypes.string
};

export default Person;

As you can see, I created a little component to show a person’s name and it’s country. We show the first and last name as a header, and add a paragraph with the country, but only if it is set. For the beginning, I just created the PropTypes to define the type without caring about mandatory props.

So what does it do? PropTypes define the type of a prop. So each time, a value is passed through a prop, it get’s validated for it’s type. If you pass a value through a prop with a different data type than it is specified in the PropTypes, an error message will be printed in the console of your browser:

Warning: Failed prop type: Invalid prop `country` of type `number` supplied to `Person`, expected `string`.
The error message you get, when you pass a value with a wrong data type

If you set up your PropTypes like that, you already got the first benefits:

  • You can easily catch bugs caused by passing data in the wrong data type (e.g.: An object instead of a string)
  • Someone that uses your component can see all available props including their desired data type at one place.
  • Some code editors support code completion for props, so you can see the available props while typing in the component in a tooltip.

Now that we know what PropTypes are, and what they are good for, let’s see what else they could do.

Data Type Validation

As shown in the example above, React PropTypes are used for data type validation. That’s what they are made for. I think most of the time you might check for basic data types.

Basic data types, arrays and objects

Here is an example for basic data types and :

Person.propTypes = {
  email: PropTypes.string,
  age: PropTypes.number,
  worksRemote: PropTypes.bool,
  updateCallback: PropTypes.func
}

Further types that can be used are:

PropTypes.array,
PropTypes.arrayOf(PropTypes.string),
PropTypes.object,
PropTypes.objectOf(PropTypes.number)

Complex data types

It is even possible to validate a plain JavaScript object against a certain shape:

Person.propTypes = { 
  car: PropTypes.shape({
    registrationNumber: PropTypes.string,
    year: PropTypes.number
  })
}

What you’ve just seen is an example on how to validate an object, that has been passed through the “car” prop. If you pass an object with a field “year” that is a string, you’ll get an error message. That’s great!

Specifying a Range of Valid Prop Values

From time to time you might want to have a prop value passed, that is exactly one out of a given set of values. Doing so, could look like this:

Person.propTypes = {
  gender: PropTypes.oneOf([
    'female', 'male'
  ])
}

If you now pass “unknown” through the “gender” prop, your browser will show an error because it didn’t comply with the specified PropTypes:

Warning: Failed prop type: Invalid prop `gender` of value `unknown` supplied to `Person`, expected one of ["female","male"].
The passed property did not comply to the specified set of values
Apart from specifying the exact values, you can also specify a set of types for the prop:

PropTypes.oneOfType([
  PropTypes.string,
  PropTypes.number
])

Flagging Props as Mandatory

This is another important topic. If you want to require anyone who uses your component to always pass a certain prop, you can flag it as mandatory. See how you could do that – it’s easy 😉

You remember the example right at the beginning of this post? I’ll show it again, but now we mark the first and the last name as required:

[...]

const Person = (props) => <div> 
  <h1>{props.firstName} {props.lastName}</h1>
  {props.country ? <p>Country: {props.country}</p> : null}
</div>;

Person.propTypes = { 
  firstName:PropTypes.string.isRequired, 
  lastName:PropTypes.string.isRequired, 
  country:PropTypes.string 
}; 

[...]

That was easy, wasn’t it? You can chain “isRequired” to any given PropType data type, which will result in an error message, if the prop is not provided.

Set Default Prop Values

If you want certain props to have default values if nothing is provided, you can do this by defining defaultProps:

Person.defaultProps = {
  country: 'Austria' 
}

The above makes sure that every time someone usese the “Person” component and does not provide a country, the person automatically becomes an Austrian 😛

Wrapping up

React PropTypes are a great way to validate your component inputs. But also, if someone is going to use your component, it provides a quick overview of all the available props and the expected data types. So in your next component, try to use PropTypes to avoid some nasty bugs and improve the reusability of the component a lot.

Call to Action

Do you want to gain more experience with React, JavaScript and other cool web development stuff? Lucky you! I just started a weekly newsletter. You just have to subscribe, to get more tips for React and more delivered right into your inbox. I would be happy to count you to my subscribers 🙂

If you liked this article, you probably might also want to learn more about React Life Cycle Methods:

How to use React Lifecycle Methods


Thanks for reading the article until the end! I would appreciate if you let me know what you think. So leave me a comment, contact me on Twitter or send an email to hi@andreasreiterer.at – I’m happy to respond to any message I get.

 

 

Leave a Reply

Your email address will not be published. Required fields are marked *