Repository navigation
Conversation
…e by default PostMessageTransport logged every message it sent, received, or ignored with console.debug, and hosts had no way to turn it off. With several Apps on a page, each View message produced one line per card, and full payloads reached anything that records the console. Add a logLevel option using MCP's LoggingLevel names. Message traffic is logged at "debug" and the default is "warning", so it stays off unless asked for. A malformed JSON-RPC message is logged at "error" and onerror fires regardless of level. An unrecognized level falls back to the default. App and useApp pass the level to the transport they create. The integration example opts in to "debug": the cross-App injection e2e test proves the source check by reading the transport's debug line. Fixes modelcontextprotocol#786 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Contributor
There was a problem hiding this comment.
🟢 Approval recommended
The focused changes preserve transport behavior and compatibility, with regression coverage and no unresolved findings.
0 open findings
What changed in this PR
Makes transport message logging opt-in, reducing console noise and default exposure of message payloads.
Changes:
- Adds configurable logging levels, defaulting to
"warning". - Exposes logging options through
App,useApp, and package exports. - Adds regression tests, documentation, and explicit debug logging for security tests.
| File | Description |
|---|---|
| src/react/useApp.tsx | Forwards the logging level to the transport. |
| src/message-transport.ts | Adds logging options and severity filtering. |
| src/message-transport.test.ts | Tests logging controls and App option forwarding. |
| src/message-transport.examples.ts | Adds a debug logging example. |
| src/app.ts | Exposes logging options and configures default transports. |
| src/app-bridge.ts | Exports the transport options type. |
| examples/integration-server/src/mcp-app.tsx | Enables debug output required by security tests. |
🧠 Review effort: Balanced
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
This branch has not been deployed
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.
Fixes #786.
Problem
PostMessageTransportlogs every message it sends, receives, or ignores withconsole.debug, and a host can't turn that off. Each card's transport listens on the samewindow, so with N Apps on a page every View message produces N host lines. The full payloads, including tool-result_meta, also reach anything that records the console: test runners, Playwright, and error-reporting breadcrumbs (#741).Change
A
logLeveloption, using MCP's ownLoggingLevelnames:"debug". The default level is"warning", so traffic stays out of the console unless asked for."error"and still prints by default.onerrorfires at every level.console.debug/console.error, so DevTools filtering keeps working once logging is on."warn"from untyped code) falls back to the default instead of logging everything.tool-input-partialskip from fix: skip debug log for high-frequency tool-input-partial notifications #546 stays.PostMessageTransportOptionsis exported from.and./app-bridge, and the class docs gain a Logging section with a type-checked example.The issue first proposed a
loggerobject. A level is a single plain value, so a server can pass its own log setting (an env variable or flag) into the View it serves, and it reuses names MCP already defines.examples/integration-serveropts in to"debug":tests/e2e/security.spec.ts("app rejects messages from sources other than its parent") proves the source check by waiting for the transport's "Ignoring message from unknown source" line.Behavior change
Code that relied on the transport's debug lines no longer sees them unless it sets
logLevel: "debug". No API breaks; existing two-argument constructors still work.Compared with #803
#803 makes the lines opt-in through a
loggerobject. Differences here:PostMessageTransport's API docs stay intact. In fix(transport): make debug logging opt-in for message privacy #803 the new interface sits between the class's JSDoc and the class, so typedoc publishes the class with an empty summary and no Security or Usage sections.AppanduseApptake the level, so Views that don't build their own transport can still turn logging on.Testing
npm test: 446 pass, 2 skip, 0 fail. New cases insrc/message-transport.test.ts: traffic stays silent at the default and at an unrecognized level; all four traffic lines log at"debug";tool-input-partialis still skipped at"debug"; a malformed message prints at the default and at"error", is dropped at"critical", and callsonerroreach time;App.connect()builds its transport at the App's level. Breaking each guarded line makes its test fail.npm run build,tsc --noEmit,npm run prettier,typedoc --treatValidationWarningsAsErrors --emit none, andscripts/check-dependency-isolation.mjspass. The pre-commitbuild:allpasses.EXAMPLE=integration-server npx playwright test tests/e2e/security.spec.ts --project=chromium --workers=2: 14 passed locally. The pinned Chromium download stalled, so this run used the newer cached build 1248.🤖 Generated with Claude Code