От компонентов класса к хукам: краткая история

Перехватчики React позволяют функциональным (неклассовым) компонентам иметь состояние и логику и потенциально могут полностью заменить компоненты на основе классов. Я надеюсь, что этот пост остановится на этом переломном моменте в разработке React и поможет опытным разработчикам понять преимущества хуков, а также поможет новым и будущим разработчикам понять компоненты старого стиля, которые заменили хуки.

До хуков: дихотомия интеллектуального и немого компонентов

До React 16.8 компоненты React можно было разделить на «умные» и «глупые» компоненты. Это не было комментарием к качеству кода или кодировщику, составляющим его, но способ отличить компоненты, которые задействовали логику и / или состояние (интеллектуальные компоненты), и те, которые просто отображали разметку (глупые компоненты).

Функциональные компоненты без сохранения состояния (тупой)

Давайте сначала рассмотрим более элегантный, но менее мощный «тупой» функциональный компонент без сохранения состояния. То есть компонент, который просто возвращает разметку.

Компоненты такого типа прекрасно справляются со своей очень простой задачей: берут некоторые данные (переданные здесь как title и description реквизиты) от своего более умного коллеги, а затем визуализируют эти данные в DOM. До перехвата, если мы хотели, чтобы компонент действительно извлекал данные или управлял каким-либо состоянием, это должно было быть значительно более сложным.

Компоненты класса (Smart)

Написание любой логики или состояния в компоненте (например, написание «умного» компонента) требовало создания компонента как класса JavaScript.

Внутри этого класса вы должны использовать constructor метод для инициализации состояния и, возможно, привязки пользовательских методов к компоненту класса. Затем вы должны ссылаться на состояние компонента по всему компоненту с помощью this.state, и обновлять любые значения в состоянии с помощью this.setState({item: value});.

Хотя технически требуется только render() метод, вы можете использовать встроенные в React методы жизненного цикла, которые вызываются в нескольких критических точках жизненного цикла компонента (рендеринг, непосредственно перед монтированием, размонтированием и т. Д.). Вы также можете написать свои собственные пользовательские методы, которые могут вызываться на любом из этих этапов жизненного цикла или запускаться действием пользователя в приложении.

Давайте посмотрим на пример компонента класса с некоторым простым состоянием, методом быстрой выборки данных и некоторой супер базовой разметкой.

Проблема, которую решают крючки

Как видите, компоненты на основе классов быстро становятся громоздкими даже с минимальной логикой и состоянием. Есть также некоторые «подводные камни» JavaScript с правильной привязкой this к компоненту, которые поначалу сбивают с толку всех, кроме самых эрудированных мастеров JavaScript.

Хуки позволяют вводить логику и состояние функциональных компонентов, больше не требуя использования класса, и всех дополнительных строк кода, которые поставляются с компонентом на основе классов.

Хотя я бы не назвал синтаксис хуков интуитивным, он определенно элегантен. Давайте посмотрим на наш приведенный выше пример компонента после тщательной привязки .

Пишите меньше кода

Самым ярким изменением здесь является размер компонента. В нашем примере с предварительными перехватами было 40 строк. В нашем примере на основе хуков одна и та же логика, состояние и разметка были записаны всего в 19 строк! Это сэкономит ваше время в напряженный день и продлит жизнь вашей больной клавиатуре Macbook Pro. Вы также увидите, что это преимущество меньшего количества строк становится еще более очевидным при преобразовании компонентов больших классов.

объекты состояния и вызовы setState ➡️ useState

Инициализация useState немного странная, но она позволяет гораздо более элегантно ссылаться на ваше состояние в вашем JSX и упростить обновление состояния. Вместо инициализации объекта состояния и обновления его значений с помощью React.setState вы инициализируете значение и соответствующую функцию для обновления этого значения, а затем передаете начальное значение useState(). В нашем примере строка инициализации заголовка выглядит так:

const [title, setTitle] = useState('');

Затем на него можно будет ссылаться в вашем JSX, просто используя title, а не this.state.title в старом стиле. Соответственно, заголовок можно обновить с помощью setTitle(value), а не this.setState({title: value});.

Методы жизненного цикла ➡️ useEffect

useEffect эффективно заменяет все методы жизненного цикла, используемые в компонентах класса. Очень просто: любая логика, записанная в функцию useEffect, будет выполняться при рендеринге компонента и в любое время при его обновлении. Здесь вы захотите запустить любую настройку компонента, которая могла произойти ранее в componentWillMount() функции.

По умолчанию это выполняется каждый раз, когда компонент изменяется или отображается, но есть параметры для управления конкретными изменениями, которые запускают эффект. Я бы посоветовал людям ознакомиться с документами, чтобы узнать подробности об этом, но быстрый ответ заключается в том, что это контролируется массивом элементов состояния, переданным в качестве второго аргумента функции useEffect(). Если используется, эффект будет выполняться только при обновлении любой из этих предоставленных частей состояния, а не каждый раз при обновлении компонента.

useEffect также имеет встроенную возможность очистки при размонтировании компонента. Используйте оператор return для useEffect, чтобы вернуть функцию, которая будет вызываться всякий раз, когда ваш компонент будет отключен от DOM. Это хорошее место для удаления прослушивателей событий и любого другого мусора, который в противном случае вы могли бы оставить в своем коде.

Подводя итог ..

Хуки были сдвигом парадигмы в разработке React. Мы можем рассчитывать на то, что в обозримом будущем мы будем писать компоненты таким образом, поэтому я призываю всех отставших (вроде меня до недавнего времени) найти время, чтобы понять их.

Тем не менее, поскольку никто в здравом уме не собирается переписывать сложное приложение для использования хуков только потому, что они новые и блестящие, разработчики React некоторое время будут работать с этими компонентами старого стиля. Я надеюсь, что этот пост поможет разработчикам понять проблемы, для которых решены эти типы компонентов, и то, как хуки улучшили то, что они начали.