@solidjs/signals 2.0.0-rc.18 → 2.0.0-rc.19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (65) hide show
  1. package/dist/dev-shared.js +168 -88
  2. package/dist/dev.attribution.js +16 -13
  3. package/dist/dev.js +272 -129
  4. package/dist/observe/boundaries.js +88 -67
  5. package/dist/observe/core/action.js +8 -0
  6. package/dist/observe/core/async.js +46 -34
  7. package/dist/observe/core/attribution.js +30 -28
  8. package/dist/observe/core/constants.js +21 -1
  9. package/dist/observe/core/core.js +164 -136
  10. package/dist/observe/core/effect.js +6 -6
  11. package/dist/observe/core/graph.js +3 -3
  12. package/dist/observe/core/heap.js +5 -5
  13. package/dist/observe/core/lanes.js +104 -84
  14. package/dist/observe/core/owner.js +10 -9
  15. package/dist/observe/core/scheduler.js +38 -35
  16. package/dist/observe/core/truth.js +6 -6
  17. package/dist/observe/core/verdict.js +13 -13
  18. package/dist/observe/deferred.js +39 -40
  19. package/dist/observe/index.js +2 -2
  20. package/dist/observe/map.js +22 -22
  21. package/dist/observe/reveal.js +5 -5
  22. package/dist/observe/signals.js +57 -15
  23. package/dist/observe/store/affects.js +1 -1
  24. package/dist/observe/store/hooks.js +3 -0
  25. package/dist/observe/store/optimistic.js +11 -11
  26. package/dist/observe/store/projection.js +34 -21
  27. package/dist/observe/store/reconcile.js +2 -2
  28. package/dist/observe/store/store.js +63 -53
  29. package/dist/observe/store/utils.js +7 -2
  30. package/dist/prod/boundaries.js +153 -132
  31. package/dist/prod/core/action.js +8 -0
  32. package/dist/prod/core/async.js +55 -43
  33. package/dist/prod/core/constants.js +14 -1
  34. package/dist/prod/core/core.js +162 -134
  35. package/dist/prod/core/effect.js +9 -9
  36. package/dist/prod/core/graph.js +3 -3
  37. package/dist/prod/core/heap.js +12 -12
  38. package/dist/prod/core/lanes.js +98 -78
  39. package/dist/prod/core/owner.js +15 -14
  40. package/dist/prod/core/scheduler.js +43 -40
  41. package/dist/prod/core/truth.js +6 -6
  42. package/dist/prod/core/verdict.js +17 -17
  43. package/dist/prod/deferred.js +39 -40
  44. package/dist/prod/index.js +2 -2
  45. package/dist/prod/map.js +14 -14
  46. package/dist/prod/reveal.js +8 -8
  47. package/dist/prod/signals.js +46 -4
  48. package/dist/prod/store/affects.js +1 -1
  49. package/dist/prod/store/hooks.js +3 -0
  50. package/dist/prod/store/optimistic.js +16 -16
  51. package/dist/prod/store/projection.js +22 -9
  52. package/dist/prod/store/reconcile.js +2 -2
  53. package/dist/prod/store/store.js +262 -262
  54. package/dist/prod/store/utils.js +2 -0
  55. package/dist/types/core/action.d.ts +8 -0
  56. package/dist/types/core/constants.d.ts +20 -0
  57. package/dist/types/core/core.d.ts +14 -1
  58. package/dist/types/core/dev.d.ts +1 -1
  59. package/dist/types/core/index.d.ts +1 -1
  60. package/dist/types/core/lanes.d.ts +5 -1
  61. package/dist/types/core/scheduler.d.ts +2 -0
  62. package/dist/types/index.d.ts +3 -1
  63. package/dist/types/signals.d.ts +37 -0
  64. package/dist/types/store/target.d.ts +2 -0
  65. package/package.json +1 -1
@@ -1,6 +1,6 @@
1
1
  import { notifyStatus, releaseFlightTeardown, handleAsync, clearStatus, parkLoadingWindow, stageError, settlePendingSource, releaseIfSettledUnobserved, settleErroredDependents } from "./async.js";
2
2
 
3
- import { STATUS_UNINITIALIZED, REACTIVE_LAZY, REACTIVE_NONE, defaultContext, CONFIG_TRANSPARENT, CONFIG_OWNED_WRITE, CONFIG_AUTO_DISPOSE, CONFIG_SYNC, CONFIG_NO_SNAPSHOT, CONFIG_PLUMBING, CONFIG_IN_SNAPSHOT_SCOPE, NOT_PENDING, NO_SNAPSHOT, CONFIG_HAS_SNAPSHOT, CONFIG_HELD, REACTIVE_MANUAL_WRITE, STATUS_ERROR, REACTIVE_DIRTY, CONFIG_OVERRIDE, REACTIVE_DISPOSED, REACTIVE_CHECK, REACTIVE_IN_HEAP, REACTIVE_REASK, REACTIVE_SNAPSHOT_STALE, CONFIG_CHILDREN_FORBIDDEN, CONFIG_VERDICT, STATUS_PENDING, REACTIVE_LANE_DIRTY, CONFIG_GUESS, REACTIVE_RECOMPUTING_DEPS, CONFIG_LAGS, EFFECT_RENDER, CONFIG_HELD_FRAME, EFFECT_TRACKED, CONFIG_STAGED, CONFIG_STAGED_ERROR, REACTIVE_ZOMBIE, REACTIVE_MISSED_WAKE, REACTIVE_JOINED, REACTIVE_STAGED_READ, REACTIVE_PROBED, REACTIVE_FRAME_READ, REACTIVE_LANE_READ, REACTIVE_SCREEN_READ, REACTIVE_PROBE_UNANSWERED, CAUGHT_REARMED, CONFIG_PROMOTED, CONFIG_INPUTS_PUBLISHED, CONFIG_FRESH_READ, REACTIVE_IN_HEAP_HEIGHT, CONFIG_SLOT_NODE, EFFECT_USER, NewSet, STATUS_NONE } from "./constants.js";
3
+ import { STATUS_UNINITIALIZED, REACTIVE_LAZY, REACTIVE_NONE, defaultContext, CONFIG_TRANSPARENT, CONFIG_OWNED_WRITE, CONFIG_AUTO_DISPOSE, CONFIG_SYNC, CONFIG_NO_SNAPSHOT, CONFIG_PLUMBING, CONFIG_IN_SNAPSHOT_SCOPE, NOT_PENDING, CONFIG_HELD, REACTIVE_MANUAL_WRITE, STATUS_ERROR, REACTIVE_DIRTY, CONFIG_OVERRIDE, NO_SNAPSHOT, CONFIG_HAS_SNAPSHOT, REACTIVE_DISPOSED, REACTIVE_CHECK, REACTIVE_IN_HEAP, REACTIVE_REASK, REACTIVE_SNAPSHOT_STALE, CONFIG_CHILDREN_FORBIDDEN, CONFIG_VERDICT, STATUS_PENDING, REACTIVE_LANE_DIRTY, CONFIG_GUESS, REACTIVE_RECOMPUTING_DEPS, CONFIG_LAGS, EFFECT_RENDER, CONFIG_HELD_FRAME, EFFECT_TRACKED, CONFIG_STAGED, CONFIG_STAGED_ERROR, REACTIVE_ZOMBIE, REACTIVE_MISSED_WAKE, REACTIVE_JOINED, REACTIVE_STAGED_READ, REACTIVE_PROBED, REACTIVE_FRAME_READ, REACTIVE_LANE_READ, REACTIVE_SCREEN_READ, REACTIVE_PROBE_UNANSWERED, CAUGHT_REARMED, CONFIG_PROMOTED, CONFIG_INPUTS_PUBLISHED, CONFIG_FRESH_READ, REACTIVE_IN_HEAP_HEIGHT, CONFIG_SLOT_NODE, EFFECT_USER, NewSet, STATUS_NONE } from "./constants.js";
4
4
 
