How requirements are tracked
A piece needs every service its handler yields. A block also needs the services of its view and its actions, and a command or message action needs the services of the Effect it defers. The app needs the services of all its pieces:moveTask needs Tracker, so does any block that lists it in actions, and so does the app that
adds the block. Until Tracker is provided, calling app.fetch or toNodeHandler(app) is a type
error that names Tracker. ReintersectApp.layer(app) accepts the app and passes Tracker on as a
requirement of the router layer.
Services read inside a component that returns an Effect
aren’t tracked, so provide those yourself.
Provide services with a layer
provide(app, layer) returns a new app whose remaining requirements are the layer’s own:
src/app.ts
provide too, so tests can provide fakes instead. See
Testing.
When a layer needs another service, provide that one as well, either by composing layers first or by
calling provide again:
When the layer is built
The SDK builds the layer the first time a delivery needs it and keeps it for the life of the process, so every delivery shares the same services. Resources acquired withLayer.scoped, such as a
connection pool, stay open until the process exits.
If the layer fails to build, the SDK logs the cause and that delivery answers 500 with the code
configuration (“The app’s services failed to start.”). The next delivery tries to build it again.
On app.fetch, a layer that reads Config sees the string values in the env argument first, such
as Cloudflare Workers bindings, then process.env.
Serve the app
ReintersectApp.layer(app, { path }) mounts the delivery path (default /reintersect), every
route and the MCP server at /mcp, under the same root. It
merges with your own routes, and the app’s unprovided services become requirements of the server:
src/server.ts
ReintersectApp.layer only accepts a complete app, the same check reintersect build makes: an app
with a missing block or an undeclared environment value is a type error.
For other servers, mount app.fetch or toNodeHandler(app) as in Self-hosted.