Skip to content

Releases: chrisp28103/sn-toolkit

v1.35.1 -- fix overstated Prerequisites claim in both READMEs

18 Jun 05:23

Choose a tag to compare

Corrects an inaccurate Prerequisites claim in both READMEs. The "without sn-scriptsync + SN Utils, every slash command times out" line overstated the dependency.

Fixed

  • README.md (repo-root marketplace front page) and sn-toolkit/README.md (plugin "Prerequisites") -- the "times out without the stack" warning is now scoped to commands that touch a live ServiceNow instance (start / pull / create / update / widget / diagnose / ...), and the instance-free commands that work without the bridge (worddoc, spec, workshop, workbook, refine-prompt, docs) are named explicitly. The stack stays not optional for the core SN dev loop.

Docs-only, zero token cost.

v1.35.0 -- rebalance edit-path guidance (update_record/_batch the default editor, file-sync opt-in)

18 Jun 05:17

Choose a tag to compare

Rebalances the artifact-editing guidance so the direct Agent API (update_record / update_record_batch) is the first-class default for editing existing artifacts -- including script fields (Script Include / Business Rule / Client Script bodies, widget code) -- and the sn-scriptsync local file-sync workflow is consistently framed as an opt-in path for those who specifically want a version-controlled local copy, not the canonical edit path.

The premise behind the old bias -- that update_record is unreliable for large script payloads -- was tested live on dev221527 and refuted: update_record persists script fields cleanly from 5 KB to 8 MB with zero truncation. The only real caveat is bumping the wrapper's default 15s timeout (-TimeoutSeconds) on multi-MB payloads.

The audit was an adversarial fan-out (one opus reader + one sonnet verifier per file) across all 33 docs / rules / hooks / agents / READMEs / tooltips; 28 came back clean, including the create scope flow, the anti-background-script tool-guard, and sync-push.md.

Changed

  • commands/update.md -- script fields removed from "Do NOT use for" and added to "DO use it for"; synced-file path named as opt-in version control; accurate timeout caveat added (no truncation limit).
  • commands/widget.md -- "Edit Existing Widget" split into Path A (direct update_record_batch, default) and Path B (file/preview loop, opt-in); drops the "for fields without local files" no-file-fallback framing.
  • skills/learn/SKILL.md -- golden path no longer treats sync-push as the universal landing step (update verifies itself); worked-example pairing leads with pull -> update.
  • CLAUDE.md.template -- update_record/update_record_batch rows and edit guidance reframed as the default for editing existing artifacts incl. script fields.

Docs-only, no behavior or code changes, no new commands, zero always-on token cost. The anti-background-script clause and create-scope guidance are untouched.

v1.34.0 -- create_artifact scoped-create fix (ensure_scope)

18 Jun 04:16

Choose a tag to compare

Fixes the real cause of create_artifact landing scoped records in global, and retires the switch_context-based scope model that v1.33.0/v1.33.1 shipped on a misdiagnosis.

Reading the sn-scriptsync source (4.5.0 -- the version on both the dev PDI and the affected engagement) settled it: a new record's sys_scope is set by the ?sysparm_transaction_scope=<sys_id> URL parameter, which the extension resolves from the scope parameter's name to a sys_id only via the instance's scopes.json (the file create_application writes). For an OOB/store scope like sn_customerservice -- or any scope not created locally via create_application -- there is no mapping, so the raw name is sent, ServiceNow can't resolve a name as a sys_id, and the record falls back to global. Reproduced on a clean single-tab dev PDI against the identical sn_customerservice sys_id, disproving both the multi-tab/tab-targeting theory and the v1.33.x "switch_context moves the scope" model.

Added

  • bin/sn-agent-api.ps1 -- new ensure_scope synthetic command. Resolves a scope's sys_id and merges { name: sys_id } into the extension's scopes.json (UTF-8, no BOM, at the real resolveInstanceFolder <workspace root>/<instance>/, not -InstanceDir) so a subsequent create_artifact with scope=<name> lands correctly and keeps the local _map.json folder named by scope. Returns {scope, sys_id, mapped, alreadyPresent}; global is a no-op.

Fixed

  • create_artifact landed scoped records in global for any scope absent from scopes.json (every OOB/store scope; cause of three failed scoped-create sessions). commands/create.md Step 5 now runs ensure_scope first; Step 7's sys_scope.scope read-back stays the authoritative gate.

Changed

  • Retired the superseded switch_context-moves-the-create-scope model across create.md, switch.md, rules/conventions.md, CLAUDE.md.template Rule 8, commands/claude-md-audit.md, and the wrapper .NOTES. The v1.33.0 anti-improvise guardrails are unchanged.

