fix(mcp): harden send_feedback against integer-extra drift, error-log echo, and dispatcher shadowing - #4915
Conversation
… echo, and dispatcher shadowing - matchesExtraSchema: a declared "integer" extra accepted any number, fractional ones included (3.5); now requires a whole value per JSON Schema semantics. - handleFeedback: a thrown onFeedback was logged with its full message, which can echo agent-controlled report text (PII, credentials, log-forging newlines) into host logs; now logs only the error name, matching the report log beside it. - prepareToolCall: every call named like the feedback tool was flagged as feedback, so a dispatcher following the documented flow suppressed a real colliding tool; a host-supplied originalTool is stateless proof a real tool owns the name and now wins. Backports the hardening found while porting the feature to posthog-python (PostHog/posthog-python#939). Generated-By: PostHog Desktop Task-Id: 0b5063cb-6fcf-4364-be5e-de945b1448f0
|
|
Note 🤖 Automated comment by QA Swarm — not written by a human Multi-perspective review: router (cheap-first pass) + narrow validation as needed Verdict: ✅ APPROVE (round 4 @ 382e084)The custom-dispatcher examples now pass the original application descriptor, and the regression test uses the same contract. The virtual-descriptor concern does not apply because Key findingsNo open findings. ConvergenceAll inline QA threads are resolved. The focused feedback suite and MCP lint pass. Reviewer summaries
Previous rounds (3)round 3 @ 8fd8198 — REQUEST CHANGES: two dispatcher contract findings remained. Automated by QA Swarm — not a human review |
gesh
left a comment
There was a problem hiding this comment.
Note
🤖 Automated comment by QA Swarm — not written by a human
QA Swarm review complete. See inline comments.
Generated-By: PostHog Desktop Task-Id: 9a0c57df-9c72-446a-acb4-cb319a85d5d7
Generated-By: PostHog Desktop Task-Id: 9a0c57df-9c72-446a-acb4-cb319a85d5d7
Generated-By: PostHog Desktop Task-Id: 9a0c57df-9c72-446a-acb4-cb319a85d5d7
Problem
While porting the
collectFeedbackfeature (#4870) to posthog-python (PostHog/posthog-python#939), review bots on the Python PR surfaced three hardening gaps that apply to this SDK too. The Python port shipped the fixes; this PR backports them so the two SDKs behave the same.Changes
matchesExtraSchema— a declaredintegerextra accepted any number, fractional ones included (3.5), becausetypeofcannot separate int from float. It now requiresNumber.isIntegerper JSON Schema semantics:3and3.0pass,3.5stays out ofextrasand the captured properties (rawkeeps it for the handler).handleFeedback— a thrownonFeedbackhandler was logged with its full message. A handler can echo the unsanitized report (PII, credentials, log-forging newlines) into its error message, so the log now carries only the error name, matching the report log beside it.prepareToolCall— every call named like the feedback tool was flaggedisFeedback, so a dispatcher following the documentedif (prepared.isFeedback) ... returnflow suppressed a real tool that collides with the name. A host-suppliedoptions.originalTool(already flowing in for model ownership) is stateless proof a real application tool owns the name — the virtual tool never exists in the host's own list — so it now wins and the real tool dispatches normally. WithoutoriginalToolthe behavior is unchanged.How did you test this code?
Three new tests in
feedback.test.ts(fractional vs whole integer extras across capture + handler surfaces, thrown-handler log carries no error text,originalToolcollision disambiguation), plus aloggerassertion added to the existing thrown-handler test. Full@posthog/mcpunit suite: 48 files, 876 tests, lint and format clean.Created with PostHog Desktop