Skip to content

Conversation

@betterclever
Copy link
Contributor

@betterclever betterclever commented Jan 4, 2026

Summary

This PR implements full HTTP observability for workflow executions, allowing users to inspect all HTTP requests made by components in a browser DevTools-style Network tab.

What's Included

1. HTTP Instrumentation Layer (@shipsec/component-sdk)

  • HAR Format Support: Full HTTP Archive format for request/response capture
  • Timing Metrics: Detailed timing breakdown (DNS, connect, SSL, send, wait, receive)
  • Instrumented Fetch: Drop-in replacement that captures request/response data
  • Trace Events: New HTTP_REQUEST_SENT, HTTP_RESPONSE_RECEIVED, HTTP_REQUEST_ERROR event types

2. Component SDK Integration

  • New context.http.fetch() method available to all components
  • Automatic header sanitization for sensitive data (Authorization, API keys, etc.)
  • toCurl() helper for debugging

3. Component Migration

Components now using instrumented HTTP:

  • core/http-request - Generic HTTP Request component
  • security/abuseipdb - AbuseIPDB IP reputation checks
  • security/virustotal - VirusTotal malware scanning
  • security/atlassian-offboarding - Atlassian user offboarding
  • notification/slack - Slack webhook/API notifications
  • github/remove-org-membership - GitHub org membership management
  • ai/ai-agent - MCP tool invocations

4. Frontend Network Tab

  • DevTools-style UI: Familiar browser Network tab experience
  • Request List: Grouped by host with expandable sections
  • Detail Panel: Headers, Payload, Response, and Timing tabs
  • Timing Visualization: Visual waterfall chart for request phases
  • Resizable Panes: Drag to resize list/detail split

Testing

  • ✅ Unit tests for HAR builder, timing adapters, instrumented fetch
  • ✅ E2E tests for HTTP observability flow
  • ✅ All 454 unit tests passing

Breaking Changes

None. The context.http.fetch() method is additive and existing components continue to work.

@betterclever betterclever self-assigned this Jan 4, 2026
@betterclever betterclever force-pushed the betterclever/http-observability branch 2 times, most recently from 9874736 to 34813e3 Compare January 8, 2026 18:56
@betterclever betterclever changed the title [WIP] feat: HTTP observability with HAR-format tracing feat: HTTP Observability with Network Tab DevTools-style Inspector Jan 8, 2026
@betterclever betterclever marked this pull request as ready for review January 8, 2026 18:58
@betterclever betterclever force-pushed the betterclever/http-observability branch from 34813e3 to 9dea811 Compare January 8, 2026 19:02
Copy link

@chatgpt-codex-connector chatgpt-codex-connector bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 9dea811d36

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines 111 to 149
const headers = maskHeaders(headersToHar(request.headers), sensitiveHeaders);
const queryString = parseQueryString(request.url);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Redact sensitive query params before storing HAR

buildHarRequest only masks headers but captures request.url and queryString verbatim, so any API key or token placed in query parameters (e.g., ?token=..., presigned URLs) will be persisted in trace data and surfaced in the Network panel without redaction. This leaks secrets in environments where query-string auth is used; consider masking query values using the same sensitive list (or a dedicated allowlist) before recording.

Useful? React with 👍 / 👎.

Comment on lines 138 to 141
const sensitiveHeaders = options.sensitiveHeaders ?? DEFAULT_SENSITIVE_HEADERS;
const maxBodySize = options.maxResponseBodySize ?? DEFAULT_MAX_RESPONSE_BODY_SIZE;
const rawBody = await response.text();
const { text } = truncateBody(rawBody, maxBodySize);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Avoid buffering full response body for HAR capture

buildHarResponse calls response.text() and only then truncates to maxResponseBodySize, which still reads the entire response into memory. For large downloads or streaming responses, this defeats the size limit and can cause significant memory/latency overhead; consider streaming and stopping once the max size is reached.

Useful? React with 👍 / 👎.

- Add comprehensive spec for HTTP request/response tracing
- Defines phased implementation plan (9 phases)
- Uses standard HAR 1.2 format for DevTools compatibility
- Adds @types/har-format dependency to component-sdk

Signed-off-by: betterclever <[email protected]>
Signed-off-by: betterclever <[email protected]>
Signed-off-by: betterclever <[email protected]>
Signed-off-by: betterclever <[email protected]>
…ling

- Add http-observability.test.ts with 3 E2E tests validating HAR capture
- Test HTTP request/response tracing with full HAR data
- Test HTTP error (404) capture in HAR
- Test multiple sequential HTTP requests with unique correlation IDs
- Fix node: prefixed imports for Webpack compatibility in Temporal bundles
- Change diagnostics_channel, crypto, perf_hooks imports to non-prefixed

Signed-off-by: betterclever <[email protected]>
…ection

- Add NetworkPanel component displaying all HTTP requests made by components
- Show request list grouped by host with method, status, path, and duration
- Request detail view with tabs: Headers, Payload, Response, Timing
- Timing waterfall visualization matching HAR format (blocked, DNS, connect, SSL, send, wait, receive)
- Color-coded HTTP methods (GET=green, POST=blue, PUT=amber, DELETE=red, PATCH=purple)
- Color-coded status codes (2xx=green, 3xx=blue, 4xx=amber, 5xx=red)
- Copy-to-clipboard for header values
- JSON response body formatting
- Filter by selected node from timeline
- Add 'network' to inspector tab options in workflowUiStore

Signed-off-by: betterclever <[email protected]>
Signed-off-by: betterclever <[email protected]>
- Mask sensitive query parameters in HAR requests (P1)
  - Added DEFAULT_SENSITIVE_QUERY_PARAMS list with common secret param names
  - Added maskQueryParams and maskUrlQueryParams functions
  - Both queryString and URL are now masked before storing

- Use streaming for response body capture (P2)
  - Updated buildHarResponse to use ReadableStream when available
  - Stops reading once maxResponseBodySize is reached
  - Falls back to response.text() for responses without body stream
  - Added 'body' property to HttpResponseLike interface

Signed-off-by: betterclever <[email protected]>
@betterclever betterclever force-pushed the betterclever/http-observability branch from b0b6097 to 4c71b03 Compare January 9, 2026 18:32
@betterclever betterclever merged commit 0c4bdfb into main Jan 9, 2026
3 checks passed
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.

2 participants