github.com/onflow/flow-go@v0.33.17/ledger/complete/wal/triequeue_test.go (about)

     1  package wal
     2  
     3  import (
     4  	"crypto/rand"
     5  	"testing"
     6  
     7  	"github.com/stretchr/testify/require"
     8  
     9  	"github.com/onflow/flow-go/ledger"
    10  	"github.com/onflow/flow-go/ledger/common/hash"
    11  	"github.com/onflow/flow-go/ledger/complete/mtrie/node"
    12  	"github.com/onflow/flow-go/ledger/complete/mtrie/trie"
    13  )
    14  
    15  func TestEmptyTrieQueue(t *testing.T) {
    16  	const capacity = 10
    17  
    18  	q := NewTrieQueue(capacity)
    19  	require.Equal(t, 0, q.Count())
    20  
    21  	tries := q.Tries()
    22  	require.Equal(t, 0, len(tries))
    23  	require.Equal(t, 0, q.Count())
    24  
    25  	// savedTries contains all tries that are pushed to queue
    26  	var savedTries []*trie.MTrie
    27  
    28  	// Push tries to queue to fill out capacity
    29  	for i := 0; i < capacity; i++ {
    30  		trie, err := randomMTrie()
    31  		require.NoError(t, err)
    32  
    33  		q.Push(trie)
    34  
    35  		savedTries = append(savedTries, trie)
    36  
    37  		tr := q.Tries()
    38  		require.Equal(t, savedTries, tr)
    39  		require.Equal(t, len(savedTries), q.Count())
    40  	}
    41  
    42  	// Push more tries to queue to overwrite older elements
    43  	for i := 0; i < capacity; i++ {
    44  		trie, err := randomMTrie()
    45  		require.NoError(t, err)
    46  
    47  		q.Push(trie)
    48  
    49  		savedTries = append(savedTries, trie)
    50  
    51  		tr := q.Tries()
    52  		require.Equal(t, capacity, len(tr))
    53  
    54  		// After queue reaches capacity in previous loop,
    55  		// queue overwrites older elements with new insertions,
    56  		// and element count is its capacity value.
    57  		// savedTries contains all elements inserted from previous loop and current loop, so
    58  		// tr (queue snapshot) matches the last C elements in savedTries (where C is capacity).
    59  		require.Equal(t, savedTries[len(savedTries)-capacity:], tr)
    60  		require.Equal(t, capacity, q.Count())
    61  	}
    62  }
    63  
    64  func TestTrieQueueWithInitialValues(t *testing.T) {
    65  	const capacity = 10
    66  
    67  	// Test TrieQueue with initial values.  Numbers of initial values
    68  	// are from 1 to capacity + 1.
    69  	for initialValueCount := 1; initialValueCount <= capacity+1; initialValueCount++ {
    70  
    71  		initialValues := make([]*trie.MTrie, initialValueCount)
    72  		for i := 0; i < len(initialValues); i++ {
    73  			tr, err := randomMTrie()
    74  			require.NoError(t, err)
    75  			initialValues[i] = tr
    76  		}
    77  
    78  		expectedCount := initialValueCount
    79  		expectedTries := initialValues
    80  		if initialValueCount > capacity {
    81  			expectedCount = capacity
    82  			expectedTries = initialValues[initialValueCount-capacity:]
    83  		}
    84  
    85  		q := NewTrieQueueWithValues(capacity, initialValues)
    86  		require.Equal(t, expectedCount, q.Count())
    87  
    88  		tries := q.Tries()
    89  		require.Equal(t, expectedTries, tries)
    90  		require.Equal(t, expectedCount, q.Count())
    91  
    92  		// savedTries contains all tries that are pushed to queue, including initial values.
    93  		savedTries := initialValues
    94  
    95  		// Push tries to queue to fill out remaining capacity.
    96  		if initialValueCount < capacity {
    97  			for i := 0; i < capacity-initialValueCount; i++ {
    98  				trie, err := randomMTrie()
    99  				require.NoError(t, err)
   100  
   101  				q.Push(trie)
   102  
   103  				savedTries = append(savedTries, trie)
   104  
   105  				tr := q.Tries()
   106  				require.Equal(t, savedTries, tr)
   107  				require.Equal(t, len(savedTries), q.Count())
   108  			}
   109  		}
   110  
   111  		// Push more tries to queue to overwrite older elements.
   112  		for i := 0; i < capacity; i++ {
   113  			trie, err := randomMTrie()
   114  			require.NoError(t, err)
   115  
   116  			q.Push(trie)
   117  
   118  			savedTries = append(savedTries, trie)
   119  
   120  			tr := q.Tries()
   121  			require.Equal(t, capacity, len(tr))
   122  			require.Equal(t, savedTries[len(savedTries)-capacity:], tr)
   123  			require.Equal(t, capacity, q.Count())
   124  		}
   125  	}
   126  }
   127  
   128  func randomMTrie() (*trie.MTrie, error) {
   129  	var randomPath ledger.Path
   130  	_, err := rand.Read(randomPath[:])
   131  	if err != nil {
   132  		return nil, err
   133  	}
   134  
   135  	var randomHashValue hash.Hash
   136  	_, err = rand.Read(randomHashValue[:])
   137  	if err != nil {
   138  		return nil, err
   139  	}
   140  
   141  	root := node.NewNode(256, nil, nil, randomPath, nil, randomHashValue)
   142  
   143  	return trie.NewMTrie(root, 1, 1)
   144  }