astrid-runtime/astrid · error

empty duration

Error message

empty duration

What it means

Input validation at the top of parse_duration: the duration specifier, after trimming, is empty. The parser accepts forms like 30s, 5m, 2h30m, 500ms or a bare integer (seconds); an empty value cannot be interpreted as any duration and quota-set aborts. Fires before any suffix parsing.

Source

Thrown at crates/astrid-cli/src/commands/quota.rs:386

        "K" | "KB" => 1_000,
        "KIB" => 1024,
        "M" | "MB" => 1_000_000,
        "MIB" => 1024 * 1024,
        "G" | "GB" => 1_000_000_000,
        "GIB" => 1024 * 1024 * 1024,
        "T" | "TB" => 1_000_000_000_000,
        "TIB" => 1024_u64.pow(4),
        other => anyhow::bail!("unknown byte suffix: {other}"),
    };
    Ok((num_part, mult))
}

/// Parse `"30s"`, `"5m"`, `"1h"`, `"2h30m"`, `"500ms"`. Falls back to
/// seconds for a bare integer.
pub(crate) fn parse_duration(s: &str) -> Result<Duration> {
    let trimmed = s.trim();
    if trimmed.is_empty() {
        anyhow::bail!("empty duration");
    }
    if let Ok(secs) = trimmed.parse::<u64>() {
        return Ok(Duration::from_secs(secs));
    }
    let mut total = Duration::ZERO;
    let mut current = String::new();
    let mut iter = trimmed.chars().peekable();
    while let Some(c) = iter.next() {
        if c.is_ascii_digit() || c == '.' {
            current.push(c);
            continue;
        }
        // Collect alpha suffix.
        let mut suffix = String::new();
        suffix.push(c);
        while let Some(&n) = iter.peek() {
            if n.is_ascii_alphabetic() {
                suffix.push(n);

View on GitHub (pinned to affd8760f4)

Solutions

  1. Provide an explicit duration, e.g. `--timeout 30s`
  2. Default empty variables in the shell: `${TIMEOUT:-60}`
  3. Validate config inputs before invoking the CLI

Example fix

// before
astrid quota set --timeout "$IDLE"
// after
astrid quota set --timeout "${IDLE:-30s}"
Defensive patterns

Strategy: validation

Validate before calling

fn ensure_duration(s: &str) -> Result<&str, String> {
    let t = s.trim();
    if t.is_empty() { Err("duration must not be empty".into()) } else { Ok(t) }
}

Prevention

When it happens

Trigger: Passing an empty/whitespace-only value to a duration-parsing quota flag in `astrid quota set` (e.g. an empty timeout/idle flag).

Common situations: Unset environment variable interpolated as empty in CI scripts, blank YAML/JSON field passed through, or a typo leaving the flag value empty.

Understand the failure class

Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.

Related errors


AI-assisted analysis of astrid-runtime/astrid@affd8760f4 (2026-09-09). Data as JSON: /api/errors/9ffcd8f06dff987a. Report an issue: GitHub.