В чем отличие между React.createClass и class extends React.component?

392
11 марта 2017, 03:28

Недавно начал учить React по видео-урокам. Пробовал писать всякие "штуки" на нем и как-то наткнулся на переведенную на русский официальную документацию вот с таким вот примером:

class Form extends React.Component {
    constructor(props) {
        super(props);
        this.state = {value: ''};
        this.handleChange = this.handleChange.bind(this);
        this.handleSubmit = this.handleSubmit.bind(this);
    }
    handleChange(event) {
        this.setState({value: event.target.value});
    }
    handleSubmit(event) {
        alert('Text field value is: ' + this.state.value);
    }
    render() {
        return (
                <div>
                    <input type="text"
                     placeholder="Hello!"
                     value={this.state.value}
                     onChange={this.handleChange} />
                    <button onClick={this.handleSubmit}>
                        Submit
                    </button>
                 </div>
             );
    }
}
 ReactDOM.render(
     <Form />,
     document.getElementById('root')
 );

В видео-уроках по которым учился я было немного не так, а именно:

  1. В чем отличие от создание компонента путем наследования class Form extends React.Component от обычного React.createClass()?
  2. Зачем в конструкторе класса привязывается this с помощью bind, если оно и без этого работает?
  3. В чем вообще преимущество кода из документации перед моим кодом? (ниже)
var Form = React.createClass({
    getInitialState: function(){
        return {
            value: ""
        }
    },
    handleChange(e){
        this.setState({value: e.target.value});
    },
    handleSubmit(e){
        alert("Text field value is: " + this.state.value);
    },
    render: function(){
            return (
                <div>
                    <input type="text"
                     placeholder="Hello!"
                     value={this.state.value}
                     onChange={this.handleChange} />
                    <button onClick={this.handleSubmit}>
                        Submit
                    </button>
                 </div>
             );
    }
});
ReactDOM.render(
        <Form />,
        document.getElementById('root')
);

Заранее спасибо:3

Answer 1

Это два способа сделать одно и то же.
В самом фейсбуке считают es6 классы более семантически верными и лелеют себя мыслью когда-нибудь в далеком-далеком счастливом будущем поддержку React.createClass прекратить (источник, первый абзац). Но будет это не в ближайший год и не в два, пока createClass даже не deprecated.

Ответ на ваш третий вопрос: пока это два равнозначных способа.
Лучше привыкать писать es6-классы, но как там будет в будущем на самом деле предсказать сложно.

Главные отличия:

  1. Классы - это es6 фича. Соответственно вся транспиляторская магия для полноценной работы с es6 у вас должна присутствовать.

  2. В React.createClass внутри работает тайная магия которая автоматически биндит все методы переданные в createClass к this. В компонентах es6-классов от такой штуки решили отказаться, потому что она часто смущала разработчиков, и биндить надо ручками. Оттуда кстати вытекает ответ на ваш второй вопрос: без этого - не работает.

  3. В компонентах-es6-классах нет миксинов. Совет мудрецов разрабатывающих реакт решил что миксины нехорошо, хорошо - композиция. И решил не давать возможность писать нехорошо в новых версиях.

  4. Вместо getInitialState используется constructor так как решили что это идиоматичнее для es6 классов, также propTypes - свойство самого класса, вместо метода getDefaultProps есть свойство класса defaultProps

Возможно есть еще какие-то отличия о которых я не вспомню, лично у меня в рабочем проекте есть и createClass в старом коде и es6 классы в новом. getInitialState аутобиндинг и propTypes - это явные заметные отличия, es6 итак уже обычно есть, миксины используют довольно редко.

READ ALSO
Не отправить большую строку POSTом

Не отправить большую строку POSTом

Здравствуйте! Через ajax пытаюсь отправить строку (файлы закодированные в base64) типа jsonПроблема в том, что если кодирую файлы общим объемом примерно...

223
Изменение порядка следования колонок в Datatables по клику

Изменение порядка следования колонок в Datatables по клику

ЗдравствуйтеИспользую плагин datables для верстки таблицы

246
Dependency injection как можно сделать лучше?

Dependency injection как можно сделать лучше?

В общем делаю как то так, думаю как сделать так чтобы можно было обратиться к существующему объекту

181
Адаптивность JS

Адаптивность JS

Есть меню-сендвич, который выезжал вниз на контент, чтобы этого не случилось при клике на меню добавил padding-top у этого самого контентаВстал...

239