Skip to content

Surface MCP HTTP requests in Site Map and normalize Repeater newlines#90

Open
humurabbi wants to merge 1 commit into
PortSwigger:mainfrom
humurabbi:fix/sitemap-visibility-and-newline-fix
Open

Surface MCP HTTP requests in Site Map and normalize Repeater newlines#90
humurabbi wants to merge 1 commit into
PortSwigger:mainfrom
humurabbi:fix/sitemap-visibility-and-newline-fix

Conversation

@humurabbi
Copy link
Copy Markdown

Summary

  • Site Map visibility for sent requests: send_http1_request and send_http2_request route through api.http().sendRequest(), which bypasses Burp's proxy. Without intervention, MCP-issued requests are invisible to the user — Proxy History is read-only to extensions, and the existing logToOutput line only records host:port. Each tool now calls api.siteMap().add(response) after a successful send so the request/response pair shows up under Target > Site map.
  • Newline normalization in create_repeater_tab: callers (LLMs in particular) often pass content with bare LF line terminators. The existing code forwarded that straight to HttpRequest.httpRequest, producing a garbled request in the Repeater tab that had to be hand-corrected. create_repeater_tab now applies the same \n\r\n normalization that send_http1_request already uses (Tools.kt:58).
  • No new tools, no API surface changes, no removed parameters.

Test plan

  • ./gradlew test passes (16 tests in ToolsKtTest)
  • verify { api.siteMap().add(httpResponse) } on the success path of both send_http1_request and send_http2_request
  • verify(exactly = 0) { api.siteMap().add(any()) } when sendRequest returns null (no spurious site-map entries on connection failure)
  • New create repeater tab should normalize line endings test asserts LF-only input is rewritten to CRLF before reaching Repeater

Manual verification

  • Issued an HTTP/1.1 and HTTP/2 request via the MCP against an in-scope host; both appeared under Target > Site map with full request/response, where previously nothing was visible.
  • Created a Repeater tab with content containing only \n line breaks; the resulting tab renders cleanly without manually re-entering carriage returns.

send_http1_request and send_http2_request now register the response
via api.siteMap().add() after sending. Previously these calls bypassed
every visible Burp surface (Proxy History is read-only to extensions,
and the existing logToOutput line only recorded host:port). Site Map
is the closest writable surface for extension-issued traffic, so users
can review requests issued by the MCP under Target > Site map.

The add is gated on HttpRequestResponse.hasResponse() so failed
attempts (e.g. HTTP/2 against an HTTP/1.1-only origin, which returns
a non-null wrapper with response() == null) do not pollute Site Map
with request-only entries. Burp's Logger continues to record those
attempts as "communication error", which is the right place for them.

create_repeater_tab now normalizes \n to \r\n before constructing the
request, matching send_http1_request. Without this, callers that pass
LF-only content (common when an LLM emits a multi-line string) produce
garbled requests in the Repeater tab.

Adds tests covering siteMap.add on the success path, the no-add case
when sendRequest returns null, the no-add case when the wrapper has
no response, and the CRLF normalization in create_repeater_tab.
@humurabbi humurabbi force-pushed the fix/sitemap-visibility-and-newline-fix branch from 9be0ae0 to f1079ab Compare May 21, 2026 07:24
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