You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Add a narrowly scoped, explicitly opt-in Contributor Metrics system so volunteers can help peerd measure reliability, efficiency, and model/surface choices in real use.
This is not a general analytics platform. It is a bounded contribution path over locally aggregated technical/interaction counters. The system must preserve peerd's local-first architecture, remain completely optional, and make the exact outbound payload inspectable.
The current product promise is "no backend, no telemetry." This project therefore represents a real trust and store-policy change, even though collection is opt-in and content-free. It must ship as such: prominently disclosed, independently revocable, adversarially reviewed, and initially limited to preview/dev.
Why
The eval harness can compare controlled runs, and local observability can export a session debug bundle, but neither answers how a choice behaves across willing users in the field. Recent examples include:
Playwright-shaped page code versus discrete web tools.
Runtime fallback frequency and causes.
Model/provider differences in actor efficiency.
Tool-error and cancellation patterns.
Whether a change reduces turns/tokens without reducing user-reported success.
Without a contribution path, those decisions depend on anecdotes or synthetic/faked-model runs.
Existing foundation
Reuse rather than replace:
extension/peerd-runtime/observability/debug-bundle.js: local failure classification and aggregation.
extension/peerd-runtime/observability/otel-export.js: local OTel mapping. It remains a file export, never an automatic upload.
extension/eval/score.js: the existing quality/efficiency vocabulary.
The local append-only audit log and generated channel defaults.
The functional-core / injected-IO pattern and module public-index boundaries.
Automatic debug-bundle or trace upload is explicitly out of scope: those artifacts contain transcripts and debugging context.
Architecture
existing typed runtime outcomes
|
v
opt-in local aggregate (closed schema, no arbitrary properties)
|
+--> exact pending-payload preview
|
v
exact-origin contribution egress (POST only, no credentials/redirects)
|
v
schema-validating aggregate-only collector
|
v
release/model/surface scorecards (no user or session reconstruction)
The collector must never return configuration, experiment assignments, prompts, code, or other behavior. This is a one-way measurement edge, not a control plane.
Non-negotiable privacy and security invariants
Off by default on every channel. No telemetry-specific counter is recorded and no contribution request is sent before affirmative consent.
Human-only consent. The model, tools, actors, pages, sandboxes, imports, hooks, and dweb peers cannot enable, trigger, broaden, or inspect contribution state.
No stable identity. No account, installation ID, device ID, session ID, actor ID, URL, origin, hostname, IP stored by the application, cookie, advertising identifier, or cross-batch correlation key.
No content. No prompts, replies, transcripts, DOM/page text, search terms, form data, files, tool arguments/results, raw error text, screenshots, audio, debug bundles, audit entries, or model context.
Closed schema only. No generic track(name, properties), arbitrary property bag, free-text event name, or caller-supplied string field. Permitted strings are versioned enums or sanitized catalog-known identifiers; unknown values collapse to other/custom.
Local aggregation first. Contributions contain bounded counters and histograms, not an event stream.
Exact preview. The UI shows the same serialized bytes the uploader will send.
Revocable. Disabling participation stops alarms/retries and clears unsent contribution state. Aggregate server rows cannot be attributed back to a person; the UI/policy must say this plainly.
One egress lane. A dedicated exact-origin contribution client, separate from provider safeFetch and open-web webFetch; HTTPS, POST-only, redirects refused, credentials omitted, bounded body/response, locally audited.
No remote control. The response is a fixed receipt only. The endpoint cannot affect models, prompts, settings, feature flags, or runtime behavior.
Store-honest. README, AGENTS, SECURITY, threat model, privacy policy, store listing/reviewer material, and browser manifests/consent declarations must agree with the shipped behavior.
Adversarially reviewed. Privacy/exfiltration, consent lifecycle, schema evolution, concurrency/retry, store packaging, and abuse/poisoning reviews must have no unresolved material findings before rollout.
Permitted v0 dimensions
Only the minimum needed to answer product questions:
Extension version and channel.
Browser family; no full user-agent, locale, timezone, OS version, hardware inventory, or extension inventory.
Known provider and catalog-known model family; unknown/custom model strings become custom.
Feature and locally selected variant, such as requested/resolved web actor surface.
Enumerated fallback and classified failure categories.
Bounded counts/histograms for operational completion, cancellation, errors, actor turns, action calls, duration, and token usage.
Optional binary task feedback ("worked" / "didn't work"), with no text field.
Operational completion is not task correctness. Only explicit binary feedback may be reported as user-reported success.
Rollout
Preview/dev first.
Store remains content-free/no-contribution until the preview implementation, collector operations, disclosures, and store review posture are independently accepted.
A later store enablement requires its own explicit go/no-go issue; it is not implied by completing this epic.
Dependency chain: #345 → #346 → #347. Each child is independently mergeable and must receive its own adversarial review.
Epic exit criteria
All child issues are complete.
Preview/dev contributors can inspect, enable, send, revoke, and verify the narrow contribution path.
Store artifacts retain their prior no-contribution posture.
No automatic raw diagnostic upload exists.
The end-to-end envelope is proven unable to carry content or arbitrary strings.
CI covers pure schema/aggregation, in-browser consent UI, live upload behavior, Firefox declarations, generated-file drift, and channel/browser packaging.
An adversarial review swarm clears the complete data flow.
Documentation describes exactly what changes and what remains local.
Explicit non-goals
General-purpose analytics or a third-party telemetry SDK.
Product usage tracking unrelated to specific engineering questions.
Decision to scope
Add a narrowly scoped, explicitly opt-in Contributor Metrics system so volunteers can help peerd measure reliability, efficiency, and model/surface choices in real use.
This is not a general analytics platform. It is a bounded contribution path over locally aggregated technical/interaction counters. The system must preserve peerd's local-first architecture, remain completely optional, and make the exact outbound payload inspectable.
The current product promise is "no backend, no telemetry." This project therefore represents a real trust and store-policy change, even though collection is opt-in and content-free. It must ship as such: prominently disclosed, independently revocable, adversarially reviewed, and initially limited to preview/dev.
Why
The eval harness can compare controlled runs, and local observability can export a session debug bundle, but neither answers how a choice behaves across willing users in the field. Recent examples include:
Without a contribution path, those decisions depend on anecdotes or synthetic/faked-model runs.
Existing foundation
Reuse rather than replace:
extension/peerd-runtime/observability/debug-bundle.js: local failure classification and aggregation.extension/peerd-runtime/observability/otel-export.js: local OTel mapping. It remains a file export, never an automatic upload.extension/eval/score.js: the existing quality/efficiency vocabulary.Automatic debug-bundle or trace upload is explicitly out of scope: those artifacts contain transcripts and debugging context.
Architecture
The collector must never return configuration, experiment assignments, prompts, code, or other behavior. This is a one-way measurement edge, not a control plane.
Non-negotiable privacy and security invariants
track(name, properties), arbitrary property bag, free-text event name, or caller-supplied string field. Permitted strings are versioned enums or sanitized catalog-known identifiers; unknown values collapse toother/custom.safeFetchand open-webwebFetch; HTTPS, POST-only, redirects refused, credentials omitted, bounded body/response, locally audited.Permitted v0 dimensions
Only the minimum needed to answer product questions:
custom.Operational completion is not task correctness. Only explicit binary feedback may be reported as user-reported success.
Rollout
Policy constraints
Chrome requires prominent disclosure and affirmative informed consent for changed user-data practices; a privacy-policy edit alone is insufficient:
https://developer.chrome.com/docs/webstore/program-policies/disclosure-requirements
Firefox provides manifest-declared data-collection permissions and built-in consent for technical/interaction data; use that path where available:
https://extensionworkshop.com/documentation/develop/firefox-builtin-data-consent/
Child work
Complete in order:
Dependency chain: #345 → #346 → #347. Each child is independently mergeable and must receive its own adversarial review.
Epic exit criteria
Explicit non-goals