github.com/matrixorigin/matrixone@v1.2.0/pkg/logservice/store_metadata_test.go (about) 1 // Copyright 2021 - 2022 Matrix Origin 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package logservice 16 17 import ( 18 "testing" 19 "time" 20 21 "github.com/lni/dragonboat/v4" 22 "github.com/lni/vfs" 23 "github.com/stretchr/testify/assert" 24 "github.com/stretchr/testify/require" 25 26 "github.com/matrixorigin/matrixone/pkg/common/runtime" 27 "github.com/matrixorigin/matrixone/pkg/pb/metadata" 28 ) 29 30 func TestHasMetadataRec(t *testing.T) { 31 cfg := getStoreTestConfig() 32 defer vfs.ReportLeakedFD(cfg.FS, t) 33 s := store{cfg: cfg} 34 s.addMetadata(10, 1) 35 has, err := hasMetadataRec(s.cfg.DataDir, logMetadataFilename, 10, 1, s.cfg.FS) 36 require.NoError(t, err) 37 assert.True(t, has) 38 has, err = hasMetadataRec(s.cfg.DataDir, logMetadataFilename, 1, 1, s.cfg.FS) 39 require.NoError(t, err) 40 assert.False(t, has) 41 } 42 43 func TestAddMetadata(t *testing.T) { 44 cfg := getStoreTestConfig() 45 defer vfs.ReportLeakedFD(cfg.FS, t) 46 s := store{cfg: cfg} 47 require.NoError(t, mkdirAll(s.cfg.DataDir, cfg.FS)) 48 s.addMetadata(10, 1) 49 ss := store{cfg: s.cfg} 50 ss.mu.metadata = metadata.LogStore{} 51 assert.NoError(t, ss.loadMetadata()) 52 require.Equal(t, 1, len(ss.mu.metadata.Shards)) 53 assert.Equal(t, uint64(10), ss.mu.metadata.Shards[0].ShardID) 54 assert.Equal(t, uint64(1), ss.mu.metadata.Shards[0].ReplicaID) 55 } 56 57 func TestAddMetadataRejectDupl(t *testing.T) { 58 cfg := getStoreTestConfig() 59 defer vfs.ReportLeakedFD(cfg.FS, t) 60 s := store{cfg: cfg, runtime: runtime.DefaultRuntime()} 61 require.NoError(t, mkdirAll(s.cfg.DataDir, cfg.FS)) 62 s.addMetadata(10, 1) 63 s.addMetadata(10, 1) 64 s.addMetadata(10, 1) 65 require.Equal(t, 1, len(s.mu.metadata.Shards)) 66 } 67 68 func TestRemoveMetadata(t *testing.T) { 69 cfg := getStoreTestConfig() 70 defer vfs.ReportLeakedFD(cfg.FS, t) 71 s := store{cfg: cfg, runtime: runtime.DefaultRuntime()} 72 require.NoError(t, mkdirAll(s.cfg.DataDir, cfg.FS)) 73 s.addMetadata(10, 1) 74 s.addMetadata(20, 2) 75 s.removeMetadata(10, 1) 76 ss := store{cfg: s.cfg, runtime: runtime.DefaultRuntime()} 77 ss.mu.metadata = metadata.LogStore{} 78 assert.NoError(t, ss.loadMetadata()) 79 require.Equal(t, 1, len(ss.mu.metadata.Shards)) 80 assert.Equal(t, uint64(20), ss.mu.metadata.Shards[0].ShardID) 81 assert.Equal(t, uint64(2), ss.mu.metadata.Shards[0].ReplicaID) 82 } 83 84 func TestStartReplicas(t *testing.T) { 85 cfg := getStoreTestConfig() 86 defer vfs.ReportLeakedFD(cfg.FS, t) 87 require.NoError(t, mkdirAll(cfg.DataDir, cfg.FS)) 88 func() { 89 store, err := getTestStore(cfg, false, nil) 90 require.NoError(t, err) 91 members := make(map[uint64]dragonboat.Target) 92 members[1] = store.id() 93 defer func() { 94 require.NoError(t, store.close()) 95 }() 96 require.NoError(t, store.startReplica(10, 1, members, false)) 97 require.NoError(t, store.startReplica(20, 1, members, false)) 98 }() 99 100 store, err := getTestStore(cfg, false, nil) 101 require.NoError(t, err) 102 defer func() { 103 require.NoError(t, store.close()) 104 }() 105 require.NoError(t, store.loadMetadata()) 106 require.NoError(t, store.startReplicas()) 107 done := false 108 for i := 0; i < 1000; i++ { 109 hb := store.getHeartbeatMessage() 110 if len(hb.Replicas) != 2 { 111 time.Sleep(10 * time.Millisecond) 112 continue 113 } 114 done = true 115 } 116 if !done { 117 t.Fatalf("failed to start all replicas") 118 } 119 }