Adding ES7 Class Properties to an ES6 React Component

I’ve been investigating React and Flux over the last three posts, but one thing really didn’t sit right with me. That one thing is the React PropTypes in an ES6 class. I had to do something like this:

import React from 'react';

class NavBrand extends React.Component {
  render() {

NavBrand.propTypes = {
  title: React.PropTypes.string.isRequired

export default NavBrand

It’s ES6 code, but the fact that I have to munge the class after it has been created did not sit well. I wanted the propTypes to be a part of the class – just like a class in just about every other language.

Fortunately, there is a current proposal for class properties in ES7 (or ES2016 or ES vNext). It’s not ratified yet and the proposal may change. The ES6 version (above) is ratified and perfectly valid code. Let’s look at what the alternate ES7 version would look like:

import React from 'react';

export default class NavBrand extends React.Component {
  static propTypes = {
    title: React.PropTypes.string.isRequired

  render() {
    return (<h1>{this.props.title}</h1>);

I like the aesthetics of this version much more than the ES6 version. The propTypes is in the right place.

The bad news: This doesn’t lint and it doesn’t compile.
The good news: We can fix that!


I use eslint for my linter. You can change the parser that eslint uses so that it uses babel just like the compiler stage. Anything that would go through the compiler will go through the linter as well. To do this I need another package – babel-eslint:

npm install --save-dev babel-eslint

Then I need to adjust my .eslintrc file to use the new parser:

  "parser": "babel-eslint",
  "plugins": [

Linting will pass if you run eslint on that JSX file, or if you run gulp eslint from my tutorial code. If you introduce an error (say, removing the semi-color from the return statement), eslint will still catch that.


To fix the transpiling, I need to make changes to my task. Here is the new task:

var babelify = require('babelify'),
    browserify = require('browserify'),
    gulp = require('gulp'),
    rename = require('gulp-rename'),
    source = require('vinyl-source-stream');

var config = {
    dest: './wwwroot'

var files = {
    entry: './app.jsx'

gulp.task('bundle', ['eslint'], function () {
    var bundler = browserify({
        extensions: ['.js', '.jsx'],
        transform: [babelify.configure({
          optional: [ "es7.classProperties" ]
        debug: true // produce source maps

    return bundler.add(files.entry)

Of course, you will put the requires at the top of your gulp file, and have extra stuff in the config and files objects. However, the task itself works. Note that I need to configure babelify to add in an optional configuration list that enables es7.classProperties. If your code uses one of the other optional experimental features, you can list those too.

Thanks to this, I can now convert all my React components to use the ES7 class properties syntax. I hope this proposal makes it in.