github.com/koko1123/flow-go-1@v0.29.6/fvm/transactionStorageLimiter_test.go (about)

     1  package fvm_test
     2  
     3  import (
     4  	"testing"
     5  
     6  	"github.com/onflow/cadence"
     7  	"github.com/stretchr/testify/mock"
     8  	"github.com/stretchr/testify/require"
     9  
    10  	"github.com/koko1123/flow-go-1/fvm"
    11  	fvmmock "github.com/koko1123/flow-go-1/fvm/environment/mock"
    12  	"github.com/koko1123/flow-go-1/fvm/errors"
    13  	"github.com/koko1123/flow-go-1/fvm/tracing"
    14  	"github.com/koko1123/flow-go-1/model/flow"
    15  )
    16  
    17  func TestTransactionStorageLimiter(t *testing.T) {
    18  	owner := flow.HexToAddress("1")
    19  	t.Run("capacity > storage -> OK", func(t *testing.T) {
    20  		chain := flow.Mainnet.Chain()
    21  		env := &fvmmock.Environment{}
    22  		env.On("Chain").Return(chain)
    23  		env.On("LimitAccountStorage").Return(true)
    24  		env.On("StartChildSpan", mock.Anything).Return(
    25  			tracing.NewMockTracerSpan())
    26  		env.On("GetStorageUsed", mock.Anything).Return(uint64(99), nil)
    27  		env.On("AccountsStorageCapacity", mock.Anything, mock.Anything, mock.Anything).Return(
    28  			cadence.NewArray([]cadence.Value{
    29  				bytesToUFix64(100),
    30  			}),
    31  			nil,
    32  		)
    33  
    34  		d := &fvm.TransactionStorageLimiter{}
    35  		err := d.CheckStorageLimits(env, []flow.Address{owner}, flow.EmptyAddress, 0)
    36  		require.NoError(t, err, "Transaction with higher capacity than storage used should work")
    37  	})
    38  	t.Run("capacity = storage -> OK", func(t *testing.T) {
    39  		chain := flow.Mainnet.Chain()
    40  		env := &fvmmock.Environment{}
    41  		env.On("Chain").Return(chain)
    42  		env.On("LimitAccountStorage").Return(true)
    43  		env.On("StartChildSpan", mock.Anything).Return(
    44  			tracing.NewMockTracerSpan())
    45  		env.On("GetStorageUsed", mock.Anything).Return(uint64(100), nil)
    46  		env.On("AccountsStorageCapacity", mock.Anything, mock.Anything, mock.Anything).Return(
    47  			cadence.NewArray([]cadence.Value{
    48  				bytesToUFix64(100),
    49  			}),
    50  			nil,
    51  		)
    52  
    53  		d := &fvm.TransactionStorageLimiter{}
    54  		err := d.CheckStorageLimits(env, []flow.Address{owner}, flow.EmptyAddress, 0)
    55  		require.NoError(t, err, "Transaction with equal capacity than storage used should work")
    56  	})
    57  	t.Run("capacity < storage -> Not OK", func(t *testing.T) {
    58  		chain := flow.Mainnet.Chain()
    59  		env := &fvmmock.Environment{}
    60  		env.On("Chain").Return(chain)
    61  		env.On("LimitAccountStorage").Return(true)
    62  		env.On("StartChildSpan", mock.Anything).Return(
    63  			tracing.NewMockTracerSpan())
    64  		env.On("GetStorageUsed", mock.Anything).Return(uint64(101), nil)
    65  		env.On("AccountsStorageCapacity", mock.Anything, mock.Anything, mock.Anything).Return(
    66  			cadence.NewArray([]cadence.Value{
    67  				bytesToUFix64(100),
    68  			}),
    69  			nil,
    70  		)
    71  
    72  		d := &fvm.TransactionStorageLimiter{}
    73  		err := d.CheckStorageLimits(env, []flow.Address{owner}, flow.EmptyAddress, 0)
    74  		require.Error(t, err, "Transaction with lower capacity than storage used should fail")
    75  	})
    76  	t.Run("if ctx LimitAccountStorage false-> OK", func(t *testing.T) {
    77  		chain := flow.Mainnet.Chain()
    78  		env := &fvmmock.Environment{}
    79  		env.On("Chain").Return(chain)
    80  		env.On("LimitAccountStorage").Return(false)
    81  		env.On("StartChildSpan", mock.Anything).Return(
    82  			tracing.NewMockTracerSpan())
    83  		env.On("GetStorageCapacity", mock.Anything).Return(uint64(100), nil)
    84  		env.On("GetStorageUsed", mock.Anything).Return(uint64(101), nil)
    85  		env.On("AccountsStorageCapacity", mock.Anything, mock.Anything, mock.Anything).Return(
    86  			cadence.NewArray([]cadence.Value{
    87  				bytesToUFix64(100),
    88  			}),
    89  			nil,
    90  		)
    91  
    92  		d := &fvm.TransactionStorageLimiter{}
    93  		err := d.CheckStorageLimits(env, []flow.Address{owner}, flow.EmptyAddress, 0)
    94  		require.NoError(t, err, "Transaction with higher capacity than storage used should work")
    95  	})
    96  	t.Run("non existing accounts or any other errors on fetching storage used -> Not OK", func(t *testing.T) {
    97  		chain := flow.Mainnet.Chain()
    98  		env := &fvmmock.Environment{}
    99  		env.On("Chain").Return(chain)
   100  		env.On("LimitAccountStorage").Return(true)
   101  		env.On("StartChildSpan", mock.Anything).Return(
   102  			tracing.NewMockTracerSpan())
   103  		env.On("GetStorageUsed", mock.Anything).Return(uint64(0), errors.NewAccountNotFoundError(owner))
   104  		env.On("AccountsStorageCapacity", mock.Anything, mock.Anything, mock.Anything).Return(
   105  			cadence.NewArray([]cadence.Value{
   106  				bytesToUFix64(100),
   107  			}),
   108  			nil,
   109  		)
   110  
   111  		d := &fvm.TransactionStorageLimiter{}
   112  		err := d.CheckStorageLimits(env, []flow.Address{owner}, flow.EmptyAddress, 0)
   113  		require.Error(t, err, "check storage used on non existing account (not general registers) should fail")
   114  	})
   115  }
   116  
   117  func bytesToUFix64(b uint64) cadence.Value {
   118  	return cadence.UFix64(b * 100)
   119  }