You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: DEVELOPER_GUIDE.md
+4-2Lines changed: 4 additions & 2 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -2654,10 +2654,11 @@ Contract guarantees that callers and operators can rely on:
2654
2654
2655
2655
Contract guarantees that downstream consumers can rely on:
2656
2656
2657
-
- **Field stability.** `timestamp`, `tool`, `arg_keys`, `arg_lengths`, `elapsed_ms`, `error_code` are emitted on every record. `caller`, `caller_version`, `request_id`, `request_id_type`, `request_id_length`, `request_id_truncated`, `arg_key_lengths`, `arg_keys_truncated`, `arg_key_truncation_reasons`, `arg_values`, `arg_values_redacted`, `arg_values_truncated`, `arg_values_truncation_reasons`, `arg_values_serialized_bytes`, `arg_values_max_bytes`, `result_count`, `error` are emitted only when non-null or true; renaming or repurposing any published field is a breaking change, the same policy as the CLI `--metrics` schema.
2657
+
- **Field stability.** `timestamp`, `tool`, `arg_keys`, `arg_lengths`, `elapsed_ms`, `error_code` are emitted on every record. `caller`, `caller_version`, `request_id`, `request_id_type`, `request_id_length`, `request_id_truncated`, `arg_key_lengths`, `arg_keys_truncated`, `arg_key_truncation_reasons`, `arg_values`, `arg_values_redacted`, `arg_values_truncated`, `arg_values_truncation_reasons`, `arg_values_serialized_bytes`, `arg_values_max_bytes`, `result_count`, `checked_root_identity`, `error` are emitted only when non-null or true; renaming or repurposing any published field is a breaking change, the same policy as the CLI `--metrics` schema.
2658
2658
- **Request-id privacy.** `request_id` is the process-salted fixed-length token described above, never the JSON-RPC wire value. A present token is accompanied by `request_id_type` and the decoded-value `request_id_length`; the legacy truncation guard is normally absent because the token is already bounded.
2659
2659
- **Error code semantics.** `0` = success, `1` = MCP tool error (`isError: true`), negative = the verbatim JSON-RPC error code (e.g. `-32602` for invalid params, `-32603` for internal error). The companion `error` string is one of `jsonrpc_error`, `tool_error`, `missing_tool_name`, or the sanitized exception type name (`McpServer.BuildSanitizedToolErrorMessage` keeps `ex.Message` out of the wire and out of the audit, #1530).
2660
2660
- **Result count.** `ExtractResultCount` prefers `structuredContent.count` over `structuredContent.results.length`; tool errors and JSON-RPC errors omit the field. Tools that return no count-shaped payload (e.g. `ping`) leave `result_count` absent rather than emitting `0`.
2661
+
- **MCP index root identity.** `index` resolves the requested root canonically, captures its platform filesystem identity, and retains a no-follow directory handle for the run. Directory enumeration is handle-relative on Linux, macOS, and Windows; the authorized filesystem seam compares each directory/file's pre-open identity, opened-handle identity, and post-open canonical containment before consuming content. Language-map and pattern sidecars are confined to the authorized project tree, opened through that seam, and cached in an authorization-scoped snapshot that excludes wider user configuration and executable workspace plugins. A root, ancestor, link, or entry identity change raises a bounded `permission_denied` tool error with `authorization_failure_reason`; successful/dry-run structured output and every post-authorization audit record carry the same fixed-length opaque `checked_root_identity`, even when the response was built by an error path. A containing repository root is used for ignore rules only when it remains authorized; otherwise discovery is confined to the requested project root.
2661
2662
- **Argument privacy.** `arg_keys` and `arg_lengths` are always recorded so query *shape* is recoverable, but argument-key count and displayed key length are capped and marked with `arg_keys_truncated`. `arg_values` is gated behind `--audit-log-include-values` because cdidx queries can carry literal source snippets or secret-shaped strings. The echo is a sanitized, budgeted clone: secret-like keys classified by the shared diagnostic/audit taxonomy and known token patterns are replaced with `[REDACTED]`, and depth, object-property, array-item, total-node, string-length, serialized-byte, and event-byte limits can mark `arg_values_truncated` before values are written.
2662
2663
- **Caller identity.** The published initialize snapshot captures the bounded client name/version from every successful `initialize.clientInfo` and replaces them on successful reconnection within the same session, so a long-running MCP loop with multiple accepted `initialize` handshakes attributes records to the *currently connected* client rather than the first one. Failed protocol negotiation never overwrites audit attribution or other session state (#4540).
2663
2664
- **Rotation.** Writes go through an open-append-close cycle so external `tail -F` consumers follow rotations and so the file is closed during the rename. When `_bytesWritten >= MaxBytes`, `RotateLocked` drops `<path>.(RotationKeep-1)` (currently `<path>.2`), cascades surviving slots up by one, and moves `<path>` to `<path>.1`. `RotationKeep = 3`, so `<path>.3` is never created — exercised by `AuditLogSinkTests.Record_KeepsAtMostThreeFiles_DropsOldestOnRotationOverflow`.
0 commit comments