5
5
  import { NotReadyError } from "./error.js";
6
6
 
@@ -28,7 +28,7 @@ GlobalQueue.Ze = e => {
28
28
  if (e.i === EFFECT_TRACKED) {
29
29
  deleteFromHeap(e, dirtyQueue);
30
30
  e.Qe = true;
31
- globalQueue.enqueue(EFFECT_USER, e.M);
31
+ globalQueue.enqueue(EFFECT_USER, e.Z);
32
32
  }
33
33
  // L2: a zombie's fate is the seam's — its owner's commit disposes it, or
34
34
  // the park cancels the pass (the write that dirtied it is held). It runs
@@ -85,8 +85,20 @@ function setSnapshotCapture(e) {
85
85
  if (e && !snapshotSources) snapshotSources = new NewSet;
86
86
  }
87
87
 
88
- function markSnapshotScope(e) {
89
- e.ot = true;
88
+ /**
89
+ * Marks `owner` a snapshot scope: while capture is on, the readers created
90
+ * under it serve each source's snapshot (the value it had when hydration
91
+ * began) and replay at `releaseSnapshotScope`.
92
+ *
93
+ * With `served` (hydration), `owner` is instead a hydrated computed and
94
+ * `served` its server answer — what the server rendered every reader of the
95
+ * node with — landing after the node was created pending (so the creation
96
+ * arm skipped it). It becomes the node's snapshot when it has none, whether
97
+ * the node committed the answer or a client write had already taken its
98
+ * compute over. A claim made later reads the value its markup shows, and
99
+ * replays the node's own value at its release, as for a written signal.
100
+ */ function markSnapshotScope(e, t) {
101
+ if (arguments.length < 2) e.ot = true; else if (snapshotCaptureActive && e.T?.st === undefined) takeSnapshot(e, t);
90
102
  }
91
103
 
92
104
  function releaseSnapshotScope(e) {
@@ -108,7 +120,7 @@ function releaseSubtree(e) {
108
120
  if (e.R & REACTIVE_SNAPSHOT_STALE) {
109
121
  e.R &= ~REACTIVE_SNAPSHOT_STALE;
110
122
  e.R |= REACTIVE_DIRTY;
111
- if (dirtyQueue.st > e.Et) dirtyQueue.st = e.Et;
123
+ if (dirtyQueue.lt > e.Et) dirtyQueue.lt = e.Et;
112
124
  insertIntoHeap(e, dirtyQueue);
113
125
  }
114
126
  }
@@ -125,7 +137,7 @@ function clearSnapshots() {
125
137
  // `!== undefined` — assign, don't `delete`: deleting a field pushes the
126
138
  // object to dictionary mode for every later read of every field.
127
139
  const t = e.T;
128
- if (t != null) t.lt = undefined;
140
+ if (t != null) t.st = undefined;
129
141
  }
130
142
  snapshotSources = null;
131
143
  }
@@ -158,8 +170,8 @@ function recompute(e, t = false) {
158
170
  // The mount a first pass belongs to: its creator's lane, or the one its
159
171
  // creator's own mount came from — a render effect a verdict lane's mount's
160
172
  // content creates is that mount's too (#4166). Lanes only, like the seat.
161
- const E = laneRoot;
162
- const l = laneStageHook && (laneRoot = t && (s || E));
173
+ const l = laneRoot;
174
+ const E = laneStageHook && (laneRoot = t && (s || l));
163
175
  setPassLane(!laneStageHook ? null : (e.R & REACTIVE_LANE_DIRTY || (e.l & (CONFIG_OVERRIDE | CONFIG_GUESS)) === CONFIG_OVERRIDE) && e.T?.Je?.V ? e.T.Je : // Loose `!=`: false with no creator lane (undefined == null).
164
176
  t && s?._parent.it != s && creatorPass(context)?.R & REACTIVE_RECOMPUTING_DEPS ? s : null);
165
177
  // Attribution hook: fired before this run touches the dep list — `_deps`
@@ -175,7 +187,7 @@ function recompute(e, t = false) {
175
187
  if (!t) {
176
188
  deleteFromHeap(e, dirtyQueue);
177
189
  if (e.T !== null) {
178
- e.T.Se = null;
190
+ e.T.Ee = null;
179
191
  // Supersede is where an iterator flight dies (#3122): close it now.
180
192
  // Idempotent with the cleanup-channel close.
181
193
  releaseFlightTeardown(e);
@@ -191,6 +203,8 @@ function recompute(e, t = false) {
191
203
  // A29, or mounted by a pass of it still awaiting its commit, #4010) keeps
192
204
  // staging: live writes keep it current, it effects at the swap (ruling
193
205
  // A).
206
+ // A boundary's structure (CONFIG_FRAME) is the frame like a render
207
+ // effect: it publishes mainline outside its transaction's flush (#4283).
194
208
  // A pending flight is the transition's own work (#3884). A probe on an
195
209
  // earlier pass left CONFIG_VERDICT, and a frame read here would serve the
196
210
  // committed screen, settle the flight and drop the hold — a superseding
@@ -204,15 +218,19 @@ function recompute(e, t = false) {
204
218
  // world (`read`), and has left it otherwise.
205
219
  // An answered deferred node's re-pass is a lagging question (D-40):
206
220
  // it joins nothing, so the write that reached it commits mainline.
207
- if (t.V || e.l & CONFIG_LAGS) ; else if (n !== EFFECT_RENDER && !(e.l & CONFIG_VERDICT)) joinPassTx(t, freshHook?.(e, e.m & STATUS_UNINITIALIZED)); else if (t !== flushTransaction && !(e.m & STATUS_UNINITIALIZED || e.l & CONFIG_HELD_FRAME)) {
221
+ // `EFFECT_RENDER << 23` is CONFIG_FRAME (a render effect, a boundary's
222
+ // tree and output), spelled from the effect type as at creation.
223
+ if (t.V || e.l & CONFIG_LAGS) ; else if (!(e.l & (CONFIG_VERDICT | EFFECT_RENDER << 23))) joinPassTx(t, freshHook?.(e, e.m & STATUS_UNINITIALIZED)); else if (t !== flushTransaction && !(e.m & STATUS_UNINITIALIZED || e.l & CONFIG_HELD_FRAME)) {
208
224
  // Published mainline, it is not held: the frame this pass builds is
209
225
  // replaced on the spot (#3404) — this flush's commit retires the
210
226
  // committed frame the held pass had parked (`commitPendingNode`),
211
227
  // after the new frame's first runs, and the held pass's own
212
228
  // children die below (`disposeChildren`). The landing re-derives a
213
229
  // fresh held frame for the reveal (`_reruns`).
214
- e.ue = NOT_PENDING;
215
- if (n === EFFECT_RENDER) e.l &= ~CONFIG_HELD;
230
+ // Not held any more, whichever frame reader it is: its readers read
231
+ // the value this pass publishes.
232
+ e.ie = NOT_PENDING;
233
+ e.l &= ~CONFIG_HELD;
216
234
  }
217
235
  }
218
236
  // The previous pass's frame. If that pass is still awaiting its commit
@@ -233,7 +251,7 @@ function recompute(e, t = false) {
233
251
  // An error a pass staged (D-41) is replaced by this pass's answer: a
234
252
  // value, a flight, or an error of its own (#4109, #4145).
235
253
  if (e.l & CONFIG_STAGED_ERROR) {
236
- e.ue = NOT_PENDING;
254
+ e.ie = NOT_PENDING;
237
255
  e.l ^= CONFIG_STAGED_ERROR;
238
256
  }
239
257
  }
@@ -241,9 +259,9 @@ function recompute(e, t = false) {
241
259
  // Capture both error and pending status before the compute clears them.
242
260
  // A conditional can drop its pending source and recover to an unchanged
243
261
  // value, leaving blocked dependents outside that source’s settle walk.
244
- const u = e.m & STATUS_ERROR ? e.T?.F : undefined;
245
- const a = (e.m & STATUS_PENDING) !== 0;
246
- const _ = a ? e.T?.se : undefined;
262
+ const a = e.m & STATUS_ERROR ? e.T?.F : undefined;
263
+ const u = (e.m & STATUS_PENDING) !== 0;
264
+ const _ = u ? e.T?.se : undefined;
247
265
  // Pending SOURCE-hood, captured before the compute clears status: a node
248
266
  // whose own flight parked dependents self-registers in _pendingSources
249
267
  // (notifyStatus, isSource). If this recompute supersedes that flight and
@@ -252,11 +270,11 @@ function recompute(e, t = false) {
252
270
  // (#3181).
253
271
  const I = e.T?.se?.has(e);
254
272
  // D-41: this pass's error is staged, not published (`stageError`).
255
- let N = false;
273
+ let f = false;
256
274
  // A19 exc. 2: a `refresh()` re-asks the question already answered — quiet
257
275
  // for the verdict — unless the question in flight is a new one, which the
258
276
  // re-ask does not launder (a poll during a quiet confirm stays quiet).
259
- const f = (e.R & REACTIVE_REASK) !== 0 && !(e.m & STATUS_PENDING && e.T !== null && !e.T.ut);
277
+ const N = (e.R & REACTIVE_REASK) !== 0 && !(e.m & STATUS_PENDING && e.T !== null && !e.T.ut);
260
278
  const T = context;
261
279
  context = e;
262
280
  e._ = null;
@@ -266,10 +284,10 @@ function recompute(e, t = false) {
266
284
  // live writes until the commit that disposes it, so every per-pass wipe
267
285
  // — here, the finally below, updateIfNecessary — carries it (#3543).
268
286
  e.R = REACTIVE_RECOMPUTING_DEPS | e.R & (REACTIVE_ZOMBIE | REACTIVE_REASK);
269
- e.ie = clock;
287
+ e.ae = clock;
270
288
  // The pass's previous value: its staging, else a lane node's lane value
271
289
  // when it has one (lanes.ts), else the committed one.
272
- let S = e.ue !== NOT_PENDING ? e.ue : e.l & CONFIG_OVERRIDE && e.T.V !== NOT_PENDING ? e.T.V : e.Ie;
290
+ let S = e.ie !== NOT_PENDING ? e.ie : e.l & CONFIG_OVERRIDE && e.T.V !== NOT_PENDING ? e.T.V : e.le;
273
291
  let c = e.Et;
274
292
  let A = false;
275
293
  // L2: did this pass read the future (REACTIVE_JOINED, set by read) — or,
@@ -280,19 +298,19 @@ function recompute(e, t = false) {
280
298
  try {
281
299
  if (!false && e.l & CONFIG_SYNC) {
282
300
  S = e.X(S);
283
- if (e.T !== null) e.T.Se = null;
301
+ if (e.T !== null) e.T.Ee = null;
284
302
  e.ce = false;
285
303
  } else {
286
304
  // A projection's body self-registers its flight through handleAsync
287
305
  // (with the commit as setter): its undefined return is not a sync
288
306
  // answer, and the outer handleAsync must not clobber the registration.
289
- const t = e.T?.Se;
307
+ const t = e.T?.Ee;
290
308
  const n = e.X(S);
291
309
  const o = typeof n === "object" && n !== null;
292
- const s = e.T?.Se !== t;
310
+ const s = e.T?.Ee !== t;
293
311
  S = s || !o ? n : handleAsync(e, n);
294
312
  if (!s && !o) {
295
- if (e.T !== null) e.T.Se = null;
313
+ if (e.T !== null) e.T.Ee = null;
296
314
  // A sync (non-object) return is the first real answer; async-shaped
297
315
  // results clear inside handleAsync at their own landing points, and a
298
316
  // self-registered flight clears when its own handleAsync lands.
@@ -318,12 +336,12 @@ function recompute(e, t = false) {
318
336
  } else {
319
337
  // D-41: a pass of a held node, or one that read a staging of this
320
338
  // flush, stages its error (`stageError`).
321
- if (n || !(N = stageError(e, t, true))) {
339
+ if (n || !(f = stageError(e, t, true))) {
322
340
  if (n) ext(e).fe = true;
323
341
  notifyStatus(e, n ? STATUS_PENDING : STATUS_ERROR, t);
324
342
  // The replacement source is fully propagated now. If no new flight
325
343
  // re-owned self, retire the superseded flight and its dependent copies.
326
- if (n && I && !e.T?.Se) settlePendingSource(e);
344
+ if (n && I && !e.T?.Ee) settlePendingSource(e);
327
345
  }
328
346
  // A re-park drops what the earlier pass carried (#3456): a source this
329
347
  // pass no longer reaches — its branch switched, or a fresh flight
@@ -334,11 +352,11 @@ function recompute(e, t = false) {
334
352
  // re-park twin of the unchanged-value recovery sweep below; dependents
335
353
  // with another path keep the source (retryReaches). A staged error
336
354
  // answered what the pass carried: the same.
337
- if ((n || N) && _) for (const t of _) if (t !== e && !e.T?.se?.has(t)) settlePendingSource(e, t);
355
+ if ((n || f) && _) for (const t of _) if (t !== e && !e.T?.se?.has(t)) settlePendingSource(e, t);
338
356
  }
339
357
  } finally {
340
358
  tracking = C;
341
- if (laneStageHook) laneRoot = E;
359
+ if (laneStageHook) laneRoot = l;
342
360
  // Consume the missed-wake latch (#3037, set by insertSubs): a dep write
343
361
  // landed beneath this pass on a link it had already validated. The wipe
344
362
  // below must not key off DIRTY/CHECK — the read-time pull protocol
@@ -348,7 +366,7 @@ function recompute(e, t = false) {
348
366
  // A mount's staged read joins it — except a nested derivation left
349
367
  // pending: no render effect reaches it yet, so it holds nothing and
350
368
  // reaches no boundary (Reader, #4203). A reader that does is caught.
351
- R = !!(e.R & (l && (s || n || !(e.m & STATUS_PENDING)) ? REACTIVE_JOINED | REACTIVE_STAGED_READ : REACTIVE_JOINED));
369
+ R = !!(e.R & (E && (s || n || !(e.m & STATUS_PENDING)) ? REACTIVE_JOINED | REACTIVE_STAGED_READ : REACTIVE_JOINED));
352
370
  // A verdict reader is one for as long as it probes, or reads a memo
353
371
  // that does (`read`): a pass that did neither (REACTIVE_PROBED, the same
354
372
  // bit) is an ordinary derivation again.
@@ -366,7 +384,7 @@ function recompute(e, t = false) {
366
384
  // A19 exc. 2: a pass that went pending on a `refresh()` re-asks the
367
385
  // question already answered — quiet for the verdict; any other pending
368
386
  // pass is a new question. Settled, there is nothing to classify.
369
- if (e.T !== null) e.T.ut = f && (e.m & STATUS_PENDING) !== 0;
387
+ if (e.T !== null) e.T.ut = N && (e.m & STATUS_PENDING) !== 0;
370
388
  }
371
389
  // A node that died during its own pass (#3621) is dead at the end of it,
372
390
  // and the pass is void. Its owner's teardown already unlinked its deps,
@@ -381,7 +399,7 @@ function recompute(e, t = false) {
381
399
  // attribution frame opened at the top is still closed.
382
400
  if (e.R & REACTIVE_DISPOSED) {
383
401
  clearDeps(e);
384
- if (e.T !== null) e.T.Se = null;
402
+ if (e.T !== null) e.T.Ee = null;
385
403
  if (attrHooks !== null) attrHooks.recomputeEnd(e, t, false, false, false, false);
386
404
  setPassLane(s);
387
405
  return;
@@ -394,7 +412,7 @@ function recompute(e, t = false) {
394
412
  let d = !laneStageHook ? null : passLane;
395
413
  // Listed before its staging, a pending pass included (the lane's own
396
414
  // flight is the lane's); false: the pass left the lane (lanes.ts).
397
- const O = !!e.T?.F || N;
415
+ const O = !!e.T?.F || f;
398
416
  if (laneStageHook && d !== null) {
399
417
  if (laneStageHook(e, d, t, O)) setPassLane(d); else d = null;
400
418
  }
@@ -419,9 +437,9 @@ function recompute(e, t = false) {
419
437
  // publishes to — the staged `_pendingValue` when staged; a lane node's
420
438
  // lane value (a node entering the lane this pass has none yet — its
421
439
  // committed value, `laneStage` having voided a frame staging).
422
- const o = e.ue !== NOT_PENDING ? e.ue : e.l & CONFIG_OVERRIDE && e.T.V !== NOT_PENDING ? e.T.V : e.Ie;
440
+ const o = e.ie !== NOT_PENDING ? e.ie : e.l & CONFIG_OVERRIDE && e.T.V !== NOT_PENDING ? e.T.V : e.le;
423
441
  // A throwing comparator is contained inside `isSame` (A3, #2837; #4111).
424
- const s = !n && r || !!e.T?.de || !isSame(e, o, S);
442
+ const s = !n && r || !!e.T?.Te || !isSame(e, o, S);
425
443
  // A committed derived change becomes a cause for this node's subscribers,
426
444
  // chaining their attribution through this node to the root write.
427
445
  if (attrHooks !== null) {
@@ -438,7 +456,7 @@ function recompute(e, t = false) {
438
456
  // last applied owes no run (lanes.ts).
439
457
  !(e.R & REACTIVE_SCREEN_READ && !e.Qe && Object.is(e._t, S)) &&
440
458
  // A re-staging pass owes no run: the commit replays the effect (#3802).
441
- e.ue === NOT_PENDING) {
459
+ e.ie === NOT_PENDING) {
442
460
  e.Qe = !e.T?.F;
443
461
  // Reuse one bound runner per effect — runEffect no-ops on a stale
444
462
  // `_modified`, so re-enqueueing the same function is harmless.
@@ -453,7 +471,8 @@ function recompute(e, t = false) {
453
471
  // confirm is a landing too — the lane's end commits it) and notifies
454
472
  // only a correction: an equal truth re-runs nothing (lanes.ts). (As the
455
473
  // lane's own work the lane judged it — `laneStage`.)
456
- if (!t && d === null && e.l & CONFIG_GUESS && laneOutcomeHook(e, S, O)) ; else if (O) ; else if (s) {
474
+ // (The hook first: a build without lanes folds the arm away.)
475
+ if (laneOutcomeHook && !t && d === null && e.l & CONFIG_GUESS && laneOutcomeHook(e, S, O)) ; else if (O) ; else if (s) {
457
476
  // L2: a first pass is born held — staged, committed with the
458
477
  // transaction, its effect's first run the landing's (A29; `effect()`
459
478
  // skips the synchronous first run on a staged value) — when the flush
@@ -477,8 +496,8 @@ function recompute(e, t = false) {
477
496
  // effect's value slot is private: the run the lane holds is what
478
497
  // shows it — unless the effect was born held, whose first run is the
479
498
  // commit's (A29): it re-stages, as below.
480
- if (n && e.ue === NOT_PENDING) e.Ie = S; else if (n || d.It) e.ue = S; else e.T.V = S;
481
- } else if (t ? !((flushTransaction !== null || passTx !== null) && (R || creatorPass(T)?.R & REACTIVE_JOINED)) : n && e.ue === NOT_PENDING) {
499
+ if (n && e.ie === NOT_PENDING) e.le = S; else if (n || d.It) e.ie = S; else e.T.V = S;
500
+ } else if (t ? !((flushTransaction !== null || passTx !== null) && (R || creatorPass(T)?.R & REACTIVE_JOINED)) : n && e.ie === NOT_PENDING) {
482
501
  // A first pass publishes directly. So does an effect: its value slot
483
502
  // is private (only its own run reads it), and the staging round-trip
484
503
  // (queuePendingNode + commitPendingNodes) paid per effect on the
@@ -489,9 +508,9 @@ function recompute(e, t = false) {
489
508
  // sources commit) must see the fresh value while PLAIN reads stay
490
509
  // committed until flush (#3009 purity). The pending round-trip is
491
510
  // that separation; it cannot be skipped on any path a pull can reach.
492
- e.Ie = S;
511
+ e.le = S;
493
512
  } else {
494
- e.ue = S;
513
+ e.ie = S;
495
514
  // Born held: in the transaction from birth, so a read of it this
496
515
  // tick is a read of its world (the mount-during-a-hold case), not
497
516
  // only after the seam parks it.
@@ -509,7 +528,7 @@ function recompute(e, t = false) {
509
528
  // #3851): the mount is part of the hold, and the boundary appears
510
529
  // at its commit, its fallback never seen (D-13, U-3) — a `<Show>`
511
530
  // mounting it over a landing included.
512
- freshHook?.(e, !l && flushTransaction);
531
+ freshHook?.(e, !E && flushTransaction);
513
532
  }
514
533
  }
515
534
  // insertSubs only walks _subs (no scheduling of its own), so a
@@ -528,7 +547,7 @@ function recompute(e, t = false) {
528
547
  // recoveries ride insertSubs above; a comparator throw re-errored the node
529
548
  // (el._x?._error re-set), so this only runs on a genuinely clean recovery.
530
549
  if (!s && !e.T?.F) {
531
- if (u !== undefined) settleErroredDependents(e, u);
550
+ if (a !== undefined) settleErroredDependents(e, a);
532
551
  // Self-registration (this node's own superseded flight) is the #3181
533
552
  // sweep's business below — retiring it here too would walk twice.
534
553
  if (_) for (const t of _) if (t !== e) settlePendingSource(e, t);
@@ -567,18 +586,18 @@ function recompute(e, t = false) {
567
586
  // kept at a park — one spurious recompute at most). A creation pass and a
568
587
  // tracked effect trim now: their frames are replaceable like a direct
569
588
  // commit, and a tracked effect's spurious run would be user-visible.
570
- if (!e.T?.F && e.ue === NOT_PENDING && !(n && e.Qe)) {
589
+ if (!e.T?.F && e.ie === NOT_PENDING && !(n && e.Qe)) {
571
590
  if (t || n === EFFECT_TRACKED) trimStaleDeps(e); else heldTrim(e);
572
591
  }
573
592
  // Observe: the posture the run executed under — lane work (optimistic:
574
593
  // overlay, never waste), a transaction's pass (held), or plain.
575
- if (attrHooks !== null) attrHooks.recomputeEnd(e, t, i, d !== null, flushTransaction !== null || passTx !== null || (e.l & CONFIG_HELD) !== 0, e.ue !== NOT_PENDING);
594
+ if (attrHooks !== null) attrHooks.recomputeEnd(e, t, i, d !== null, flushTransaction !== null || passTx !== null || (e.l & CONFIG_HELD) !== 0, e.ie !== NOT_PENDING);
576
595
  // A staged value, a parked frame (L2: the commit retires it), or status the
577
596
  // commit sweep must settle (a pending or uninitialized pass), queues the
578
597
  // node for this flush's commit. A first pass queues only when pending or
579
598
  // born held: otherwise its value published directly. A queued pass's
580
599
  // children are uncommitted (CONFIG_STAGED) until that commit.
581
- if (e.ue !== NOT_PENDING || e.T !== null && (e.T.Nt !== null || e.T.ft !== null) || (e.m & (STATUS_PENDING | STATUS_UNINITIALIZED)) !== 0 && (!t || (e.m & STATUS_PENDING) !== 0)) {
600
+ if (e.ie !== NOT_PENDING || e.T !== null && (e.T.ft !== null || e.T.Nt !== null) || (e.m & (STATUS_PENDING | STATUS_UNINITIALIZED)) !== 0 && (!t || (e.m & STATUS_PENDING) !== 0)) {
582
601
  e.l |= CONFIG_STAGED;
583
602
  // Lane work is the lane's to reveal (its seam), not this flush's commit.
584
603
  if (d === null) queuePendingNode(e);
@@ -614,7 +633,7 @@ function updateIfNecessary(e) {
614
633
  }
615
634
  }
616
635
  }
617
- if (e.R & REACTIVE_DIRTY || e.T?.F && e.ie < clock && !e.T?.Se) {
636
+ if (e.R & REACTIVE_DIRTY || e.T?.F && e.ae < clock && !e.T?.Ee) {
618
637
  recompute(e);
619
638
  }
620
639
  // The guard above refused an already-disposed node; the recompute it just
@@ -644,16 +663,16 @@ function computed(e, t) {
644
663
  // plus the slots.
645
664
  const s = {
646
665
  id: inheritId(t, n, context),
647
- l: (n ? CONFIG_TRANSPARENT : 0) | (t?.ownedWrite ? CONFIG_OWNED_WRITE : 0) | (!context || t?.lazy ? CONFIG_AUTO_DISPOSE : 0) | (t?.sync ? CONFIG_SYNC : 0) | (t?.le ? CONFIG_NO_SNAPSHOT : 0) | (
666
+ l: (n ? CONFIG_TRANSPARENT : 0) | (t?.ownedWrite ? CONFIG_OWNED_WRITE : 0) | (!context || t?.lazy ? CONFIG_AUTO_DISPOSE : 0) | (t?.sync ? CONFIG_SYNC : 0) | (t?.ue ? CONFIG_NO_SNAPSHOT : 0) | (
648
667
  // Plumbing is an observe-tier notion (a name and records to
649
668
  // withhold); the prod literal never carries the bit.
650
669
  t?.Tt ? CONFIG_PLUMBING : 0) | (t?.St ?? 0) | (snapshotCaptureActive && ownerInSnapshotScope(context) ? CONFIG_IN_SNAPSHOT_SCOPE : 0),
651
- Ye: t?.equals ?? isEqual,
670
+ je: t?.equals ?? isEqual,
652
671
  rt: null,
653
672
  A: context?.A ?? defaultContext,
654
673
  ct: 0,
655
674
  X: e,
656
- Ie: o ? t.loadingValue : undefined,
675
+ le: o ? t.loadingValue : undefined,
657
676
  Et: 0,
658
677
  At: undefined,
659
678
  Rt: null,
@@ -668,8 +687,8 @@ function computed(e, t) {
668
687
  ze: null,
669
688
  R: t?.lazy ? REACTIVE_LAZY : REACTIVE_NONE,
670
689
  m: o ? 0 : STATUS_UNINITIALIZED,
671
- ie: clock,
672
- ue: NOT_PENDING,
690
+ ae: clock,
691
+ ie: NOT_PENDING,
673
692
  Ot: -1,
674
693
  ce: o,
675
694
  T: null,
@@ -691,23 +710,23 @@ function computed(e, t) {
691
710
  * this; hot paths read `el._x?._field` gated by the _config presence bits.
692
711
  * Never call ext() just to store a field's default. */ function ext(e) {
693
712
  return e.T ??= {
713
+ Ee: null,
694
714
  Se: null,
695
- ae: null,
696
715
  F: undefined,
697
716
  fe: undefined,
698
717
  se: undefined,
699
718
  Dt: undefined,
700
- lt: undefined,
701
- Nt: null,
719
+ st: undefined,
702
720
  ft: null,
721
+ Nt: null,
703
722
  Je: null,
704
723
  ut: false,
705
724
  Gt: NOT_PENDING,
706
725
  Ft: -1,
707
- Ee: 0,
726
+ de: 0,
708
727
  V: NOT_PENDING,
709
728
  I: 0,
710
- de: undefined
729
+ Te: undefined
711
730
  };
712
731
  }
713
732
 
@@ -771,10 +790,16 @@ function computed(e, t) {
771
790
  // read the screen. Lane work with no committed value yet reads a flight
772
791
  // as a mount's memo does: it enters, and the boundary it mounts catches
773
792
  // the pending (#3540).
793
+ // A boundary's tree and output (CONFIG_FRAME) read as a render effect
794
+ // does: structure, not a derivation of what it shows (#4283). A mount
795
+ // under a hold still enters it: the content memo it reads is born held,
796
+ // with no committed value to serve.
774
797
  // (Verdict readers and lanes exist only with their engines installed.)
775
798
  const n = observeFlightHook && e.l & CONFIG_VERDICT;
776
799
  const o = laneStageHook && passLane !== null;
777
- if ((!o || e.m & STATUS_UNINITIALIZED && t.m & STATUS_PENDING) && !n && (e.i !== EFFECT_RENDER || t.l & CONFIG_INPUTS_PUBLISHED)) return false;
800
+ if ((!o || e.m & STATUS_UNINITIALIZED && t.m & STATUS_PENDING) && !n && (
801
+ // CONFIG_FRAME, spelled as at the effect's creation.
802
+ !(e.l & EFFECT_RENDER << 23) || t.l & CONFIG_INPUTS_PUBLISHED)) return false;
778
803
  const s = txOf(t);
779
804
  // Lane work and verdict readers are never the transaction's pass, whichever
780
805
  // flush runs it: a node T holds re-enters T when it re-runs (`recompute`'s
@@ -794,7 +819,7 @@ function computed(e, t) {
794
819
 
795
820
  /** The computed whose pass a creation under `owner` belongs to (a root's is
796
821
  * its nearest computed ancestor's), or null outside every pass. */ function creatorPass(e) {
797
- return e !== null && e.Pt ? e.Ht : e;
822
+ return e !== null && e.Pt ? e.ht : e;
798
823
  }
799
824
 
800
825
  /** L2 — park the previous pass's frame for this node's commit: the children
@@ -803,8 +828,8 @@ function computed(e, t) {
803
828
  * the frame that replaces them (`commitPendingNode`) or when the owner does. */ function parkChildren(e) {
804
829
  markDisposal(e);
805
830
  const t = ext(e);
806
- t.ft = e.rt;
807
- t.Nt = e.ze;
831
+ t.Nt = e.rt;
832
+ t.ft = e.ze;
808
833
  e.rt = null;
809
834
  e.ze = null;
810
835
  e.ct = 0;
@@ -816,21 +841,24 @@ function computed(e, t) {
816
841
  * mode (recompute is called explicitly by `effect()`), so we hardcode the lazy bits and skip
817
842
  * the auto-dispose CONFIG bit (effect() previously cleared it post-construction).
818
843
  */ function createEffectNode(e, t, n, o, s) {
819
- const E = s?.transparent ?? false;
844
+ const l = s?.transparent ?? false;
820
845
  // Prod and observe boilerplates — see computed() for why the observe tier
821
846
  // gets its `_name` as a literal slot rather than a write after the fact.
822
847
  // The default label is the node kind (tracked effects relabel their computed
823
848
  // in trackedEffect); the wrappers in signals.ts no longer spread a name into
824
849
  // the options to get it.
825
- const l = {
826
- id: inheritId(s, E, context),
827
- l: (E ? CONFIG_TRANSPARENT : 0) | (s?.ownedWrite ? CONFIG_OWNED_WRITE : 0) | (s?.sync ? CONFIG_SYNC : 0) | (s?.St ?? 0) | (snapshotCaptureActive && ownerInSnapshotScope(context) ? CONFIG_IN_SNAPSHOT_SCOPE : 0),
828
- Ye: false,
850
+ const E = {
851
+ id: inheritId(s, l, context),
852
+ l:
853
+ // CONFIG_FRAME for a render effect (EFFECT_RENDER = 1; a user
854
+ // effect's 1 << 24 is unused).
855
+ o << 23 | (l ? CONFIG_TRANSPARENT : 0) | (s?.ownedWrite ? CONFIG_OWNED_WRITE : 0) | (s?.sync ? CONFIG_SYNC : 0) | (s?.St ?? 0) | (snapshotCaptureActive && ownerInSnapshotScope(context) ? CONFIG_IN_SNAPSHOT_SCOPE : 0),
856
+ je: false,
829
857
  rt: null,
830
858
  A: context?.A ?? defaultContext,
831
859
  ct: 0,
832
860
  X: e,
833
- Ie: undefined,
861
+ le: undefined,
834
862
  Et: 0,
835
863
  At: undefined,
836
864
  Rt: null,
@@ -845,14 +873,14 @@ function computed(e, t) {
845
873
  ze: null,
846
874
  R: REACTIVE_LAZY,
847
875
  m: STATUS_UNINITIALIZED,
848
- ie: clock,
849
- ue: NOT_PENDING,
876
+ ae: clock,
877
+ ie: NOT_PENDING,
850
878
  Ot: -1,
851
879
  ce: false,
852
880
  Qe: false,
853
881
  _t: undefined,
854
882
  Ge: t,
855
- ht: n,
883
+ Ht: n,
856
884
  kt: undefined,
857
885
  i: o,
858
886
  T: null,
@@ -865,9 +893,9 @@ function computed(e, t) {
865
893
  // allocation on EVERY effect at creation (an alloc + 19 field stores,
866
894
  // +23% effect creation, caught by the creation benches). Only genuinely
867
895
  // per-node channels (boundaries) live on _x.
868
- if (s?.unobserved) ext(l).Dt = s.unobserved;
869
- setupComputedNode(l, lazyOptions);
870
- return l;
896
+ if (s?.unobserved) ext(E).Dt = s.unobserved;
897
+ setupComputedNode(E, lazyOptions);
898
+ return E;
871
899
  }
872
900
 
873
901
  /**
@@ -895,17 +923,13 @@ const lazyOptions = {
895
923
 
896
924
  function setupComputedNode(e, t) {
897
925
  e.Rt = e;
898
- const n = context?.Pt ? context.Ht : context;
926
+ const n = context?.Pt ? context.ht : context;
899
927
  if (context) linkChild(context, e);
900
928
  if (n) e.Et = n.Et + 1;
901
929
  wireExternalSourceHook?.(e);
902
930
  !t?.lazy && recompute(e, true);
903
931
  if (snapshotCaptureActive && !t?.lazy) {
904
- if (!(e.m & STATUS_PENDING) && !(e.l & CONFIG_NO_SNAPSHOT)) {
905
- ext(e).lt = e.Ie === undefined ? NO_SNAPSHOT : e.Ie;
906
- e.l |= CONFIG_HAS_SNAPSHOT;
907
- snapshotSources.add(e);
908
- }
932
+ if (!(e.m & STATUS_PENDING) && !(e.l & CONFIG_NO_SNAPSHOT)) takeSnapshot(e, e.le);
909
933
  }
910
934
  }
911
935
 
@@ -915,13 +939,13 @@ function signal(e, t) {
915
939
  // createSignal nodes so ownerPath can locate signal subjects; null here,
916
940
  // and staying null on internal signals — one shape either way).
917
941
  const n = {
918
- Ye: t?.equals ?? isEqual,
919
- l: (t?.ownedWrite ? CONFIG_OWNED_WRITE : 0) | (t?.le ? CONFIG_NO_SNAPSHOT : 0),
920
- Ie: e,
942
+ je: t?.equals ?? isEqual,
943
+ l: (t?.ownedWrite ? CONFIG_OWNED_WRITE : 0) | (t?.ue ? CONFIG_NO_SNAPSHOT : 0),
944
+ le: e,
921
945
  o: null,
922
946
  Ct: null,
923
- ie: clock,
924
- ue: NOT_PENDING,
947
+ ae: clock,
948
+ ie: NOT_PENDING,
925
949
  Ot: -1,
926
950
  T: null,
927
951
  _name: t?.name ?? "signal",
@@ -929,11 +953,7 @@ function signal(e, t) {
929
953
  H: null
930
954
  };
931
955
  if (t?.unobserved) ext(n).Dt = t.unobserved;
932
- if (snapshotCaptureActive && !(n.l & CONFIG_NO_SNAPSHOT)) {
933
- ext(n).lt = e === undefined ? NO_SNAPSHOT : e;
934
- n.l |= CONFIG_HAS_SNAPSHOT;
935
- snapshotSources.add(n);
936
- }
956
+ if (snapshotCaptureActive && !(n.l & CONFIG_NO_SNAPSHOT)) takeSnapshot(n, e);
937
957
  return n;
938
958
  }
939
959
 
@@ -952,14 +972,14 @@ function isEqual(e, t) {
952
972
  * the store's notification machinery. The observe literal adds the label
953
973
  * and location slots (the store relabels `store.<key>` and stamps the
954
974
  * store's `loc` when the engine is installed). */ function slotSignal(e, t, n, o, s) {
955
- const E = {
956
- Ye: t,
975
+ const l = {
976
+ je: t,
957
977
  l: CONFIG_OWNED_WRITE | CONFIG_SLOT_NODE,
958
- Ie: e,
978
+ le: e,
959
979
  o: null,
960
980
  Ct: null,
961
- ie: clock,
962
- ue: NOT_PENDING,
981
+ ae: clock,
982
+ ie: NOT_PENDING,
963
983
  Ot: -1,
964
984
  T: null,
965
985
  O: n,
@@ -971,7 +991,7 @@ function isEqual(e, t) {
971
991
  _loc: undefined,
972
992
  H: null
973
993
  };
974
- return E;
994
+ return l;
975
995
  }
976
996
 
977
997
  /**
@@ -1092,7 +1112,7 @@ function setVerdict(e) {
1092
1112
  * never the graph — A32).
1093
1113
  * False means the reader derives from the staged value.
1094
1114
  */ function readerSeesCommitted(e, t) {
1095
- return !t || e.ue === NOT_PENDING || t.l & CONFIG_CHILDREN_FORBIDDEN;
1115
+ return !t || e.ie === NOT_PENDING || t.l & CONFIG_CHILDREN_FORBIDDEN;
1096
1116
  }
1097
1117
 
1098
1118
  /** A28 — set when a node is staged (queuePendingNode) OUTSIDE a flush;
@@ -1113,12 +1133,12 @@ function markUnflushedStaged() {
1113
1133
  * is unflushed. Exempt: promoted writes (A28 (4): a write issued inside a
1114
1134
  * recompute is promoted at that recompute's end — boundary and loading
1115
1135
  * machinery, signals declared for in-computation writes). */ function unflushedValue(e) {
1116
- if (globalQueue.q || e.ue === NOT_PENDING || e.l & CONFIG_PROMOTED) return NOT_PENDING;
1136
+ if (globalQueue.q || e.ie === NOT_PENDING || e.l & CONFIG_PROMOTED) return NOT_PENDING;
1117
1137
  // A held node (L2) carries a staged value between flushes too, but it was
1118
1138
  // flushed — and parked. Not an unflushed write — unless rewritten since:
1119
1139
  // then the flushed staging is what the world sees until the next flush.
1120
1140
  if (e.l & CONFIG_HELD) return e.T.Ft === clock ? e.T.Gt : NOT_PENDING;
1121
- return e.Ie;
1141
+ return e.le;
1122
1142
  }
1123
1143
 
1124
1144
  /** A28: a held node rewritten outside a flush keeps the staging the last
@@ -1126,7 +1146,7 @@ function markUnflushedStaged() {
1126
1146
  * stash is stamped with the clock, which that flush advances. */ function stashFlushed(e) {
1127
1147
  const t = e.T;
1128
1148
  if (t.Ft !== clock) {
1129
- t.Gt = e.ue;
1149
+ t.Gt = e.ie;
1130
1150
  t.Ft = clock;
1131
1151
  unflushedStaged = true;
1132
1152
  }
@@ -1155,7 +1175,7 @@ function resyncUnflushedCompanions() {
1155
1175
  /** A tracked read's pull of a computed: bring it current when the flush has
1156
1176
  * reached its height (or the reader is a fresh-pull waiter), and sit the
1157
1177
  * reader above it. */ function pullComputed(e, t) {
1158
- if (e.Et >= dirtyQueue.st) {
1178
+ if (e.Et >= dirtyQueue.lt) {
1159
1179
  markNode(t);
1160
1180
  markHeap(dirtyQueue);
1161
1181
  updateIfNecessary(e);
@@ -1174,7 +1194,7 @@ function resyncUnflushedCompanions() {
1174
1194
 
1175
1195
  function read(e) {
1176
1196
  let t = context;
1177
- if (t?.Pt) t = t.Ht;
1197
+ if (t?.Pt) t = t.ht;
1178
1198
  const n = e;
1179
1199
  // CARVE 1: `owner` was `el._firewall || el` — a store leaf's status,
1180
1200
  // height and error were read off its projection computed. (Typed loosely
@@ -1185,7 +1205,7 @@ function read(e) {
1185
1205
  // The verdict windows (`latest`, `isPending`; verdict.ts): one cold path,
1186
1206
  // off this one, present only while a window is open.
1187
1207
  if (verdict !== null) return verdict(e, t);
1188
- if (!n.X && e.T?.lt === undefined && !snapshotCaptureActive && (!unflushedStaged || e.ue === NOT_PENDING) && // A28, see readNodeFast
1208
+ if (!n.X && e.T?.st === undefined && !snapshotCaptureActive && (!unflushedStaged || e.ie === NOT_PENDING) && // A28, see readNodeFast
1189
1209
  !(e.l & CONFIG_OVERRIDE) && // lanes: the slow path's one arm
1190
1210
  true) {
1191
1211
  if (t) {
@@ -1201,18 +1221,18 @@ function read(e) {
1201
1221
  // future (REACTIVE_JOINED): a first pass that did is born held (A29),
1202
1222
  // wherever it was created. Lane work sees the screen (`frameRead`).
1203
1223
  if (e.l & CONFIG_HELD && !(t.l & CONFIG_CHILDREN_FORBIDDEN)) {
1204
- if (frameRead(t, e)) return e.Ie;
1224
+ if (frameRead(t, e)) return e.le;
1205
1225
  joinPass(t, e);
1206
1226
  }
1207
1227
  }
1208
1228
  // Committed visibility for untracked and children-forbidden readers.
1209
- if (!t || e.ue === NOT_PENDING || t.l & CONFIG_CHILDREN_FORBIDDEN) return e.Ie;
1229
+ if (!t || e.ie === NOT_PENDING || t.l & CONFIG_CHILDREN_FORBIDDEN) return e.le;
1210
1230
  // (A plain signal is never uninitialized — the carve-out is `serve`'s.)
1211
1231
  // Lane work over a folded lane (D-34), once the frame has a
1212
1232
  // transaction, reads the screen too.
1213
- if ((observeFlightHook && t.l & CONFIG_VERDICT || laneStageHook && passLane?.folded) && stagedScreen(t)) return e.Ie;
1233
+ if ((observeFlightHook && t.l & CONFIG_VERDICT || laneStageHook && passLane?.folded) && stagedScreen(t)) return e.le;
1214
1234
  stagedRead(t);
1215
- return e.ue;
1235
+ return e.ie;
1216
1236
  }
1217
1237
  // Rule 3: this read serves the committed value to a render effect outside a
1218
1238
  // parking flush (decided after the pull below — a pull can join).
@@ -1245,6 +1265,19 @@ function read(e) {
1245
1265
  const n = laneReadHook(t, e);
1246
1266
  if (n !== NOT_PENDING) return n;
1247
1267
  }
1268
+ // A reader in a snapshot scope (a hydration claim) is served the value the
1269
+ // server rendered with: a client write's recompute still in flight does
1270
+ // not pull the claim off the markup it adopts — the reader replays at the
1271
+ // scope's release. An errored node throws below as for any reader.
1272
+ if (snapshotCaptureActive && t && t.l & CONFIG_IN_SNAPSHOT_SCOPE) {
1273
+ const n = e.T?.st;
1274
+ if (n !== undefined && !(o.m & STATUS_ERROR)) {
1275
+ const o = n === NO_SNAPSHOT ? undefined : n;
1276
+ const s = e.ie !== NOT_PENDING ? e.ie : e.le;
1277
+ if (s !== o) t.R |= REACTIVE_SNAPSHOT_STALE;
1278
+ return o;
1279
+ }
1280
+ }
1248
1281
  // A stale reader of a held flight (rule 3, A15's reveal corollary) is served
1249
1282
  // the committed value — coherent with the frame, whose inputs are the
1250
1283
  // committed ones too — and does not go pending on it. So is lane work
@@ -1289,25 +1322,16 @@ function read(e) {
1289
1322
  // Only a genuine reactive re-read may retry an errored async source:
1290
1323
  // - tracking: owned/tracked scope only (never events / `untrack` / effect side-effect phase)
1291
1324
  // - owner._time < clock: only on a later cycle than the one the error was found
1292
- if (tracking && o.ie < clock) {
1325
+ if (tracking && o.ae < clock) {
1293
1326
  recompute(o);
1294
1327
  return read(e);
1295
1328
  } else throw o.T?.F;
1296
1329
  }
1297
- if (snapshotCaptureActive && t && t.l & CONFIG_IN_SNAPSHOT_SCOPE) {
1298
- const n = e.T?.lt;
1299
- if (n !== undefined) {
1300
- const o = n === NO_SNAPSHOT ? undefined : n;
1301
- const s = e.ue !== NOT_PENDING ? e.ue : e.Ie;
1302
- if (s !== o) t.R |= REACTIVE_SNAPSHOT_STALE;
1303
- return o;
1304
- }
1305
- }
1306
- if (s) return e.Ie;
1330
+ if (s) return e.le;
1307
1331
  // D-41: an untracked read reads the screen, and a shown error is on it
1308
1332
  // until the answer that replaces it commits.
1309
- if (!t && e.T?.de) throw e.T.de;
1310
- const E = serve(e, t);
1333
+ if (!t && e.T?.Te) throw e.T.Te;
1334
+ const l = serve(e, t);
1311
1335
  if (!t && typeof n.X === "function" && e.l & CONFIG_AUTO_DISPOSE && !(o.m & STATUS_PENDING) && !e.o) {
1312
1336
  // Deferred, not inline (#3078): an inline unobserved() here made untracked
1313
1337
  // reads destructive — dispose on this read, full revival recompute on the
@@ -1318,7 +1342,7 @@ function read(e) {
1318
1342
  dormantNodes.add(e);
1319
1343
  schedule();
1320
1344
  }
1321
- return E;
1345
+ return l;
1322
1346
  }
1323
1347
 
1324
1348
  /**
@@ -1335,18 +1359,18 @@ function read(e) {
1335
1359
  // an untracked reader has nothing to serve and holds (A19 exception 1) — a
1336
1360
  // bookkeeping read (`spectate`) likewise, and a children-forbidden reader
1337
1361
  // (A32: the frame, which has nothing here).
1338
- if (e.ue !== NOT_PENDING && e.m & STATUS_UNINITIALIZED && (!t || spectating || t.l & CONFIG_CHILDREN_FORBIDDEN)) throw new NotReadyError(null);
1362
+ if (e.ie !== NOT_PENDING && e.m & STATUS_UNINITIALIZED && (!t || spectating || t.l & CONFIG_CHILDREN_FORBIDDEN)) throw new NotReadyError(null);
1339
1363
  const n = t && unflushedStaged ? unflushedValue(e) : NOT_PENDING;
1340
1364
  if (n !== NOT_PENDING) {
1341
1365
  markLateLinker(t);
1342
1366
  return n;
1343
1367
  }
1344
- if (readerSeesCommitted(e, t)) return e.Ie;
1345
- if (observeFlightHook && t.l & CONFIG_VERDICT && !(e.m & STATUS_UNINITIALIZED) && stagedScreen(t)) return e.Ie;
1368
+ if (readerSeesCommitted(e, t)) return e.le;
1369
+ if (observeFlightHook && t.l & CONFIG_VERDICT && !(e.m & STATUS_UNINITIALIZED) && stagedScreen(t)) return e.le;
1346
1370
  stagedRead(t, e);
1347
1371
  // D-41: the staged answer is an error (`stageError`).
1348
- if (e.l & CONFIG_STAGED_ERROR) throw e.ue;
1349
- return e.ue;
1372
+ if (e.l & CONFIG_STAGED_ERROR) throw e.ie;
1373
+ return e.ie;
1350
1374
  }
1351
1375
 
1352
1376
  /** A pass read a staging of this flush: it derives from what the flush may
@@ -1400,8 +1424,12 @@ function read(e) {
1400
1424
  * REVEALS — the creation-time arm skips pending computeds for the same
1401
1425
  * reason. Firewall leaves belong to a projection whose compute is the tree's
1402
1426
  * own work, captured (or deliberately not) at creation. */ function captureWriteSnapshot(e, t) {
1403
- if (e.l & CONFIG_NO_SNAPSHOT || e.X !== undefined || e.T?.lt !== undefined) return;
1404
- ext(e).lt = t === undefined ? NO_SNAPSHOT : t;
1427
+ if (e.l & CONFIG_NO_SNAPSHOT || e.X !== undefined || e.T?.st !== undefined) return;
1428
+ takeSnapshot(e, t);
1429
+ }
1430
+
1431
+ function takeSnapshot(e, t) {
1432
+ ext(e).st = t === undefined ? NO_SNAPSHOT : t;
1405
1433
  e.l |= CONFIG_HAS_SNAPSHOT;
1406
1434
  snapshotSources.add(e);
1407
1435
  }
@@ -1431,9 +1459,9 @@ function read(e) {
1431
1459
  * unwinding a flush or a setter; answered "same" so nothing commits.
1432
1460
  * @internal
1433
1461
  */ function isSame(e, t, n) {
1434
- if (e.Ye === isEqual) return t === n;
1462
+ if (e.je === isEqual) return t === n;
1435
1463
  try {
1436
- return e.Ye && e.Ye(t, n);
1464
+ return e.je && e.je(t, n);
1437
1465
  } catch (t) {
1438
1466
  if (!(t instanceof NotReadyError)) return notifyStatus(e, STATUS_ERROR, t), true;
1439
1467
  }
@@ -1441,7 +1469,7 @@ function read(e) {
1441
1469
 
1442
1470
  function setSignal(e, t) {
1443
1471
  if (writeHook !== null) writeHook(e);
1444
- const n = e.ue === NOT_PENDING ? e.Ie : e.ue;
1472
+ const n = e.ie === NOT_PENDING ? e.le : e.ie;
1445
1473
  if (typeof t === "function") t = t(n);
1446
1474
  // Lanes: a write landing on a guess is its truth (A18 — an async guess's
1447
1475
  // own landing), judged against the guess; one landing on a lane's
@@ -1456,7 +1484,7 @@ function setSignal(e, t) {
1456
1484
  // user comparator must not run against `undefined` (matches recompute).
1457
1485
  // D-41: a write over a shown error is a change whatever the last good
1458
1486
  // value was — the error leaves at its commit (`commitPendingNode`).
1459
- const o = !!(e.m & STATUS_UNINITIALIZED) || !!e.T?.de || !isSame(e, n, t);
1487
+ const o = !!(e.m & STATUS_UNINITIALIZED) || !!e.T?.Te || !isSame(e, n, t);
1460
1488
  if (!o) return t;
1461
1489
  // Attribution hook: this committed write is where a re-run chain begins.
1462
1490
  if (attrHooks !== null) attrHooks.write(e, n, t);
@@ -1470,16 +1498,16 @@ function setSignal(e, t) {
1470
1498
  // pass reads a value the server never had. Store leaves written here are
1471
1499
  // plain signals and qualify the same way.
1472
1500
  if (snapshotCaptureActive) captureWriteSnapshot(e, n);
1473
- const s = e.ue !== NOT_PENDING;
1501
+ const s = e.ie !== NOT_PENDING;
1474
1502
  if (!s) queuePendingNode(e);
1475
1503
  // A28: a held node rewritten outside a flush keeps its flushed staging
1476
1504
  // for every reader until the flush that carries the rewrite.
1477
1505
  else if (e.l & CONFIG_HELD && !globalQueue.q) stashFlushed(e);
1478
- e.ue = t;
1506
+ e.ie = t;
1479
1507
  if (context !== null) notePromotedWrite(e);
1480
1508
  // _time is a computed-only slot (§12e): writing it on a signal would fork
1481
1509
  // the lean shape. Every read site is computed-typed.
1482
- if (e.X !== undefined) e.ie = clock;
1510
+ if (e.X !== undefined) e.ae = clock;
1483
1511
  // Staged-rewrite fast path (§12d): a re-write to a node whose subscribers
1484
1512
  // were already walked — and where nothing has recomputed or linked since
1485
1513
  // (epoch) — re-stages the value and stops. The walk is idempotent (subs
@@ -1512,7 +1540,7 @@ function setSignal(e, t) {
1512
1540
  const n = e.l & CONFIG_HELD && !(e.R & REACTIVE_MANUAL_WRITE) && txOf(e) !== flushTransaction;
1513
1541
  // The writer read the committed frame; its updater composes on it.
1514
1542
  if (n && typeof t === "function") {
1515
- const n = t(e.Ie);
1543
+ const n = t(e.le);
1516
1544
  t = () => n;
1517
1545
  }
1518
1546
  // #4110: the write replaces a failed derivation's outcome. It lands without
@@ -1520,7 +1548,7 @@ function setSignal(e, t) {
1520
1548
  // every later read keeps throwing the error the derivation left behind.
1521
1549
  // The error stays the display until the write commits (D-41).
1522
1550
  if (e.m & STATUS_ERROR) {
1523
- e.T.de = e.T.F;
1551
+ e.T.Te = e.T.F;
1524
1552
  notifyStatus(e, STATUS_NONE, undefined);
1525
1553
  }
1526
1554
  t = setSignal(e, t);
@@ -1532,7 +1560,7 @@ function setSignal(e, t) {
1532
1560
  e.R = e.R & ~REACTIVE_CHECK | REACTIVE_DIRTY;
1533
1561
  insertIntoHeap(e, dirtyQueue);
1534
1562
  schedule();
1535
- } else if (e.ue !== NOT_PENDING) e.R |= REACTIVE_MANUAL_WRITE;
1563
+ } else if (e.ie !== NOT_PENDING) e.R |= REACTIVE_MANUAL_WRITE;
1536
1564
  return t;
1537
1565
  }
1538
1566