From 0abc0d05a4874500bbfeeb758b9efefeb6dd4249 Mon Sep 17 00:00:00 2001 From: Jiquan Long Date: Wed, 15 May 2024 10:07:34 +0800 Subject: [PATCH] fix: etcd txn exceeds limit due to too many fields (#33040) (#33049) fix: #33038 pr: #33040 --------- Signed-off-by: longjiquan --- internal/metastore/kv/rootcoord/kv_catalog.go | 7 +++++++ internal/metastore/kv/rootcoord/suffix_snapshot.go | 7 +++++-- 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/internal/metastore/kv/rootcoord/kv_catalog.go b/internal/metastore/kv/rootcoord/kv_catalog.go index 117575a7fb..69c34bee98 100644 --- a/internal/metastore/kv/rootcoord/kv_catalog.go +++ b/internal/metastore/kv/rootcoord/kv_catalog.go @@ -4,6 +4,7 @@ import ( "context" "encoding/json" "fmt" + "sort" "github.com/cockroachdb/errors" "github.com/golang/protobuf/proto" @@ -94,6 +95,12 @@ func batchMultiSaveAndRemoveWithPrefix(snapshot kv.SnapShotKV, maxTxnNum int, sa return err } + // avoid a case that the former key is the prefix of the later key. + // for example, `root-coord/fields/collection_id/1` is the prefix of `root-coord/fields/collection_id/100`. + sort.Slice(removals, func(i, j int) bool { + return removals[i] > removals[j] + }) + removeFn := func(partialKeys []string) error { return snapshot.MultiSaveAndRemoveWithPrefix(nil, partialKeys, ts) } diff --git a/internal/metastore/kv/rootcoord/suffix_snapshot.go b/internal/metastore/kv/rootcoord/suffix_snapshot.go index 45171a97ae..832bfd45d9 100644 --- a/internal/metastore/kv/rootcoord/suffix_snapshot.go +++ b/internal/metastore/kv/rootcoord/suffix_snapshot.go @@ -521,14 +521,17 @@ func (ss *SuffixSnapshot) MultiSaveAndRemoveWithPrefix(saves map[string]string, // load each removal, change execution to adding tombstones for _, removal := range removals { - keys, _, err := ss.MetaKv.LoadWithPrefix(removal) + keys, values, err := ss.MetaKv.LoadWithPrefix(removal) if err != nil { log.Warn("SuffixSnapshot MetaKv LoadwithPrefix failed", zap.String("key", removal), zap.Error(err)) return err } // add tombstone to original key and add ts entry - for _, key := range keys { + for idx, key := range keys { + if IsTombstone(values[idx]) { + continue + } key = ss.hideRootPrefix(key) execute[key] = string(SuffixSnapshotTombstone) execute[ss.composeTSKey(key, ts)] = string(SuffixSnapshotTombstone)