From dcf7c4a02ab6ab7c8476fdb0e5897b1cd52eb0c8 Mon Sep 17 00:00:00 2001 From: PJ Date: Mon, 13 Jul 2026 07:05:11 +0530 Subject: [PATCH] feat(verifier): read llm config off globalThis.generator --- internal/runner/llm_source_test.go | 2 +- internal/verifier/llm.go | 16 +++++++++------- internal/verifier/llm_test.go | 6 +++--- 3 files changed, 13 insertions(+), 11 deletions(-) diff --git a/internal/runner/llm_source_test.go b/internal/runner/llm_source_test.go index 5fa32e5..044cc73 100644 --- a/internal/runner/llm_source_test.go +++ b/internal/runner/llm_source_test.go @@ -31,7 +31,7 @@ var llmInputCorpus = []string{ const llmFixtureSpec = ` import { llm, always } from "@sanderling/spec"; globalThis.properties = { ok: always(() => true) }; -globalThis.actions = llm({ model: "test/model" }); +globalThis.generator = llm({ model: "test/model" }); ` const llmTreeJSON = `{ diff --git a/internal/verifier/llm.go b/internal/verifier/llm.go index fe9c1a3..dc78de0 100644 --- a/internal/verifier/llm.go +++ b/internal/verifier/llm.go @@ -8,8 +8,10 @@ import ( "github.com/priyanshujain/sanderling/internal/hierarchy" ) -// LLMConfig is the spec-declared configuration for the LLM action backend, -// read off globalThis.actions when the spec assigned `actions = llm({...})`. +// LLMConfig is the spec-declared configuration for the LLM action generator, +// read off globalThis.generator when the spec assigned `generator = llm({...})`. +// It is orthogonal to globalThis.actions (the weighted tree the LLM picks from); +// only the picker differs. type LLMConfig struct { Model string // Instructions is optional spec-level guidance appended to the prompt to @@ -17,15 +19,15 @@ type LLMConfig struct { Instructions string } -// LLMConfig reports the LLM action backend config when the spec selected it -// (globalThis.actions.kind === "llm"). The second return is false for every +// LLMConfig reports the LLM action-generator config when the spec declared one +// (globalThis.generator.kind === "llm"). The second return is false for every // other spec, so the runner falls back to the seeded picker. func (v *Verifier) LLMConfig() (LLMConfig, bool) { - actions := v.runtime.GlobalObject().Get("actions") - if actions == nil || goja.IsUndefined(actions) || goja.IsNull(actions) { + generator := v.runtime.GlobalObject().Get("generator") + if generator == nil || goja.IsUndefined(generator) || goja.IsNull(generator) { return LLMConfig{}, false } - object := actions.ToObject(v.runtime) + object := generator.ToObject(v.runtime) if object == nil { return LLMConfig{}, false } diff --git a/internal/verifier/llm_test.go b/internal/verifier/llm_test.go index a1a4fb4..ae26430 100644 --- a/internal/verifier/llm_test.go +++ b/internal/verifier/llm_test.go @@ -88,7 +88,7 @@ func TestAllCandidatesNilTree(t *testing.T) { } func TestLLMConfigDetectsMarker(t *testing.T) { - v := newLoadedVerifier(t, `globalThis.actions = { kind: "llm", config: { model: "vendor/model" } };`) + v := newLoadedVerifier(t, `globalThis.generator = { kind: "llm", config: { model: "vendor/model" } };`) config, ok := v.LLMConfig() if !ok { t.Fatal("LLMConfig not detected for llm marker") @@ -102,7 +102,7 @@ func TestLLMConfigDetectsMarker(t *testing.T) { } func TestLLMConfigReadsInstructions(t *testing.T) { - v := newLoadedVerifier(t, `globalThis.actions = { kind: "llm", config: { model: "m", instructions: "find bugs" } };`) + v := newLoadedVerifier(t, `globalThis.generator = { kind: "llm", config: { model: "m", instructions: "find bugs" } };`) config, ok := v.LLMConfig() if !ok { t.Fatal("LLMConfig not detected") @@ -115,7 +115,7 @@ func TestLLMConfigReadsInstructions(t *testing.T) { func TestLLMConfigAbsentForSeededSpec(t *testing.T) { v := newLoadedVerifier(t, `globalThis.actions = { kind: "builtin", verb: "taps" };`) if _, ok := v.LLMConfig(); ok { - t.Error("LLMConfig should be false for a non-llm actions root") + t.Error("LLMConfig should be false when no generator is declared") } }