vitessio/vitess · error
Binary.ReverseMap: keyspaceId is nil
Error message
Binary.ReverseMap: keyspaceId is nil
What it means
Returned by Binary.ReverseMap when the input keyspaceId is nil. The binary vindex requires a non-nil keyspace ID to reverse-map back to the source value; nil input indicates an upstream mapping bug or corrupted data.
Source
Thrown at go/vt/vtgate/vindexes/binary.go:105
idBytes, err := vind.Hash(id)
if err != nil {
return out, err
}
out = append(out, key.DestinationKeyspaceID(idBytes))
}
return out, nil
}
func (vind *Binary) Hash(id sqltypes.Value) ([]byte, error) {
return id.ToBytes()
}
// ReverseMap returns the associated ids for the ksids.
func (*Binary) ReverseMap(_ VCursor, ksids [][]byte) ([]sqltypes.Value, error) {
reverseIds := make([]sqltypes.Value, len(ksids))
for rownum, keyspaceID := range ksids {
if keyspaceID == nil {
return nil, errors.New("Binary.ReverseMap: keyspaceId is nil")
}
reverseIds[rownum] = sqltypes.MakeTrusted(sqltypes.VarBinary, keyspaceID)
}
return reverseIds, nil
}
// RangeMap can map ids to key.ShardDestination objects.
func (vind *Binary) RangeMap(ctx context.Context, vcursor VCursor, startId sqltypes.Value, endId sqltypes.Value) ([]key.ShardDestination, error) {
startKsId, err := vind.Hash(startId)
if err != nil {
return nil, err
}
endKsId, err := vind.Hash(endId)
if err != nil {
return nil, err
}
out := []key.ShardDestination{&key.DestinationKeyRange{KeyRange: key.NewKeyRange(startKsId, endKsId)}}
return out, nilView on GitHub (pinned to 01a25a7d17)
Solutions
- Ensure all keyspace IDs passed to ReverseMap are non-nil
- Check upstream code that builds the ksids slice for a path that leaves entries nil
- Use a Owned/lookup vindex flow that always produces valid keyspace IDs for existing rows
Example fix
// before
ksids := [][]byte{nil}
vals, err := vindex.ReverseMap(ctx, vcursor, ksids)
// after
ksids := [][]byte{[]byte("\x80\x00")}
vals, err := vindex.ReverseMap(ctx, vcursor, ksids) Defensive patterns
Strategy: validation
Validate before calling
for i, ksid := range ksids {
if ksid == nil {
return fmt.Errorf("ksid[%d] is nil before ReverseMap", i)
}
} Try / catch
vals, err := vindex.ReverseMap(ctx, vcursor, ksids)
if err != nil && strings.Contains(err.Error(), "keyspaceId is nil") {
// inspect upstream routing data construction
} Prevention
- Never insert nil into [][]byte keyspace ID slices
- Assert keyspace IDs are non-nil where they are produced
- Add table-driven tests covering nil ksid inputs to custom vindexes
When it happens
Trigger: Calling ReverseMap on a Binary vindex with a [][]byte containing at least one nil entry — typically from a lookup/routing path where the keyspace ID was never populated.
Common situations: Routing queries through vindexes with incomplete routing data; bugs in custom code or callers constructing VCursor requests with missing ksids.
Related errors
- cannot map vindex to unique keyspace id: %v
- values %v for column %v does not map to keyspace ids
- values %v for column %v does not map to keyspace ids
- lookup.Update.convert: %v
- UnicodeLooseMD5.Verify: %v
AI-assisted analysis of vitessio/vitess@01a25a7d17 (2026-09-01).
Data as JSON: /api/errors/7b1a694a0ed5e285.
Report an issue: GitHub.