go-redis/redis · error
unexpected type %T, want map or key/value array
Error message
unexpected type %T, want map or key/value array
What it means
Returned by parseCollectEntry when an individual COLLECT entry is neither a map (RESP3 map[interface{}]interface{} or map[string]interface{}) nor a flat key/value array ([]interface{}). The '%T' shows the actual Go type, e.g. string or int64, that appeared where an entry map was expected.
Source
Thrown at search_collect.go:233
}
return out, nil
case map[string]interface{}: // already string-keyed
return m, nil
case []interface{}: // RESP2 flat [field, value, field, value, ...]
if len(m)%2 != 0 {
return nil, fmt.Errorf("odd-length key/value array of length %d", len(m))
}
out := make(CollectEntry, len(m)/2)
for i := 0; i < len(m); i += 2 {
key, ok := m[i].(string)
if !ok {
key = fmt.Sprint(m[i])
}
out[key] = m[i+1]
}
return out, nil
default:
return nil, fmt.Errorf("unexpected type %T, want map or key/value array", e)
}
}
View on GitHub (pinned to 36d97525cd)
Solutions
- Inspect the raw reply (cmd.RawVal()) to identify the scalar and where it came from.
- Confirm the alias is exclusively used by a COLLECT reducer and not shared with another reducer/field.
- Verify the negotiated protocol (RESP2 vs RESP3) matches the server's reply type.
- Check server/proxy version and logs for an upstream error that was serialized into the results array.
Defensive patterns
Strategy: type-guard
Type guard
func isCollectEntryShape(e interface{}) bool {
switch e.(type) {
case map[interface{}]interface{}, map[string]interface{}, []interface{}:
return true
}
return false
} Try / catch
col, err := row.Collect(alias)
if err != nil {
raw, _ := cmd.RawResult()
log.Printf("COLLECT entry malformed on %q; raw=%v err=%v", alias, raw, err)
return nil, err
} Prevention
- Ensure the alias is used solely by a COLLECT reducer.
- Verify protocol negotiation (RESP2 vs RESP3) matches the server reply.
- Inspect cmd.RawVal() when this fires to identify the scalar that landed where an entry map was expected.
When it happens
Trigger: AggregateRow.Collect over an array whose element is a scalar (string, number, bulk-string error) rather than a per-entry map/array. Triggered purely during response decoding.
Common situations: Server returned an error string inline in the results array instead of as a top-level error. Protocol mismatch (RESP3 expected, RESP2 returned, or vice versa) causing the decoder to see a bare scalar. A non-COLLECT reducer's output landing in the same alias. Proxy rewriting the reply.
Related errors
- redis: COLLECT value has type %T, want array of entries
- redis: COLLECT entry %d: %w
- odd-length key/value array of length %d
- invalid total format
- invalid row format
AI-assisted analysis of go-redis/redis@36d97525cd (2026-08-06).
Data as JSON: /data/errors/78dc7dd367c5fee3.json.
Report an issue: GitHub.