gastownhall/beads · error
count comparison requires integer value, got %q: %w
Error message
count comparison requires integer value, got %q: %w
What it means
For a count aggregate (children(x).count(...) or steps.complete N), the comparison value must parse as an integer via strconv.Atoi. The count of matching steps is an int, so a non-numeric expected value cannot be compared and evaluation aborts with this wrapped error.
Source
Thrown at internal/formula/condition.go:376
case "count":
count := 0
for _, s := range steps {
// For steps.complete pattern, field is the status to count
if c.AggregateOver == "steps" && (c.Field == "complete" || c.Field == "failed" || c.Field == "pending" || c.Field == "in_progress") {
if s.Status == c.Field {
count++
}
} else {
satisfied, _ := matchStep(s, c.Field, OpEqual, c.Value)
if satisfied {
count++
}
}
}
expected, err := strconv.Atoi(c.Value)
if err != nil {
return nil, fmt.Errorf("count comparison requires integer value, got %q: %w", c.Value, err)
}
satisfied, reason := compareInt(count, c.Operator, expected)
return &ConditionResult{
Satisfied: satisfied,
Reason: reason,
}, nil
}
return nil, fmt.Errorf("unknown aggregate function: %s", c.AggregateFunc)
}
func (c *Condition) evaluateExternal(ctx *ConditionContext) (*ConditionResult, error) {
switch c.ExternalType {
case "file.exists":
path := c.ExternalArg
// Substitute variables
for k, v := range ctx.Vars {
path = strings.ReplaceAll(path, "{{"+k+"}}", v)View on GitHub (pinned to 71377f2769)
Solutions
- Use a plain integer literal in the comparison: `children(task).count(status == 'complete') >= 3`
- Strip quotes/whitespace from the value before constructing the Condition.Value field
- Parse with strconv.Atoi yourself (or ValidateRange-style check) before calling Evaluate to fail fast with a clearer message
Example fix
// before
cond, _ := formula.ParseCondition("children(t).count(status == 'complete') >= 'three'")
res, err := cond.Evaluate(ctx) // count comparison requires integer value, got "three"
// after
cond, _ := formula.ParseCondition("children(t).count(status == 'complete') >= 3")
res, err := cond.Evaluate(ctx) Defensive patterns
Strategy: validation
Validate before calling
if _, err := strconv.Atoi(cond.Value); err != nil {
return fmt.Errorf("count condition needs integer value, got %q", cond.Value)
}
res, err := cond.Evaluate(ctx) Type guard
func isIntString(s string) bool { _, err := strconv.Atoi(s); return err == nil } Try / catch
res, err := cond.Evaluate(ctx)
if err != nil && strings.Contains(err.Error(), "count comparison requires integer value") {
return fmt.Errorf("fix the count literal in %q", cond.Raw)
}
return res, err Prevention
- Always write count comparisons with bare integer literals (>= 3, not 'three' or 3.0)
- Strip quotes/whitespace from interpolated values before building count conditions
- Pre-parse count values with strconv.Atoi at formula-load time
When it happens
Trigger: Evaluate() on a Type=aggregate condition with AggregateFunc="count" whose Value is non-integer — e.g. `children(task).count(status == 'complete') >= three`, or a quoted value like `'3'` that includes stray characters/whitespace.
Common situations: Hand-writing the trailing comparison of a count expression with a word instead of a number; variable substitution injecting a non-numeric string; copying a float (3.0) or value with a unit (3x); programmatic construction where Value was populated from the inner condition's quoted string instead of the trailing comparison.
Related errors
- unknown aggregate function: %s
- parsing formula: %w
- resolving formula: %w
- applying control flow: %w
- applying inline expansions: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/fc4465308f6019c4.
Report an issue: GitHub.