zeroclaw-labs/zeroclaw · info
static Slack token regex must compile
Error message
static Slack token regex must compile
What it means
check_api_keys() in the secret leak detector compiles its regex patterns on every call; the Slack bot/user token pattern xox[baprs]-... is a hardcoded literal, and regex literals fail to compile only through programmer error. The expect("static Slack token regex must compile") is a deliberately loud assertion for that case.
Source
Thrown at crates/zeroclaw-runtime/src/security/leak_detector.rs:202
(Regex::new(r"gsk_[a-zA-Z0-9]{20,}").unwrap(), "Groq API key"),
// Google
(
Regex::new(r"AIza[a-zA-Z0-9_-]{35}").unwrap(),
"Google API key",
),
// GitHub
(
Regex::new(r"gh[pousr]_[a-zA-Z0-9]{36,}").unwrap(),
"GitHub token",
),
(
Regex::new(r"github_pat_[a-zA-Z0-9_]{22,}").unwrap(),
"GitHub PAT",
),
// Slack
(
Regex::new(r"xox[baprs]-[0-9A-Za-z-]{10,}")
.expect("static Slack token regex must compile"),
"Slack token",
),
(
Regex::new(r"xapp-[0-9A-Za-z-]{10,}")
.expect("static Slack app-level token regex must compile"),
"Slack app-level token",
),
(
Regex::new(r"xwfp-[0-9A-Za-z-]{10,}")
.expect("static Slack workflow token regex must compile"),
"Slack workflow token",
),
(
// Rotation family: refresh tokens (`xoxe-…`) and rotated
// access tokens (`xoxe.xoxb-…`, `xoxe.xoxp-…`). The base
// `xox[baprs]-` class excludes `e`, and matching only the
// inner `xoxb-`/`xoxp-` would leave the `xoxe.` prefix
// unredacted, so cover the whole token explicitly.View on GitHub (pinned to 88bb9c8533)
Solutions
- Validate the edited pattern locally: Regex::new(r"xox[baprs]-[0-9A-Za-z-]{10,}") must succeed before committing.
- Run the leak-detector unit tests after touching patterns.
- Better: compile the patterns once in a LazyLock/OnceLock so an invalid pattern fails on first use in tests deterministically.
Example fix
// before: pattern rebuilt per call, typo breaks every scan at runtime
Regex::new(r"xox[baprs-[0-9A-Za-z-]{10,}").expect("static Slack token regex must compile")
// after: compile once, fail fast and clearly
static SLACK_TOKEN: LazyLock<Regex> =
LazyLock::new(|| Regex::new(r"xox[baprs]-[0-9A-Za-z-]{10,}").expect("static Slack token regex must compile")); Defensive patterns
Strategy: validation
Validate before calling
// Keep pattern edits test-covered; assert compilation in a unit test:
#[test]
fn leak_detector_patterns_compile() {
assert!(regex::Regex::new(r"xox[baprs]-[0-9A-Za-z-]{10,}").is_ok());
} Prevention
- Run the leak-detector tests after any pattern edit; they exercise check_api_keys end to end.
- Prefer LazyLock statics over per-call Regex::new so invalid patterns fail deterministically on first use.
- Validate edited regex literals in a scratch test before committing.
When it happens
Trigger: Any scan_with_protected_spans() invocation compiles this pattern; a panic means the literal regex in leak_detector.rs is syntactically invalid, e.g. someone edited it and introduced a malformed escape or unbalanced group.
Common situations: Contributors tuning leak-detection patterns; backports where the pattern was hand-merged and corrupted. In released builds the pattern has already been exercised by tests, so it cannot fire.
Related errors
- static Slack app-level token regex must compile
- Schema missing required 'type' field
- HMAC accepts any key length
- needs_reassembly implies a step agent alias
- owned implies a reassembly handle
AI-assisted analysis of zeroclaw-labs/zeroclaw@88bb9c8533 (2026-08-23).
Data as JSON: /api/errors/d63918f9aec63950.
Report an issue: GitHub.