v1.33.1 -- scoped-create docs corrected after live re-verification

18 Jun 02:49

Choose a tag to compare

Corrects the scoped-create supporting docs after a live re-verification on dev221527, and keeps the v1.33.0 mechanism intact.

Bottom line: the v1.33.0 picker mechanism is CORRECT (re-confirmed by 9 controlled create_artifact runs, including the exact sn_customerservice/CSM scope). A record's sys_scope follows the helper-tab session's current application, set ONLY by the switch_context Agent API command. The scope param, a sys_scope field in the payload, and the bare apps.current_app preference are all ignored. The earlier "refutation" was a flawed test: a manually-set picker writes the preference but does NOT move the helper-tab session create_artifact runs in (replicated exactly).

Fixed

  • rules/conventions.md -- "the create_artifact command sets sys_scope ... from that parameter" was FALSE and contradicted create.md. Rewritten to the verified picker-session model (scope param / sys_scope payload field / apps.current_app pref all named as non-drivers).
  • commands/switch.md -- "get_instance_info shows the active picker state" was FALSE; it returns only {instanceName, hasSettings, connected}. Replaced with the read-back sys_scope.scope verification.

Changed

  • commands/create.md -- added the manual-picker-vs-switch_context nuance, the sys_scope-field-ignored fact, and the result.scope cheap-check; dropped the over-strong "reload required" claim.
  • commands/switch.md + bin/sn-agent-api.ps1 -- softened the reload-required framing (app scope applies without a reload; reload still needed for domain + the visible tab).

Docs-only plus two .NOTES comment lines. The v1.33.0 safety hardening is unchanged. Findings adversarially reviewed (root-cause skeptic + doc-claim auditor + diff reviewer).

v1.33.0 -- guard against improvise-instead-of-fail-loud SN mutations

18 Jun 00:21

Choose a tag to compare

