regex string-pattern API + test-harness host-call-fn mock

Ported from loops/sx-vm-extensions 4ab9db05 + 8ec36b31.

- sx_primitives.ml (shared serving binary): regex-replace/split/match/etc. accept
  a raw pattern string (auto-compiled) as well as a compiled regex dict. Fixes
  (regex-replace "[0-9]" "_" s) / (regex-split "[ \t]+" s) which required a dict.
- run_tests.ml (test harness only): bind host-call-fn (= apply) + host-call-fn-raising
  / host-new-function / host-iter? / host-to-list in the mock DOM block. Recovers 712
  hyperscript behavioral tests that died on "Undefined symbol: host-call-fn"
  (run_tests --jit 1073 → 361 failures). No serving impact (test binary only).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-07-01 14:46:01 +00:00
parent 921db09f5e
commit 5968c0173f
2 changed files with 41 additions and 1 deletions

View File

@@ -3516,6 +3516,32 @@ let run_spec_tests env test_files =
reg "host-await" (fun _args -> Nil);
(* host-call-fn: hyperscript's call bridge — (host-call-fn fn arg-list). In a
real host it reaches into JS; in the headless mock it is simply apply. This
was the single biggest gap: ~900 behavioral tests failed on "Undefined
symbol: host-call-fn". host-call-fn-raising propagates errors (used by the
try/catch machinery); host-new-function can't run raw JS headless so stubs. *)
let list_elems = function
| List l | ListRef { contents = l } -> l
| Nil -> []
| v -> [v] in
reg "host-call-fn" (fun args ->
match args with
| fn :: rest ->
let call_args = match rest with a :: _ -> list_elems a | [] -> [] in
(try Sx_ref.cek_call fn (List call_args)
with e -> Printf.eprintf "[mock] host-call-fn error: %s\n%!" (Printexc.to_string e); Nil)
| _ -> Nil);
reg "host-call-fn-raising" (fun args ->
match args with
| fn :: rest ->
let call_args = match rest with a :: _ -> list_elems a | [] -> [] in
Sx_ref.cek_call fn (List call_args)
| _ -> Nil);
reg "host-new-function" (fun _ -> NativeFn ("host-new-function-stub", fun _ -> Nil));
reg "host-iter?" (fun _ -> Bool false);
reg "host-to-list" (fun args -> match args with [v] -> List (list_elems v) | _ -> List []);
(* Minimal JSON parse/stringify used by hs-coerce (as JSON / as JSONString). *)
let rec json_of_value = function
| Nil -> `Null