pub struct ReactiveRuntime {
pub owners: SlotMap<Owner, Scope>,
pub nodes: SlotMap<NodeId, ReactiveNode>,
pub owner_stack: Vec<Owner>,
pub current_tracker: Option<NodeId>,
pub pending: Vec<NodeId>,
pub deferred: Vec<NodeId>,
pub flushing: bool,
pub component_owners: HashMap<*const (), Vec<Owner>>,
pub fn_ptr_mounts: HashMap<*const (), Vec<MountId>>,
pub mount_id_counter: u64,
pub pending_mounts: Vec<Box<dyn FnOnce()>>,
/* private fields */
}Expand description
The reactive runtime itself. One per thread (held in a
thread_local! slot in mod.rs).
All public reactive operations route through here. The pattern is always:
- Open a short
with_borrow_mutto read or mutateowners/nodes/current_*. - If user code needs to run (effect / computed closure), drop the borrow first by cloning the necessary handles out, then call the closure.
- Re-open a short borrow to restore book-keeping.
This keeps the RefCell borrow window narrow enough that user code
running inside a closure can re-enter the runtime (read signals,
write signals, register new effects) without panicking.
Fields§
§owners: SlotMap<Owner, Scope>§nodes: SlotMap<NodeId, ReactiveNode>§owner_stack: Vec<Owner>Owner stack: the topmost is the “current” owner — new signals,
effects, computed values, and lifecycle hooks register against it. Push
when entering a Owner::with (or #[component]) scope, pop on
exit.
current_tracker: Option<NodeId>The effect/computed currently being computed, if any. Signal reads
inside this effect register a sources/subscribers link
against it.
pending: Vec<NodeId>Queue of effect/computed nodes scheduled to re-run on the next flush.
Populated by signal writes; drained by [flush_pending].
deferred: Vec<NodeId>Nodes that were scheduled to run but whose owner is paused.
Sit here until their owner is resumed; on resume, drain back
into Self::pending so the deferred work fires. See
Owner::pause / Owner::resume for the lifecycle.
flushing: boolTrue while [flush_pending] is actively draining pending.
Used to avoid recursive flushes (signal writes inside a running
effect just enqueue; we keep draining the queue until empty
rather than recursing).
component_owners: HashMap<*const (), Vec<Owner>>Component-fn-pointer → list of live owners that ran that fn.
Populated by register_component; consulted by the A6 hot-
reload path to find which owners to dispose when a fn body
gets subsecond-patched.
fn_ptr_mounts: HashMap<*const (), Vec<MountId>>Component-fn-pointer → list of remountable mount sites that
ran that fn. Mirror of component_owners indexed by
MountId instead of Owner so it survives the dispose +
re-create cycle on each hot-reload remount (the owner is
fresh every time, the mount id is stable).
mount_id_counter: u64Monotonic counter for fresh MountIds.
pending_mounts: Vec<Box<dyn FnOnce()>>Pending on_mount callbacks, in the order they were registered.
Drained by super::flush_mounts — which the renderer (A3)
will call after appending a component’s view to its parent.