OSDN Git Service

netsync add test case (#365)
[bytom/vapor.git] / netsync / chainmgr / block_keeper_test.go
index 4a12346..9472f21 100644 (file)
@@ -11,17 +11,108 @@ import (
        dbm "github.com/vapor/database/leveldb"
        "github.com/vapor/errors"
        msgs "github.com/vapor/netsync/messages"
+       "github.com/vapor/netsync/peers"
+       "github.com/vapor/protocol"
        "github.com/vapor/protocol/bc"
        "github.com/vapor/protocol/bc/types"
        "github.com/vapor/test/mock"
        "github.com/vapor/testutil"
 )
 
+func TestCheckSyncType(t *testing.T) {
+       tmp, err := ioutil.TempDir(".", "")
+       if err != nil {
+               t.Fatalf("failed to create temporary data folder: %v", err)
+       }
+       fastSyncDB := dbm.NewDB("testdb", "leveldb", tmp)
+       defer func() {
+               fastSyncDB.Close()
+               os.RemoveAll(tmp)
+       }()
+
+       blocks := mockBlocks(nil, 50)
+       chain := mock.NewChain(nil)
+       chain.SetBestBlockHeader(&blocks[len(blocks)-1].BlockHeader)
+       for _, block := range blocks {
+               chain.SetBlockByHeight(block.Height, block)
+       }
+
+       type syncPeer struct {
+               peer               *P2PPeer
+               bestHeight         uint64
+               irreversibleHeight uint64
+       }
+
+       cases := []struct {
+               peers    []*syncPeer
+               syncType int
+       }{
+               {
+                       peers:    []*syncPeer{},
+                       syncType: noNeedSync,
+               },
+               {
+                       peers: []*syncPeer{
+                               {peer: &P2PPeer{id: "peer1", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 1000, irreversibleHeight: 500},
+                               {peer: &P2PPeer{id: "peer2", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 50, irreversibleHeight: 50},
+                       },
+                       syncType: fastSyncType,
+               },
+               {
+                       peers: []*syncPeer{
+                               {peer: &P2PPeer{id: "peer1", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 1000, irreversibleHeight: 100},
+                               {peer: &P2PPeer{id: "peer2", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 500, irreversibleHeight: 50},
+                       },
+                       syncType: regularSyncType,
+               },
+               {
+                       peers: []*syncPeer{
+                               {peer: &P2PPeer{id: "peer1", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 51, irreversibleHeight: 50},
+                       },
+                       syncType: regularSyncType,
+               },
+               {
+                       peers: []*syncPeer{
+                               {peer: &P2PPeer{id: "peer1", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 30, irreversibleHeight: 30},
+                       },
+                       syncType: noNeedSync,
+               },
+               {
+                       peers: []*syncPeer{
+                               {peer: &P2PPeer{id: "peer1", flag: consensus.SFFullNode}, bestHeight: 1000, irreversibleHeight: 1000},
+                       },
+                       syncType: regularSyncType,
+               },
+               {
+                       peers: []*syncPeer{
+                               {peer: &P2PPeer{id: "peer1", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 1000, irreversibleHeight: 50},
+                               {peer: &P2PPeer{id: "peer2", flag: consensus.SFFullNode | consensus.SFFastSync}, bestHeight: 800, irreversibleHeight: 800},
+                       },
+                       syncType: fastSyncType,
+               },
+       }
+
+       for i, c := range cases {
+               peers := peers.NewPeerSet(NewPeerSet())
+               blockKeeper := newBlockKeeper(chain, peers, fastSyncDB)
+               for _, syncPeer := range c.peers {
+                       blockKeeper.peers.AddPeer(syncPeer.peer)
+                       blockKeeper.peers.SetStatus(syncPeer.peer.id, syncPeer.bestHeight, nil)
+                       blockKeeper.peers.SetIrreversibleStatus(syncPeer.peer.id, syncPeer.irreversibleHeight, nil)
+               }
+               gotType := blockKeeper.checkSyncType()
+               if c.syncType != gotType {
+                       t.Errorf("case %d: got %d want %d", i, gotType, c.syncType)
+               }
+       }
+}
+
 func TestRegularBlockSync(t *testing.T) {
        baseChain := mockBlocks(nil, 50)
        chainX := append(baseChain, mockBlocks(baseChain[50], 60)...)
        chainY := append(baseChain, mockBlocks(baseChain[50], 70)...)
        chainZ := append(baseChain, mockBlocks(baseChain[50], 200)...)
+       chainE := append(baseChain, mockErrorBlocks(baseChain[50], 200, 60)...)
 
        cases := []struct {
                syncTimeout time.Duration
@@ -55,9 +146,23 @@ func TestRegularBlockSync(t *testing.T) {
                        syncTimeout: 30 * time.Second,
                        aBlocks:     chainX[:52],
                        bBlocks:     chainZ,
-                       want:        chainZ[:201],
+                       want:        chainZ[:180],
                        err:         nil,
                },
+               {
+                       syncTimeout: 0 * time.Second,
+                       aBlocks:     chainX[:52],
+                       bBlocks:     chainZ,
+                       want:        chainX[:52],
+                       err:         errRequestTimeout,
+               },
+               {
+                       syncTimeout: 30 * time.Second,
+                       aBlocks:     chainX[:52],
+                       bBlocks:     chainE,
+                       want:        chainE[:60],
+                       err:         protocol.ErrBadStateRoot,
+               },
        }
        tmp, err := ioutil.TempDir(".", "")
        if err != nil {
@@ -84,6 +189,7 @@ func TestRegularBlockSync(t *testing.T) {
                        go A2B.postMan()
                }
 
+               requireBlockTimeout = c.syncTimeout
                a.blockKeeper.syncPeer = a.peers.GetPeer("test node B")
                if err := a.blockKeeper.regularBlockSync(); errors.Root(err) != c.err {
                        t.Errorf("case %d: got %v want %v", i, err, c.err)
@@ -308,11 +414,19 @@ func TestLocateBlocks(t *testing.T) {
                locator    []uint64
                stopHash   bc.Hash
                wantHeight []uint64
+               wantErr    error
        }{
                {
                        locator:    []uint64{20},
                        stopHash:   blocks[100].Hash(),
                        wantHeight: []uint64{20, 21, 22, 23, 24},
+                       wantErr:    nil,
+               },
+               {
+                       locator:    []uint64{20},
+                       stopHash:   bc.NewHash([32]byte{0x01, 0x02}),
+                       wantHeight: []uint64{},
+                       wantErr:    mock.ErrFoundHeaderByHash,
                },
        }
 
@@ -334,7 +448,11 @@ func TestLocateBlocks(t *testing.T) {
                        want = append(want, blocks[i])
                }
 
-               got, _ := bk.locateBlocks(locator, &c.stopHash)
+               got, err := bk.locateBlocks(locator, &c.stopHash)
+               if err != c.wantErr {
+                       t.Errorf("case %d: got %v want err = %v", i, err, c.wantErr)
+               }
+
                if !testutil.DeepEqual(got, want) {
                        t.Errorf("case %d: got %v want %v", i, got, want)
                }
@@ -358,7 +476,7 @@ func TestLocateHeaders(t *testing.T) {
                stopHash    *bc.Hash
                skip        uint64
                wantHeight  []uint64
-               err         bool
+               err         error
        }{
                {
                        chainHeight: 100,
@@ -366,7 +484,7 @@ func TestLocateHeaders(t *testing.T) {
                        stopHash:    &blocksHash[100],
                        skip:        0,
                        wantHeight:  []uint64{90, 91, 92, 93, 94, 95, 96, 97, 98, 99},
-                       err:         false,
+                       err:         nil,
                },
                {
                        chainHeight: 100,
@@ -374,28 +492,28 @@ func TestLocateHeaders(t *testing.T) {
                        stopHash:    &blocksHash[24],
                        skip:        0,
                        wantHeight:  []uint64{20, 21, 22, 23, 24},
-                       err:         false,
+                       err:         nil,
                },
                {
                        chainHeight: 100,
                        locator:     []uint64{20},
                        stopHash:    &blocksHash[20],
                        wantHeight:  []uint64{20},
-                       err:         false,
+                       err:         nil,
                },
                {
                        chainHeight: 100,
                        locator:     []uint64{20},
                        stopHash:    &blocksHash[120],
                        wantHeight:  []uint64{},
-                       err:         false,
+                       err:         mock.ErrFoundHeaderByHash,
                },
                {
                        chainHeight: 100,
                        locator:     []uint64{120, 70},
                        stopHash:    &blocksHash[78],
                        wantHeight:  []uint64{70, 71, 72, 73, 74, 75, 76, 77, 78},
-                       err:         false,
+                       err:         nil,
                },
                {
                        chainHeight: 100,
@@ -403,7 +521,7 @@ func TestLocateHeaders(t *testing.T) {
                        stopHash:    &blocksHash[10],
                        skip:        10,
                        wantHeight:  []uint64{},
-                       err:         false,
+                       err:         nil,
                },
                {
                        chainHeight: 100,
@@ -411,7 +529,7 @@ func TestLocateHeaders(t *testing.T) {
                        stopHash:    &blocksHash[80],
                        skip:        10,
                        wantHeight:  []uint64{15, 26, 37, 48, 59, 70, 80},
-                       err:         false,
+                       err:         nil,
                },
                {
                        chainHeight: 100,
@@ -419,7 +537,7 @@ func TestLocateHeaders(t *testing.T) {
                        stopHash:    &blocksHash[100],
                        skip:        9,
                        wantHeight:  []uint64{0, 10, 20, 30, 40, 50, 60, 70, 80, 90},
-                       err:         false,
+                       err:         nil,
                },
        }
 
@@ -442,7 +560,7 @@ func TestLocateHeaders(t *testing.T) {
                }
 
                got, err := bk.locateHeaders(locator, c.stopHash, c.skip, maxNumOfHeadersPerMsg)
-               if err != nil != c.err {
+               if err != c.err {
                        t.Errorf("case %d: got %v want err = %v", i, err, c.err)
                }
                if !testutil.DeepEqual(got, want) {