github.com/core-coin/go-core/v2@v2.1.9/les/lespay/client/fillset_test.go (about) 1 // Copyright 2020 by the Authors 2 // This file is part of the go-core library. 3 // 4 // The go-core library is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU Lesser General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // The go-core library is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU Lesser General Public License for more details. 13 // 14 // You should have received a copy of the GNU Lesser General Public License 15 // along with the go-core library. If not, see <http://www.gnu.org/licenses/>. 16 17 package client 18 19 import ( 20 "math/rand" 21 "testing" 22 "time" 23 24 "github.com/core-coin/go-core/v2/common/mclock" 25 "github.com/core-coin/go-core/v2/p2p/enode" 26 "github.com/core-coin/go-core/v2/p2p/enr" 27 "github.com/core-coin/go-core/v2/p2p/nodestate" 28 ) 29 30 type testIter struct { 31 waitCh chan struct{} 32 nodeCh chan *enode.Node 33 node *enode.Node 34 } 35 36 func (i *testIter) Next() bool { 37 i.waitCh <- struct{}{} 38 i.node = <-i.nodeCh 39 return i.node != nil 40 } 41 42 func (i *testIter) Node() *enode.Node { 43 return i.node 44 } 45 46 func (i *testIter) Close() {} 47 48 func (i *testIter) push() { 49 var id enode.ID 50 rand.Read(id[:]) 51 i.nodeCh <- enode.SignNull(new(enr.Record), id) 52 } 53 54 func (i *testIter) waiting(timeout time.Duration) bool { 55 select { 56 case <-i.waitCh: 57 return true 58 case <-time.After(timeout): 59 return false 60 } 61 } 62 63 func TestFillSet(t *testing.T) { 64 ns := nodestate.NewNodeStateMachine(nil, nil, &mclock.Simulated{}, testSetup) 65 iter := &testIter{ 66 waitCh: make(chan struct{}), 67 nodeCh: make(chan *enode.Node), 68 } 69 fs := NewFillSet(ns, iter, sfTest1) 70 ns.Start() 71 72 expWaiting := func(i int, push bool) { 73 for ; i > 0; i-- { 74 if !iter.waiting(time.Second * 10) { 75 t.Fatalf("FillSet not waiting for new nodes") 76 } 77 if push { 78 iter.push() 79 } 80 } 81 } 82 83 expNotWaiting := func() { 84 if iter.waiting(time.Millisecond * 100) { 85 t.Fatalf("FillSet unexpectedly waiting for new nodes") 86 } 87 } 88 89 expNotWaiting() 90 fs.SetTarget(3) 91 expWaiting(3, true) 92 expNotWaiting() 93 fs.SetTarget(100) 94 expWaiting(2, true) 95 expWaiting(1, false) 96 // lower the target before the previous one has been filled up 97 fs.SetTarget(0) 98 iter.push() 99 expNotWaiting() 100 fs.SetTarget(10) 101 expWaiting(4, true) 102 expNotWaiting() 103 // remove all previosly set flags 104 ns.ForEach(sfTest1, nodestate.Flags{}, func(node *enode.Node, state nodestate.Flags) { 105 ns.SetState(node, nodestate.Flags{}, sfTest1, 0) 106 }) 107 // now expect FillSet to fill the set up again with 10 new nodes 108 expWaiting(10, true) 109 expNotWaiting() 110 111 fs.Close() 112 ns.Stop() 113 }