fix(stats): lower k-anonymity floor from 5 to 2 so /stats shows real client names#62
Merged
Merged
Conversation
…client names
Live prod state at v0.9.69 (4 total installs):
OpenClaw 19 events, 1 install
Claude 7 events, 1 install
Codex 4 events, 1 install
ChatGPT 3 events, 1 install
unknown 93 events, 4 installs
Every real client has uniq_installs = 1. The k>=5 floor in
housekeeper.js drops every single label into "Other", so /stats
shows `popular_mcp_clients: [{ label: 'Other', uniq: 6 }]` and the
charts never display real client names. At single-digit total
install counts this is mathematically unreachable -- even if every
install converged on one client, uniq would still be < 5.
Fix: K_ANONYMITY_FLOOR 5 -> 2 in
showcase/server/src/telemetry/housekeeper.js. Per-label names still
collapse into "Other" until they reach 2 distinct installs (mild
anonymity preserved). Raise back to 5 once total install count
comfortably exceeds 50.
Tests: server-telemetry-housekeeper.test.js's k=5 assertion (today's
Claude+Codex collapsed to suppressed empty list because aggregate
2 < k=5) updated to assert the k=2 expectation (Claude+Codex both
below k=2, aggregate 2 >= k=2 -> single "Other" bucket with uniq=2).
Per-label names still hidden so anonymity at the chosen k is
preserved. Docstrings in housekeeper.js + server.js updated to
reference the floor symbol rather than the literal 5.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
4 tasks
LakshmanTurlapati
added a commit
that referenced
this pull request
May 18, 2026
* docs: start milestone v0.9.70 Showcase Dashboard Reliability (Streaming + Sync + Viewport) Three target features: (1) diagnose-first dashboard DOM-streaming fix continuing STREAM-07 attempt 2 of 5 from v0.9.69 Phase 276; (2) Sync-tab remote-control restoration on full-selfbrowsing.com; (3) 16:10 desktop viewport lock on the dashboard preview pane (mobile out of scope). PROJECT.md "Current Milestone" rewritten to v0.9.70 with goals + target features + key constraints + deferred candidates. Footer "Last updated" bumped to 2026-05-16. "Last shipped" updated to reflect v0.9.69 SHIP + four post-milestone fixes (PR #57/59/61/62/63/64) and the published artifacts (extension v0.9.67 zip, mcp-v0.9.2 npm, Fly auto-deploy). STATE.md frontmatter reset (milestone v0.9.70, status in_progress, progress 0%). Current Position set to "Not started (defining requirements)". Active Milestone Risk Register replaced with Active Milestone Carry-Forward (STREAM-07 attempt 2 + CWS click-through). Quick Tasks Completed table extended with PRs #59 / #61 / #62 / #63 / #64. Pending User-Gated Actions: v0.9.0 npm publish marked superseded by v0.9.2; added v0.9.67 -> extension-v0.9.67 retag decision. Phases dir cleared (8 v0.9.69 phase directories removed by gsd-tools phases clear). Carries over: 999.1-mcp-tool-gaps, INTEGRATION-CHECK.md, v0.9.63-INTEGRATION-CHECK.md. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * fix(showcase): lock dashboard preview pane to 16:10 on desktop Phase 280 VIEWPORT requirement: the live DOM preview frame in the showcase dashboard had no fixed aspect ratio and stretched freely to container height, producing inconsistent letterboxing and the bug visible in milestone 0.9.70. Pin it to 16/10 on desktop, unset on mobile (<=768px and <=480px) where vertical layout takes over, and keep Maximized (100vh) and PiP layouts coherent (auto for maximized, explicit 16/10 for PiP). Adds tests/dashboard-preview-aspect-ratio.test.js — parses the SCSS and asserts the rule lives in the right selectors (desktop, both mobile media queries, Maximized, PiP). Wired into the root `npm test` chain. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
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.
Summary
Lower
K_ANONYMITY_FLOORfrom5to2inshowcase/server/src/telemetry/housekeeper.jsso/statscan actually display MCP client names. At single-digit total install counts (currently 4), no real label can mathematically clear k=5, so every name collapses intoOtherand the chart stays empty.Evidence (live prod, post all telemetry fixes from PRs #57, #59)
telemetry_eventsDB:/api/public-stats/globalresponse:{ "popular_mcp_clients": [{ "label": "Other", "uniq": 6 }] }All four real labels (OpenClaw, Claude, Codex, ChatGPT) recorded correctly into
telemetry_eventspost-PR #59. The k>=5 floor inhousekeeper.js:97then collapses every entry into theOtherbucket becauseuniq=1 < 5. Even if every install converged on a single client,uniqwould still be 4 and below k=5. Mathematically unreachable.Change
Per-label names still hide until a label reaches 2 distinct installs, so mild anonymity is preserved at the chosen k. Raise back to 5 once the total install count comfortably exceeds 50.
Test plan
node tests/server-telemetry-housekeeper.test.js— 24/24 PASS (k=5 expectation updated to k=2: today's Claude+Codex both have uniq=1, aggregate below-k installs = 2, 2 >= k=2 -> singleOtherbucket with uniq=2).npm test(full root suite) — exit 0./api/public-stats/globalnow lists at least oneOther (uniq=N)entry or a real label if any client crosses k=2.Operational follow-up
None. House-cleaning tick runs hourly on the deployed server; first re-aggregation after deploy will rewrite
telemetry_global_aggregates.popular_mcp_jsonwith the new floor.🤖 Generated with Claude Code