Почему useEffect выполняется дважды в React

Если вы недавно создали новый проект с помощью Create React App
или обновились до React версии 18, вы увидите, что хук useEffect выполняется дважды в режиме разработки.

Если вы новичок в использовании хука useEffect, вы можете прочитать одну из моих предыдущих статей: полное руководство по использованию хука useEffect.

Воспроизведение проблемы

Создайте новое приложение react с помощью следующей команды:

npx create-react-app react-use-effect-twice
Войти в полноэкранный режим Выйти из полноэкранного режима

Обновите App.js следующим кодом:

import { useEffect } from "react"

function App() {
  useEffect(() => {
    console.log("useEffect executed (component mounted)")
  }, [])

  return <div className="App"></div>
}

export default App
Войти в полноэкранный режим Выйти из полноэкранного режима

Здесь у нас есть хук useEffect, и мы регистрируем сообщение внутри него.

Если вы запустите приложение и откроете консоль браузера, вы увидите, что сообщение отображается дважды.

Понимание проблемы

В StrictMode, начиная с React 18, в режиме разработки эффекты будут монтироваться, размонтироваться и снова монтироваться.

Это происходит только в режиме разработки, но не в режиме производства.

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

Мы можем подтвердить это поведение, добавив функцию очистки в хук useEffect:

import { useEffect } from "react"

function App() {
  useEffect(() => {
    console.log("useEffect executed (component mounted)")
    return () => {
      console.log("useEffect cleanup (component unmounted)")
    }
  }, [])

  return <div className="App"></div>
}

export default App
Вход в полноэкранный режим Выход из полноэкранного режима

Если вы запустите приложение, то увидите следующие сообщения в консоли браузера:

Устранение проблемы

Если вы читали предыдущий раздел, это не совсем проблема. Следовательно, она не требует исправления.

Если вы все же хотите, чтобы useEffect не вызывался дважды, вы можете удалить тег <StickMode> из файла index.js.

Оцените статью
devanswers.ru
Добавить комментарий