fix lifecycle of BlockMiner.
This commit is contained in:
parent
25daa0c8e4
commit
20dfe220f3
@ -17,18 +17,19 @@ import (
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
func TestAPI(t *testing.T) {
|
||||
t.Run("direct", func(t *testing.T) {
|
||||
runAPITest(t, kit.Builder)
|
||||
})
|
||||
t.Run("rpc", func(t *testing.T) {
|
||||
runAPITest(t, kit.RPCBuilder)
|
||||
})
|
||||
}
|
||||
|
||||
type apiSuite struct {
|
||||
makeNodes kit.APIBuilder
|
||||
}
|
||||
|
||||
func TestAPI(t *testing.T) {
|
||||
runAPITest(t, kit.Builder)
|
||||
}
|
||||
|
||||
func TestAPIRPC(t *testing.T) {
|
||||
runAPITest(t, kit.RPCBuilder)
|
||||
}
|
||||
|
||||
// runAPITest is the entry point to API test suite
|
||||
func runAPITest(t *testing.T, b kit.APIBuilder) {
|
||||
ts := apiSuite{
|
||||
|
@ -2,6 +2,7 @@ package kit
|
||||
|
||||
import (
|
||||
"context"
|
||||
"sync"
|
||||
"sync/atomic"
|
||||
"testing"
|
||||
"time"
|
||||
@ -17,37 +18,45 @@ type BlockMiner struct {
|
||||
miner TestMiner
|
||||
|
||||
nextNulls int64
|
||||
stopCh chan chan struct{}
|
||||
wg sync.WaitGroup
|
||||
cancel context.CancelFunc
|
||||
}
|
||||
|
||||
func NewBlockMiner(t *testing.T, miner TestMiner) *BlockMiner {
|
||||
return &BlockMiner{
|
||||
t: t,
|
||||
miner: miner,
|
||||
stopCh: make(chan chan struct{}),
|
||||
cancel: func() {},
|
||||
}
|
||||
}
|
||||
|
||||
func (bm *BlockMiner) MineBlocks(ctx context.Context, blocktime time.Duration) {
|
||||
time.Sleep(time.Second)
|
||||
|
||||
// wrap context in a cancellable context.
|
||||
ctx, bm.cancel = context.WithCancel(ctx)
|
||||
|
||||
bm.wg.Add(1)
|
||||
go func() {
|
||||
defer bm.wg.Done()
|
||||
|
||||
for {
|
||||
select {
|
||||
case <-time.After(blocktime):
|
||||
case <-ctx.Done():
|
||||
return
|
||||
case ch := <-bm.stopCh:
|
||||
close(ch)
|
||||
close(bm.stopCh)
|
||||
return
|
||||
}
|
||||
|
||||
nulls := atomic.SwapInt64(&bm.nextNulls, 0)
|
||||
if err := bm.miner.MineOne(ctx, miner.MineReq{
|
||||
err := bm.miner.MineOne(ctx, miner.MineReq{
|
||||
InjectNulls: abi.ChainEpoch(nulls),
|
||||
Done: func(bool, abi.ChainEpoch, error) {},
|
||||
}); err != nil {
|
||||
})
|
||||
switch {
|
||||
case err == nil: // wrap around
|
||||
case ctx.Err() != nil: // context fired.
|
||||
return
|
||||
default: // log error
|
||||
bm.t.Error(err)
|
||||
}
|
||||
}
|
||||
@ -110,11 +119,6 @@ func (bm *BlockMiner) MineUntilBlock(ctx context.Context, fn TestFullNode, cb fu
|
||||
// Stop stops the block miner.
|
||||
func (bm *BlockMiner) Stop() {
|
||||
bm.t.Log("shutting down mining")
|
||||
if _, ok := <-bm.stopCh; ok {
|
||||
// already stopped
|
||||
return
|
||||
}
|
||||
ch := make(chan struct{})
|
||||
bm.stopCh <- ch
|
||||
<-ch
|
||||
bm.cancel()
|
||||
bm.wg.Wait()
|
||||
}
|
||||
|
@ -370,6 +370,7 @@ func mockBuilderOpts(t *testing.T, fullOpts []FullNodeOpts, storage []StorageMin
|
||||
wait.Lock()
|
||||
|
||||
bm := NewBlockMiner(t, miners[0])
|
||||
t.Cleanup(bm.Stop)
|
||||
|
||||
bm.MineUntilBlock(ctx, fulls[0], func(epoch abi.ChainEpoch) {
|
||||
wait.Unlock()
|
||||
|
Loading…
Reference in New Issue
Block a user