Skip to content

feat(http-request): gzip/br decompression, basicAuthHeader, pattern-based redaction#196

Merged
John-David Dalton (jdalton) merged 5 commits into
mainfrom
feat/http-headers
May 29, 2026
Merged

feat(http-request): gzip/br decompression, basicAuthHeader, pattern-based redaction#196
John-David Dalton (jdalton) merged 5 commits into
mainfrom
feat/http-headers

Conversation

@jdalton
Copy link
Copy Markdown
Collaborator

What

Centralizes three HTTP-request concerns in the lib so fleet callers stop hand-rolling them.

gzip / br response decompression

httpRequest now advertises Accept-Encoding: gzip, br on buffered requests, and response-reader transparently decompresses the body by Content-Encoding. Node's http client neither negotiates encoding nor decompresses, so a compressed Socket API response previously reached callers as raw deflated bytes and failed JSON parsing.

Streamed requests (stream: true, e.g. httpDownload) omit Accept-Encoding — they pipe the response straight to disk, so a compressed body would land deflated and break checksum verification. Callers can override the header (e.g. identity).

basicAuthHeader(token)

Builds the Socket API Basic-auth value (token as username, empty password). socket-sdk-js hand-rolls Basic ${btoa(token + ':')} today; it can now import this.

Pattern-based header redaction

sanitizeHeaders redacts by header-name shape (isSensitiveHeaderName: /auth|cookie|credential|key|password|secret|token/i) instead of a fixed name list. Custom token headers (x-amz-security-token, api-key, x-functions-key, …) are now covered without enumeration. Same reasoning as the fleet's "a denylist is itself a leak."

Tests

  • headers.test.mts: basicAuthHeader, isSensitiveHeaderName (positive + benign), pattern redaction of unlisted custom headers.
  • response-reader.test.mts: gzip + br decompression, case-insensitive encoding, identity/absent passthrough, empty-body short-circuit.
  • http-request-advanced-1.test.mts (isolated): Accept-Encoding present on buffered requests, absent on streamed, caller override honored.
  • Full http-request suite: 210 passing.

Notes

sanitizeHeaders behavior widened (more names redacted, never fewer) — strictly safer for logs. No wire-level behavior change except the new Accept-Encoding on non-stream requests.

…pattern-based redaction

Three centralizations so fleet callers stop hand-rolling HTTP concerns:

- Accept-Encoding: gzip, br on buffered requests + transparent
  decompression in response-reader by Content-Encoding. Node's http client
  neither negotiates nor decompresses, so a compressed Socket API response
  previously reached callers as raw deflated bytes. Streamed requests
  (stream: true, e.g. httpDownload) deliberately omit Accept-Encoding —
  they pipe raw to disk and would otherwise land compressed and fail
  checksum. Callers can override (e.g. 'identity').
- basicAuthHeader(token) in headers.ts — the Socket API Basic-auth shape
  (token as username, empty password). socket-sdk-js hand-rolls this today.
- sanitizeHeaders now redacts by name SHAPE (isSensitiveHeaderName regex:
  auth|cookie|credential|key|password|secret|token) instead of a fixed
  list, so custom token headers (x-amz-security-token, api-key, …) are
  covered without enumeration. Same reasoning as 'a denylist is itself a
  leak'.
normalizePath('D:\\') collapses the trailing separator to 'D:' — correct
for general paths ('D:' = current dir on D:), wrong for the filesystem root
walkUp must yield. The final ancestor on Windows then differed from
path.parse(dir).root, failing test/unit/paths/walk.test.mts on windows-latest.
Add normalizeWalkDir: keeps the root slash on a bare drive letter, leaves
every other path to normalizePath unchanged.
Fix the bug at its source rather than in walkUp: normalizePath('D:\\')
collapsed the trailing separator to 'D:', but a drive ROOT's slash is
significant — 'D:' alone means 'current directory on D:', a different
location from the root 'D:/'. Now a bare-drive-letter result whose input had
a separator right after the colon keeps its slash; drive-relative 'D:foo' is
unaffected. Reverts the walkUp-side normalizeWalkDir workaround from the
previous commit. Posix paths and every other shape are unchanged (565
paths+fs tests pass).
walkUp('/a', { stopAt: '/a' }) yields the resolved path, which on Windows is
'D:/a' not '/a'. The assertion hardcoded the posix form, so it failed on
windows-latest once the drive-root normalizePath fix let the run get past the
earlier root-emit assertion. Wrap in the file's withDrive() helper like the
sibling cases.
…ndows

resolveBazel()/resolveSbt() do real PATH/binary resolution; Windows CI
agents can take >10s on a cold cache, timing out vitest's 10s default
(bazel flaked on PR #196's windows-latest run). Apply the established
{ timeout: 30_000 } per-test bump already used by jre/resolve + which.
Variant fix across both untimed sibling resolvers.
@jdalton John-David Dalton (jdalton) merged commit 21f0c0a into main May 29, 2026
11 checks passed
@jdalton John-David Dalton (jdalton) deleted the feat/http-headers branch May 29, 2026 06:16
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