SuperOleg dev notes

Description
Обзоры новостей и статей из мира frontend, интересные кейсы, исследования и мысли вслух

https://github.com/SuperOleg39

https://twitter.com/ODrapeza

@SuperOleg39
Advertising
We recommend to visit
HAYZON
HAYZON
6,442,108 @hayzonn

💼 How to create capital and increase it using cryptocurrency

👤 𝐅𝐨𝐮𝐧𝐝𝐞𝐫: @Tg_Syprion
🗓 ᴀᴅᴠᴇʀᴛɪsɪɴɢ: @SEO_Fam
Мои каналы: @mazzafam

Last updated 22 hours ago

Канал для поиска исполнителей для разных задач и организации мини конкурсов

Last updated 3 months ago

Новые и перспективные Web3 игры с добычей токенов.

Чат: https://t.me/Crypto_Wolf_Chat

Правила чата смотрите в описании чата.

Все свои вопросы направляйте в чат или главному модератору чата: @Exudna_118

По теме сотрудничества: @Zombini

Last updated 2 months, 2 weeks ago

2 months, 3 weeks ago
Крутой внутренний продукт вышел на публику …

Крутой внутренний продукт вышел на публику - https://t.me/unidrawio

Пользуюсь регулярно, в том числе проектировал в нем Microfrontends Platform (о котором уже рассказывал в этом канале), приятно порекламировать.

2 months, 3 weeks ago
Возможно будет история еще об одной …

Возможно будет история еще об одной утечке, связанной с Async Local Storage, но как минимум хочу рассказать про интересный кейс, связанный с отладкой этой проблемы.

Мы используем Fastify в качестве веб-сервера для Tramvai, разбираясь с утечкой поставил логи на хуки onRequest и onResponse.

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

Хорошо (хоть и поздно) заметил что не хватает ровно столько onResponse сколько запросов к параллельному вызову я указал для autocannon, условные 10 последних из 100 отправленных.

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

Обнаружил это через подписку на события finish и close объекта Request - оказалос что finish так же не вызывается эти 10 раз, а последние 10 close прилетают пачкой одновременно.

app.addHook('onRequest', async (request, reply) => { request.raw.on('finish', () => { ... }); request.raw.on('close', () => { ... }); })

Понаставил логов в fastify, посмотрел исходники, и оказывается хук onResponse вызывается как раз на событие finish.

И это получается дефолтное поведение в Node.js, если Request был отменен клиентом (request.aborted), событие finish не срабатывает, даже когда reply.send(...) будет вызван после отмены и фактически завершит стрим.

Это кстати можно мониторить, есть гайд у fastify - https://fastify.dev/docs/latest/Guides/Detecting-When-Clients-Abort/#detecting-when-clients-abort

Вот такой вот случайно обнаруженный сайд-эффект из-за нюансов работы autocannon, который в теории может воспроизводиться и на продакшене, и получается onResponse не самый надежный вариант для очистки чего-либо после завершения запроса.

2 months, 3 weeks ago

Итак, а что же утекает?

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

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

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

А в Tramvai есть модуль прогрева кэшей, который на старте сервера делает запросы к каждому роуту приложения.

Таким образом сразу после релиза, кэши прогреты, приложения работают быстрее, но и потребление памяти растет сразу при наличии утечки.

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

Также, не до конца понятно на каких уровнях надо чинить утечку.

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

С другой стороны хочется предотвратить возможность выстрела в ногу, и исправить такие места как createCache с ссылкой на commandLineExecutionContext.

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

5 months, 1 week ago

Также, очень приятно видеть в твиттере много довольных мейнтейнеров open source проектов - Microsoft поддержал финансово внушительный список проектов - https://x.com/jeffwilcox/status/1801794149815095495?s=19

Вдохновляет ❤️

5 months, 1 week ago

Не так давно писал про интересное изменение в React 19 - последовательная загрузка компонентов в рамках Suspense границ - https://t.me/super_oleg_dev/181

Как я понимаю это сильно ударило по перфу SPA приложений, где нет возможности предзагрузить ассеты и данные параллельно как это делают при SSR.

В итоге будут искать более удачное / универсальное решение:
- https://github.com/facebook/react/issues/29898
- https://x.com/sophiebits/status/1801663976973209620?s=19

