package dao import ( "testing" "github.com/nspcc-dev/neo-go/pkg/config/netmode" "github.com/nspcc-dev/neo-go/pkg/core/state" "github.com/nspcc-dev/neo-go/pkg/core/storage" "github.com/nspcc-dev/neo-go/pkg/crypto/hash" "github.com/nspcc-dev/neo-go/pkg/internal/random" "github.com/nspcc-dev/neo-go/pkg/smartcontract" "github.com/nspcc-dev/neo-go/pkg/smartcontract/manifest" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" ) func TestCachedDaoAccounts(t *testing.T) { store := storage.NewMemoryStore() // Persistent DAO to check for backing storage. pdao := NewSimple(store, netmode.UnitTestNet) // Cached DAO. cdao := NewCached(pdao) hash := random.Uint160() _, err := cdao.GetAccountState(hash) require.NotNil(t, err) acc, err := cdao.GetAccountStateOrNew(hash) require.Nil(t, err) _, err = pdao.GetAccountState(hash) require.NotNil(t, err) acc.Version = 42 require.NoError(t, cdao.PutAccountState(acc)) _, err = pdao.GetAccountState(hash) require.NotNil(t, err) acc2, err := cdao.GetAccountState(hash) require.Nil(t, err) require.Equal(t, acc, acc2) acc2, err = cdao.GetAccountStateOrNew(hash) require.Nil(t, err) require.Equal(t, acc, acc2) _, err = cdao.Persist() require.Nil(t, err) acct, err := pdao.GetAccountState(hash) require.Nil(t, err) require.Equal(t, acc, acct) } func TestCachedDaoContracts(t *testing.T) { store := storage.NewMemoryStore() pdao := NewSimple(store, netmode.UnitTestNet) dao := NewCached(pdao) script := []byte{0xde, 0xad, 0xbe, 0xef} sh := hash.Hash160(script) _, err := dao.GetContractState(sh) require.NotNil(t, err) m := manifest.NewManifest(hash.Hash160(script)) m.ABI.EntryPoint.Name = "somename" m.ABI.EntryPoint.Parameters = []manifest.Parameter{ manifest.NewParameter("first", smartcontract.IntegerType), manifest.NewParameter("second", smartcontract.StringType), } m.ABI.EntryPoint.ReturnType = smartcontract.BoolType cs := &state.Contract{ ID: 123, Script: script, Manifest: *m, } require.NoError(t, dao.PutContractState(cs)) cs2, err := dao.GetContractState(sh) require.Nil(t, err) require.Equal(t, cs, cs2) _, err = dao.Persist() require.Nil(t, err) dao2 := NewCached(pdao) cs2, err = dao2.GetContractState(sh) require.Nil(t, err) require.Equal(t, cs, cs2) require.NoError(t, dao.DeleteContractState(sh)) cs2, err = dao2.GetContractState(sh) require.Nil(t, err) require.Equal(t, cs, cs2) _, err = dao.GetContractState(sh) require.NotNil(t, err) } func TestCachedCachedDao(t *testing.T) { store := storage.NewMemoryStore() // Persistent DAO to check for backing storage. pdao := NewSimple(store, netmode.UnitTestNet) assert.NotEqual(t, store, pdao.Store) // Cached DAO. cdao := NewCached(pdao) cdaoDao := cdao.DAO.(*Simple) assert.NotEqual(t, store, cdaoDao.Store) assert.NotEqual(t, pdao.Store, cdaoDao.Store) // Cached cached DAO. ccdao := NewCached(cdao) ccdaoDao := ccdao.DAO.(*Cached) intDao := ccdaoDao.DAO.(*Simple) assert.NotEqual(t, store, intDao.Store) assert.NotEqual(t, pdao.Store, intDao.Store) assert.NotEqual(t, cdaoDao.Store, intDao.Store) id := int32(random.Int(0, 1024)) key := []byte("qwerty") si := &state.StorageItem{Value: []byte("poiuyt")} require.NoError(t, ccdao.PutStorageItem(id, key, si)) resi := ccdao.GetStorageItem(id, key) assert.Equal(t, si, resi) resi = cdao.GetStorageItem(id, key) assert.Equal(t, (*state.StorageItem)(nil), resi) resi = pdao.GetStorageItem(id, key) assert.Equal(t, (*state.StorageItem)(nil), resi) cnt, err := ccdao.Persist() assert.NoError(t, err) assert.Equal(t, 1, cnt) resi = cdao.GetStorageItem(id, key) assert.Equal(t, si, resi) resi = pdao.GetStorageItem(id, key) assert.Equal(t, (*state.StorageItem)(nil), resi) cnt, err = cdao.Persist() assert.NoError(t, err) assert.Equal(t, 1, cnt) resi = pdao.GetStorageItem(id, key) assert.Equal(t, si, resi) }