{"record":{"id":"7e5263180bf9f828","repo":"vitessio/vitess","slug":"cannot-map-vindex-to-unique-keyspace-id-v","errorCode":null,"errorMessage":"cannot map vindex to unique keyspace id: %v","messagePattern":"cannot map vindex to unique keyspace id: (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"go/vt/vtgate/engine/dml.go","lineNumber":135,"sourceCode":"\tvar destinations []key.ShardDestination\n\tvar err error\n\tswitch vdx := vindex.(type) {\n\tcase vindexes.MultiColumn:\n\t\tdestinations, err = vdx.Map(ctx, vcursor, [][]sqltypes.Value{vindexKey})\n\tcase vindexes.SingleColumn:\n\t\tdestinations, err = vdx.Map(ctx, vcursor, vindexKey)\n\t}\n\n\tif err != nil {\n\t\treturn nil, err\n\t}\n\tswitch ksid := destinations[0].(type) {\n\tcase key.DestinationKeyspaceID:\n\t\treturn ksid, nil\n\tcase key.DestinationNone:\n\t\treturn nil, nil\n\tdefault:\n\t\treturn nil, fmt.Errorf(\"cannot map vindex to unique keyspace id: %v\", destinations[0])\n\t}\n}\n","sourceCodeStart":117,"sourceCodeEnd":138,"githubUrl":"https://github.com/vitessio/vitess/blob/01a25a7d176f94613b8d59d799f438380a8760e4/go/vt/vtgate/engine/dml.go#L117-L138","documentation":"During DML vindex maintenance, resolveKeyspaceID expects the vindex mapping to produce a single unique DestinationKeyspaceID. If the destination is something else (a multi-keyspace-id destination, a range/scatter destination, etc.), the DML cannot identify the exact row's keyspace id and fails with this error.","triggerScenarios":"Executing UPDATE/DELETE whose WHERE clause resolves via a vindex to a non-unique destination (e.g. DestinationKeyRange or DestinationKeyspaceIDs) when deleteVindexEntries/updateVindexEntries call resolveKeyspaceID.","commonSituations":"Updating rows through a non-unique vindex or lookup vindex returning multiple keyspace ids; queries touching multiple shards through a vindex where only one unique ksid is supported.","solutions":["Ensure the WHERE clause uses a unique vindex (primary vindex or unique lookup vindex) so it maps to exactly one keyspace id","Rewrite the query to include equality predicates on the primary vindex columns","If a lookup vindex returns multiple rows, clean up duplicate entries in the lookup table"],"exampleFix":"// before\nUPDATE user SET name='x' WHERE email LIKE '%@a.com'\n// after\nUPDATE user SET name='x' WHERE id = 123 AND email = 'a@b.com'","handlingStrategy":"validation","validationCode":"// ensure WHERE uses the primary/unique vindex with equality predicates\nif !queryUsesUniqueVindexEquality(where) {\n    return errors.New(\"DML must filter on a unique vindex\")\n}","typeGuard":"func isUniqueDestination(dest key.Destination) bool {\n    _, ok := dest.(key.DestinationKeyspaceID)\n    return ok\n}","tryCatchPattern":"err := executeUpdate(q)\nif err != nil && strings.Contains(err.Error(), \"cannot map vindex to unique keyspace id\") {\n    // fall back to a query with an explicit unique-vindex equality predicate\n}","preventionTips":["Always include the primary vindex columns with equality predicates in UPDATE/DELETE WHERE clauses","Check vindex type (unique vs non-unique) before issuing DML through it","Monitor lookup vindexes for duplicate mappings that break uniqueness"],"tags":["vtgate","vindex","dml","sharding"],"backgroundTag":"vindex-mapping-failure","analyzedSha":"01a25a7d176f94613b8d59d799f438380a8760e4","analyzedAt":"2026-09-01T17:28:30.605Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}