feat: auto-flush on process exit + PII redaction across all packages - #16
Merged
Conversation
…stom attributes
- installAutterAutoFlush(): force-flushes all exporters on beforeExit/SIGINT/
SIGTERM so a forgotten shutdown() no longer silently drops buffered telemetry.
Installed by default via initAutterServer({ autoFlush }); coexists with the
app's own signal handlers and never changes their exit path. Timeout-bounded,
second signal exits immediately, conventional 130/143 exit codes.
- redactAttributes()/makeSafeCapture(): masks emails, JWTs, sk-/ghp_/AWS/Slack
tokens, bearer headers, scheme://user:pass@ URLs and sensitive-keyed
attributes before they leave the process — closing the server-side gap to
match the browser relay's payload whitelist. On by default
({ redactAttributes: false } opts out); covers captureException,
captureMessage, withProcessSpan and LLM attributes.
- debug mode (debug: true or AUTTER_DEBUG=1): 'exported N span(s)' lines plus a
stderr warning when the process exits with unconfirmed captures.
- node:test suite (17 tests) incl. an e2e asserting redaction on the wire;
wired into CI. Test tokens are fragment-assembled so secret scanners don't
mistake fixtures for real credentials.
…orage, Next.js re-exports - runtime-browser: new redactContext() masks sensitive-keyed values and email-shaped strings in custom context before anything leaves the page, applied at the enqueue choke point (beforeSend sees the final form). Bundle stays at ~1.3 kB under the 5 kB size-limit. The 'never sent: emails' claim is now actually true for custom context. - otlp-ingester: scrub event.context at normalize time before it reaches ClickHouse — defense-in-depth that also protects payloads from outdated SDK versions. - runtime-next: re-export makeSafeCapture / installAutterAutoFlush / redactAttributes (+ types); registerAutter already passes the new initAutterServer options through. README documents the defaults. - fix(runtime-browser): build script now emits dist/index.d.ts (--dts) to match its declared types entry — @autter/runtime-next's DTS build depended on it and broke on a clean checkout once --clean wiped the stale artifact. - tests: browser redaction suite (5) + ingester normalize-browser suite (4); CI runs both alongside the node suite.
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.
Problem
Two real-world DX failures found while testing the SDK end-to-end:
shutdown()is forgotten. With default batching (~2 s errors, ~5 s traces, 60 s metrics), exiting without awaitingautter.shutdown()dropped everything still buffered — no warning, nothing.captureException(err, { "user.email": … })was forwarded verbatim on the server side, and browsercontextbags were stored verbatim ingest-side — while the browser relay whitelist-sanitises its whole payload.Changes
@autter/runtime-nodeinstallAutterAutoFlush()(installed by default viainitAutterServer({ autoFlush })) — force-flushes every exporter onbeforeExit/SIGINT/SIGTERM:forceFlush())redactAttributes()/makeSafeCapture()(on by default,{ redactAttributes: false }opts out) — masks emails, JWTs,sk-/ghp_/AWS/Slack tokens, bearer headers,scheme://user:pass@URLs, and sensitive-keyed attributes (password,token,secret,cookie, …) before export; coverscaptureException,captureMessage,withProcessSpan, and LLM attributesdebug: trueorAUTTER_DEBUG=1) —[autter] exported N span(s)lines plus an explicit stderr warning if the process exits with captures never confirmed exportedOther packages
@autter/runtime-browser— newredactContext(): same scrubbing applied to custom context at theenqueue()choke point before anything leaves the page. Bundle stays at ~1.3 kB under the 5 kB size-limit.@autter/otlp-ingester—event.contextis scrubbed at normalize time before ClickHouse: defense-in-depth that also protects payloads from outdated SDK versions.@autter/runtime-next— re-exportsmakeSafeCapture/installAutterAutoFlush/redactAttributes;registerAutteralready passes the new options through.Drive-by fix
runtime-browser's build never emitteddist/index.d.tsdespite declaring it —runtime-next's DTS build only worked off a stale artifact; now deterministic (--dts).Tests
44 tests across three zero-dependency
node:testsuites (no new deps):discard_count,author_id,card_brand), plus child-process e2e: SIGTERM sole-handler → flush+exit 143, app-owned signal → app's exit code wins, double-signal cuts through,beforeExitflush completes without looping, and a wire-level e2e asserting no raw email/JWT/bearer reaches a local collector while[redacted]doesTest fixtures assemble fake tokens from string fragments so GitHub push protection doesn't mistake them for real credentials. CI now runs all three suites.