block/buzz · error
delete requires target_event_id
Error message
delete requires target_event_id
What it means
`run_atomic_mutation` was asked to execute a "delete" enforcement action, but `EnforcementCtx.target_event_id` was `None`. Deleting a reported event requires its id; the handler cannot proceed. Like the kick/timeout variants, this is an internal invariant failure indicating the enforcement-context builder failed to decode or attach the report's event target.
Source
Thrown at crates/buzz-relay/src/handlers/report_resolution.rs:752
ctx.community_id,
ch,
target,
ctx.actor_pubkey,
)
.await
.map_err(|e| anyhow::anyhow!("kick failed: {e}"))?
{
buzz_db::relay_admin_actions::KickWithMarkerResult::Removed => Ok(true),
buzz_db::relay_admin_actions::KickWithMarkerResult::AlreadyMarked => Ok(false),
buzz_db::relay_admin_actions::KickWithMarkerResult::AlreadyGone => Err(
anyhow::anyhow!("kick target was already absent before this action"),
),
}
}
"delete" => {
let target = ctx
.target_event_id
.ok_or_else(|| anyhow::anyhow!("delete requires target_event_id"))?;
let meta = state
.db
.get_thread_metadata_by_event(ctx.community_id, target)
.await
.map_err(|e| anyhow::anyhow!("thread metadata lookup failed: {e}"))?;
let parent_id = meta.as_ref().and_then(|m| m.parent_event_id.clone());
let root_id = meta.as_ref().and_then(|m| m.root_event_id.clone());
state
.db
.execute_delete_with_marker(
action_id,
lease_token,
ctx.community_id,
target,
parent_id.as_deref(),
root_id.as_deref(),
)
.awaitView on GitHub (pinned to eed74bde2f)
Solutions
- Verify the resolution action matches the report's target kind: only resolve event-kind reports (target decode yields an event id) with "delete".
- Check the report row's stored target (kind + hex) — re-trigger resolution after fixing the target, or resolve with "ban"/"kick" instead.
- If building contexts in code/tests, populate `target_event_id` from the decoded report target before calling `drive_enforcement`.
- Add early validation in the resolve endpoint that rejects delete-on-pubkey reports with a client-facing error rather than this internal one.
Example fix
// before
let ctx = EnforcementCtx { action: "delete", target_event_id: None, ..base };
// after
let target_event_id = report.target_event_id
.ok_or_else(|| anyhow::anyhow!("cannot delete: report target is not an event"))?;
let ctx = EnforcementCtx { action: "delete", target_event_id: Some(target_event_id), ..base }; Defensive patterns
Strategy: validation
Validate before calling
fn ensure_delete_ctx(ctx: &EnforcementCtx) -> anyhow::Result<&EnforcementCtx<'_>> {
anyhow::ensure!(ctx.action != "delete" || ctx.target_event_id.is_some(),
"delete enforcement requires target_event_id; report target must be an event");
Ok(ctx)
}
// call before drive_enforcement:
// ensure_delete_ctx(&ctx)?; Type guard
fn delete_ctx_is_complete(ctx: &EnforcementCtx<'_>) -> bool {
ctx.action != "delete" || ctx.target_event_id.is_some()
} Try / catch
match run_atomic_mutation(state, action_id, lease_token, &ctx).await {
Err(e) if e.to_string().contains("delete requires target_event_id") => {
mark_action_failed(action_id, "report target is not an event; delete impossible".into());
}
other => other?,
} Prevention
- Only expose "delete" as a resolution option on event-kind reports.
- Validate the report target decodes to an event id before persisting a delete action.
- Keep one code path (derive_enforcement_target_pub) populating target fields.
- Reject delete-on-pubkey resolutions at the API boundary with a client-facing error.
When it happens
Trigger: 1) The report targeted a pubkey (user-level report) but was resolved with a "delete" action instead. 2) The report target hex failed to decode to a valid event id upstream and was left as `None`. 3) A custom or hand-rolled `EnforcementCtx` for delete omitted `target_event_id`. 4) Legacy admin-action rows whose stored report target predates event-id scoping.
Common situations: Operator UIs letting admins pick "delete" on a user-level report; corrupt or partially-written report target columns; forks or scripts inserting recovery actions with the wrong target kind; report kind registry changes leaving old rows un-decodable.
Related errors
- kick requires channel_id
- kick failed: {e}
- kick target was already absent before this action
- thread metadata lookup failed: {e}
AI-assisted analysis of block/buzz@eed74bde2f (2026-08-30).
Data as JSON: /api/errors/579ffc88930ff6ed.
Report an issue: GitHub.