0Pricing
React Academy · Урок

API и параметры useSyncExternalStore

Изучите аргументы subscribe, getSnapshot и getServerSnapshot и узнайте, какие гарантии они должны обеспечивать.

«API и параметры useSyncExternalStore» — бесплатный урок React Academy на CoddyKit. Это урок 2 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения React Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс React Academy содержит 4 уроков всего.

Обзор трех аргументов

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

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

Функция подписки

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

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

getSnapshot возвращает текущее значение

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

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

getServerSnapshot для SSR

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

Его указание предотвращает несоответствия при гидратации, предоставляя серверу разумное значение для рендеринга, совпадающее с тем, которое клиент изначально создаст.

Возвращаемое значение

Хук возвращает текущее значение снимка, которое Вы используете непосредственно в компоненте, как любую другую часть состояния. Когда хранилище изменяется, React повторно выполняет рендеринг, и хук возвращает обновленный снимок.

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

getSnapshot должен быть синхронным и согласованным

getSnapshot должен выполняться синхронно и возвращать значение, полностью полученное из текущего состояния хранилища. Он не должен выполнять асинхронные операции или выдавать разные результаты для одних и тех же исходных данных.

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

Паттерн неизменяемого снимка

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

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

Ошибка, приводящая к бесконечному циклу

Распространенная ошибка — возвращать из getSnapshot новый объект или массив при каждом вызове, например выполняя внутри него преобразование или фильтрацию. React видит новую ссылку каждый раз и считает, что значение изменилось.

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

Стабильность снимков

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

Главное правило: два вызова getSnapshot при неизменившихся данных хранилища должны возвращать абсолютно одну и ту же ссылку.

Объединение параметров

На практике Вы создаете функцию подписки, которая добавляет и удаляет слушателя, функцию getSnapshot, считывающую стабильное текущее значение, и, для SSR, getServerSnapshot, возвращающую безопасное для сервера значение.

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

Быстрая проверка: параметры useSyncExternalStore

Определите назначение getSnapshot.

Итоги: API useSyncExternalStore

Хук принимает функцию подписки, getSnapshot и, при необходимости, getServerSnapshot. Функция подписки подключает слушателя и возвращает функцию отмены подписки; getSnapshot синхронно считывает текущее значение и должен возвращать стабильный результат по ссылке; getServerSnapshot предоставляет значение, безопасное для SSR.

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

Часто задаваемые вопросы

Урок «API и параметры useSyncExternalStore» бесплатный?

Да — полный текст урока «API и параметры useSyncExternalStore» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс React Academy, подпишись на CoddyKit PRO. Курс React Academy содержит 4 уроков всего.

Чему я научусь в уроке «API и параметры useSyncExternalStore»?

Изучите аргументы subscribe, getSnapshot и getServerSnapshot и узнайте, какие гарантии они должны обеспечивать. Ты практикуешь React Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.

Нужен ли мне опыт, чтобы начать React Academy?

Предыдущий опыт не требуется. React Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 2 из 4.

Сколько времени занимает урок «API и параметры useSyncExternalStore»?

Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.

Можно ли писать и запускать код в этом уроке React Academy?

Да. Каждый урок React Academy включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.

Все уроки этого курса

  1. Проблема подписок на внешнее хранилище
  2. API и параметры useSyncExternalStore
  3. Подписка на API браузера
  4. Создание пользовательского хранилища с useSyncExternalStore
← Назад к React Academy