Skip to content

land kanban 575 - #394

Merged
StevenTCramer merged 8 commits into
feature/overnight-2026-11-14from
task/530-json-member-binding-a-jsonexception-is-a-bind
Nov 13, 2026
Merged

StevenTCramer merged 8 commits into
feature/overnight-2026-11-14from
task/530-json-member-binding-a-jsonexception-is-a-bind

Conversation

@StevenTCramer

Copy link
Copy Markdown
Contributor

Summary

What changed

  • source/timewarp-nuru-analyzers/generators/emitters/json-args-emitter.assign.cs: the ValueShape.Json
    assign wraps JsonSerializer.Deserialize in try/catch (Exception) when (NuruBindError.IsJsonMemberFailure(...)), sets __ok = false and records
    NuruBindError.ForJsonMember(key, pattern, exception). The route pattern is threaded in from EmitFill
    (json-args-emitter.validation.cs). The bind method then returns the failure like any scalar bind error,
    so --json-args, TryBind, the daemon and McpHost all report it as a bind error.
  • source/timewarp-nuru/invocation/nuru-bind-error.cs: two public static helpers called by generated code.
    IsJsonMemberFailure is true for JsonException, NotSupportedException, InvalidOperationException
    and FormatException (a typed-ID converter that parses text). ForJsonMember builds an InvalidValue
    error: Error: Invalid value for '<key>' on '<pattern>'. <key>: <json path>: <serializer message without the " Path: … | LineNumber …" suffix>. No stack trace.
  • documentation/user/features/agent-invocation.md: one bullet on JSON-member failures being
    InvalidValue.
  • Tests: tests/timewarp-nuru-mcphost-tests/mcphost-06-json-member-bind-errors.cs (also in the CI
    multi-mode assembly). An [Operation] with IReadOnlyList<JbStep> Steps and JbOptions? Options covers
    an unknown enum name in an array item (Steps: $[0].Tool), a nested-object type mismatch
    (Options: $.Limits.Max) and an unparsable nested Guid (Steps: $[0].Target). It checks TryBind
    (kind InvalidValue, key, message, no stack trace), in-process --json-args with plain errors (exit 1),
    with UseProblemRendererForErrors() and with --no-daemon (exit 1, error=Invalid), McpHost in process
    (isError, error=Invalid), and forwarded through a real NuruDaemonServer for McpHost and for the CLI
    via AddServeRoute() (same text as in process). A handler exception stays error=Faulted over McpHost
    (local and forwarded) and still escapes the in-process CLI as itself.

Gates

Gate Command Result
Build ./bin/dev build Pass, 0 warnings, 0 errors
Test ./bin/dev test Pass: CI multi-mode 2190 total, 2184 passed, 6 skipped, 0 failed; standalone phase 0 failed
Audit ganda repo audit Pass: 44 passed, 0 failed, 1 skipped (after --fix for the advisory vscode-window-icon; see ## Session)

Test plan

Smoke:

ganda runfile cache --clear
dotnet run tests/timewarp-nuru-mcphost-tests/mcphost-06-json-member-bind-errors.cs

Expect: 5 tests pass. Before this change the in-process --json-args cases crash with an unhandled
System.Text.Json.JsonException, and McpHost reports error=Faulted instead of error=Invalid.

Kanban task 530
Session: Roslynk

StevenTCramer and others added 8 commits November 14, 2026 02:59
Land-Holder: cramer
Land-Holder: cramer
…(InvalidValue)

A JsonException (or NotSupported/InvalidOperation/Format exception) thrown while
deserializing an object or array member now becomes a NuruBindError for that
member, naming the member and JSON path, instead of crashing the process or
surfacing as Faulted through the daemon and McpHost.

Task 530.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Task 530.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@StevenTCramer
StevenTCramer merged commit acd838c into feature/overnight-2026-11-14 Nov 13, 2026
7 checks passed
@StevenTCramer
StevenTCramer deleted the task/530-json-member-binding-a-jsonexception-is-a-bind branch November 13, 2026 20:36
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant