From 6d2e8d721d9430ca54f20f418dd640496272001c Mon Sep 17 00:00:00 2001 From: Steven Allen Date: Mon, 8 Mar 2021 16:15:55 -0800 Subject: [PATCH 1/2] test: attempt to make the splitstore test deterministic At a minimum, make it thread-safe. --- blockstore/splitstore/splitstore_test.go | 28 ++++++++++++++---------- 1 file changed, 16 insertions(+), 12 deletions(-) diff --git a/blockstore/splitstore/splitstore_test.go b/blockstore/splitstore/splitstore_test.go index db5144039..540d3ea23 100644 --- a/blockstore/splitstore/splitstore_test.go +++ b/blockstore/splitstore/splitstore_test.go @@ -14,6 +14,7 @@ import ( cid "github.com/ipfs/go-cid" datastore "github.com/ipfs/go-datastore" + dssync "github.com/ipfs/go-datastore/sync" logging "github.com/ipfs/go-log/v2" ) @@ -25,8 +26,6 @@ func init() { } func testSplitStore(t *testing.T, cfg *Config) { - t.Helper() - chain := &mockChain{} // genesis genBlock := mock.MkBlock(nil, 0, 0) @@ -34,7 +33,7 @@ func testSplitStore(t *testing.T, cfg *Config) { chain.push(genTs) // the myriads of stores - ds := datastore.NewMapDatastore() + ds := dssync.MutexWrap(datastore.NewMapDatastore()) hot := blockstore.NewMemorySync() cold := blockstore.NewMemorySync() @@ -61,6 +60,8 @@ func testSplitStore(t *testing.T, cfg *Config) { t.Fatal(err) } + //time.Sleep(time.Second) + // make some tipsets, but not enough to cause compaction mkBlock := func(curTs *types.TipSet, i int) *types.TipSet { blk := mock.MkBlock(curTs, uint64(i), uint64(i)) @@ -93,10 +94,13 @@ func testSplitStore(t *testing.T, cfg *Config) { curTs := genTs for i := 1; i < 5; i++ { curTs = mkBlock(curTs, i) + time.Sleep(time.Second) } mkGarbageBlock(genTs, 1) + time.Sleep(time.Second) + // count objects in the cold and hot stores ctx, cancel := context.WithCancel(context.Background()) defer cancel() @@ -117,11 +121,11 @@ func testSplitStore(t *testing.T, cfg *Config) { hotCnt := countBlocks(hot) if coldCnt != 1 { - t.Fatalf("expected %d blocks, but got %d", 1, coldCnt) + t.Errorf("expected %d blocks, but got %d", 5, coldCnt) } - if hotCnt != 4 { - t.Fatalf("expected %d blocks, but got %d", 4, hotCnt) + if hotCnt != 5 { + t.Errorf("expected %d blocks, but got %d", 5, hotCnt) } // trigger a compaction @@ -135,31 +139,31 @@ func testSplitStore(t *testing.T, cfg *Config) { if !cfg.EnableFullCompaction { if coldCnt != 5 { - t.Fatalf("expected %d cold blocks, but got %d", 5, coldCnt) + t.Errorf("expected %d cold blocks, but got %d", 5, coldCnt) } if hotCnt != 5 { - t.Fatalf("expected %d hot blocks, but got %d", 5, hotCnt) + t.Errorf("expected %d hot blocks, but got %d", 5, hotCnt) } } if cfg.EnableFullCompaction && !cfg.EnableGC { if coldCnt != 3 { - t.Fatalf("expected %d cold blocks, but got %d", 3, coldCnt) + t.Errorf("expected %d cold blocks, but got %d", 3, coldCnt) } if hotCnt != 7 { - t.Fatalf("expected %d hot blocks, but got %d", 7, hotCnt) + t.Errorf("expected %d hot blocks, but got %d", 7, hotCnt) } } if cfg.EnableFullCompaction && cfg.EnableGC { if coldCnt != 2 { - t.Fatalf("expected %d cold blocks, but got %d", 2, coldCnt) + t.Errorf("expected %d cold blocks, but got %d", 2, coldCnt) } if hotCnt != 7 { - t.Fatalf("expected %d hot blocks, but got %d", 7, hotCnt) + t.Errorf("expected %d hot blocks, but got %d", 7, hotCnt) } } } From ae6410d02f2da1db365a24e218dbe974bfc669a8 Mon Sep 17 00:00:00 2001 From: vyzo Date: Tue, 9 Mar 2021 09:05:36 +0200 Subject: [PATCH 2/2] use compacting atomic to make the test deterministic --- blockstore/splitstore/splitstore_test.go | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/blockstore/splitstore/splitstore_test.go b/blockstore/splitstore/splitstore_test.go index 540d3ea23..e5314b80f 100644 --- a/blockstore/splitstore/splitstore_test.go +++ b/blockstore/splitstore/splitstore_test.go @@ -4,6 +4,7 @@ import ( "context" "fmt" "sync" + "sync/atomic" "testing" "time" @@ -60,8 +61,6 @@ func testSplitStore(t *testing.T, cfg *Config) { t.Fatal(err) } - //time.Sleep(time.Second) - // make some tipsets, but not enough to cause compaction mkBlock := func(curTs *types.TipSet, i int) *types.TipSet { blk := mock.MkBlock(curTs, uint64(i), uint64(i)) @@ -91,16 +90,20 @@ func testSplitStore(t *testing.T, cfg *Config) { } } + waitForCompaction := func() { + for atomic.LoadInt32(&ss.compacting) == 1 { + time.Sleep(100 * time.Millisecond) + } + } + curTs := genTs for i := 1; i < 5; i++ { curTs = mkBlock(curTs, i) - time.Sleep(time.Second) + waitForCompaction() } mkGarbageBlock(genTs, 1) - time.Sleep(time.Second) - // count objects in the cold and hot stores ctx, cancel := context.WithCancel(context.Background()) defer cancel() @@ -121,7 +124,7 @@ func testSplitStore(t *testing.T, cfg *Config) { hotCnt := countBlocks(hot) if coldCnt != 1 { - t.Errorf("expected %d blocks, but got %d", 5, coldCnt) + t.Errorf("expected %d blocks, but got %d", 1, coldCnt) } if hotCnt != 5 { @@ -131,7 +134,7 @@ func testSplitStore(t *testing.T, cfg *Config) { // trigger a compaction for i := 5; i < 10; i++ { curTs = mkBlock(curTs, i) - time.Sleep(time.Second) + waitForCompaction() } coldCnt = countBlocks(cold)