github.com/igggame/nebulas-go@v2.1.0+incompatible/consensus/dpos/dpos_state_test.go (about)

     1  // Copyright (C) 2017 go-nebulas authors
     2  //
     3  // This file is part of the go-nebulas library.
     4  //
     5  // the go-nebulas library is free software: you can redistribute it and/or modify
     6  // it under the terms of the GNU General Public License as published by
     7  // the Free Software Foundation, either version 3 of the License, or
     8  // (at your option) any later version.
     9  //
    10  // the go-nebulas library is distributed in the hope that it will be useful,
    11  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    12  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    13  // GNU General Public License for more details.
    14  //
    15  // You should have received a copy of the GNU General Public License
    16  // along with the go-nebulas library.  If not, see <http://www.gnu.org/licenses/>.
    17  //
    18  
    19  package dpos
    20  
    21  import (
    22  	"testing"
    23  
    24  	"github.com/gogo/protobuf/proto"
    25  	"github.com/nebulasio/go-nebulas/core/pb"
    26  
    27  	"github.com/nebulasio/go-nebulas/consensus/pb"
    28  
    29  	"github.com/nebulasio/go-nebulas/core"
    30  	"github.com/nebulasio/go-nebulas/crypto/keystore"
    31  
    32  	"github.com/stretchr/testify/assert"
    33  
    34  	"github.com/nebulasio/go-nebulas/common/trie"
    35  	"github.com/nebulasio/go-nebulas/storage"
    36  	"github.com/nebulasio/go-nebulas/util/byteutils"
    37  )
    38  
    39  func checkDynasty(t *testing.T, consensus core.Consensus, consensusRoot *consensuspb.ConsensusRoot, storage storage.Storage) {
    40  	consensusState, err := consensus.NewState(consensusRoot, storage, false)
    41  	assert.Nil(t, err)
    42  	dynasty, err := consensusState.Dynasty()
    43  	assert.Nil(t, err)
    44  	for i := 0; i < DynastySize-1; i++ {
    45  		a, _ := core.AddressParseFromBytes(dynasty[i])
    46  		assert.Equal(t, a.String(), DefaultOpenDynasty[i])
    47  	}
    48  }
    49  
    50  func TestBlock_NextDynastyContext(t *testing.T) {
    51  	neb := mockNeb(t)
    52  	block := neb.BlockChain().GenesisBlock()
    53  
    54  	context, err := block.WorldState().NextConsensusState(BlockIntervalInMs / SecondInMs)
    55  	assert.Nil(t, err)
    56  	miners, _ := block.WorldState().Dynasty()
    57  	assert.Equal(t, context.Proposer(), miners[1])
    58  	// check dynasty
    59  	consensusRoot := context.RootHash()
    60  	assert.Nil(t, err)
    61  	checkDynasty(t, neb.Consensus(), consensusRoot, neb.Storage())
    62  
    63  	context, err = block.WorldState().NextConsensusState((BlockIntervalInMs + DynastyIntervalInMs) / SecondInMs)
    64  	assert.Nil(t, err)
    65  	miners, _ = block.WorldState().Dynasty()
    66  	assert.Equal(t, context.Proposer(), miners[1])
    67  	// check dynasty
    68  	consensusRoot = context.RootHash()
    69  	assert.Nil(t, err)
    70  	checkDynasty(t, neb.Consensus(), consensusRoot, neb.Storage())
    71  
    72  	context, err = block.WorldState().NextConsensusState(DynastyIntervalInMs / SecondInMs / 2)
    73  	assert.Nil(t, err)
    74  	miners, _ = block.WorldState().Dynasty()
    75  	assert.Equal(t, context.Proposer(), miners[int(DynastyIntervalInMs/2/BlockIntervalInMs)%DynastySize])
    76  	// check dynasty
    77  	consensusRoot = context.RootHash()
    78  	assert.Nil(t, err)
    79  	checkDynasty(t, neb.Consensus(), consensusRoot, neb.Storage())
    80  
    81  	context, err = block.WorldState().NextConsensusState((DynastyIntervalInMs*2 + DynastyIntervalInMs/3) / SecondInMs)
    82  	assert.Nil(t, err)
    83  	miners, _ = block.WorldState().Dynasty()
    84  	index := int((DynastyIntervalInMs*2+DynastyIntervalInMs/3)%DynastyIntervalInMs) / int(BlockIntervalInMs) % DynastySize
    85  	assert.Equal(t, context.Proposer(), miners[index])
    86  	// check dynasty
    87  	consensusRoot = context.RootHash()
    88  	assert.Nil(t, err)
    89  	checkDynasty(t, neb.Consensus(), consensusRoot, neb.Storage())
    90  
    91  	// new block
    92  	coinbase, err := core.AddressParseFromBytes(miners[4])
    93  	assert.Nil(t, err)
    94  	assert.Nil(t, neb.AccountManager().Unlock(coinbase, []byte("passphrase"), keystore.DefaultUnlockDuration))
    95  
    96  	newBlock, _ := core.NewBlock(neb.BlockChain().ChainID(), coinbase, neb.BlockChain().TailBlock())
    97  	newBlock.SetTimestamp((DynastyIntervalInMs*2 + DynastyIntervalInMs/3) / SecondInMs)
    98  	newBlock.WorldState().SetConsensusState(context)
    99  	assert.Equal(t, newBlock.Seal(), nil)
   100  	assert.Nil(t, neb.AccountManager().SignBlock(coinbase, newBlock))
   101  	newBlock, _ = mockBlockFromNetwork(newBlock)
   102  	newBlock.LinkParentBlock(neb.BlockChain(), neb.BlockChain().TailBlock())
   103  	assert.Nil(t, newBlock.VerifyExecution()) //neb.chain.TailBlock(), neb.chain.ConsensusHandler()
   104  }
   105  
   106  func TestTraverseDynasty(t *testing.T) {
   107  	stor, err := storage.NewMemoryStorage()
   108  	assert.Nil(t, err)
   109  	dynasty, err := trie.NewTrie(nil, stor, false)
   110  	assert.Nil(t, err)
   111  	members, err := TraverseDynasty(dynasty)
   112  	assert.Nil(t, err)
   113  	assert.Equal(t, members, []byteutils.Hash{})
   114  }
   115  
   116  func TestInitialDynastyNotEnough(t *testing.T) {
   117  	neb := mockNeb(t)
   118  	neb.Genesis().Consensus.Dpos.Dynasty = []string{}
   119  	chain, err := core.NewBlockChain(neb)
   120  	assert.Nil(t, err)
   121  	assert.Equal(t, chain.Setup(neb), core.ErrGenesisNotEqualDynastyLenInDB)
   122  	storage, err := storage.NewMemoryStorage()
   123  	assert.Nil(t, err)
   124  	neb.SetStorage(storage)
   125  	chain, err = core.NewBlockChain(neb)
   126  	assert.Nil(t, err)
   127  	assert.Equal(t, chain.Setup(neb), ErrInitialDynastyNotEnough)
   128  }
   129  
   130  func TestNewGenesisBlock(t *testing.T) {
   131  	neb := mockNeb(t)
   132  	conf := neb.Genesis()
   133  	chain := neb.BlockChain()
   134  	dumpConf, err := core.DumpGenesis(chain)
   135  	assert.Nil(t, err)
   136  	assert.Equal(t, dumpConf.Meta.ChainId, conf.Meta.ChainId)
   137  	assert.Equal(t, dumpConf.Consensus.Dpos.Dynasty, conf.Consensus.Dpos.Dynasty)
   138  	assert.Equal(t, dumpConf.TokenDistribution, conf.TokenDistribution)
   139  }
   140  
   141  func TestCheckGenesisAndDBConsense(t *testing.T) {
   142  	neb := mockNeb(t)
   143  	conf := neb.Genesis()
   144  	chain := neb.BlockChain()
   145  
   146  	confBytes, err := proto.Marshal(conf)
   147  	assert.Nil(t, err)
   148  
   149  	genesisDB, err := core.DumpGenesis(chain)
   150  	assert.Nil(t, err)
   151  	err = core.CheckGenesisConfByDB(genesisDB, conf)
   152  	assert.Nil(t, err)
   153  
   154  	conf4 := new(corepb.Genesis)
   155  	proto.Unmarshal(confBytes, conf4)
   156  	conf4.TokenDistribution[0].Value = "1001"
   157  	err = core.CheckGenesisConfByDB(genesisDB, conf4)
   158  	assert.NotNil(t, err)
   159  	assert.Equal(t, err, core.ErrGenesisNotEqualTokenInDB)
   160  
   161  	conf1 := new(corepb.Genesis)
   162  	proto.Unmarshal(confBytes, conf1)
   163  	conf1.Consensus.Dpos.Dynasty = nil
   164  	// fmt.Printf("conf1:%v\n", conf1)
   165  	err = core.CheckGenesisConfByDB(genesisDB, conf1)
   166  	assert.NotNil(t, err)
   167  	assert.Equal(t, err, core.ErrGenesisNotEqualDynastyLenInDB)
   168  
   169  	conf2 := new(corepb.Genesis)
   170  	proto.Unmarshal(confBytes, conf2)
   171  	conf2.Consensus.Dpos.Dynasty[0] = "12b"
   172  	err = core.CheckGenesisConfByDB(genesisDB, conf2)
   173  	assert.NotNil(t, err)
   174  	assert.Equal(t, err, core.ErrGenesisNotEqualDynastyInDB)
   175  
   176  	conf3 := new(corepb.Genesis)
   177  	proto.Unmarshal(confBytes, conf3)
   178  	conf3.TokenDistribution = nil
   179  	err = core.CheckGenesisConfByDB(genesisDB, conf3)
   180  	assert.NotNil(t, err)
   181  	assert.Equal(t, err, core.ErrGenesisNotEqualTokenLenInDB)
   182  
   183  }