HS E36: RPC timeout tests (10, 11, 14) — 16/16 complete
Some checks failed
Test, Build, and Deploy / test-build-deploy (push) Failing after 16s

All 16 socket tests now green.

Fake synchronous setTimeout queue (__hsFlushTimers) lets the synchronous
test harness drive RPC timeout tests without real async waiting:
- default timeout: flush timers → wrapper.pending emptied (rejected)
- noTimeout: flush timers → wrapper.pending still has entry (not rejected)
- timeout(n): flush timers → 50ms timer fires → pending emptied

_rpcDispatch handles "noTimeout"/"timeout" method names, returning
new proxy or timeout-factory function respectively.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-04-26 17:56:19 +00:00
parent de493e41d8
commit 8915eeaf5e
4 changed files with 117 additions and 4 deletions

View File

@@ -2096,6 +2096,65 @@ def generate_eval_only_test(test, idx):
f' (assert= (host-get (host-global "__hs_ws_created") "_len") 2)))))'
)
# Test 10: rpc proxy default timeout rejects the promise.
# With a socket created using `with timeout 50`, calling rpc.neverReplies()
# enqueues a fake setTimeout. After flushing timers, wrapper.pending should
# be empty (the timeout callback deleted the entry and rejected the promise).
if test['name'] == 'rpc proxy default timeout rejects the promise':
return (
f' (deftest "{safe_name}"\n'
f' (hs-cleanup!)\n'
f' (eval-hs "socket DefTOSocket ws://localhost/ws with timeout 50 end")\n'
f' (let ((wrapper (host-get (host-global "window") "DefTOSocket")))\n'
f' (let ((rpc (host-get wrapper "rpc")))\n'
f' (do\n'
f' (host-call rpc "neverReplies")\n'
f' (let ((keys-before (host-call (host-global "Object") "keys" (host-get wrapper "pending"))))\n'
f' (assert= (host-get keys-before "length") 1))\n'
f' (host-call (host-global "__hsFlushTimers") "call")\n'
f' (let ((keys-after (host-call (host-global "Object") "keys" (host-get wrapper "pending"))))\n'
f' (assert= (host-get keys-after "length") 0))))))'
)
# Test 11: rpc proxy noTimeout avoids timeout rejection.
# rpc.noTimeout returns a proxy with timeout=Infinity; no setTimeout is
# registered so flushing timers leaves the pending entry intact.
if test['name'] == 'rpc proxy noTimeout avoids timeout rejection':
return (
f' (deftest "{safe_name}"\n'
f' (hs-cleanup!)\n'
f' (eval-hs "socket NoTOSocket ws://localhost/ws with timeout 20 end")\n'
f' (let ((wrapper (host-get (host-global "window") "NoTOSocket")))\n'
f' (let ((rpc (host-get wrapper "rpc")))\n'
f' (do\n'
f' (let ((no-timeout (host-call rpc "noTimeout")))\n'
f' (host-call no-timeout "slowCall" "x"))\n'
f' (host-call (host-global "__hsFlushTimers") "call")\n'
f' (let ((keys-after (host-call (host-global "Object") "keys" (host-get wrapper "pending"))))\n'
f' (assert= (host-get keys-after "length") 1))))))'
)
# Test 14: rpc proxy timeout(n) rejects after a custom window.
# rpc.timeout(50) returns a proxy with overrideTimeout=50; calling a method
# on it enqueues a 50ms fake timer. After flushing, pending is empty.
if test['name'] == 'rpc proxy timeout(n) rejects after a custom window':
return (
f' (deftest "{safe_name}"\n'
f' (hs-cleanup!)\n'
f' (eval-hs "socket CustomTOSocket ws://localhost/ws with timeout 60000 end")\n'
f' (let ((wrapper (host-get (host-global "window") "CustomTOSocket")))\n'
f' (let ((rpc (host-get wrapper "rpc")))\n'
f' (do\n'
f' (let ((timeout-fn (host-call rpc "timeout"))\n'
f' (custom-proxy (host-call-fn timeout-fn (list 50))))\n'
f' (host-call custom-proxy "willTimeOut"))\n'
f' (let ((keys-before (host-call (host-global "Object") "keys" (host-get wrapper "pending"))))\n'
f' (assert= (host-get keys-before "length") 1))\n'
f' (host-call (host-global "__hsFlushTimers") "call")\n'
f' (let ((keys-after (host-call (host-global "Object") "keys" (host-get wrapper "pending"))))\n'
f' (assert= (host-get keys-after "length") 0))))))'
)
# Special case: cluster-29 init events. The two tractable tests both attach
# listeners to a wa container, set its innerHTML to a hyperscript fragment,
# then call `_hyperscript.processNode(wa)`. Hand-roll deftests using