Hardens the toolkit against a "session improvises a dangerous mutation instead of failing loud" failure family, surfaced by two real incidents and resolved through a two-iteration PFSAI loop plus a dedicated five-lens code review. In one engagement a session created a Business Rule by raw new GlideRecord('sys_script').insert() inside run_background_script after concluding "create_artifact can't target sn_customerservice" -- a partial hallucination (it can; the record's scope follows the helper-tab live Concourse-Picker, not the scope param). In another, a session improvised raw sys_dictionary record inserts to fake a column add after add_column came back Unknown command on a stripped extension build, then retried into a half-applied schema. The fix is defense-in-depth, validated with a 39-payload empirical battery against the live hook and independently reviewed across correctness, false-positive, false-negative, regression, and consistency lenses before shipping.

Added

  • hooks/tool-guard.ps1 PreToolUse Guard 3 (Bash + PowerShell, fail-open). 3a hard-blocks a run_background_script that opens new GlideRecord('<artifact/metadata table>') AND calls a write method, across 21 code/definition tables; 3b hard-blocks create_artifact on sys_dictionary (columns go through add_column). Data/config tables and reads are not tripped; update_record on metadata stays permitted (sanctioned edit path). hooks/hooks.json adds PowerShell to the PreToolUse matcher -- the invocation path the incident actually used.
  • CLAUDE.md.template Rules 7 + 8 -- artifacts via /sn-toolkit:create + /sn-toolkit:update; on a failed/unavailable command, STOP rather than improvise, don't blind-retry a half-applied write, verify sent != committed.
  • rules/sn-error-codes.md "Judgment guardrails" -- the STOP / no-retry / verify-commit discipline, with E_DISABLED and E_TIMEOUT carve-outs intact.
  • commands/claude-md-audit.md capability-assertion + false-capability lenses; commands/start.md Step 4b capability spot-check (catches a stripped build at session start).

Changed

  • commands/create.md -- scope preflight (switch_context before create_artifact) + unconditional scope-verify (sys_scope.scope, STOP on a global landing) + the misleading "always include scope" guidance rewritten; trigger now fires on agent-initiated build steps.
  • commands/update.md trigger broadened; CLAUDE.md.template Essential Commands table reframed so the slash commands are the first-glance path.

Fixed

  • bin/bootstrap-project.ps1 -- sn-platform-first.md added to the rule copy-list (shipped v1.32.0, never wired into bootstrap).

v1.32.0 -- concept-audit ranks 1/2/4: platform-first rule + update.md blast-radius line + Mermaid-in-PDF for /spec

15 Jun 20:17

Choose a tag to compare

Builds the three items picked from the 2026-06-15 concept-audit backlog (a PFSAI loop over four external concepts: Mermaid diagramming, Scribe auto-docs, Karpathy coding guidelines, Ponytail minimalism). The Mermaid render path was spike-validated, then re-rendered end-to-end on a real machine and screenshot-verified.

Added

  • rules/sn-platform-first.md -- a path-scoped rule (**/*.js, **/*.html, **/*.scss only) encoding the OOTB-before-custom decision hierarchy: does it need to exist -> does ServiceNow do it natively -> does an existing artifact cover it -> can it be config/one line -> only then custom script. Establishes a greppable // PLATFORM-FIRST: <reason> justification convention. Narrower than conventions.md; no agentrules/ mirror; zero always-on token cost.
  • Native Mermaid diagrams in /sn-toolkit:spec PDFs -- mermaid.min.js (v11 UMD, 3.16MB) is vendored into templates/spec/ and the template <head> loads it with theme:'neutral' (prints cleanly in grayscale). Drop a <pre class="mermaid"> block in a .figure div and it rasterizes to SVG in the existing headless-Chrome pass -- self-contained PDF, no CDN. flowchart, erDiagram, and sequenceDiagram all verified. spec.md Phase 0 now copies the JS (mandatory), and a .mermaid svg rule keeps wide erDiagrams within US Letter.

Changed

  • commands/update.md -- one imperative blast-radius line in the boundary block: touch only the field(s) the user named; surface and ask before silently widening a live-record write (Business Rules and Workflows fire, and run_background_script is globally enabled).

Fixed

  • templates/spec/render.ps1 -- renders now run in an isolated, unique --user-data-dir per invocation (cleaned up after). Without it, Chrome hands the render off to the user's already-running instance and returns in ~20ms with NO PDF -- a singleton collision that bit /spec because it renders Part A then Part B back-to-back. Also switched to Start-Process -Wait. --virtual-time-budget stays at 10000.

Run /plugin update sn-toolkit@infocenter to pick up the new version.

v1.31.0 -- wrapper down-bridge fast-fail + offline whats-new

10 Jun 15:11

Choose a tag to compare

Ships the two tail items agreed at the close of v1.30.0: the wrapper-level down-bridge fast-fail deferred as decision 2 of the lazy-bridge design (docs/design-lazy-bridge-probe.md), and an offline path for /sn-toolkit:learn whats-new on installer machines. The wrapper change passes an 18-check smoke suite (no-port-file, stale-pid, forced-file bypass, legacy layout, no-InstanceDir, plus a simulated live server on both a supported and an unsupported protocol); the offline whats-new path was proven both ways against a simulated installed layout. Zero per-prompt token cost.

Changed

  • bin/sn-agent-api.ps1 -- wrapper-level fast-fail on a down bridge: check_connection on auto transport with no live HTTP server AND no pre-existing legacy agent/requests dir returns a structured E_SERVER_NOT_RUNNING immediately (the capabilities shape, already mapped in rules/sn-error-codes.md) instead of creating agent/ scratch dirs and polling out the full -TimeoutSeconds. check_session on a down apiVersion-7 bridge now verdicts BRIDGE_DOWN in ~0.2s with zero cruft (was ~5s + orphaned dirs). Guard rails: explicit -Transport file bypasses the gate, an already-existing agent/requests dir keeps the pre-4.3 file-only contract intact, and a live server on an unsupported protocol still fails closed to the file transport.
  • Get-SnServerHealth gains a pid-liveness pre-check before any network I/O -- a stale port file left by a crashed server rejects in ~0.07s instead of burning ~2s on the dead port's connect attempt. Benefits every HTTP-path caller and mirrors the hooks' proven Test-SnServerLive semantics.
  • docs/design-lazy-bridge-probe.md -- decision 2 updated from DEFERRED to follow-on shipped, with the validation record inline.

Added

  • sn-toolkit/CHANGELOG.md -- the changelog now SHIPS inside the plugin dir, so /sn-toolkit:learn whats-new works offline on installer machines for the first time. bin/sn-learn.ps1's Resolve-Changelog already probed <pluginRoot>/CHANGELOG.md as its second path, so this needed zero code change -- the release flow now syncs the shipped copy from the canonical root file on every release.

v1.30.0 -- sn-scriptsync 4.5.0 P2 backlog closed: code_search wiring, capabilities synthetic, /sn-toolkit:catalog-test

10 Jun 13:53

Choose a tag to compare

Closes the sn-scriptsync 4.5.0 carry-over backlog (docs/backlog-snscriptsync-450.md) -- the three P2 items deferred from the v1.26.0 audit batch, plus the flagged stale-comment hazard. Every behavioral claim was live-validated against dev221527 (sn-scriptsync 4.5.0, HTTP protocol apiVersion 5, 40 verbs advertised), and the wrapper transport changes additionally pass a 13-check mock-server suite. Token posture: every edit lives in lazily-loaded command/rule/agent bodies or the wrapper's .NOTES -- zero per-prompt cost.

Added

  • capabilities synthetic command in bin/sn-agent-api.ps1 (NOT relayed; HTTP-only; one /api/health GET, nothing POSTed): returns result.commands[] -- the verbs the live server actually supports -- plus .apiVersion, .protocolSupported, and .commandCount, so callers gate features on real capability instead of version integers. A down/absent server returns a structured E_SERVER_NOT_RUNNING -- fast, no agent/ dir littering. The port-file + pid-match health gate was factored into a shared Get-SnServerHealth used by both the HTTP transport and the synthetic (semantics unchanged; check_session regression-tested HEALTHY live). An unsupported future protocol is REPORTED (protocolSupported: false) rather than refused -- the diagnostic that names the mismatch while the transport fails closed. Consumers wired: rules/sn-error-codes.md and /sn-toolkit:diagnose pre-flight.
  • /sn-toolkit:catalog-test (commands/catalog-test.md) -- the 34th slash command: end-to-end catalog item / Record Producer SUBMIT testing through the real browser form, the one loop REST cannot exercise (RP scripts, variable-set client scripts, catalog UI policies, onSubmit validation). Composes navigate -> get_form_state -> set_field -> take_screenshot -> run_ui_action submit -> query_records verification -> optional upload_attachment evidence. Load-bearing claims live-verified before authoring: variables enumerate as IO:<item_option_new.sys_id> keys on the platform catalog view, set_field accepts both the variable name and the IO: key, and /sp?id= exposes no g_form (platform view only). Sub-production only; submit creates real records.

Changed

  • code_search wired in as the duplicate-LOGIC discovery pre-pass (the headline 4.5.0 feature, confirmed Pro/Trial/Enterprise-gated -- live call returns E_DISABLED, HTTP 423): wrapper .NOTES catalog entry (v2.1.0), a step-4b pre-pass in /sn-toolkit:create with the silent E_DISABLED -> query_records LIKE fallback inline, and agents/sn-explorer.md's allow-list widened to include it. Every caller treats E_DISABLED as a silent fallback, never a hard failure.
  • P5 write-guard comments refreshed to the post-4.4.1 reality (bin/apply-snscriptsync-patch.ps1, CLAUDE.md.template): the destructive overwrite the guard originally targeted is gone; its surviving jobs (suppressing the ~126KB @agentinstructions.md append, protecting pre-4.4.1 machines) are now stated with an explicit "NOT dead code, do NOT remove".
  • docs/backlog-snscriptsync-450.md marked CLOSED with a shipped-state record per item; command count 33 -> 34 across both READMEs and both manifests; /sn-toolkit:learn Operations group gains catalog-test.

v1.29.0 -- Fable 5 audit rows 4-7: sessionTitle hook, argument-hint rollout, context-budget lens, Haiku compare-team

10 Jun 13:22

Choose a tag to compare

Closes out the Fable 5 / Mythos 5 upgrade-audit backlog (docs/audit-2026-06-09-fable5.md, rows 4-7 -- the four S-effort rows left open after v1.28.0's top-3). All four are token-neutral or token-saving: two are pure UI metadata that never touches session context, one extends a lazily-loaded command body, and one demotes mechanical teammate work to Haiku pricing. The session-start change was smoke-tested live both ways (HEALTHY title against dev221527; title-only payload on a never-connected scratch workspace) and frontmatter structure was validated across all 23 edited commands.

Added

  • hooks/session-start.ps1 -- the SessionStart hook now emits sessionTitle (honored by Claude Code >= 2.1.152; older CLIs ignore the field), titling each session by instance + bridge state: SN: dev221527 -- HEALTHY, -- DEGRADED, -- WRONG INSTANCE, -- UNAUTHENTICATED, -- NO TAB, -- BRIDGE DOWN, -- OFFLINE, plus legacy-transport variants. This makes the Desktop + VS Code multi-session pattern navigable by instance at a glance, at zero context tokens. The never-connected silent path keeps its v1.25.7 "no context" contract but now sends a title-only payload (bare SN: <name>, no additionalContext property), and the error catch path titles too.
  • argument-hint frontmatter on all 23 $ARGUMENTS-taking commands (Claude Code 1.0.54+) -- the / menu now advertises each command's expected argument shape at type-time, e.g. /sn-toolkit:audit "<update-set-name|sys_id>", /sn-toolkit:switch "<updateset|scope|domain> <target>", /sn-toolkit:inspect "<form|widget|workspace|url> <target> [--attach <table>:<sys_id>] [--no-tn]". UI metadata only -- frontmatter is not injected per-prompt, so the rollout costs zero context tokens. Matches the style the docs and learn skills already used, and /sn-toolkit:learn surfaces the new hints automatically (bin/sn-learn.ps1 already reads the key).

Changed

  • commands/claude-md-audit.md -- new context-budget lens (step 4, local-only, zero instance calls) alongside the existing instance-drift audit: per-file line + approximate-token footprint vs the 200-line lean threshold, naming the largest sections of over-budget files as trim targets; load-reality checks on "auto-loads"/"auto-attaches" claims (a project's .claude/rules/ loads, a plugin's rules/ does not -- the exact in-repo drift class the v1.28.0 rules fix corrected, now caught per-project); and dead-weight detection for sections duplicating the harness's always-present catalogs. The drift report gains a "Context budget" section and the totals line counts budget flags.
  • commands/compare-team.md -- per-instance teammates demoted Sonnet -> Haiku ($1/$5 vs $3/$15 per MTok; the audit's one "experiment" verdict). The teammate job is mechanical (REST query -> normalize -> write inventory JSON to file) and the Sonnet lead keeps ALL diff synthesis, so the demotion does not move judgment to a weaker model -- the same reasoning as v1.25.8's reviewer demotion. The cost note documents the ~3x-cheaper teammate share and the escape hatch (rerun with Sonnet teammates if inventories come back malformed); diagnose-team teammates intentionally stay Sonnet, since debate-mode hypothesis work is judgment, not gathering.

v1.28.0 -- Fable 5 audit top-3: rules auto-load fix, agent effort pins, template dedup

10 Jun 04:55

Choose a tag to compare

Top-3 batch from the Claude Fable 5 / Mythos 5 launch-day upgrade audit (docs/audit-2026-06-09-fable5.md: evergreen gather -> 5-surface match -> 24 candidate rows adversarially verified one-by-one, 16 killed). The audit's focused verdict: the plugin's posture against the new $10/$50 Fable tier ABOVE Opus is defensive and already correct -- every command and agent pins model: sonnet, so no plugin surface inherits Fable pricing in a Fable session, and no Fable upgrade was justified anywhere. The headline that DID survive is a correctness bug: the four path-scoped scripting rules never auto-attached in engagement workspaces.

Fixed

  • Rules auto-load: bin/bootstrap-project.ps1 gains a scaffold step copying the four path-scoped rules (conventions.md, sn-scripting.md, sn-testing.md, sn-ui-components.md) into the new project's .claude/rules/, making the designed file-touch-gated attach real for the first time (plugins have no rules component; only a project's own .claude/rules/ is honored). The three Agent-API reference rules stay plugin-side as explicit-Read references. Smoke-tested end-to-end.
  • The three false "auto-loads" claims (CLAUDE.md.template x2, agents/sn-explorer.md) now describe the real path-scoped attach mechanism, and the template's directory-structure block documents .claude/rules/.

Changed

  • effort: medium frontmatter pins on all three agents (sn-reviewer, sn-explorer, sn-platform-admin) -- sonnet subagents otherwise default to effort high; the saving multiplies across /sn-toolkit:review's up-to-10-parallel fan-out at zero main-thread cache cost.
  • CLAUDE.md.template drops the duplicated "Plugin Slash Commands (most used)" block (~90 tokens at every session launch in every scaffolded project, drift-prone; /sn-toolkit:learn is the drift-free catalog).
  • rules/conventions.md paths: globs tightened from **/*.md + **/*.json catch-alls to code files plus **/agent/**/*.json.

Added

  • docs/audit-2026-06-09-fable5.md -- the full audit report (7 surviving recommendations with rows 4-7 still open, 16 kills grouped by reason, Fable/Mythos posture analysis, and the live mid-run cost incident that led to model-pinning the audit engine itself).

Existing workspaces note: the rules copy runs at bootstrap, so projects scaffolded before v1.28.0 won't have .claude/rules/ populated -- copy the four rules from the plugin's rules/ once, or re-run bootstrap into a fresh workspace.