本文整理汇总了Golang中github.com/cockroachdb/cockroach/storage/engine.MVCCScan函数的典型用法代码示例。如果您正苦于以下问题:Golang MVCCScan函数的具体用法?Golang MVCCScan怎么用?Golang MVCCScan使用的例子?那么恭喜您, 这里精选的函数代码示例或许可以为您提供帮助。
在下文中一共展示了MVCCScan函数的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于我们的系统推荐出更棒的Golang代码示例。
示例1: TestRangeSplitMeta
// TestRangeSplitMeta executes various splits (including at meta addressing)
// and checks that all created intents are resolved. This includes both intents
// which are resolved synchronously with EndTransaction and via RPC.
func TestRangeSplitMeta(t *testing.T) {
defer leaktest.AfterTest(t)
s := createTestDB(t)
defer s.Stop()
splitKeys := []roachpb.Key{roachpb.Key("G"), keys.RangeMetaKey(roachpb.Key("F")),
keys.RangeMetaKey(roachpb.Key("K")), keys.RangeMetaKey(roachpb.Key("H"))}
// Execute the consecutive splits.
for _, splitKey := range splitKeys {
log.Infof("starting split at key %q...", splitKey)
if err := s.DB.AdminSplit(splitKey); err != nil {
t.Fatal(err)
}
log.Infof("split at key %q complete", splitKey)
}
if err := util.IsTrueWithin(func() bool {
if _, _, err := engine.MVCCScan(s.Eng, keys.LocalMax, roachpb.KeyMax, 0, roachpb.MaxTimestamp, true, nil); err != nil {
log.Infof("mvcc scan should be clean: %s", err)
return false
}
return true
}, 500*time.Millisecond); err != nil {
t.Error("failed to verify no dangling intents within 500ms")
}
}
开发者ID:rohanahata,项目名称:cockroach,代码行数:30,代码来源:split_test.go
示例2: Scan
// Scan scans the key range specified by start key through end key up
// to some maximum number of results. The last key of the iteration is
// returned with the reply.
func (r *Range) Scan(batch engine.Engine, args proto.ScanRequest) (proto.ScanResponse, []proto.Intent, error) {
var reply proto.ScanResponse
rows, intents, err := engine.MVCCScan(batch, args.Key, args.EndKey, args.MaxResults, args.Timestamp, args.ReadConsistency == proto.CONSISTENT, args.Txn)
reply.Rows = rows
return reply, intents, err
}
开发者ID:routhcr,项目名称:cockroach,代码行数:10,代码来源:range_command.go
示例3: Get
// Get looks up the latest sequence number recorded for this transaction ID.
// The latest entry is that with the highest epoch (and then, highest
// sequence). On a miss, zero is returned for both. If an entry is found and a
// SequenceCacheEntry is provided, it is populated from the found value.
func (sc *SequenceCache) Get(e engine.Engine, id []byte, dest *roachpb.SequenceCacheEntry) (uint32, uint32, error) {
if len(id) == 0 {
return 0, 0, errEmptyTxnID
}
// Pull response from disk and read into reply if available. Sequence
// number sorts in decreasing order, so this gives us the largest entry or
// an entry which isn't ours. To avoid encoding an end key for the scan,
// we just scan and check via a simple prefix check whether we read a
// key for "our" cache id.
prefix := keys.SequenceCacheKeyPrefix(sc.rangeID, id)
kvs, _, err := engine.MVCCScan(e, prefix, sc.max, 1, /* num */
roachpb.ZeroTimestamp, true /* consistent */, nil /* txn */)
if err != nil || len(kvs) == 0 || !bytes.HasPrefix(kvs[0].Key, prefix) {
return 0, 0, err
}
_, epoch, seq, err := decodeSequenceCacheKey(kvs[0].Key, sc.scratchBuf[:0])
if err != nil {
return 0, 0, err
}
if dest != nil {
dest.Reset()
// Caller wants to have the unmarshaled value.
if err := kvs[0].Value.GetProto(dest); err != nil {
return 0, 0, err
}
}
return epoch, seq, nil
}
开发者ID:billhongs,项目名称:cockroach,代码行数:33,代码来源:sequence_cache.go
示例4: TestRangeSplitsWithWritePressure
// TestRangeSplitsWithWritePressure sets the zone config max bytes for
// a range to 256K and writes data until there are five ranges.
func TestRangeSplitsWithWritePressure(t *testing.T) {
defer leaktest.AfterTest(t)
s := createTestDB(t)
defer s.Stop()
setTestRetryOptions()
// Rewrite a zone config with low max bytes.
zoneConfig := &proto.ZoneConfig{
ReplicaAttrs: []proto.Attributes{
{},
{},
{},
},
RangeMinBytes: 1 << 8,
RangeMaxBytes: 1 << 18,
}
if err := s.DB.Put(keys.MakeKey(keys.ConfigZonePrefix, proto.KeyMin), zoneConfig); err != nil {
t.Fatal(err)
}
// Start test writer write about a 32K/key so there aren't too many writes necessary to split 64K range.
done := make(chan struct{})
var wg sync.WaitGroup
wg.Add(1)
go startTestWriter(s.DB, int64(0), 1<<15, &wg, nil, nil, done, t)
// Check that we split 5 times in allotted time.
if err := util.IsTrueWithin(func() bool {
// Scan the txn records.
rows, err := s.DB.Scan(keys.Meta2Prefix, keys.MetaMax, 0)
if err != nil {
t.Fatalf("failed to scan meta2 keys: %s", err)
}
return len(rows) >= 5
}, 6*time.Second); err != nil {
t.Errorf("failed to split 5 times: %s", err)
}
close(done)
wg.Wait()
// This write pressure test often causes splits while resolve
// intents are in flight, causing them to fail with range key
// mismatch errors. However, LocalSender should retry in these
// cases. Check here via MVCC scan that there are no dangling write
// intents. We do this using an IsTrueWithin construct to account
// for timing of finishing the test writer and a possibly-ongoing
// asynchronous split.
if err := util.IsTrueWithin(func() bool {
if _, _, err := engine.MVCCScan(s.Eng, keys.LocalMax, proto.KeyMax, 0, proto.MaxTimestamp, true, nil); err != nil {
log.Infof("mvcc scan should be clean: %s", err)
return false
}
return true
}, 500*time.Millisecond); err != nil {
t.Error("failed to verify no dangling intents within 500ms")
}
}
开发者ID:Hellblazer,项目名称:cockroach,代码行数:59,代码来源:split_test.go
示例5: TestRangeSplitsWithWritePressure
// TestRangeSplitsWithWritePressure sets the zone config max bytes for
// a range to 256K and writes data until there are five ranges.
func TestRangeSplitsWithWritePressure(t *testing.T) {
defer leaktest.AfterTest(t)()
// Override default zone config.
cfg := config.DefaultZoneConfig()
cfg.RangeMaxBytes = 1 << 18
defer config.TestingSetDefaultZoneConfig(cfg)()
dbCtx := client.DefaultDBContext()
dbCtx.TxnRetryOptions = retry.Options{
InitialBackoff: 1 * time.Millisecond,
MaxBackoff: 10 * time.Millisecond,
Multiplier: 2,
}
s, _ := createTestDBWithContext(t, dbCtx)
// This is purely to silence log spam.
config.TestingSetupZoneConfigHook(s.Stopper)
defer s.Stop()
// Start test writer write about a 32K/key so there aren't too many writes necessary to split 64K range.
done := make(chan struct{})
var wg sync.WaitGroup
wg.Add(1)
go startTestWriter(s.DB, int64(0), 1<<15, &wg, nil, nil, done, t)
// Check that we split 5 times in allotted time.
util.SucceedsSoon(t, func() error {
// Scan the txn records.
rows, err := s.DB.Scan(keys.Meta2Prefix, keys.MetaMax, 0)
if err != nil {
return util.Errorf("failed to scan meta2 keys: %s", err)
}
if lr := len(rows); lr < 5 {
return util.Errorf("expected >= 5 scans; got %d", lr)
}
return nil
})
close(done)
wg.Wait()
// This write pressure test often causes splits while resolve
// intents are in flight, causing them to fail with range key
// mismatch errors. However, LocalSender should retry in these
// cases. Check here via MVCC scan that there are no dangling write
// intents. We do this using a SucceedsSoon construct to account
// for timing of finishing the test writer and a possibly-ongoing
// asynchronous split.
util.SucceedsSoon(t, func() error {
if _, _, err := engine.MVCCScan(context.Background(), s.Eng, keys.LocalMax, roachpb.KeyMax, 0, hlc.MaxTimestamp, true, nil); err != nil {
return util.Errorf("failed to verify no dangling intents: %s", err)
}
return nil
})
}
开发者ID:csdigi,项目名称:cockroach,代码行数:55,代码来源:split_test.go
示例6: TestRangeSplitsWithWritePressure
// TestRangeSplitsWithWritePressure sets the zone config max bytes for
// a range to 256K and writes data until there are five ranges.
func TestRangeSplitsWithWritePressure(t *testing.T) {
defer leaktest.AfterTest(t)
// Override default zone config.
previousMaxBytes := config.DefaultZoneConfig.RangeMaxBytes
config.DefaultZoneConfig.RangeMaxBytes = 1 << 18
defer func() { config.DefaultZoneConfig.RangeMaxBytes = previousMaxBytes }()
s := createTestDB(t)
// This is purely to silence log spam.
config.TestingSetupZoneConfigHook(s.Stopper)
defer s.Stop()
setTestRetryOptions()
// Start test writer write about a 32K/key so there aren't too many writes necessary to split 64K range.
done := make(chan struct{})
var wg sync.WaitGroup
wg.Add(1)
go startTestWriter(s.DB, int64(0), 1<<15, &wg, nil, nil, done, t)
// Check that we split 5 times in allotted time.
if err := util.IsTrueWithin(func() bool {
// Scan the txn records.
rows, err := s.DB.Scan(keys.Meta2Prefix, keys.MetaMax, 0)
if err != nil {
t.Fatalf("failed to scan meta2 keys: %s", err)
}
return len(rows) >= 5
}, 6*time.Second); err != nil {
t.Errorf("failed to split 5 times: %s", err)
}
close(done)
wg.Wait()
// This write pressure test often causes splits while resolve
// intents are in flight, causing them to fail with range key
// mismatch errors. However, LocalSender should retry in these
// cases. Check here via MVCC scan that there are no dangling write
// intents. We do this using an IsTrueWithin construct to account
// for timing of finishing the test writer and a possibly-ongoing
// asynchronous split.
if err := util.IsTrueWithin(func() bool {
if _, _, err := engine.MVCCScan(s.Eng, keys.LocalMax, roachpb.KeyMax, 0, roachpb.MaxTimestamp, true, nil); err != nil {
log.Infof("mvcc scan should be clean: %s", err)
return false
}
return true
}, cleanMVCCScanTimeout); err != nil {
t.Error("failed to verify no dangling intents within 500ms")
}
}
开发者ID:Ralkage,项目名称:cockroach,代码行数:52,代码来源:split_test.go
示例7: getActualData
// getActualData returns the actual value of all time series keys in the
// underlying engine. Data is returned as a map of strings to roachpb.Values.
func (tm *testModel) getActualData() map[string]roachpb.Value {
// Scan over all TS Keys stored in the engine
startKey := keys.TimeseriesPrefix
endKey := startKey.PrefixEnd()
keyValues, _, err := engine.MVCCScan(context.Background(), tm.Eng, startKey, endKey, 0, tm.Clock.Now(), true, nil)
if err != nil {
tm.t.Fatalf("error scanning TS data from engine: %s", err.Error())
}
kvMap := make(map[string]roachpb.Value)
for _, kv := range keyValues {
kvMap[string(kv.Key)] = kv.Value
}
return kvMap
}
开发者ID:chzyer-dev,项目名称:cockroach,代码行数:18,代码来源:db_test.go
示例8: getActualData
// getActualData returns the actual value of all time series keys in the
// underlying engine. Data is returned as a map of strings to proto.Values.
func (tm *testModel) getActualData() map[string]*proto.Value {
// Scan over all TS Keys stored in the engine
startKey := keyDataPrefix
endKey := keyDataPrefix.PrefixEnd()
keyValues, _, err := engine.MVCCScan(tm.Eng, startKey, endKey, 0, tm.Clock.Now(), true, nil)
if err != nil {
tm.t.Fatalf("error scanning TS data from engine: %s", err.Error())
}
kvMap := make(map[string]*proto.Value)
for _, kv := range keyValues {
val := kv.Value
kvMap[string(kv.Key)] = &val
}
return kvMap
}
开发者ID:husttom,项目名称:cockroach,代码行数:19,代码来源:db_test.go
示例9: loadConfigMap
// loadConfigMap scans the config entries under keyPrefix and
// instantiates/returns a config map and its sha256 hash. Prefix
// configuration maps include accounting, permissions, and zones.
func loadConfigMap(eng engine.Engine, keyPrefix proto.Key, configI interface{}) (PrefixConfigMap, []byte, error) {
// TODO(tschottdorf): Currently this does not handle intents well.
kvs, _, err := engine.MVCCScan(eng, keyPrefix, keyPrefix.PrefixEnd(), 0, proto.MaxTimestamp, true /* consistent */, nil)
if err != nil {
return nil, nil, err
}
var configs []*PrefixConfig
sha := sha256.New()
for _, kv := range kvs {
// Instantiate an instance of the config type by unmarshalling
// proto encoded config from the Value into a new instance of configI.
config := reflect.New(reflect.TypeOf(configI)).Interface().(gogoproto.Message)
if err := gogoproto.Unmarshal(kv.Value.Bytes, config); err != nil {
return nil, nil, util.Errorf("unable to unmarshal config key %s: %s", string(kv.Key), err)
}
configs = append(configs, &PrefixConfig{Prefix: bytes.TrimPrefix(kv.Key, keyPrefix), Config: config})
sha.Write(kv.Value.Bytes)
}
m, err := NewPrefixConfigMap(configs)
return m, sha.Sum(nil), err
}
开发者ID:huaxling,项目名称:cockroach,代码行数:24,代码来源:range.go
示例10: TestBootstrapCluster
// TestBootstrapCluster verifies the results of bootstrapping a
// cluster. Uses an in memory engine.
func TestBootstrapCluster(t *testing.T) {
defer leaktest.AfterTest(t)()
stopper := stop.NewStopper()
defer stopper.Stop()
e := engine.NewInMem(roachpb.Attributes{}, 1<<20, stopper)
if _, err := bootstrapCluster([]engine.Engine{e}, kv.NewTxnMetrics(metric.NewRegistry())); err != nil {
t.Fatal(err)
}
// Scan the complete contents of the local database directly from the engine.
rows, _, err := engine.MVCCScan(context.Background(), e, keys.LocalMax, roachpb.KeyMax, 0, roachpb.MaxTimestamp, true, nil)
if err != nil {
t.Fatal(err)
}
var foundKeys keySlice
for _, kv := range rows {
foundKeys = append(foundKeys, kv.Key)
}
var expectedKeys = keySlice{
testutils.MakeKey(roachpb.Key("\x02"), roachpb.KeyMax),
testutils.MakeKey(roachpb.Key("\x03"), roachpb.KeyMax),
roachpb.Key("\x04node-idgen"),
roachpb.Key("\x04range-tree-root"),
roachpb.Key("\x04store-idgen"),
}
// Add the initial keys for sql.
for _, kv := range GetBootstrapSchema().GetInitialValues() {
expectedKeys = append(expectedKeys, kv.Key)
}
// Resort the list. The sql values are not sorted.
sort.Sort(expectedKeys)
if !reflect.DeepEqual(foundKeys, expectedKeys) {
t.Errorf("expected keys mismatch:\n%s\n -- vs. -- \n\n%s",
formatKeys(foundKeys), formatKeys(expectedKeys))
}
// TODO(spencer): check values.
}
开发者ID:GitGoldie,项目名称:cockroach,代码行数:41,代码来源:node_test.go
示例11: TestRangeSplitMeta
// TestRangeSplitMeta executes various splits (including at meta addressing)
// and checks that all created intents are resolved. This includes both intents
// which are resolved synchronously with EndTransaction and via RPC.
func TestRangeSplitMeta(t *testing.T) {
defer leaktest.AfterTest(t)()
s := createTestDB(t)
defer s.Stop()
splitKeys := []roachpb.RKey{roachpb.RKey("G"), mustMeta(roachpb.RKey("F")),
mustMeta(roachpb.RKey("K")), mustMeta(roachpb.RKey("H"))}
// Execute the consecutive splits.
for _, splitKey := range splitKeys {
log.Infof("starting split at key %q...", splitKey)
if pErr := s.DB.AdminSplit(roachpb.Key(splitKey)); pErr != nil {
t.Fatal(pErr)
}
log.Infof("split at key %q complete", splitKey)
}
util.SucceedsSoon(t, func() error {
if _, _, err := engine.MVCCScan(s.Eng, keys.LocalMax, roachpb.KeyMax, 0, roachpb.MaxTimestamp, true, nil); err != nil {
return util.Errorf("failed to verify no dangling intents: %s", err)
}
return nil
})
}
开发者ID:petermattis,项目名称:cockroach,代码行数:27,代码来源:split_test.go
示例12: GetAllTransactionID
// GetAllTransactionID returns all the key-value pairs for the given transaction ID from
// the engine.
func (sc *SequenceCache) GetAllTransactionID(e engine.Engine, id []byte) ([]roachpb.KeyValue, error) {
prefix := keys.SequenceCacheKeyPrefix(sc.rangeID, id)
kvs, _, err := engine.MVCCScan(e, prefix, prefix.PrefixEnd(), 0, /* max */
roachpb.ZeroTimestamp, true /* consistent */, nil /* txn */)
return kvs, err
}
开发者ID:billhongs,项目名称:cockroach,代码行数:8,代码来源:sequence_cache.go
示例13: InternalRangeLookup
// InternalRangeLookup is used to look up RangeDescriptors - a RangeDescriptor
// is a metadata structure which describes the key range and replica locations
// of a distinct range in the cluster.
//
// RangeDescriptors are stored as values in the cockroach cluster's key-value
// store. However, they are always stored using special "Range Metadata keys",
// which are "ordinary" keys with a special prefix prepended. The Range Metadata
// Key for an ordinary key can be generated with the `keys.RangeMetaKey(key)`
// function. The RangeDescriptor for the range which contains a given key can be
// retrieved by generating its Range Metadata Key and dispatching it to
// InternalRangeLookup.
//
// Note that the Range Metadata Key sent to InternalRangeLookup is NOT the key
// at which the desired RangeDescriptor is stored. Instead, this method returns
// the RangeDescriptor stored at the _lowest_ existing key which is _greater_
// than the given key. The returned RangeDescriptor will thus contain the
// ordinary key which was originally used to generate the Range Metadata Key
// sent to InternalRangeLookup.
//
// The "Range Metadata Key" for a range is built by appending the end key of
// the range to the meta[12] prefix because the RocksDB iterator only supports
// a Seek() interface which acts as a Ceil(). Using the start key of the range
// would cause Seek() to find the key after the meta indexing record we're
// looking for, which would result in having to back the iterator up, an option
// which is both less efficient and not available in all cases.
//
// This method has an important optimization: instead of just returning the
// request RangeDescriptor, it also returns a slice of additional range
// descriptors immediately consecutive to the desired RangeDescriptor. This is
// intended to serve as a sort of caching pre-fetch, so that the requesting
// nodes can aggressively cache RangeDescriptors which are likely to be desired
// by their current workload.
func (r *Range) InternalRangeLookup(batch engine.Engine, args *proto.InternalRangeLookupRequest, reply *proto.InternalRangeLookupResponse) []proto.Intent {
if err := keys.ValidateRangeMetaKey(args.Key); err != nil {
reply.SetGoError(err)
return nil
}
rangeCount := int64(args.MaxRanges)
if rangeCount < 1 {
reply.SetGoError(util.Errorf(
"Range lookup specified invalid maximum range count %d: must be > 0", rangeCount))
return nil
}
if args.IgnoreIntents {
rangeCount = 1 // simplify lookup because we may have to retry to read new
}
// We want to search for the metadata key just greater than args.Key. Scan
// for both the requested key and the keys immediately afterwards, up to
// MaxRanges.
startKey, endKey := keys.MetaScanBounds(args.Key)
// Scan inconsistently. Any intents encountered are bundled up, but other-
// wise ignored.
kvs, intents, err := engine.MVCCScan(batch, startKey, endKey, rangeCount,
args.Timestamp, false /* !consistent */, args.Txn)
if err != nil {
// An error here would likely amount to something seriously going
// wrong.
reply.SetGoError(err)
return nil
}
if args.IgnoreIntents && len(intents) > 0 {
// NOTE (subtle): in general, we want to try to clean up dangling
// intents on meta records. However, if we're in the process of
// cleaning up a dangling intent on a meta record by pushing the
// transaction, we don't want to create an infinite loop:
//
// intent! -> push-txn -> range-lookup -> intent! -> etc...
//
// Instead we want:
//
// intent! -> push-txn -> range-lookup -> ignore intent, return old/new ranges
//
// On the range-lookup from a push transaction, we therefore
// want to suppress WriteIntentErrors and return a value
// anyway. But which value? We don't know whether the range
// update succeeded or failed, but if we don't return the
// correct range descriptor we may not be able to find the
// transaction to push. Since we cannot know the correct answer,
// we choose randomly between the pre- and post- transaction
// values. If we guess wrong, the client will try again and get
// the other value (within a few tries).
if rand.Intn(2) == 0 {
key, txn := intents[0].Key, &intents[0].Txn
val, _, err := engine.MVCCGet(batch, key, txn.Timestamp, true, txn)
if err != nil {
reply.SetGoError(err)
return nil
}
kvs = []proto.KeyValue{{Key: key, Value: *val}}
}
}
if len(kvs) == 0 {
// No matching results were returned from the scan. This could
// indicate a very bad system error, but for now we will just
// treat it as a retryable Key Mismatch error.
err := proto.NewRangeKeyMismatchError(args.Key, args.EndKey, r.Desc())
reply.SetGoError(err)
//.........这里部分代码省略.........
开发者ID:simonzhangsm,项目名称:cockroach,代码行数:101,代码来源:range_command.go
示例14: Scan
// Scan scans the key range specified by start key through end key up
// to some maximum number of results. The last key of the iteration is
// returned with the reply.
func (r *Range) Scan(batch engine.Engine, args *proto.ScanRequest, reply *proto.ScanResponse) []proto.Intent {
kvs, intents, err := engine.MVCCScan(batch, args.Key, args.EndKey, args.MaxResults, args.Timestamp, args.ReadConsistency == proto.CONSISTENT, args.Txn)
reply.Rows = kvs
reply.SetGoError(err)
return intents
}
开发者ID:simonzhangsm,项目名称:cockroach,代码行数:9,代码来源:range_command.go
示例15: TestUpdateRangeAddressing
// TestUpdateRangeAddressing verifies range addressing records are
// correctly updated on creation of new range descriptors.
func TestUpdateRangeAddressing(t *testing.T) {
defer leaktest.AfterTest(t)
store, _, stopper := createTestStore(t)
defer stopper.Stop()
// When split is false, merging treats the right range as the merged
// range. With merging, expNewLeft indicates the addressing keys we
// expect to be removed.
testCases := []struct {
split bool
leftStart, leftEnd roachpb.RKey
rightStart, rightEnd roachpb.RKey
leftExpNew, rightExpNew [][]byte
}{
// Start out with whole range.
{false, roachpb.RKeyMin, roachpb.RKeyMax, roachpb.RKeyMin, roachpb.RKeyMax,
[][]byte{}, [][]byte{meta1Key(roachpb.RKeyMax), meta2Key(roachpb.RKeyMax)}},
// Split KeyMin-KeyMax at key "a".
{true, roachpb.RKeyMin, roachpb.RKey("a"), roachpb.RKey("a"), roachpb.RKeyMax,
[][]byte{meta1Key(roachpb.RKeyMax), meta2Key(roachpb.RKey("a"))}, [][]byte{meta2Key(roachpb.RKeyMax)}},
// Split "a"-KeyMax at key "z".
{true, roachpb.RKey("a"), roachpb.RKey("z"), roachpb.RKey("z"), roachpb.RKeyMax,
[][]byte{meta2Key(roachpb.RKey("z"))}, [][]byte{meta2Key(roachpb.RKeyMax)}},
// Split "a"-"z" at key "m".
{true, roachpb.RKey("a"), roachpb.RKey("m"), roachpb.RKey("m"), roachpb.RKey("z"),
[][]byte{meta2Key(roachpb.RKey("m"))}, [][]byte{meta2Key(roachpb.RKey("z"))}},
// Split KeyMin-"a" at meta2(m).
{true, roachpb.RKeyMin, metaKey(roachpb.RKey("m")), metaKey(roachpb.RKey("m")), roachpb.RKey("a"),
[][]byte{meta1Key(roachpb.RKey("m"))}, [][]byte{meta1Key(roachpb.RKeyMax), meta2Key(roachpb.RKey("a"))}},
// Split meta2(m)-"a" at meta2(z).
{true, metaKey(roachpb.RKey("m")), metaKey(roachpb.RKey("z")), metaKey(roachpb.RKey("z")), roachpb.RKey("a"),
[][]byte{meta1Key(roachpb.RKey("z"))}, [][]byte{meta1Key(roachpb.RKeyMax), meta2Key(roachpb.RKey("a"))}},
// Split meta2(m)-meta2(z) at meta2(r).
{true, metaKey(roachpb.RKey("m")), metaKey(roachpb.RKey("r")), metaKey(roachpb.RKey("r")), metaKey(roachpb.RKey("z")),
[][]byte{meta1Key(roachpb.RKey("r"))}, [][]byte{meta1Key(roachpb.RKey("z"))}},
// Now, merge all of our splits backwards...
// Merge meta2(m)-meta2(z).
{false, metaKey(roachpb.RKey("m")), metaKey(roachpb.RKey("r")), metaKey(roachpb.RKey("m")), metaKey(roachpb.RKey("z")),
[][]byte{meta1Key(roachpb.RKey("r"))}, [][]byte{meta1Key(roachpb.RKey("z"))}},
// Merge meta2(m)-"a".
{false, metaKey(roachpb.RKey("m")), metaKey(roachpb.RKey("z")), metaKey(roachpb.RKey("m")), roachpb.RKey("a"),
[][]byte{meta1Key(roachpb.RKey("z"))}, [][]byte{meta1Key(roachpb.RKeyMax), meta2Key(roachpb.RKey("a"))}},
// Merge KeyMin-"a".
{false, roachpb.RKeyMin, metaKey(roachpb.RKey("m")), roachpb.RKeyMin, roachpb.RKey("a"),
[][]byte{meta1Key(roachpb.RKey("m"))}, [][]byte{meta1Key(roachpb.RKeyMax), meta2Key(roachpb.RKey("a"))}},
// Merge "a"-"z".
{false, roachpb.RKey("a"), roachpb.RKey("m"), roachpb.RKey("a"), roachpb.RKey("z"),
[][]byte{meta2Key(roachpb.RKey("m"))}, [][]byte{meta2Key(roachpb.RKey("z"))}},
// Merge "a"-KeyMax.
{false, roachpb.RKey("a"), roachpb.RKey("z"), roachpb.RKey("a"), roachpb.RKeyMax,
[][]byte{meta2Key(roachpb.RKey("z"))}, [][]byte{meta2Key(roachpb.RKeyMax)}},
// Merge KeyMin-KeyMax.
{false, roachpb.RKeyMin, roachpb.RKey("a"), roachpb.RKeyMin, roachpb.RKeyMax,
[][]byte{meta2Key(roachpb.RKey("a"))}, [][]byte{meta1Key(roachpb.RKeyMax), meta2Key(roachpb.RKeyMax)}},
}
expMetas := metaSlice{}
for i, test := range testCases {
left := &roachpb.RangeDescriptor{RangeID: roachpb.RangeID(i * 2), StartKey: test.leftStart, EndKey: test.leftEnd}
right := &roachpb.RangeDescriptor{RangeID: roachpb.RangeID(i*2 + 1), StartKey: test.rightStart, EndKey: test.rightEnd}
b := &client.Batch{}
if test.split {
if err := splitRangeAddressing(b, left, right); err != nil {
t.Fatal(err)
}
} else {
if err := mergeRangeAddressing(b, left, right); err != nil {
t.Fatal(err)
}
}
if err := store.DB().Run(b); err != nil {
t.Fatal(err)
}
// Scan meta keys directly from engine.
kvs, _, err := engine.MVCCScan(store.Engine(), keys.MetaPrefix, keys.MetaMax, 0, roachpb.MaxTimestamp, true, nil)
if err != nil {
t.Fatal(err)
}
metas := metaSlice{}
for _, kv := range kvs {
scannedDesc := &roachpb.RangeDescriptor{}
if err := proto.Unmarshal(kv.Value.GetRawBytes(), scannedDesc); err != nil {
t.Fatal(err)
}
metas = append(metas, metaRecord{key: kv.Key, desc: scannedDesc})
}
// Continue to build up the expected metas slice, replacing any earlier
// version of same key.
addOrRemoveNew := func(keys [][]byte, desc *roachpb.RangeDescriptor, add bool) {
for _, n := range keys {
found := -1
for i := range expMetas {
if expMetas[i].key.Equal(roachpb.Key(n)) {
found = i
expMetas[i].desc = desc
//.........这里部分代码省略.........
开发者ID:nporsche,项目名称:cockroach,代码行数:101,代码来源:addressing_test.go
注:本文中的github.com/cockroachdb/cockroach/storage/engine.MVCCScan函数示例整理自Github/MSDocs等源码及文档管理平台,相关代码片段筛选自各路编程大神贡献的开源项目,源码版权归原作者所有,传播和使用请参考对应项目的License;未经允许,请勿转载。 |
请发表评论