Remote / foldkit-remote
Routing Remote's Messages
The first run folds Remote's Messages under one variant of the application's
union, the shape Foldkit gives a Submodel. The fold's fetch, mutate, and
subscriptions yield that variant too, with the lift recorded so a Story
resolves a fetch or a mutation by Remote's own answer.
The shorter path, for an update that only reduces, spreads Remote's cases
into the union and narrows by tag; the rest of update is then a partial
match over tags the application never handles:
const Message = defineMessageUnion({ ...Remote.messages })
function update(model: Model, message: Message): Update.Return<Model, Message, RemoteClient> {
if (Remote.reduces(message)) return { model: Data.reduce(model, message) }
return { model }
}The rest of this guide uses the fold. With the spread, read Data.subscriptions
for foldData.subscriptions and Data.mutate for foldData.mutate.
One value with foldkit-bundle: Data.wiring
The integration steps above — fold or reduce, derive the Subscriptions,
provide the client — are one value when the application uses foldkit-bundle:
import { Bundle } from 'foldkit-bundle'
const Page = Bundle.parent({ Model, Message })
const wiring = Page.assemble(
Data.wiring({
project: Surface.at(ProjectPage, model =>
model.route._tag === 'project'
? Option.some({ projectId: model.route.projectId })
: Option.none(),
),
}),
)
const update = wiring.update(model => ({ model }))Data.wiring routes Remote's Messages into Data.reduce, brings the active
Surfaces' Subscriptions and the domain's contract, and requires RemoteClient
from the runtime's resources — the same client layer from above. One assembly
holds at most one Remote domain: every domain claims the same Message tags,
and the assembly refuses a second claimant at startup, naming both.