Telegram

SuperOleg dev notes

Парочка интересных кейсы из беты React 19, которые особо не освещались: - Прощай useIsomorphicLayoutEffect, больше нет варнинга на сервере - https://github.com/facebook/react/pull/26395 - Если вы используете throw promise или либы с поддержкой Suspense…

5 months, 4 weeks ago

Про "все-в-React" или "все-в-компоненте" и декларативность.

Что мы видели интересного в коде компонентов:
- <Route> и <Redirect> из React Router
- <Script> из Next.js и <Scripts> из Remix
- useQuery из React Query или Apollo
- useForm из React Hook Form
- не могу не вспомнить <FormSpy> из Formik

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

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

Но в масштабе, проблемы есть.

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

Но декларативность в React мире доходит до того, что например в React Router вообще нет такой цельной сущности как Router! Есть только набор хуков, а сделать что-то с роутингом вне компонентов мы просто не имеем возможности.

Например (императивно) создать const router = new Router(), предзаполнить router.addRoute(...), в лоадере/экшены выполнить router.redirect(..), передать в <Router.Provider router={router} > и так далее.

Отсутствует жизненный цикл, настолько RR связан с реактом. Механизм loader'ов добавил хотя бы один этап жизненного цикла. Но для какой-нибудь авторизации разработчики все-равно будут создавать всякие <Auth> и <ProtectedRoute> компоненты.

Наглядный пример в этой статье - https://blog.logrocket.com/authentication-react-router-v6/. Хороший гайд, все аккуратно, react way, но насколько же сильно размазана аутентификация по компонентам, и не существует снаружи.

Просто сравните с Angular, где через DI предоставляется отдельный сервис для аутентификации, используемый и в UI и в гуарде роутера.

React Query большие молодцы, выделяют логику в отдельные сущности, и с ними можно работать где угодно, например QueryClient. Такие вещи очень упрощают интеграцию для SSR фреймворка.

Но и тут есть проблемы, возьмем сами квери. Как отдельной сущности их просто нет, есть набор параметров вида const query = useQuery({ queryKey: ['todos'], queryFn: getTodos }), и только через queryKey возможна связь для одной и той же квери между использованием в компоненте и прямой работой через QueryClient в других местах.

Сложно делать расширяемые и переиспользуемые query, параметры считываются и сохраняются сразу при рендере хука - нельзя сделать queryKey функцией, на момент рендера useQuery надо иметь все параметры для формирования массива ключей.

Используя React Query и React Hook Form, можно делать хороший UX и писать мало кода на сложные кейсы, но очень сложно явно выделить сущности / модели / бизнес-логику, что опять-таки может выстрелить в ногу в масштабе, и уж точно не поможет сделать архитектуру "кричащей".

По поводу таких кейсов как Scripts в Remix, или поддержка метаданных и стилей в React 19.

Реакт или Ремикс не дает нам условный AssetsManager, в который мы смогли бы добавить ресурс явно по конкретному условию, например:

if (analyticsEnabled) { assetManager.addScript({ src: anaylicsScript, async }) }

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

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

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

GitHub

Add useRouter Hook · Issue #6430 · remix-run/react-router

Hi guys, at current React Conf Hooks have been announced for React v16.7. What's the plan for supporting them? Will there be a useRouter() any time soon? https://reactjs.org/docs/hooks-faq.html...

6 months, 2 weeks ago

Собрал для вас в одну папку авторов, ведущих блоги по фронтенду, веб-разработке и вокруг неё.

? https://t.me/addlist/Z6Efi4jXwe9lODcy

Специально отобрал именно ламповые авторские блоги, а не перепосты ссылок, документации или тексты не про код.

Для меня это хороший способ следить за реакциями о событиях индустрии. Например, конференции проходят не так часто, и контент с них становится общедоступным не сразу. Кроме того, там обычно рассказывают о чём-то эпичном, не сиюминутном, так как формат обязывает. А вот в авторских бложиках (и комментариях к постам) можно собрать цельную картинку происходящего в рутине, и не просто факты, а именно авторскую интерпретацию и комментарии.

Надеюсь, будет полезно ✌️

