vitess.io/vitess@v0.16.2/go/vt/vtorc/logic/keyspace_discovery_test.go (about) 1 /* 2 Copyright 2022 The Vitess Authors. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package logic 18 19 import ( 20 "context" 21 "testing" 22 23 "github.com/stretchr/testify/assert" 24 "github.com/stretchr/testify/require" 25 _ "modernc.org/sqlite" 26 27 topodatapb "vitess.io/vitess/go/vt/proto/topodata" 28 "vitess.io/vitess/go/vt/topo" 29 "vitess.io/vitess/go/vt/topo/memorytopo" 30 "vitess.io/vitess/go/vt/topotools" 31 "vitess.io/vitess/go/vt/vtctl/reparentutil/reparenttestutil" 32 "vitess.io/vitess/go/vt/vtorc/db" 33 "vitess.io/vitess/go/vt/vtorc/inst" 34 ) 35 36 var ( 37 keyspaceDurabilityNone = &topodatapb.Keyspace{ 38 KeyspaceType: topodatapb.KeyspaceType_NORMAL, 39 DurabilityPolicy: "none", 40 } 41 keyspaceDurabilitySemiSync = &topodatapb.Keyspace{ 42 KeyspaceType: topodatapb.KeyspaceType_NORMAL, 43 DurabilityPolicy: "semi_sync", 44 } 45 keyspaceDurabilityTest = &topodatapb.Keyspace{ 46 KeyspaceType: topodatapb.KeyspaceType_NORMAL, 47 DurabilityPolicy: "test", 48 } 49 keyspaceSnapshot = &topodatapb.Keyspace{ 50 KeyspaceType: topodatapb.KeyspaceType_SNAPSHOT, 51 } 52 ) 53 54 func TestRefreshAllKeyspaces(t *testing.T) { 55 // Store the old flags and restore on test completion 56 oldTs := ts 57 oldClustersToWatch := clustersToWatch 58 defer func() { 59 ts = oldTs 60 clustersToWatch = oldClustersToWatch 61 }() 62 63 // Open the vtorc 64 // After the test completes delete everything from the vitess_keyspace table 65 orcDb, err := db.OpenVTOrc() 66 require.NoError(t, err) 67 defer func() { 68 _, err = orcDb.Exec("delete from vitess_keyspace") 69 require.NoError(t, err) 70 }() 71 72 ts = memorytopo.NewServer("zone1") 73 keyspaceNames := []string{"ks1", "ks2", "ks3", "ks4"} 74 keyspaces := []*topodatapb.Keyspace{keyspaceDurabilityNone, keyspaceDurabilitySemiSync, keyspaceSnapshot, keyspaceDurabilityTest} 75 76 // Create 4 keyspaces 77 for i, keyspace := range keyspaces { 78 err := ts.CreateKeyspace(context.Background(), keyspaceNames[i], keyspace) 79 require.NoError(t, err) 80 } 81 82 // Set clusters to watch to only watch ks1 and ks3 83 onlyKs1and3 := []string{"ks1/-", "ks3/-80", "ks3/80-"} 84 clustersToWatch = onlyKs1and3 85 RefreshAllKeyspaces() 86 87 // Verify that we only have ks1 and ks3 in vtorc's db. 88 verifyKeyspaceInfo(t, "ks1", keyspaceDurabilityNone, "") 89 verifyKeyspaceInfo(t, "ks2", nil, "keyspace not found") 90 verifyKeyspaceInfo(t, "ks3", keyspaceSnapshot, "") 91 verifyKeyspaceInfo(t, "ks4", nil, "keyspace not found") 92 93 // Set clusters to watch to watch all keyspaces 94 clustersToWatch = nil 95 // Change the durability policy of ks1 96 reparenttestutil.SetKeyspaceDurability(context.Background(), t, ts, "ks1", "semi_sync") 97 RefreshAllKeyspaces() 98 99 // Verify that all the keyspaces are correctly reloaded 100 verifyKeyspaceInfo(t, "ks1", keyspaceDurabilitySemiSync, "") 101 verifyKeyspaceInfo(t, "ks2", keyspaceDurabilitySemiSync, "") 102 verifyKeyspaceInfo(t, "ks3", keyspaceSnapshot, "") 103 verifyKeyspaceInfo(t, "ks4", keyspaceDurabilityTest, "") 104 } 105 106 func TestRefreshKeyspace(t *testing.T) { 107 // Store the old flags and restore on test completion 108 oldTs := ts 109 defer func() { 110 ts = oldTs 111 }() 112 113 // Open the vtorc 114 // After the test completes delete everything from the vitess_keyspace table 115 orcDb, err := db.OpenVTOrc() 116 require.NoError(t, err) 117 defer func() { 118 _, err = orcDb.Exec("delete from vitess_keyspace") 119 require.NoError(t, err) 120 }() 121 122 tests := []struct { 123 name string 124 keyspaceName string 125 keyspace *topodatapb.Keyspace 126 ts *topo.Server 127 keyspaceWanted *topodatapb.Keyspace 128 err string 129 }{ 130 { 131 name: "Success with keyspaceType and durability", 132 keyspaceName: "ks1", 133 ts: memorytopo.NewServer("zone1"), 134 keyspace: &topodatapb.Keyspace{ 135 KeyspaceType: topodatapb.KeyspaceType_NORMAL, 136 DurabilityPolicy: "semi_sync", 137 }, 138 keyspaceWanted: nil, 139 err: "", 140 }, { 141 name: "Success with keyspaceType and no durability", 142 keyspaceName: "ks2", 143 ts: memorytopo.NewServer("zone1"), 144 keyspace: &topodatapb.Keyspace{ 145 KeyspaceType: topodatapb.KeyspaceType_NORMAL, 146 }, 147 keyspaceWanted: nil, 148 err: "", 149 }, { 150 name: "Success with snapshot keyspaceType", 151 keyspaceName: "ks3", 152 ts: memorytopo.NewServer("zone1"), 153 keyspace: &topodatapb.Keyspace{ 154 KeyspaceType: topodatapb.KeyspaceType_SNAPSHOT, 155 }, 156 keyspaceWanted: nil, 157 err: "", 158 }, { 159 name: "Success with fields that are not stored", 160 keyspaceName: "ks4", 161 ts: memorytopo.NewServer("zone1"), 162 keyspace: &topodatapb.Keyspace{ 163 KeyspaceType: topodatapb.KeyspaceType_NORMAL, 164 DurabilityPolicy: "none", 165 BaseKeyspace: "baseKeyspace", 166 }, 167 keyspaceWanted: &topodatapb.Keyspace{ 168 KeyspaceType: topodatapb.KeyspaceType_NORMAL, 169 DurabilityPolicy: "none", 170 }, 171 err: "", 172 }, { 173 name: "No keyspace found", 174 keyspaceName: "ks5", 175 ts: memorytopo.NewServer("zone1"), 176 keyspace: nil, 177 keyspaceWanted: nil, 178 err: "node doesn't exist: keyspaces/ks5/Keyspace", 179 }, 180 } 181 for _, tt := range tests { 182 t.Run(tt.name, func(t *testing.T) { 183 if tt.keyspaceWanted == nil { 184 tt.keyspaceWanted = tt.keyspace 185 } 186 187 ts = tt.ts 188 if tt.keyspace != nil { 189 err := ts.CreateKeyspace(context.Background(), tt.keyspaceName, tt.keyspace) 190 require.NoError(t, err) 191 } 192 193 err := RefreshKeyspace(tt.keyspaceName) 194 if tt.err != "" { 195 require.EqualError(t, err, tt.err) 196 } else { 197 require.NoError(t, err) 198 verifyKeyspaceInfo(t, tt.keyspaceName, tt.keyspaceWanted, "") 199 } 200 }) 201 } 202 } 203 204 // verifyKeyspaceInfo verifies that the keyspace information read from the vtorc database 205 // is the same as the one provided or reading it gives the same error as expected 206 func verifyKeyspaceInfo(t *testing.T, keyspaceName string, keyspace *topodatapb.Keyspace, errString string) { 207 t.Helper() 208 ksInfo, err := inst.ReadKeyspace(keyspaceName) 209 if errString != "" { 210 assert.EqualError(t, err, errString) 211 } else { 212 assert.Equal(t, keyspaceName, ksInfo.KeyspaceName()) 213 assert.True(t, topotools.KeyspaceEquality(keyspace, ksInfo.Keyspace)) 214 } 215 }