github.com/hasnat/dolt/go@v0.0.0-20210628190320-9eb5d843fbb7/libraries/doltcore/merge/integration_test.go (about) 1 // Copyright 2021 Dolthub, Inc. 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 merge_test 16 17 import ( 18 "context" 19 "testing" 20 21 "github.com/dolthub/go-mysql-server/sql" 22 "github.com/stretchr/testify/assert" 23 "github.com/stretchr/testify/require" 24 25 cmd "github.com/dolthub/dolt/go/cmd/dolt/commands" 26 "github.com/dolthub/dolt/go/cmd/dolt/commands/cnfcmds" 27 dtu "github.com/dolthub/dolt/go/libraries/doltcore/dtestutils" 28 "github.com/dolthub/dolt/go/libraries/doltcore/sqle" 29 ) 30 31 func TestMerge(t *testing.T) { 32 33 setupCommon := []testCommand{ 34 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE test (pk int PRIMARY KEY, c0 int);"}}, 35 {cmd.CommitCmd{}, args{"-am", "created table test"}}, 36 } 37 38 tests := []struct { 39 name string 40 setup []testCommand 41 42 query string 43 expected []sql.Row 44 }{ 45 { 46 name: "smoke test", 47 query: "SELECT * FROM test;", 48 }, 49 { 50 name: "fast-forward merge", 51 setup: []testCommand{ 52 {cmd.CheckoutCmd{}, args{"-b", "other"}}, 53 {cmd.SqlCmd{}, args{"-q", "INSERT INTO test VALUES (1,1),(2,2);"}}, 54 {cmd.CommitCmd{}, args{"-am", "added rows on other"}}, 55 {cmd.CheckoutCmd{}, args{"master"}}, 56 {cmd.MergeCmd{}, args{"other"}}, 57 }, 58 query: "SELECT * FROM test", 59 expected: []sql.Row{ 60 {int32(1), int32(1)}, 61 {int32(2), int32(2)}, 62 }, 63 }, 64 { 65 name: "three-way merge", 66 setup: []testCommand{ 67 {cmd.BranchCmd{}, args{"other"}}, 68 {cmd.SqlCmd{}, args{"-q", "INSERT INTO test VALUES (11,11),(22,22);"}}, 69 {cmd.CommitCmd{}, args{"-am", "added rows on master"}}, 70 {cmd.CheckoutCmd{}, args{"other"}}, 71 {cmd.SqlCmd{}, args{"-q", "INSERT INTO test VALUES (1,1),(2,2);"}}, 72 {cmd.CommitCmd{}, args{"-am", "added rows on other"}}, 73 {cmd.CheckoutCmd{}, args{"master"}}, 74 {cmd.MergeCmd{}, args{"other"}}, 75 }, 76 query: "SELECT * FROM test", 77 expected: []sql.Row{ 78 {int32(1), int32(1)}, 79 {int32(2), int32(2)}, 80 {int32(11), int32(11)}, 81 {int32(22), int32(22)}, 82 }, 83 }, 84 { 85 name: "create the same table schema, with different row data, on two branches", 86 setup: []testCommand{ 87 {cmd.BranchCmd{}, args{"other"}}, 88 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE quiz (pk varchar(120) primary key);"}}, 89 {cmd.SqlCmd{}, args{"-q", "INSERT INTO quiz VALUES ('a'),('b'),('c');"}}, 90 {cmd.CommitCmd{}, args{"-am", "added rows on master"}}, 91 {cmd.CheckoutCmd{}, args{"other"}}, 92 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE quiz (pk varchar(120) primary key);"}}, 93 {cmd.SqlCmd{}, args{"-q", "INSERT INTO quiz VALUES ('x'),('y'),('z');"}}, 94 {cmd.CommitCmd{}, args{"-am", "added rows on other"}}, 95 {cmd.CheckoutCmd{}, args{"master"}}, 96 {cmd.MergeCmd{}, args{"other"}}, 97 }, 98 query: "SELECT * FROM quiz ORDER BY pk", 99 expected: []sql.Row{ 100 {"a"}, 101 {"b"}, 102 {"c"}, 103 {"x"}, 104 {"y"}, 105 {"z"}, 106 }, 107 }, 108 } 109 110 for _, test := range tests { 111 t.Run(test.name, func(t *testing.T) { 112 ctx := context.Background() 113 dEnv := dtu.CreateTestEnv() 114 115 for _, tc := range setupCommon { 116 tc.exec(t, ctx, dEnv) 117 } 118 for _, tc := range test.setup { 119 tc.exec(t, ctx, dEnv) 120 } 121 122 root, err := dEnv.WorkingRoot(ctx) 123 require.NoError(t, err) 124 actRows, err := sqle.ExecuteSelect(dEnv, dEnv.DoltDB, root, test.query) 125 require.NoError(t, err) 126 127 require.Equal(t, len(test.expected), len(actRows)) 128 for i := range test.expected { 129 assert.Equal(t, test.expected[i], actRows[i]) 130 } 131 }) 132 } 133 } 134 135 func TestMergeConflicts(t *testing.T) { 136 137 setupCommon := []testCommand{ 138 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE test (pk int PRIMARY KEY, c0 int);"}}, 139 {cmd.CommitCmd{}, args{"-am", "created table test"}}, 140 } 141 142 tests := []struct { 143 name string 144 setup []testCommand 145 146 query string 147 expected []sql.Row 148 }{ 149 { 150 name: "conflict on merge", 151 setup: []testCommand{ 152 {cmd.CheckoutCmd{}, args{"-b", "other"}}, 153 {cmd.SqlCmd{}, args{"-q", "INSERT INTO test VALUES (1,1),(2,2);"}}, 154 {cmd.CommitCmd{}, args{"-am", "added rows on other"}}, 155 {cmd.CheckoutCmd{}, args{"master"}}, 156 {cmd.SqlCmd{}, args{"-q", "INSERT INTO test VALUES (1,11),(2,22);"}}, 157 {cmd.CommitCmd{}, args{"-am", "added the same rows on master"}}, 158 {cmd.MergeCmd{}, args{"other"}}, 159 }, 160 query: "SELECT * FROM dolt_conflicts", 161 expected: []sql.Row{ 162 {"test", uint64(2)}, 163 }, 164 }, 165 { 166 name: "conflict on merge, resolve with ours", 167 setup: []testCommand{ 168 {cmd.CheckoutCmd{}, args{"-b", "other"}}, 169 {cmd.SqlCmd{}, args{"-q", "INSERT INTO test VALUES (1,1),(2,2);"}}, 170 {cmd.CommitCmd{}, args{"-am", "added rows on other"}}, 171 {cmd.CheckoutCmd{}, args{"master"}}, 172 {cmd.SqlCmd{}, args{"-q", "INSERT INTO test VALUES (1,11),(2,22);"}}, 173 {cmd.CommitCmd{}, args{"-am", "added the same rows on master"}}, 174 {cmd.MergeCmd{}, args{"other"}}, 175 {cnfcmds.ResolveCmd{}, args{"--ours", "test"}}, 176 }, 177 query: "SELECT * FROM test", 178 expected: []sql.Row{ 179 {int32(1), int32(11)}, 180 {int32(2), int32(22)}, 181 }, 182 }, 183 { 184 name: "conflict on merge, no table in ancestor", 185 setup: []testCommand{ 186 {cmd.CheckoutCmd{}, args{"-b", "other"}}, 187 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE quiz (pk int PRIMARY KEY, c0 int);"}}, 188 {cmd.SqlCmd{}, args{"-q", "INSERT INTO quiz VALUES (1,1),(2,2);"}}, 189 {cmd.CommitCmd{}, args{"-am", "added rows on other"}}, 190 {cmd.CheckoutCmd{}, args{"master"}}, 191 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE quiz (pk int PRIMARY KEY, c0 int);"}}, 192 {cmd.SqlCmd{}, args{"-q", "INSERT INTO quiz VALUES (1,11),(2,22);"}}, 193 {cmd.CommitCmd{}, args{"-am", "added the same rows on master"}}, 194 {cmd.MergeCmd{}, args{"other"}}, 195 }, 196 query: "SELECT * FROM dolt_conflicts", 197 expected: []sql.Row{ 198 {"quiz", uint64(2)}, 199 }, 200 }, 201 { 202 name: "conflict on merge, no table in ancestor, resolve with theirs", 203 setup: []testCommand{ 204 {cmd.CheckoutCmd{}, args{"-b", "other"}}, 205 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE quiz (pk int PRIMARY KEY, c0 int);"}}, 206 {cmd.SqlCmd{}, args{"-q", "INSERT INTO quiz VALUES (1,1),(2,2);"}}, 207 {cmd.CommitCmd{}, args{"-am", "added rows on other"}}, 208 {cmd.CheckoutCmd{}, args{"master"}}, 209 {cmd.SqlCmd{}, args{"-q", "CREATE TABLE quiz (pk int PRIMARY KEY, c0 int);"}}, 210 {cmd.SqlCmd{}, args{"-q", "INSERT INTO quiz VALUES (1,11),(2,22);"}}, 211 {cmd.CommitCmd{}, args{"-am", "added the same rows on master"}}, 212 {cmd.MergeCmd{}, args{"other"}}, 213 {cnfcmds.ResolveCmd{}, args{"--theirs", "quiz"}}, 214 }, 215 query: "SELECT * FROM quiz", 216 expected: []sql.Row{ 217 {int32(1), int32(1)}, 218 {int32(2), int32(2)}, 219 }, 220 }, 221 } 222 223 for _, test := range tests { 224 t.Run(test.name, func(t *testing.T) { 225 ctx := context.Background() 226 dEnv := dtu.CreateTestEnv() 227 228 for _, tc := range setupCommon { 229 tc.exec(t, ctx, dEnv) 230 } 231 for _, tc := range test.setup { 232 tc.exec(t, ctx, dEnv) 233 } 234 235 root, err := dEnv.WorkingRoot(ctx) 236 require.NoError(t, err) 237 actRows, err := sqle.ExecuteSelect(dEnv, dEnv.DoltDB, root, test.query) 238 require.NoError(t, err) 239 240 require.Equal(t, len(test.expected), len(actRows)) 241 for i := range test.expected { 242 assert.Equal(t, test.expected[i], actRows[i]) 243 } 244 }) 245 } 246 }