Окружай себя правильно
#frontend #reactjs #nodejs
Недавно мы получили frontend-приложение на React.js для оценки трудозатрат по расширению его функциональности. Для того чтобы запустить полученный сервис, нам пришлось модифицировать код. Всему виной — отсутствие механизма работы с переменными окружения.
DevOps-инженер должен иметь возможность конфигурировать приложение в рамках конкретной среды развертывания. А разработчик должен обеспечить такую возможность без вмешательства в код.
К переменным окружения относятся порты, на которых будет запущено приложение или URL-адрес RESTful-сервиса. Значения этих параметров могут отличаться для разных сред, например, для тестового стенда и боевого сервера.
В проектах мы выделяем такие переменные в .env-файлы. А чтобы упростить процесс развертывания и ничего не потерять, в репозиторий проекта укладывается файл .env.example. Он содержит перечень всех переменных окружения для текущего проекта. Файл .env создается путем копирования .env.example и не находится под контролем git.
Для конфигурации react-приложений можно использовать npm-пакет dotenv.
#frontend #reactjs #nodejs
Недавно мы получили frontend-приложение на React.js для оценки трудозатрат по расширению его функциональности. Для того чтобы запустить полученный сервис, нам пришлось модифицировать код. Всему виной — отсутствие механизма работы с переменными окружения.
DevOps-инженер должен иметь возможность конфигурировать приложение в рамках конкретной среды развертывания. А разработчик должен обеспечить такую возможность без вмешательства в код.
К переменным окружения относятся порты, на которых будет запущено приложение или URL-адрес RESTful-сервиса. Значения этих параметров могут отличаться для разных сред, например, для тестового стенда и боевого сервера.
В проектах мы выделяем такие переменные в .env-файлы. А чтобы упростить процесс развертывания и ничего не потерять, в репозиторий проекта укладывается файл .env.example. Он содержит перечень всех переменных окружения для текущего проекта. Файл .env создается путем копирования .env.example и не находится под контролем git.
Для конфигурации react-приложений можно использовать npm-пакет dotenv.
12factor.net
The Twelve-Factor App
A methodology for building modern, scalable, maintainable software-as-a-service apps.
Останься в памяти моей
#frontend #backend #reactjs #nodejs
Даже опытный react-разработчик может не до конца осознавать, как используется оперативная память компонентами его приложения. Недавно мы обнаружили memory leak в сервисе — через N дней многопоточное приложение на стороне SSR переставало работать из-за нехватки оперативной памяти.
Оказалось, что при очередном запросе пользователя составной заголовок страницы записывался в глобальный объект, не затирая предыдущие значения.
Встречается распространенная проблема, при которой react-компонент был размонтирован, но инициализированные в нем
С ростом кодовой базы продукта увеличивается и объем хранимой информации как на стороне клиента, так и на стороне сервера. Повышается вероятность возникновения новых утечек.
На стороне клиента контролировать потребляемую браузером память и работу сборщика мусора помогают инструменты разработчика. Например, браузер Google Chrome и его DevTools позволяют делать периодические снепшоты состояния памяти в различные промежутки времени работы приложения. Снимки можно анализировать и сравнивать между собой специальными средствами.
На серверной стороне также возможно настроить мониторинг используемой памяти. Для этого необходимо запустить nodejs с флагом --inspect и открыть в Chrome специальную страницу
#frontend #backend #reactjs #nodejs
Даже опытный react-разработчик может не до конца осознавать, как используется оперативная память компонентами его приложения. Недавно мы обнаружили memory leak в сервисе — через N дней многопоточное приложение на стороне SSR переставало работать из-за нехватки оперативной памяти.
Оказалось, что при очередном запросе пользователя составной заголовок страницы записывался в глобальный объект, не затирая предыдущие значения.
Встречается распространенная проблема, при которой react-компонент был размонтирован, но инициализированные в нем
setTimeout или setInterval не были остановлены и продолжают выполняться в фоне. Сборщик мусора не будет выполнять очистку памяти от данных, используемых в этих методах, следовательно, происходит систематическая утечка памяти.С ростом кодовой базы продукта увеличивается и объем хранимой информации как на стороне клиента, так и на стороне сервера. Повышается вероятность возникновения новых утечек.
На стороне клиента контролировать потребляемую браузером память и работу сборщика мусора помогают инструменты разработчика. Например, браузер Google Chrome и его DevTools позволяют делать периодические снепшоты состояния памяти в различные промежутки времени работы приложения. Снимки можно анализировать и сравнивать между собой специальными средствами.
На серверной стороне также возможно настроить мониторинг используемой памяти. Для этого необходимо запустить nodejs с флагом --inspect и открыть в Chrome специальную страницу
chrome://inspect. Здесь настраивается интеграция с серверной частью вашего приложения для работы отладочного механизма. Затем процесс работы со снимками памяти сервера и их анализа происходит в таком же интерфейсе, как и в случае с клиентской частью.React: профилирование жизненного цикла
#frontend #reactjs
Среди React-разработчиков популярно браузерное расширение React DevTools, позволяющее отлаживать клиентскую часть React-приложения. Это расширение содержит полезный инструмент профилирования, который нативно поддерживается самой библиотекой React, начиная с версии 16.5.
Используя профилировщик, можно анализировать жизненный цикл и производительность вашего приложения, выявляя потенциальные проблемы оптимизации.
Рассмотрим пример уровня кода. В функциональный компонент
Такие ситуации легко обнаружить с помощью профилировщика, который покажет списки компонентов в древовидной структуре и данные по каждому компоненту: количество рендеров, текущие пропсы и затраченное время на его обновление.
В текущем примере для оптимизации повторного рендеринга компонентов применим механизм мемоизации, представленный в HOC
На Reactjs.org есть отличное введение, которого будет достаточно для базовой проверки своих проектов.
#frontend #reactjs
Среди React-разработчиков популярно браузерное расширение React DevTools, позволяющее отлаживать клиентскую часть React-приложения. Это расширение содержит полезный инструмент профилирования, который нативно поддерживается самой библиотекой React, начиная с версии 16.5.
Используя профилировщик, можно анализировать жизненный цикл и производительность вашего приложения, выявляя потенциальные проблемы оптимизации.
Рассмотрим пример уровня кода. В функциональный компонент
SomeList передается объект с данными состояния dataSource из родительского компонента App. SomeList содержит дочерний компонент SomeItem, который оперирует переданным ему dataSource-объектом. При обновлении состояния в компоненте App, даже если сам объект dataSource не изменился, производится цепной ререндер нижестоящих компонентов SomeList и SomeItem, которые отслеживают dataSource. В данном случае обновление этих компонентов является избыточным.Такие ситуации легко обнаружить с помощью профилировщика, который покажет списки компонентов в древовидной структуре и данные по каждому компоненту: количество рендеров, текущие пропсы и затраченное время на его обновление.
В текущем примере для оптимизации повторного рендеринга компонентов применим механизм мемоизации, представленный в HOC
React.memo(...). Теперь запустим профилировщик и почувствуем разницу.На Reactjs.org есть отличное введение, которого будет достаточно для базовой проверки своих проектов.
Во всем виноваты объекты[?]
#frontend #reactjs
Хуки, без сомнения, можно назвать главной фичей React-библиотеки. Однако из-за перехода от классовых компонентов к функциональным появился ряд подводных камней. Об одном камушке расскажем далее 👇
Распространенной ошибкой при использовании механизма хуков является неоптимальное применение массива зависимостей. Иногда в зависимостях перечисляют объекты, которые могут стать причиной лишних вычислений и ререндера компонентов.
Например, наш код производит сложнейшие вычисления на основе данных, полученных из локального хранилища 😱
Казалось бы, все правильно: есть сложное вычисление, и мы его мемоизируем. Но если объект data обновится, а значения его свойств count и limit не изменятся, то хук useMemo снова выполнится, вместо того чтобы вернуть уже вычисленное значение, которое также не изменилось.
Это связано с тем, что хуки в своих зависимостях используют для сравнения объектов строгое равенство, не сличая при этом значения свойств.
Решить проблему достаточно легко. Можно заставить хук сравнивать только необходимые нам конечные свойства объекта. Вот так. Теперь useMemo будет вычислять новое значение, только если изменятся свойства count или limit.
Добавлять объекты как зависимости хука нужно только при крайней необходимости. В остальных же случаях лучше использовать примитивы. Мы рекомендуем добавить в проект правила для линтера, которые помогут контролировать использование хуков React.
#frontend #reactjs
Хуки, без сомнения, можно назвать главной фичей React-библиотеки. Однако из-за перехода от классовых компонентов к функциональным появился ряд подводных камней. Об одном камушке расскажем далее 👇
Распространенной ошибкой при использовании механизма хуков является неоптимальное применение массива зависимостей. Иногда в зависимостях перечисляют объекты, которые могут стать причиной лишних вычислений и ререндера компонентов.
Например, наш код производит сложнейшие вычисления на основе данных, полученных из локального хранилища 😱
Казалось бы, все правильно: есть сложное вычисление, и мы его мемоизируем. Но если объект data обновится, а значения его свойств count и limit не изменятся, то хук useMemo снова выполнится, вместо того чтобы вернуть уже вычисленное значение, которое также не изменилось.
Это связано с тем, что хуки в своих зависимостях используют для сравнения объектов строгое равенство, не сличая при этом значения свойств.
Решить проблему достаточно легко. Можно заставить хук сравнивать только необходимые нам конечные свойства объекта. Вот так. Теперь useMemo будет вычислять новое значение, только если изменятся свойства count или limit.
Добавлять объекты как зависимости хука нужно только при крайней необходимости. В остальных же случаях лучше использовать примитивы. Мы рекомендуем добавить в проект правила для линтера, которые помогут контролировать использование хуков React.