zeroclaw-labs/zeroclaw · error · anyhow::Error
slash command registration failed for '{name}' ({status}): {
Error message
slash command registration failed for '{name}' ({status}): {err} What it means
While reconciling, registering (creating or updating) the slash command named '{name}' failed with a non-success status; the response body is included. Registration happens per command after the listing diff decides an upsert is needed, and a 429 is converted into a RateLimited outcome before this bail.
Source
Thrown at crates/zeroclaw-channels/src/discord/slash.rs:716
.await
.map_err(reqwest::Error::without_url)?;
if resp.status() == reqwest::StatusCode::TOO_MANY_REQUESTS {
// Stop on the first 429 and surface the cooldown rather than
// hammering the remaining upserts into the same rate limit.
let until = rate_limit_deadline(resp).await;
::zeroclaw_log::record!(
WARN,
::zeroclaw_log::Event::new(module_path!(), ::zeroclaw_log::Action::Note)
.with_outcome(::zeroclaw_log::EventOutcome::Unknown)
.with_attrs(::serde_json::json!({"command": name, "retry_after_until": until})),
"discord slash command reconcile rate-limited; backing off"
);
return Ok(ReconcileOutcome::RateLimited { until });
}
if !resp.status().is_success() {
let status = resp.status();
let err = resp.text().await.unwrap_or_default();
anyhow::bail!("slash command registration failed for '{name}' ({status}): {err}");
}
upserted += 1;
}
if upserted > 0 {
::zeroclaw_log::record!(
INFO,
::zeroclaw_log::Event::new(module_path!(), ::zeroclaw_log::Action::Note)
.with_attrs(::serde_json::json!({"upserted": upserted})),
"discord slash commands upserted"
);
}
if failed_deletes > 0 {
anyhow::bail!(
"{failed_deletes} stale skill command delete(s) failed; \
reconcile not recorded, next READY retries"
);
}
Ok(ReconcileOutcome::Reconciled)View on GitHub (pinned to 88bb9c8533)
Solutions
- Read '{name}' and the body: 50035-style errors point at the exact offending field
- Enforce Discord's rules: name lowercase, 1–32 chars, no spaces; description ≤ 100 chars
- Deduplicate command names across skills
- 401/403 → fix the token / application id pairing
Example fix
// before let name = "ConvertCurrency"; // rejected: must be lowercase // after let name = "convert-currency"; // valid: lowercase, hyphenated, <= 32 chars
Defensive patterns
Strategy: try-catch
Validate before calling
// Rust — enforce Discord's command naming rules before reconcile
fn valid_command_shape(name: &str, description: &str) -> bool {
let ok_name = !name.is_empty()
&& name.len() <= 32
&& name.chars().all(|c| c.is_ascii_lowercase() || c.is_ascii_digit() || c == '-');
ok_name && !description.is_empty() && description.chars().count() <= 100
} Try / catch
match reconcile_slash_commands(&client, &token, &app_id, &desired, base, scope, &guilds).await {
Ok(outcome) => Ok(outcome),
Err(e) if e.to_string().contains("slash command registration failed") => {
// payload/credential problem, not transient: the error names the command and body
tracing::error!("reconcile aborted on registration: {e}");
Err(e)
}
Err(e) => Err(e),
} Prevention
- Lint skill command names against Discord's rules before deploying
- Keep descriptions under 100 characters
- Avoid two skills claiming the same command name in one scope
When it happens
Trigger: POST/PATCH of a command definition fails: 400 duplicate command names in the same scope, name not lowercase or over 32 chars, description over 100 chars, malformed options; 401/403 credential or app-id problems.
Common situations: Skill command names violating Discord's naming rules (uppercase, spaces, punctuation) after adding a new skill; two skills mapping to the same command name; description templates growing past 100 chars.
Related errors
- interaction defer failed ({status}): {err}
- modal custom_id exceeds Discord's 100-char limit; cannot ope
- desired command set is not an array
- listing commands failed ({})
- {failed_deletes} stale skill command delete(s) failed; recon
AI-assisted analysis of zeroclaw-labs/zeroclaw@88bb9c8533 (2026-08-23).
Data as JSON: /api/errors/936dd36a165b5820.
Report an issue: GitHub.