Перейти к основному содержимому

Scope

Независимый изолированный инстанс приложения, содержит копию всех юнитов (включая связи между ними) и основные методы для доступа к ним.

Основные области применения - реализация SSR и тестирование приложения.

Scope может быть создан с помощью fork

Формула

interface Scope {
getState<T>(store: Store<T>): T
}

Методы

getState

Возвращает значение стора в данном scope

scope.getState<T>(store: Store<T>): T

Пример использования getState

Создание двух инстансов приложения, вызов событий в них и проверка сохранения значения стора $counter в каждом из них

import {
createStore,
createEvent,
createDomain,
forward,
fork,
allSettled,
} from 'effector'

const domain = createDomain()
const inc = domain.createEvent()
const dec = domain.createEvent()
const $counter = domain
.createStore(0)
.on(inc, value => value + 1)
.on(dec, value => value - 1)

const scopeA = fork(domain)
const scopeB = fork(domain)

await allSettled(inc, {scope: scopeA})
await allSettled(dec, {scope: scopeB})

console.log($counter.getState()) // => 0
console.log(scopeA.getState($counter)) // => 1
console.log(scopeB.getState($counter)) // => -1

Запустить пример

Императивные вызовы эффектов и scope

Если эффект вызывает другие эффекты, то он может вызывать только эффекты, а не обычные асинхронные функции, и вызовы эффектов должны иметь await:

Правильно, эффект без внутренних эффектов:

const delayFx = app.createEffect(async () => {
await new Promise(rs => setTimeout(rs, 80))
})

Правильно, эффект с внутренними эффектами:

const authUserFx = app.createEffect()
const sendMessageFx = app.createEffect()

const sendWithAuthFx = app.createEffect(async () => {
await authUserFx()
await delayFx()
await sendMessageFx()
})

Неправильно, эффект с внутренними эффектами после обычных асинхронных вызовов:

const sendWithAuthFx = app.createEffect(async () => {
await authUserFx()
//НЕ ПРАВИЛЬНО! этот код следует сделать отдельным эффектом delayFx
await new Promise(rs => setTimeout(rs, 80))
//потеря контекста
await sendMessageFx()
})

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

tip

Вместо императивных вызовов оптимальнее использовать attach

caution

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