caddyserver/caddy · error
[/%s] array index out of bounds: %s
Error message
[/%s] array index out of bounds: %s
What it means
Thrown while traversing an intermediate array when the numeric index is negative or >= the array length. Unlike the final-segment case, there is no PUT append allowance here: intermediate hops must land on an existing element. The message includes the traversed prefix and the bad index.
Source
Thrown at admin.go:1325
}
} else {
// if we are "PUTting" a new resource, the key(s) in its path
// might not exist yet; that's OK but we need to make them as
// we go, while we still have a pointer from the level above
if v[part] == nil && method == http.MethodPut {
v[part] = make(map[string]any)
}
ptr = v[part]
}
case []any:
partInt, err := parseCanonicalArrayIndex(part)
if err != nil {
return fmt.Errorf("[/%s] invalid array index '%s': %v",
strings.Join(parts[:i+1], "/"), part, err)
}
if partInt < 0 || partInt >= len(v) {
return fmt.Errorf("[/%s] array index out of bounds: %s",
strings.Join(parts[:i+1], "/"), part)
}
ptr = v[partInt]
default:
return fmt.Errorf("invalid traversal path at: %s", strings.Join(parts[:i+1], "/"))
}
}
return nil
}
// RemoveMetaFields removes meta fields like "@id" from a JSON message
// by using a simple regular expression. (An alternate way to do this
// would be to delete them from the raw, map[string]any
// representation as they are indexed, then iterate the index we made
// and add them back after encoding as JSON, but this is simpler.)
func RemoveMetaFields(rawJSON []byte) []byte {View on GitHub (pinned to 50e54ee279)
Solutions
- GET the array at the failing prefix to see its actual length, then use a valid 0..len-1 index
- Recompute indexes after any DELETE that shifts subsequent elements
- Generate paths programmatically from the live config instead of hardcoding indexes
Example fix
# before (only 1 route exists) curl http://localhost:2019/config/apps/http/servers/myserver/routes/2/handle/0 # after curl http://localhost:2019/config/apps/http/servers/myserver/routes/0/handle/0
Defensive patterns
Strategy: validation
Validate before calling
prefix="apps/http/servers/myserver/routes"
n=$(curl -s "http://localhost:2019/config/$prefix" | jq 'length')
assert 0 <= idx < n, f'index {idx} out of range for array of {n}' Try / catch
On out-of-bounds during traversal, GET the prefix from the error message, recompute a valid index, and retry the full path once; persistent failure means your path model is wrong.
Prevention
- Recompute indexes after any DELETE shifts array elements
- Derive deep paths from live config rather than templates with fixed indexes
When it happens
Trigger: GET /config/apps/http/servers/myserver/routes/3/... when the routes array has fewer elements; any path that indexes past the end of an intermediate array such as match sets or handler lists.
Common situations: 0-based vs 1-based confusion; stale indexes after elements were deleted or the config reloaded with fewer entries; paths generated from a template with an unfilled or default index.
Related errors
- [%s] array index out of bounds: %s
- [/%s] invalid array index '%s': %v
- decoding request body: %w, at offset %d
- decoding request body: %w
- [%s] invalid array index '%s': %v
AI-assisted analysis of caddyserver/caddy@50e54ee279 (2026-08-15).
Data as JSON: /api/errors/fd477f9e9770096d.
Report an issue: GitHub.