Rust runtime parity fixes + make authenticationMode optional#333
Merged
Conversation
…unwrap, events, roles - trace_span_async: use Arc<SpanEmitter>, properly end() spans in both paths - Nonce global state: remove global Mutex, thread nonces through pipeline - Structured unwrap: return processed directly from invoke(), let callers cast() - AgentEvent: add data payloads to MessagesUpdated and Done variants - Parser: remove developer role (spec: system/user/assistant only) - Body trimming: trim only trailing newlines, preserve leading whitespace - Context summary: use [Context summary: ...] format - Redaction: add cookie/authorization to sensitive key regex - Load tracing: add trace spans to load()/load_async() - Render validation: call validate_inputs() before rendering - turn_from_path: convenience function matching TS API - InvokerError::Load variant for load failures 448 tests passing, 0 failures. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Quality fixes: - fix-edition-mismatch: prompty-foundry and prompty-anthropic now edition 2024 - fix-client-reuse: static LazyLock<reqwest::Client> in all 3 executor crates - fix-rwlock-await: Box<dyn Trait> → Arc<dyn Trait> in registry and tool_dispatch, clone Arc before dropping guard to avoid holding lock across .await - fix-file-resolve-async: load_async() uses spawn_blocking for build_agent() Feature gap fixes: - add-tool-bindings: resolve_bindings() injects parent inputs per tool.bindings - add-prompty-tool-dispatch: PromptyToolHandler (recursive .prompty loading with circular reference detection), McpToolHandler, OpenApiToolHandler, CustomToolHandler - add-reference-connection: all 3 executor crates resolve kind=reference connections from the connection registry via Cow<Value> pattern - add-entra-id-auth: optional entra_id feature on prompty-foundry, async get_auth_header with DefaultAzureCredential token acquisition - add-anthropic-structured-wire: outputSchema → output_config with json_schema format - fix-usage-hoisting: hoist __usage from result.usage, array results, and child frames in PromptyTracer 462 tests pass, 0 failures, 15 ignored. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
PromptyToolHandler (4 tests): - Missing __source_path metadata → clear error - Missing path field in tool def → clear error - Circular reference detection → error not hang - Nonexistent child .prompty → load failure Reference connection resolution (14 tests across 3 executors): - Passthrough for kind=key connections (no-op path) - Missing name field on reference connection → error - Successful reference lookup via connection registry - End-to-end flow: reference → build_url / get_api_key / get_auth_header Kind handler dispatch via dispatch_tool (2 tests): - Layer 3 kind-based dispatch routes to MCP handler - Wildcard (*) handler catches unknown kinds Entra ID auth (1 test): - Foundry connection without API key or entra_id feature → error 483 tests pass, 0 failures, 15 ignored. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
authenticationMode is defined on the base Connection type but no runtime ever reads or branches on it. It is purely metadata for tooling and orchestrators. Making it optional (rather than required-with-default) avoids forcing every .prompty file to carry a field nobody consumes. - Changed authenticationMode from required (default 'system') to optional in schema/model/connection.tsp - Regenerated all 6 emitter targets: TypeScript, Python, C#, Go, Rust, VS Code JSON Schema, and markdown reference docs - All runtimes updated: String -> Option<String> (Rust), str -> Optional (Python), string -> string? (C#/TS), etc. - All existing tests pass (483 Rust tests, model tests across runtimes) Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
sethjuarez
marked this pull request as ready for review
April 10, 2026 21:59
sethjuarez
added a commit
that referenced
this pull request
Apr 10, 2026
Bump Python (2.0.0a8), TypeScript (2.0.0-alpha.8), C# (2.0.0-alpha.8), and VS Code extension packages for release including: - fix: recursive array/object JSON Schema in tool params (#332) - feat: Rust runtime parity + optional authenticationMode (#333) Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
sethjuarez
added a commit
that referenced
this pull request
Apr 11, 2026
* chore: bump all runtimes to alpha.8 Bump Python (2.0.0a8), TypeScript (2.0.0-alpha.8), C# (2.0.0-alpha.8), and VS Code extension packages for release including: - fix: recursive array/object JSON Schema in tool params (#332) - feat: Rust runtime parity + optional authenticationMode (#333) Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * fix: nonce type coercion bug in parser strict mode across all runtimes When randomBytes/token_hex generates an all-digit hex nonce (e.g. '1234567890123456'), parseAttrs type coercion converts it to a number. The subsequent strict comparison (number !== string) always fails, causing a spurious 'Nonce mismatch' error. Fix: compare nonces as strings in buildMessage/build_message across Python, TypeScript, and Rust parsers. Probability of all-digit 16-char hex: (10/16)^16 ≈ 0.01% — matches the observed flaky CI failure rate. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * docs: add conceptual documentation for thread inputs (conversation history) Adds a new core-concepts page explaining how thread inputs work in Prompty: - What threads are and why they use nonce-based expansion - How to declare kind: thread inputs and place them in templates - Data format with multi-language examples (Python, TypeScript, C#, Rust) - Internal pipeline mechanics (render → parse → expand) - Best practices: token budgets, sliding windows, stateless design - Integration with agent mode Also adds cross-references from the file-format doc, core-concepts index, and the chat-assistant tutorial. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --------- Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
This PR brings the Rust Prompty runtime to full parity with TypeScript/Python/C# and fixes 23 audit gaps, plus a schema-level change making
Connection.authenticationModeoptional.Rust Runtime Parity Fixes (commits 1-3)
🔴 Critical fixes (5)
trace_span_async()now properly ends spans viaArc<SpanEmitter>invoke()/turn()no longer unwrapStructuredResultearly — callers usecast()Mutexto thread-through-pipeline patterndeveloper:role (spec: system/user/assistant only)AgentEventpayloads now carry data (messages, results) for event consumers❌ Feature gaps closed (6)
tool.bindingsspec fieldentra_idfeature flagoutput_config)turn_from_path()convenience function🟡 Spec correctness (7)
validate_inputs()called before renderingload()/load_async()traced.trim())[Context summary: ...]🔧 Rust quality (4)
LazyLock<reqwest::Client>— no new client per requestBox<dyn Trait>→Arc<dyn Trait>— no RwLock held across.awaitspawn_blockingfor sync file I/O in async pathsSchema Change (commit 4)
Connection.authenticationMode→ optionalauthenticationModeis defined on the baseConnectiontype but no runtime reads or branches on it. It is purely metadata for orchestrators. Making it optional avoids forcing every.promptyfile to carry a field nobody consumes.Test Results
Commits (unsigned — will be signed before merge)
de1afe0— Critical fixes + spec correctness279f3d1— Quality fixes + feature gaps9e4e697— Targeted confidence tests189e800— Schema: authenticationMode optional