Abuse observability: link/approve/unlink audit trail + report path #78

Closed
opened 2026-07-10 23:51:24 +00:00 by robocub · 2 comments
Collaborator

Reactive abuse tooling for open registration: an audit trail and a report path feeding the existing ban tooling.

Context

Two-sided auth structurally prevents non-consensual bridging, but residual vectors remain for a public instance: rapid bridge churn, resource hogging, or a legitimate owner using the voice relay abusively (voice content is not moderatable by design — no recording/transcription).

Need 1 — audit observability

A consistent, queryable record of lifecycle-security events: link / approve / unlink / ban with who, which guild+room, when, and (for approvals) the approver. Some of this is already logged and the approval outcome is posted in-channel (#64) — consolidate into a coherent audit trail so patterns are visible for manual bans before automated detection is worth building.

Need 2 — abuse report path

A way for someone to report an abusive bridge (a management/DM command, and/or a documented contact address), feeding the existing owner/guild/room deny-list tooling. Pair with the docs work (#75).

Related: #47, #43, #63/#64 (consent + disclosure).

Reactive abuse tooling for open registration: an audit trail and a report path feeding the existing ban tooling. ## Context Two-sided auth structurally prevents non-consensual bridging, but residual vectors remain for a public instance: rapid bridge churn, resource hogging, or a legitimate owner using the voice relay abusively (voice content is not moderatable by design — no recording/transcription). ## Need 1 — audit observability A consistent, queryable record of lifecycle-security events: `link` / `approve` / `unlink` / `ban` with who, which guild+room, when, and (for approvals) the approver. Some of this is already logged and the approval outcome is posted in-channel (#64) — consolidate into a coherent audit trail so patterns are visible for **manual** bans before automated detection is worth building. ## Need 2 — abuse report path A way for someone to report an abusive bridge (a management/DM command, and/or a documented contact address), feeding the existing owner/guild/room deny-list tooling. Pair with the docs work (#75). Related: #47, #43, #63/#64 (consent + disclosure).
Author
Collaborator

Merged to master (44386f3). Implements both needs; reactive by design (voice content is unmoderatable — never recorded/transcribed).

Need 1 — coherent, queryable audit trail. The <data_dir>/audit.jsonl trail (from #47) already covered link/approve/unlink/ban; this adds:

  • reports [count] — operator-only command that renders recent report events over DM (no host shell), each next to the exact ban <kind> <value> to run.
  • Invite accept/reject decisions are now audited (operator / open_registration / banned / not_direct / not_allowlisted), closing the reachability-attempt gap.

Need 2 — abuse report path → deny-list.

  • report <owner|guild|room> <value> [reason] — self-serve-tier + operators. Records an advisory report audit event and acks; it never auto-bans (auto-acting on untrusted input is itself an abuse vector — feeds manual bans). Rate-limited via the shared mgmt_cooldown; reason trimmed + length-capped.

No new config knobs. All in crates/matrix-rtc/src/mgmt.rs; README "Abuse controls" section + CHANGELOG added.

Verification. Workspace clippy -D warnings clean; nvb-matrix-rtc 99 tests, nvb-e2e 19 tests. Live on staging: mgmt_self_serve_link PASS 53.4s (extended with report/reports/operator-readback steps), with the report event + invite-audit events confirmed in the real bridge's audit.jsonl.

Not yet released/deployed (code on master). The out-of-band report contact address half of Need 2 is docs → #75; prod should set mgmt_cooldown_secs so report is rate-gated before enabling open registration.

Merged to `master` (`44386f3`). Implements both needs; reactive by design (voice content is unmoderatable — never recorded/transcribed). **Need 1 — coherent, queryable audit trail.** The `<data_dir>/audit.jsonl` trail (from #47) already covered link/approve/unlink/ban; this adds: - `reports [count]` — operator-only command that renders recent report events over DM (no host shell), each next to the exact `ban <kind> <value>` to run. - Invite accept/reject decisions are now audited (operator / open_registration / banned / not_direct / not_allowlisted), closing the reachability-attempt gap. **Need 2 — abuse report path → deny-list.** - `report <owner|guild|room> <value> [reason]` — self-serve-tier + operators. Records an advisory `report` audit event and acks; it **never auto-bans** (auto-acting on untrusted input is itself an abuse vector — feeds *manual* bans). Rate-limited via the shared `mgmt_cooldown`; reason trimmed + length-capped. No new config knobs. All in `crates/matrix-rtc/src/mgmt.rs`; README "Abuse controls" section + CHANGELOG added. **Verification.** Workspace clippy `-D warnings` clean; `nvb-matrix-rtc` 99 tests, `nvb-e2e` 19 tests. Live on staging: `mgmt_self_serve_link` PASS 53.4s (extended with report/reports/operator-readback steps), with the `report` event + invite-audit events confirmed in the real bridge's `audit.jsonl`. Not yet released/deployed (code on master). The out-of-band report **contact address** half of Need 2 is docs → #75; prod should set `mgmt_cooldown_secs` so `report` is rate-gated before enabling open registration.
Author
Collaborator

Done. Abuse observability + report path: report <owner|guild|room> <value> [reason] (self-serve, advisory — feeds manual bans), operator reports [count] review command, and invite accept/reject audit coverage, all on the existing audit.jsonl trail. Merged (master 44386f3), live-validated with the report event confirmed in the real trail, shipped in v0.3.0-alpha.16, deployed.

Done. Abuse observability + report path: `report <owner|guild|room> <value> [reason]` (self-serve, advisory — feeds manual bans), operator `reports [count]` review command, and invite accept/reject audit coverage, all on the existing `audit.jsonl` trail. Merged (master `44386f3`), live-validated with the report event confirmed in the real trail, shipped in v0.3.0-alpha.16, deployed.
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
dark/nether-voicebridge#78
No description provided.