@web_platform | Поддержать канал ?

7 months ago

Парочка интересных кейсы из беты React 19, которые особо не освещались:

- Прощай useIsomorphicLayoutEffect, больше нет варнинга на сервере - https://github.com/facebook/react/pull/26395

- Если вы используете throw promise или либы с поддержкой Suspense, в рамках одного Suspense загрузка данных в параллельных компонентах начнет происходить последовательно - https://github.com/facebook/react/pull/26380

Пример кода где будет водопад запросов при использовании условного useSuspenseQuery:

const Root = () => { return <> <Suspense>         <CmpWithUseSuspenseQuery /> <CmpWithUseSuspenseQuery /> </Suspense> }

В релизе очень порадовало улучшение ошибок гидрации, и централизованная обработка ошибок Error Boundaries.

Также я никак не пойму в какой версии удалили или удалят 421 ошибку гидрации - https://github.com/facebook/react/issues/24959#issuecomment-1317309116

Ошибка происходит при ререндере Suspense компонента, поддерево которого не завершило гидрацию, и приводит к деоптимизации - клиентский рендер вместо гидрации.

Очень легко словить такую ошибку используя useSyncExternalStore.

Потратил часы на разборы таких ошибок, а ситуация в итоге странная - ошибку выпиливают, а деоптимизация остаётся.

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

GitHub

Remove layout effect warning on the server by rickhanlonii · Pull Request #26395 · facebook/react

Overview This PR unfortunately removes the warning emitted when using layout effects on the server: useLayoutEffect does nothing on the server, because its effect cannot be encoded into the server...

7 months ago

Подведу некий summary:

- Round Trip Time важен на каждом из многочисленных этапов загрузки HTML, в идеальном мире точка входа в приложение - это CDN
- Редиректы не бесплатные как для клиента, так и для приложения, лучше их не делать или делать поближе к пользователю, например на уровне балансера
- Service Worker может как ускорить, так и замедлить ваше приложение - измеряйте все что можете, пробуйте Navigation Preload, не используйте SW для "галочки" - браузер и так отлично все кэширует
- Раздутый HTML и плохой интернет - это значительная проблема для SSR, которую трудно исправить малыми усилиями

Круто, что есть много браузерных API для мониторинга таких деталей.

8 months, 2 weeks ago

Про разработку.

Запланированные процессы такие:
- один разработчик пишет бэк, один фронт- до разработки, создается задача на конкретный небольшой функционал
- бэк пишет Open API схему и тест кейсы до реализации, на этом этапе асинхронно ревью/приемка заказчиком
- фронт накидывает мокапы и тест кейсы до реализации, на этом этапе асинхронно ревью/приемка заказчиком
- фронт получает сгенерированные API клиенты + моки от бэка до реализации
- реализация обязательно с тестами (Mostly integration!)

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

Также, большой объем работы потребовался на изначальную настройку инфраструктуры, это и тестовое окружение, Allure, генераторы клиентов и моков, CI/CD, и многое другое.

Поэтому процессы еще совсем не прошли проверку временем.

История далека от завершения, но очень надеюсь в следующих постах затронуть сторонние темы, и возвращаться тут к MF Platform по мере возникновения интересных инсайтов, точно будет что рассказать по SRE (платформу будут использовать критичные сервисы, что подразумевает высокие требования к доступности и поддержке).

We recommend to visit
HAYZON
HAYZON
6,442,108 @hayzonn

💼 How to create capital and increase it using cryptocurrency

👤 𝐅𝐨𝐮𝐧𝐝𝐞𝐫: @Tg_Syprion
🗓 ᴀᴅᴠᴇʀᴛɪsɪɴɢ: @SEO_Fam
Мои каналы: @mazzafam

Last updated 22 hours ago

Канал для поиска исполнителей для разных задач и организации мини конкурсов

Last updated 3 months ago

Новые и перспективные Web3 игры с добычей токенов.

Чат: https://t.me/Crypto_Wolf_Chat

Правила чата смотрите в описании чата.

Все свои вопросы направляйте в чат или главному модератору чата: @Exudna_118

По теме сотрудничества: @Zombini

Last updated 2 months, 2 weeks ago