Разделение задач с помощью перехватчиков React PlatoBlockchain Data Intelligence. Вертикальный поиск. Ай.

Разделение проблем с помощью хуков React

Если вы некоторое время работали с React, вы, вероятно, сталкивались с контейнер и презентационные компоненты , или умные и тупые компоненты. Эти термины описывают описания который отделяет слой пользовательского интерфейса компонентов React от логики.

В отделении пользовательского интерфейса от бизнес-логики нет ничего уникального для React: разделение задач — это принцип дизайна, который уже был в 70-х. Например, общепринятой практикой является отделение кода, обращающегося к базе данных, от бизнес-логики серверной части.

Итак, в React мы решили эту проблему, создав компоненты-контейнеры, содержащие всю логику, которые затем передавали данные через свойства в презентационный компонент.

С введением хуков React появился новый подход к этому: использование нестандартные крючки.

Почему мы должны отделять логику от компонента?

Прежде чем мы начнем отделять логику от наших компонентов React, мы должны знать, почему.

Организация нашего кода таким образом, чтобы каждая функция или компонент отвечали только за одну вещь, имеет то преимущество, что проще менять и обслуживать (Дэйв и Эндрю называют это «ортогональностьв своей книге Прагматичный программист).

Применение этого к React означает, что наш компонент будет выглядеть чище и организованнее. Например, нам не нужно прокручивать стену логики перед редактированием пользовательского интерфейса.

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

Тестирование также более доступно: мы можем протестировать логику отдельно от пользовательского интерфейса, если захотим. Однако самым значительным преимуществом для меня является то, как этот подход организует мой код.

Как отделить логику с помощью хуков React

Чтобы отделить логику от нашего компонента, мы сначала создадим собственный хук.

Возьмем этот компонент в качестве примера. Он вычисляет экспоненциальное значение основного числа и показателя степени:

Вы можете найти полный исходный код здесь.

Код выглядит следующим образом:

export const ExponentCalculator = () => {
  const [base, setBase] = useState(4);
  const [exponent, setExponent] = useState(4);
  const result = (base ** exponent).toFixed(2);

  const handleBaseChange = (e) => {
    e.preventDefault();
    setBase(e.target.value);
  };

  const handleExponentChange = (e) => {
    e.preventDefault();
    setExponent(e.target.value);
  };

  return (
    <div className="blue-wrapper">
      <input
        type="number"
        className="base"
        onChange={handleBaseChange}
        placeholder="Base"
        value={base}
      />
      <input
        type="number"
        className="exponent"
        onChange={handleExponentChange}
        placeholder="Exp."
        value={exponent}
      />
      <h1 className="result">{result}</h1>
    </div>
  );
};

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

В качестве первого шага мы будем переместите логику в пользовательский хук и вызовем его внутри нашего компонента.

const useExponentCalculator = () => {
  const [base, setBase] = useState(4);
  const [exponent, setExponent] = useState(4);
  const result = (base ** exponent).toFixed(2);

  const handleBaseChange = (e) => {
    e.preventDefault();
    setBase(e.target.value);
  };

  const handleExponentChange = (e) => {
    e.preventDefault();
    setExponent(e.target.value);
  };

  return {
    base,
    exponent,
    result,
    handleBaseChange,
    handleExponentChange,
  };
};

export const ExponentCalculator = () => {
  const {
    base,
    exponent,
    result,
    handleExponentChange,
    handleBaseChange,
  } = useExponentCalculator();

  // ...
};

Мы могли бы переместить этот крючок в отдельный файл для более заметного разделения интересов.

Кроме того, мы можем дополнительно разделить наш хук на более мелкие повторно используемые функции. В этом случае мы можем извлечь только calculateExponent.

использоватьExComponentCalculator.js

const calculateExponent = (base, exponent) => base ** exponent;

const useExponentCalculator = () => {
  const [base, setBase] = useState(4);
  const [exponent, setExponent] = useState(4);
  const result = calculateExponent(base, exponent).toFixed(2);

  // ...
};

Тестировать эти функции гораздо проще, чем тестировать весь код компонента из первого примера. Мы могли бы протестировать их с любой библиотекой тестирования Node.js, которой даже не нужно поддерживать компоненты React.

Теперь у нас есть код, специфичный для фреймворка (React), в коде компонента и хука, в то время как наша бизнес-логика живет в различных функциях, которые мы определили позже (которые не зависят от фреймворка).

Лучшие практики

Именование

Мне нравится называть свои пользовательские хуки после компонента как конкатенацию use и имя компонента (например, useExponentCalculator). Затем я звоню подать то же самое как крючок.

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

Если я могу повторно использовать части пользовательского хука, я обычно перемещаю его в другой файл под src/hooks.

Не переусердствуйте

Постарайтесь быть прагматичным. Если в компоненте всего несколько строк JS, логику выделять не нужно.

CSS-в-JS

Если вы используете библиотеку CSS-in-JS (useStyles), вы также можете переместить этот код в другой файл.

Вы можете переместить его в тот же файл, что и хук. Однако я предпочитаю либо держать его над компонентом в том же файле, либо перемещать его в отдельный файл, если он становится слишком большим.

Заключение

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

Пользовательские хуки — это только один из способов увеличить модульность; я бы тоже очень рекомендовал разделение компонентов и функций на более мелкие повторно используемые фрагменты когда возможно.

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

Отметка времени:

Больше от Codementor Реагировать Факт