vitess.io/vitess@v0.16.2/go/vt/vttablet/tabletmanager/vreplication/journal_test.go (about) 1 /* 2 Copyright 2019 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 vreplication 18 19 import ( 20 "fmt" 21 "testing" 22 23 "context" 24 25 binlogdatapb "vitess.io/vitess/go/vt/proto/binlogdata" 26 qh "vitess.io/vitess/go/vt/vttablet/tabletmanager/vreplication/queryhistory" 27 ) 28 29 func TestJournalOneToOne(t *testing.T) { 30 defer deleteTablet(addTablet(100)) 31 defer deleteTablet(addOtherTablet(101, "other_keyspace", "0")) 32 33 execStatements(t, []string{ 34 "create table t(id int, val varbinary(128), primary key(id))", 35 fmt.Sprintf("create table %s.t(id int, val varbinary(128), primary key(id))", vrepldb), 36 }) 37 defer execStatements(t, []string{ 38 "drop table t", 39 fmt.Sprintf("drop table %s.t", vrepldb), 40 }) 41 env.SchemaEngine.Reload(context.Background()) 42 43 filter := &binlogdatapb.Filter{ 44 Rules: []*binlogdatapb.Rule{{ 45 Match: "t", 46 }}, 47 } 48 bls := &binlogdatapb.BinlogSource{ 49 Keyspace: env.KeyspaceName, 50 Shard: env.ShardName, 51 Filter: filter, 52 OnDdl: binlogdatapb.OnDDLAction_IGNORE, 53 } 54 55 _, firstID := startVReplication(t, bls, "") 56 57 journal := &binlogdatapb.Journal{ 58 Id: 1, 59 MigrationType: binlogdatapb.MigrationType_SHARDS, 60 Participants: []*binlogdatapb.KeyspaceShard{{ 61 Keyspace: "vttest", 62 Shard: "0", 63 }}, 64 ShardGtids: []*binlogdatapb.ShardGtid{{ 65 Keyspace: "other_keyspace", 66 Shard: "0", 67 Gtid: "MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-10", 68 }}, 69 } 70 query := fmt.Sprintf("insert into _vt.resharding_journal(id, db_name, val) values (1, 'vttest', %v)", encodeString(journal.String())) 71 execStatements(t, []string{query}) 72 defer execStatements(t, []string{"delete from _vt.resharding_journal"}) 73 74 expectDBClientQueries(t, qh.Expect( 75 "begin", 76 `/insert into _vt.vreplication.*workflow, source, pos.*values.*'test', 'keyspace:\\"other_keyspace\\" shard:\\"0\\.*'MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-10'`, 77 fmt.Sprintf("delete from _vt.vreplication where id=%d", firstID), 78 "commit", 79 "/update _vt.vreplication set message='Picked source tablet.*", 80 "/update _vt.vreplication set state='Running', message='' where id.*", 81 )) 82 83 // Delete all vreplication streams. There should be only one, but we don't know its id. 84 if _, err := playerEngine.Exec("delete from _vt.vreplication"); err != nil { 85 t.Fatal(err) 86 } 87 expectDeleteQueries(t) 88 } 89 90 func TestJournalOneToMany(t *testing.T) { 91 defer deleteTablet(addTablet(100)) 92 defer deleteTablet(addOtherTablet(101, "other_keyspace", "-80")) 93 defer deleteTablet(addOtherTablet(102, "other_keyspace", "80-")) 94 95 execStatements(t, []string{ 96 "create table t(id int, val varbinary(128), primary key(id))", 97 fmt.Sprintf("create table %s.t(id int, val varbinary(128), primary key(id))", vrepldb), 98 }) 99 defer execStatements(t, []string{ 100 "drop table t", 101 fmt.Sprintf("drop table %s.t", vrepldb), 102 }) 103 env.SchemaEngine.Reload(context.Background()) 104 105 filter := &binlogdatapb.Filter{ 106 Rules: []*binlogdatapb.Rule{{ 107 Match: "t", 108 }}, 109 } 110 bls := &binlogdatapb.BinlogSource{ 111 Keyspace: env.KeyspaceName, 112 Shard: env.ShardName, 113 Filter: filter, 114 OnDdl: binlogdatapb.OnDDLAction_IGNORE, 115 } 116 117 _, firstID := startVReplication(t, bls, "") 118 119 journal := &binlogdatapb.Journal{ 120 Id: 1, 121 MigrationType: binlogdatapb.MigrationType_SHARDS, 122 Participants: []*binlogdatapb.KeyspaceShard{{ 123 Keyspace: "vttest", 124 Shard: "0", 125 }}, 126 ShardGtids: []*binlogdatapb.ShardGtid{{ 127 Keyspace: "other_keyspace", 128 Shard: "-80", 129 Gtid: "MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-5", 130 }, { 131 Keyspace: "other_keyspace", 132 Shard: "80-", 133 Gtid: "MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:5-10", 134 }}, 135 } 136 query := fmt.Sprintf("insert into _vt.resharding_journal(id, db_name, val) values (1, 'vttest', %v)", encodeString(journal.String())) 137 execStatements(t, []string{query}) 138 defer execStatements(t, []string{"delete from _vt.resharding_journal"}) 139 140 expectDBClientQueries(t, qh.Expect( 141 "begin", 142 `/insert into _vt.vreplication.*workflow, source, pos.*values.*'test', 'keyspace:\\"other_keyspace\\" shard:\\"-80\\.*'MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-5'`, 143 `/insert into _vt.vreplication.*workflow, source, pos.*values.*'test', 'keyspace:\\"other_keyspace\\" shard:\\"80-\\.*'MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:5-10'`, 144 fmt.Sprintf("delete from _vt.vreplication where id=%d", firstID), 145 "commit", 146 "/update _vt.vreplication set message='Picked source tablet.*", 147 "/update _vt.vreplication set message='Picked source tablet.*", 148 "/update _vt.vreplication set state='Running', message='' where id.*", 149 "/update _vt.vreplication set state='Running', message='' where id.*", 150 )) 151 152 // Delete all vreplication streams. There should be only one, but we don't know its id. 153 if _, err := playerEngine.Exec("delete from _vt.vreplication"); err != nil { 154 t.Fatal(err) 155 } 156 expectDeleteQueries(t) 157 } 158 159 func TestJournalTablePresent(t *testing.T) { 160 defer deleteTablet(addTablet(100)) 161 defer deleteTablet(addOtherTablet(101, "other_keyspace", "0")) 162 163 execStatements(t, []string{ 164 "create table t(id int, val varbinary(128), primary key(id))", 165 fmt.Sprintf("create table %s.t(id int, val varbinary(128), primary key(id))", vrepldb), 166 }) 167 defer execStatements(t, []string{ 168 "drop table t", 169 fmt.Sprintf("drop table %s.t", vrepldb), 170 }) 171 env.SchemaEngine.Reload(context.Background()) 172 173 filter := &binlogdatapb.Filter{ 174 Rules: []*binlogdatapb.Rule{{ 175 Match: "t", 176 }}, 177 } 178 bls := &binlogdatapb.BinlogSource{ 179 Keyspace: env.KeyspaceName, 180 Shard: env.ShardName, 181 Filter: filter, 182 OnDdl: binlogdatapb.OnDDLAction_IGNORE, 183 } 184 _, firstID := startVReplication(t, bls, "") 185 186 journal := &binlogdatapb.Journal{ 187 Id: 1, 188 MigrationType: binlogdatapb.MigrationType_TABLES, 189 Participants: []*binlogdatapb.KeyspaceShard{{ 190 Keyspace: "vttest", 191 Shard: "0", 192 }}, 193 Tables: []string{"t"}, 194 ShardGtids: []*binlogdatapb.ShardGtid{{ 195 Keyspace: "other_keyspace", 196 Shard: "0", 197 Gtid: "MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-10", 198 }}, 199 } 200 query := fmt.Sprintf("insert into _vt.resharding_journal(id, db_name, val) values (1, 'vttest', %v)", encodeString(journal.String())) 201 execStatements(t, []string{query}) 202 defer execStatements(t, []string{"delete from _vt.resharding_journal"}) 203 204 expectDBClientQueries(t, qh.Expect( 205 "begin", 206 `/insert into _vt.vreplication.*workflow, source, pos.*values.*'test', 'keyspace:\\"other_keyspace\\" shard:\\"0\\.*'MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-10'`, 207 fmt.Sprintf("delete from _vt.vreplication where id=%d", firstID), 208 "commit", 209 "/update _vt.vreplication set message='Picked source tablet.*", 210 "/update _vt.vreplication set state='Running', message='' where id.*", 211 )) 212 213 // Delete all vreplication streams. There should be only one, but we don't know its id. 214 if _, err := playerEngine.Exec("delete from _vt.vreplication"); err != nil { 215 t.Fatal(err) 216 } 217 expectDeleteQueries(t) 218 } 219 220 func TestJournalTableNotPresent(t *testing.T) { 221 defer deleteTablet(addTablet(100)) 222 defer deleteTablet(addOtherTablet(101, "other_keyspace", "0")) 223 224 execStatements(t, []string{ 225 "create table t(id int, val varbinary(128), primary key(id))", 226 fmt.Sprintf("create table %s.t(id int, val varbinary(128), primary key(id))", vrepldb), 227 }) 228 defer execStatements(t, []string{ 229 "drop table t", 230 fmt.Sprintf("drop table %s.t", vrepldb), 231 }) 232 env.SchemaEngine.Reload(context.Background()) 233 234 filter := &binlogdatapb.Filter{ 235 Rules: []*binlogdatapb.Rule{{ 236 Match: "t", 237 }}, 238 } 239 bls := &binlogdatapb.BinlogSource{ 240 Keyspace: env.KeyspaceName, 241 Shard: env.ShardName, 242 Filter: filter, 243 OnDdl: binlogdatapb.OnDDLAction_IGNORE, 244 } 245 246 _, _ = startVReplication(t, bls, "") 247 248 journal := &binlogdatapb.Journal{ 249 Id: 1, 250 MigrationType: binlogdatapb.MigrationType_TABLES, 251 Participants: []*binlogdatapb.KeyspaceShard{{ 252 Keyspace: "vttest", 253 Shard: "0", 254 }}, 255 Tables: []string{"t1"}, 256 ShardGtids: []*binlogdatapb.ShardGtid{{ 257 Keyspace: "other_keyspace", 258 Shard: "0", 259 Gtid: "MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-10", 260 }}, 261 } 262 query := fmt.Sprintf("insert into _vt.resharding_journal(id, db_name, val) values (1, 'vttest', %v)", encodeString(journal.String())) 263 execStatements(t, []string{query}) 264 defer execStatements(t, []string{"delete from _vt.resharding_journal"}) 265 266 // Delete all vreplication streams. There should be only one, but we don't know its id. 267 if _, err := playerEngine.Exec("delete from _vt.vreplication"); err != nil { 268 t.Fatal(err) 269 } 270 expectDeleteQueries(t) 271 } 272 273 func TestJournalTableMixed(t *testing.T) { 274 defer deleteTablet(addTablet(100)) 275 defer deleteTablet(addOtherTablet(101, "other_keyspace", "0")) 276 277 execStatements(t, []string{ 278 "create table t(id int, val varbinary(128), primary key(id))", 279 "create table t1(id int, val varbinary(128), primary key(id))", 280 fmt.Sprintf("create table %s.t(id int, val varbinary(128), primary key(id))", vrepldb), 281 fmt.Sprintf("create table %s.t1(id int, val varbinary(128), primary key(id))", vrepldb), 282 }) 283 defer execStatements(t, []string{ 284 "drop table t", 285 "drop table t1", 286 fmt.Sprintf("drop table %s.t", vrepldb), 287 fmt.Sprintf("drop table %s.t1", vrepldb), 288 }) 289 env.SchemaEngine.Reload(context.Background()) 290 291 filter := &binlogdatapb.Filter{ 292 Rules: []*binlogdatapb.Rule{{ 293 Match: "t", 294 }, { 295 Match: "t1", 296 }}, 297 } 298 bls := &binlogdatapb.BinlogSource{ 299 Keyspace: env.KeyspaceName, 300 Shard: env.ShardName, 301 Filter: filter, 302 OnDdl: binlogdatapb.OnDDLAction_IGNORE, 303 } 304 _, _ = startVReplication(t, bls, "") 305 306 journal := &binlogdatapb.Journal{ 307 Id: 1, 308 MigrationType: binlogdatapb.MigrationType_TABLES, 309 Participants: []*binlogdatapb.KeyspaceShard{{ 310 Keyspace: "vttest", 311 Shard: "0", 312 }}, 313 Tables: []string{"t"}, 314 ShardGtids: []*binlogdatapb.ShardGtid{{ 315 Keyspace: "other_keyspace", 316 Shard: "0", 317 Gtid: "MySQL56/7b04699f-f5e9-11e9-bf88-9cb6d089e1c3:1-10", 318 }}, 319 } 320 query := fmt.Sprintf("insert into _vt.resharding_journal(id, db_name, val) values (1, 'vttest', %v)", encodeString(journal.String())) 321 execStatements(t, []string{query}) 322 defer execStatements(t, []string{"delete from _vt.resharding_journal"}) 323 324 expectDBClientQueries(t, qh.Expect( 325 "/update _vt.vreplication set state='Stopped', message='unable to handle journal event: tables were partially matched' where id", 326 )) 327 328 // Delete all vreplication streams. There should be only one, but we don't know its id. 329 if _, err := playerEngine.Exec("delete from _vt.vreplication"); err != nil { 330 t.Fatal(err) 331 } 332 expectDeleteQueries(t) 333 }