github.com/hasnat/dolt/go@v0.0.0-20210628190320-9eb5d843fbb7/store/cmd/noms/noms_log_test.go (about) 1 // Copyright 2019 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 // This file incorporates work covered by the following copyright and 16 // permission notice: 17 // 18 // Copyright 2016 Attic Labs, Inc. All rights reserved. 19 // Licensed under the Apache License, version 2.0: 20 // http://www.apache.org/licenses/LICENSE-2.0 21 22 package main 23 24 import ( 25 "context" 26 "testing" 27 28 "github.com/stretchr/testify/assert" 29 "github.com/stretchr/testify/suite" 30 31 "github.com/dolthub/dolt/go/store/d" 32 "github.com/dolthub/dolt/go/store/datas" 33 "github.com/dolthub/dolt/go/store/spec" 34 "github.com/dolthub/dolt/go/store/types" 35 "github.com/dolthub/dolt/go/store/util/clienttest" 36 "github.com/dolthub/dolt/go/store/util/test" 37 ) 38 39 func TestNomsLog(t *testing.T) { 40 suite.Run(t, &nomsLogTestSuite{}) 41 } 42 43 type nomsLogTestSuite struct { 44 clienttest.ClientTestSuite 45 } 46 47 func testCommitInResults(s *nomsLogTestSuite, str string, i int) { 48 sp, err := spec.ForDataset(str) 49 s.NoError(err) 50 defer sp.Close() 51 52 db := sp.GetDatabase(context.Background()) 53 db.CommitValue(context.Background(), sp.GetDataset(context.Background()), types.Float(i)) 54 s.NoError(err) 55 56 commit, ok := sp.GetDataset(context.Background()).MaybeHead() 57 s.True(ok) 58 res, _ := s.MustRun(main, []string{"log", str}) 59 h, err := commit.Hash(db.Format()) 60 s.NoError(err) 61 s.Contains(res, h.String()) 62 } 63 64 func (s *nomsLogTestSuite) TestNomsLog() { 65 sp, err := spec.ForDataset(spec.CreateValueSpecString("nbs", s.DBDir, "dsTest")) 66 s.NoError(err) 67 defer sp.Close() 68 69 sp.GetDatabase(context.Background()) // create the database 70 s.Panics(func() { s.MustRun(main, []string{"log", sp.String()}) }) 71 72 testCommitInResults(s, sp.String(), 1) 73 testCommitInResults(s, sp.String(), 2) 74 } 75 76 func (s *nomsLogTestSuite) TestNomsLogPath() { 77 sp, err := spec.ForPath(spec.CreateValueSpecString("nbs", s.DBDir, "dsTest.value.bar")) 78 s.NoError(err) 79 defer sp.Close() 80 81 db := sp.GetDatabase(context.Background()) 82 ds := sp.GetDataset(context.Background()) 83 for i := 0; i < 3; i++ { 84 data, err := types.NewStruct(db.Format(), "", types.StructData{ 85 "bar": types.Float(i), 86 }) 87 s.NoError(err) 88 ds, err = db.CommitValue(context.Background(), ds, data) 89 s.NoError(err) 90 } 91 92 stdout, stderr := s.MustRun(main, []string{"log", "--show-value", sp.String()}) 93 s.Empty(stderr) 94 test.EqualsIgnoreHashes(s.T(), pathValue, stdout) 95 96 stdout, stderr = s.MustRun(main, []string{"log", sp.String()}) 97 s.Empty(stderr) 98 test.EqualsIgnoreHashes(s.T(), pathDiff, stdout) 99 } 100 101 func addCommit(ds datas.Dataset, v string) (datas.Dataset, error) { 102 return ds.Database().CommitValue(context.Background(), ds, types.String(v)) 103 } 104 105 func addCommitWithValue(ds datas.Dataset, v types.Value) (datas.Dataset, error) { 106 return ds.Database().CommitValue(context.Background(), ds, v) 107 } 108 109 func addBranchedDataset(vrw types.ValueReadWriter, newDs, parentDs datas.Dataset, v string) (datas.Dataset, error) { 110 p, err := types.NewList(context.Background(), vrw, mustHeadRef(parentDs)) 111 112 if err != nil { 113 return datas.Dataset{}, err 114 } 115 116 return newDs.Database().Commit(context.Background(), newDs, types.String(v), datas.CommitOptions{ParentsList: p}) 117 } 118 119 func mergeDatasets(vrw types.ValueReadWriter, ds1, ds2 datas.Dataset, v string) (datas.Dataset, error) { 120 p, err := types.NewList(context.Background(), vrw, mustHeadRef(ds1), mustHeadRef(ds2)) 121 122 if err != nil { 123 return datas.Dataset{}, err 124 } 125 126 return ds1.Database().Commit(context.Background(), ds1, types.String(v), datas.CommitOptions{ParentsList: p}) 127 } 128 129 func mustHead(ds datas.Dataset) types.Struct { 130 s, ok := ds.MaybeHead() 131 if !ok { 132 panic("no head") 133 } 134 135 return s 136 } 137 138 func mustHeadRef(ds datas.Dataset) types.Ref { 139 hr, ok, err := ds.MaybeHeadRef() 140 d.PanicIfError(err) 141 142 if !ok { 143 panic("no head") 144 } 145 146 return hr 147 } 148 149 func mustHeadValue(ds datas.Dataset) types.Value { 150 val, ok, err := ds.MaybeHeadValue() 151 d.PanicIfError(err) 152 153 if !ok { 154 panic("no head") 155 } 156 157 return val 158 } 159 160 func (s *nomsLogTestSuite) TestNArg() { 161 dsName := "nArgTest" 162 163 sp, err := spec.ForDatabase(spec.CreateDatabaseSpecString("nbs", s.DBDir)) 164 s.NoError(err) 165 defer sp.Close() 166 167 db := sp.GetDatabase(context.Background()) 168 ds, err := db.GetDataset(context.Background(), dsName) 169 s.NoError(err) 170 171 ds, err = addCommit(ds, "1") 172 s.NoError(err) 173 h1, err := mustHead(ds).Hash(db.Format()) 174 s.NoError(err) 175 ds, err = addCommit(ds, "2") 176 s.NoError(err) 177 h2, err := mustHead(ds).Hash(db.Format()) 178 s.NoError(err) 179 ds, err = addCommit(ds, "3") 180 s.NoError(err) 181 h3, err := mustHead(ds).Hash(db.Format()) 182 s.NoError(err) 183 184 dsSpec := spec.CreateValueSpecString("nbs", s.DBDir, dsName) 185 res, _ := s.MustRun(main, []string{"log", "-n1", dsSpec}) 186 s.NotContains(res, h1.String()) 187 res, _ = s.MustRun(main, []string{"log", "-n0", dsSpec}) 188 s.Contains(res, h3.String()) 189 s.Contains(res, h2.String()) 190 s.Contains(res, h1.String()) 191 192 vSpec := spec.CreateValueSpecString("nbs", s.DBDir, "#"+h3.String()) 193 res, _ = s.MustRun(main, []string{"log", "-n1", vSpec}) 194 s.NotContains(res, h1.String()) 195 res, _ = s.MustRun(main, []string{"log", "-n0", vSpec}) 196 s.Contains(res, h3.String()) 197 s.Contains(res, h2.String()) 198 s.Contains(res, h1.String()) 199 } 200 201 func (s *nomsLogTestSuite) TestEmptyCommit() { 202 sp, err := spec.ForDatabase(spec.CreateDatabaseSpecString("nbs", s.DBDir)) 203 s.NoError(err) 204 defer sp.Close() 205 206 db := sp.GetDatabase(context.Background()) 207 ds, err := db.GetDataset(context.Background(), "ds1") 208 209 s.NoError(err) 210 211 meta, err := types.NewStruct(db.Format(), "Meta", map[string]types.Value{ 212 "longNameForTest": types.String("Yoo"), 213 "test2": types.String("Hoo"), 214 }) 215 s.NoError(err) 216 ds, err = db.Commit(context.Background(), ds, types.String("1"), datas.CommitOptions{Meta: meta}) 217 s.NoError(err) 218 219 ds, err = db.Commit(context.Background(), ds, types.String("2"), datas.CommitOptions{}) 220 s.NoError(err) 221 222 dsSpec := spec.CreateValueSpecString("nbs", s.DBDir, "ds1") 223 res, _ := s.MustRun(main, []string{"log", dsSpec}) 224 test.EqualsIgnoreHashes(s.T(), metaRes1, res) 225 226 res, _ = s.MustRun(main, []string{"log", "--oneline", dsSpec}) 227 test.EqualsIgnoreHashes(s.T(), metaRes2, res) 228 } 229 230 func (s *nomsLogTestSuite) TestTruncation() { 231 sp, err := spec.ForDatabase(spec.CreateDatabaseSpecString("nbs", s.DBDir)) 232 s.NoError(err) 233 defer sp.Close() 234 db := sp.GetDatabase(context.Background()) 235 236 toNomsList := func(l []string) types.List { 237 nv := []types.Value{} 238 for _, v := range l { 239 nv = append(nv, types.String(v)) 240 } 241 242 lst, err := types.NewList(context.Background(), db, nv...) 243 s.NoError(err) 244 245 return lst 246 } 247 248 t, err := db.GetDataset(context.Background(), "truncate") 249 s.NoError(err) 250 251 t, err = addCommit(t, "the first line") 252 s.NoError(err) 253 254 l := []string{"one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten", "eleven"} 255 _, err = addCommitWithValue(t, toNomsList(l)) 256 s.NoError(err) 257 258 dsSpec := spec.CreateValueSpecString("nbs", s.DBDir, "truncate") 259 res, _ := s.MustRun(main, []string{"log", "--graph", "--show-value", dsSpec}) 260 test.EqualsIgnoreHashes(s.T(), truncRes1, res) 261 res, _ = s.MustRun(main, []string{"log", "--graph", dsSpec}) 262 test.EqualsIgnoreHashes(s.T(), diffTrunc1, res) 263 264 res, _ = s.MustRun(main, []string{"log", "--graph", "--show-value", "--max-lines=-1", dsSpec}) 265 test.EqualsIgnoreHashes(s.T(), truncRes2, res) 266 res, _ = s.MustRun(main, []string{"log", "--graph", "--max-lines=-1", dsSpec}) 267 test.EqualsIgnoreHashes(s.T(), diffTrunc2, res) 268 269 res, _ = s.MustRun(main, []string{"log", "--graph", "--show-value", "--max-lines=0", dsSpec}) 270 test.EqualsIgnoreHashes(s.T(), truncRes3, res) 271 res, _ = s.MustRun(main, []string{"log", "--graph", "--max-lines=0", dsSpec}) 272 test.EqualsIgnoreHashes(s.T(), diffTrunc3, res) 273 } 274 275 func TestBranchlistSplice(t *testing.T) { 276 assert := assert.New(t) 277 bl := branchList{} 278 for i := 0; i < 4; i++ { 279 bl = bl.Splice(0, 0, branch{}) 280 } 281 assert.Equal(4, len(bl)) 282 bl = bl.Splice(3, 1) 283 bl = bl.Splice(0, 1) 284 bl = bl.Splice(1, 1) 285 bl = bl.Splice(0, 1) 286 assert.Zero(len(bl)) 287 288 for i := 0; i < 4; i++ { 289 bl = bl.Splice(0, 0, branch{}) 290 } 291 assert.Equal(4, len(bl)) 292 293 branchesToDelete := []int{1, 2, 3} 294 bl = bl.RemoveBranches(branchesToDelete) 295 assert.Equal(1, len(bl)) 296 } 297 298 const ( 299 truncRes1 = "* p1442asfqnhgv1ebg6rijhl3kb9n4vt3\n| Parent: 4tq9si4tk8n0pead7hovehcbuued45sa\n| [ // 11 items\n| \"one\",\n| \"two\",\n| \"three\",\n| \"four\",\n| \"five\",\n| \"six\",\n| \"seven\",\n| ...\n| \n* 4tq9si4tk8n0pead7hovehcbuued45sa\n| Parent: None\n| \"the first line\"\n" 300 diffTrunc1 = "* p1442asfqnhgv1ebg6rijhl3kb9n4vt3\n| Parent: 4tq9si4tk8n0pead7hovehcbuued45sa\n| - \"the first line\"\n| + [ // 11 items\n| + \"one\",\n| + \"two\",\n| + \"three\",\n| + \"four\",\n| + \"five\",\n| + \"six\",\n| ...\n| \n* 4tq9si4tk8n0pead7hovehcbuued45sa\n| Parent: None\n| \n" 301 302 truncRes2 = "* p1442asfqnhgv1ebg6rijhl3kb9n4vt3\n| Parent: 4tq9si4tk8n0pead7hovehcbuued45sa\n| [ // 11 items\n| \"one\",\n| \"two\",\n| \"three\",\n| \"four\",\n| \"five\",\n| \"six\",\n| \"seven\",\n| \"eight\",\n| \"nine\",\n| \"ten\",\n| \"eleven\",\n| ]\n| \n* 4tq9si4tk8n0pead7hovehcbuued45sa\n| Parent: None\n| \"the first line\"\n" 303 diffTrunc2 = "* p1442asfqnhgv1ebg6rijhl3kb9n4vt3\n| Parent: 4tq9si4tk8n0pead7hovehcbuued45sa\n| - \"the first line\"\n| + [ // 11 items\n| + \"one\",\n| + \"two\",\n| + \"three\",\n| + \"four\",\n| + \"five\",\n| + \"six\",\n| + \"seven\",\n| + \"eight\",\n| + \"nine\",\n| + \"ten\",\n| + \"eleven\",\n| + ]\n| \n* 4tq9si4tk8n0pead7hovehcbuued45sa\n| Parent: None\n| \n" 304 305 truncRes3 = "* p1442asfqnhgv1ebg6rijhl3kb9n4vt3\n| Parent: 4tq9si4tk8n0pead7hovehcbuued45sa\n* 4tq9si4tk8n0pead7hovehcbuued45sa\n| Parent: None\n" 306 diffTrunc3 = "* p1442asfqnhgv1ebg6rijhl3kb9n4vt3\n| Parent: 4tq9si4tk8n0pead7hovehcbuued45sa\n* 4tq9si4tk8n0pead7hovehcbuued45sa\n| Parent: None\n" 307 308 metaRes1 = "p7jmuh67vhfccnqk1bilnlovnms1m67o\nParent: f8gjiv5974ojir9tnrl2k393o4s1tf0r\n- \"1\"\n+ \"2\"\n\nf8gjiv5974ojir9tnrl2k393o4s1tf0r\nParent: None\nLongNameForTest: \"Yoo\"\nTest2: \"Hoo\"\n\n" 309 metaRes2 = "p7jmuh67vhfccnqk1bilnlovnms1m67o (Parent: f8gjiv5974ojir9tnrl2k393o4s1tf0r)\nf8gjiv5974ojir9tnrl2k393o4s1tf0r (Parent: None)\n" 310 311 pathValue = "oki4cv7vkh743rccese3r3omf6l6mao4\nParent: lca4vejkm0iqsk7ok5322pt61u4otn6q\n2\n\nlca4vejkm0iqsk7ok5322pt61u4otn6q\nParent: u42pi8ukgkvpoi6n7d46cklske41oguf\n1\n\nu42pi8ukgkvpoi6n7d46cklske41oguf\nParent: hgmlqmsnrb3sp9jqc6mas8kusa1trrs2\n0\n\nhgmlqmsnrb3sp9jqc6mas8kusa1trrs2\nParent: hffiuecdpoq622tamm3nvungeca99ohl\n<nil>\nhffiuecdpoq622tamm3nvungeca99ohl\nParent: None\n<nil>\n" 312 313 pathDiff = "oki4cv7vkh743rccese3r3omf6l6mao4\nParent: lca4vejkm0iqsk7ok5322pt61u4otn6q\n- 1\n+ 2\n\nlca4vejkm0iqsk7ok5322pt61u4otn6q\nParent: u42pi8ukgkvpoi6n7d46cklske41oguf\n- 0\n+ 1\n\nu42pi8ukgkvpoi6n7d46cklske41oguf\nParent: hgmlqmsnrb3sp9jqc6mas8kusa1trrs2\nold (#hgmlqmsnrb3sp9jqc6mas8kusa1trrs2.value.bar) not found\n\nhgmlqmsnrb3sp9jqc6mas8kusa1trrs2\nParent: hffiuecdpoq622tamm3nvungeca99ohl\nnew (#hgmlqmsnrb3sp9jqc6mas8kusa1trrs2.value.bar) not found\nold (#hffiuecdpoq622tamm3nvungeca99ohl.value.bar) not found\n\nhffiuecdpoq622tamm3nvungeca99ohl\nParent: None\n\n" 314 )