Fix WASM browser: broken links (&rest bytecode) + broken reactive counter (ListRef mutation)
Two bugs fixed: 1. Links: bytecode compiler doesn't handle &rest params — treats them as positional, so (first rest) gets a raw string instead of a list. Replaced &rest with explicit optional params in all bytecode-compiled web SX files (dom-query, dom-add-listener, browser-push-state, etc.). The VM already pads missing args with Nil. 2. Reactive counter: signal-remove-sub! used (filter ...) which returns immutable List, but signal-add-sub! uses (append!) which only mutates ListRef. Subscribers silently vanished after first effect re-run. Fixed by adding remove! primitive that mutates ListRef in-place. Also: - Added evalVM API to WASM kernel (compile + run through bytecode VM) - Added scope tracing (scope-push!/pop!/peek/context instrumentation) - Added Playwright reactive mode for debugging island signal/DOM state - Replaced cek-call with direct calls in core-signals.sx effect/computed - Recompiled all 23 bytecode modules Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -1,21 +1,110 @@
|
||||
(define assert-signal-value :effects () (fn ((sig :as any) expected) (let ((actual (deref sig))) (assert= actual expected (str "Expected signal value " expected ", got " actual)))))
|
||||
(define
|
||||
assert-signal-value
|
||||
:effects ()
|
||||
(fn
|
||||
((sig :as any) expected)
|
||||
(let
|
||||
((actual (deref sig)))
|
||||
(assert=
|
||||
actual
|
||||
expected
|
||||
(str "Expected signal value " expected ", got " actual)))))
|
||||
|
||||
(define assert-signal-has-subscribers :effects () (fn ((sig :as any)) (assert (> (len (signal-subscribers sig)) 0) "Expected signal to have subscribers")))
|
||||
(define
|
||||
assert-signal-has-subscribers
|
||||
:effects ()
|
||||
(fn
|
||||
((sig :as any))
|
||||
(assert
|
||||
(> (len (signal-subscribers sig)) 0)
|
||||
"Expected signal to have subscribers")))
|
||||
|
||||
(define assert-signal-no-subscribers :effects () (fn ((sig :as any)) (assert (= (len (signal-subscribers sig)) 0) "Expected signal to have no subscribers")))
|
||||
(define
|
||||
assert-signal-no-subscribers
|
||||
:effects ()
|
||||
(fn
|
||||
((sig :as any))
|
||||
(assert
|
||||
(= (len (signal-subscribers sig)) 0)
|
||||
"Expected signal to have no subscribers")))
|
||||
|
||||
(define assert-signal-subscriber-count :effects () (fn ((sig :as any) (n :as number)) (let ((actual (len (signal-subscribers sig)))) (assert= actual n (str "Expected " n " subscribers, got " actual)))))
|
||||
(define
|
||||
assert-signal-subscriber-count
|
||||
:effects ()
|
||||
(fn
|
||||
((sig :as any) (n :as number))
|
||||
(let
|
||||
((actual (len (signal-subscribers sig))))
|
||||
(assert= actual n (str "Expected " n " subscribers, got " actual)))))
|
||||
|
||||
(define simulate-signal-set! :effects (mutation) (fn ((sig :as any) value) (reset! sig value)))
|
||||
(define
|
||||
simulate-signal-set!
|
||||
:effects (mutation)
|
||||
(fn ((sig :as any) value) (reset! sig value)))
|
||||
|
||||
(define simulate-signal-swap! :effects (mutation) (fn ((sig :as any) (f :as lambda) &rest args) (apply swap! (cons sig (cons f args)))))
|
||||
(define
|
||||
simulate-signal-swap!
|
||||
:effects (mutation)
|
||||
(fn ((sig :as any) (f :as lambda)) (swap! sig f)))
|
||||
|
||||
(define assert-computed-dep-count :effects () (fn ((sig :as any) (n :as number)) (let ((actual (len (signal-deps sig)))) (assert= actual n (str "Expected " n " deps, got " actual)))))
|
||||
(define
|
||||
assert-computed-dep-count
|
||||
:effects ()
|
||||
(fn
|
||||
((sig :as any) (n :as number))
|
||||
(let
|
||||
((actual (len (signal-deps sig))))
|
||||
(assert= actual n (str "Expected " n " deps, got " actual)))))
|
||||
|
||||
(define assert-computed-depends-on :effects () (fn ((computed-sig :as any) (dep-sig :as any)) (assert (contains? (signal-deps computed-sig) dep-sig) "Expected computed to depend on the given signal")))
|
||||
(define
|
||||
assert-computed-depends-on
|
||||
:effects ()
|
||||
(fn
|
||||
((computed-sig :as any) (dep-sig :as any))
|
||||
(assert
|
||||
(contains? (signal-deps computed-sig) dep-sig)
|
||||
"Expected computed to depend on the given signal")))
|
||||
|
||||
(define count-effect-runs :effects (mutation) (fn ((thunk :as lambda)) (let ((count (signal 0))) (effect (fn () (deref count))) (let ((run-count 0) (tracker (effect (fn () (set! run-count (+ run-count 1)) (cek-call thunk nil))))) run-count))))
|
||||
(define
|
||||
count-effect-runs
|
||||
:effects (mutation)
|
||||
(fn
|
||||
((thunk :as lambda))
|
||||
(let
|
||||
((count (signal 0)))
|
||||
(effect (fn () (deref count)))
|
||||
(let
|
||||
((run-count 0)
|
||||
(tracker
|
||||
(effect
|
||||
(fn () (set! run-count (+ run-count 1)) (cek-call thunk nil)))))
|
||||
run-count))))
|
||||
|
||||
(define make-test-signal :effects (mutation) (fn (initial-value) (let ((sig (signal initial-value)) (history (list))) (effect (fn () (append! history (deref sig)))) {:signal sig :history history})))
|
||||
(define
|
||||
make-test-signal
|
||||
:effects (mutation)
|
||||
(fn
|
||||
(initial-value)
|
||||
(let
|
||||
((sig (signal initial-value)) (history (list)))
|
||||
(effect (fn () (append! history (deref sig))))
|
||||
{:signal sig :history history})))
|
||||
|
||||
(define assert-batch-coalesces :effects (mutation) (fn ((thunk :as lambda) (expected-notify-count :as number)) (let ((notify-count 0) (sig (signal 0))) (effect (fn () (deref sig) (set! notify-count (+ notify-count 1)))) (set! notify-count 0) (batch thunk) (assert= notify-count expected-notify-count (str "Expected " expected-notify-count " notifications, got " notify-count)))))
|
||||
(define
|
||||
assert-batch-coalesces
|
||||
:effects (mutation)
|
||||
(fn
|
||||
((thunk :as lambda) (expected-notify-count :as number))
|
||||
(let
|
||||
((notify-count 0) (sig (signal 0)))
|
||||
(effect (fn () (deref sig) (set! notify-count (+ notify-count 1))))
|
||||
(set! notify-count 0)
|
||||
(batch thunk)
|
||||
(assert=
|
||||
notify-count
|
||||
expected-notify-count
|
||||
(str
|
||||
"Expected "
|
||||
expected-notify-count
|
||||
" notifications, got "
|
||||
notify-count)))))
|
||||
|
||||
Reference in New Issue
Block a user