opencode-mobile is now the org's #1 Sentry volume source (~4,500 events/mo
against a 3,500/mo org quota, AGE-105). ~1,100 of those events are three
non-defects: `connect timeout` (462), `connect server-unreachable` (157), and
one device's `API Error: 401` token-refresh loop firing 498 times.
Adds a pure, unit-tested noise gate (src/lib/sentry-noise.ts) wired into
`beforeSend`, applying three layers cheapest-first:
1. Always-send allowlist — OOM/ANR/native/fatal crash classes bypass every
limit. Quota is worthless if it silences real crashes.
2. Transport drop-list — hard drop for client-side network conditions. Hard,
not sampled: the gate runs per-install, so "1 per device per day" would
multiply by the install base straight back into thousands per month.
3. Dedup + rate cap — 6h per-fingerprint cooldown, ≤6 new fingerprints/h,
≤10 events/h, mirroring the openclaw-box-bot shim (AGE-55).
Nothing is lost by the transport drop: those failures are already user-visible
as connection UI and already trended, PII-free, as the PostHog
`connection_failed{error_class}` event. captureDiagnostic() also short-circuits
for those classifications so the event is never even built. Drops are auditable
— the count since the last delivered event rides along as a
`noise.dropped_since_last` tag.
Replaying the observed 1,126-event hour through the gate yields 5 delivered
events (1 auth report + 4 real OOMs).
Tests: 18 new, 257 total passing; tsc --noEmit clean.
Co-authored-by: engineer <engineer@macbookpro.lan>
Co-authored-by: Paperclip <noreply@paperclip.ing>
Two scoped changes for the no-spend growth launch (Growth Launch Kit,
Notion page 3a1ac25eb49f81099cc9f3a4286c8ec4):
1. README.md and distribution/play-listing.md said Google Play was
"coming soon" / internal-testing-only, while distribution/retention-analysis.md
and the live play.google.com listing show it's actually public with 1K+
installs. Fixed the contradiction, added Google Play as a third install
channel, and added an accurate mention of the new offline demo mode
("Try a Demo" — reasoning, grep, diff, permission prompt, ~30s, no server)
matching what app/demo.tsx + src/lib/demo-script.ts actually render.
play-listing.md's stale pre-launch checklists are marked historical
instead of rewritten, so #83's ASO copy/keyword work is untouched.
2. Added the demo funnel's key metric (demo-completion, per the launch
kit) as four consent-gated PostHog events: demo_started,
demo_step_advanced, demo_completed, demo_exited_to_connect. Pure
property-derivation logic lives in src/lib/demo-analytics.ts (no
RN/PostHog imports, unit-tested with node --test, same pattern as
analytics-classify.ts) and is wired into app/demo.tsx's lifecycle.
Updated docs/analytics.md's event table and the privacy policy's event
list (distribution/privacy-policy.md + its two HTML mirrors) per the
repo's "new event requires a policy update" convention.
Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
The app ships PostHog activation-funnel analytics gated behind the same
consent flag as Sentry, but the consent modal, Settings toggle, privacy
policy, and Play Data safety draft only mentioned crash reporting. Fix
the disclosure everywhere:
- TelemetryConsentModal: body + bullets + a11y labels now cover anonymous
usage analytics (PostHog EU) alongside crash reports
- Settings: toggle renamed 'Crash Reports & Usage Analytics', description
names both Sentry and PostHog
- Privacy policy (md + html + live gh-pages mirror): new section 3a with
the full event/property table, PostHog EU destination, anonymous-ID
statement, decline/revoke (drop-on-revoke) semantics; sections 4-7, 9
and the Apple nutrition-label addendum updated for analytics
- play-listing.md: Data safety draft declares App interactions + Device
or other IDs (opt-in, default OFF, shared with PostHog/Sentry)
- docs/playstore.md: Data safety row flipped to re-verify with pointer
to the new design record
- docs/analytics.md: new design record — event schema, consent gating
incl. buffered-event drop on revoke, disclosure surfaces to keep in
sync, verification checklist (all TODO)
- website privacy page metadata mentions analytics opt-in
Closes#63
Claude-Session: https://claude.ai/code/session_01NJKAQ6HAikWGQK7PGZ5Y4E
Co-authored-by: engineer <engineer@gray-knight-m1.local>
Co-authored-by: Claude Fable 5 <noreply@anthropic.com>