mirror of
https://github.com/status-im/status-go.git
synced 2025-01-09 22:26:30 +00:00
2df9df10ab
interface for initializing db, which is implemented for appdatabase and walletdatabase. TBD for multiaccounts DB. Unified DB initializion for all tests using helpers and new interface. Reduced sqlcipher kdf iterations for all tests to 1.
396 lines
11 KiB
Go
396 lines
11 KiB
Go
package wallet
|
|
|
|
import (
|
|
"strconv"
|
|
"testing"
|
|
"time"
|
|
|
|
"github.com/stretchr/testify/require"
|
|
|
|
"github.com/ethereum/go-ethereum/common"
|
|
"github.com/status-im/status-go/t/helpers"
|
|
"github.com/status-im/status-go/walletdatabase"
|
|
)
|
|
|
|
const (
|
|
ensMember int = iota
|
|
isTestMember
|
|
addressMember
|
|
)
|
|
|
|
func setupTestSavedAddressesDB(t *testing.T) (*SavedAddressesManager, func()) {
|
|
db, err := helpers.SetupTestMemorySQLDB(walletdatabase.DbInitializer{})
|
|
require.NoError(t, err)
|
|
|
|
return &SavedAddressesManager{db}, func() {
|
|
require.NoError(t, db.Close())
|
|
}
|
|
}
|
|
|
|
func TestSavedAddressesAdd(t *testing.T) {
|
|
manager, stop := setupTestSavedAddressesDB(t)
|
|
defer stop()
|
|
|
|
rst, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Nil(t, rst)
|
|
|
|
sa := SavedAddress{
|
|
Address: common.Address{1},
|
|
Name: "Zilliqa",
|
|
Favourite: true,
|
|
ChainShortNames: "eth:arb:",
|
|
ENSName: "test.stateofus.eth",
|
|
IsTest: false,
|
|
}
|
|
|
|
_, err = manager.UpdateMetadataAndUpsertSavedAddress(sa)
|
|
require.NoError(t, err)
|
|
|
|
rst, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(rst))
|
|
require.Equal(t, sa.Address, rst[0].Address)
|
|
require.Equal(t, sa.Name, rst[0].Name)
|
|
require.Equal(t, sa.Favourite, rst[0].Favourite)
|
|
require.Equal(t, sa.ChainShortNames, rst[0].ChainShortNames)
|
|
require.Equal(t, sa.ENSName, rst[0].ENSName)
|
|
require.Equal(t, sa.IsTest, rst[0].IsTest)
|
|
}
|
|
|
|
func contains[T comparable](container []T, element T, isEqual func(T, T) bool) bool {
|
|
for _, e := range container {
|
|
if isEqual(e, element) {
|
|
return true
|
|
}
|
|
}
|
|
return false
|
|
}
|
|
|
|
func haveSameElements[T comparable](a []T, b []T, isEqual func(T, T) bool) bool {
|
|
for _, v := range a {
|
|
if !contains(b, v, isEqual) {
|
|
return false
|
|
}
|
|
}
|
|
return true
|
|
}
|
|
|
|
func savedAddressDataIsEqual(a, b SavedAddress) bool {
|
|
return a.Address == b.Address && a.Name == b.Name && a.Favourite == b.Favourite &&
|
|
a.ChainShortNames == b.ChainShortNames && a.ENSName == b.ENSName && a.IsTest == b.IsTest
|
|
}
|
|
|
|
func TestSavedAddressesMetadata(t *testing.T) {
|
|
manager, stop := setupTestSavedAddressesDB(t)
|
|
defer stop()
|
|
|
|
savedAddresses, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Nil(t, savedAddresses)
|
|
|
|
// Add raw saved addresses
|
|
sa1 := SavedAddress{
|
|
Address: common.Address{1},
|
|
Name: "Raw",
|
|
Favourite: true,
|
|
savedAddressMeta: savedAddressMeta{
|
|
Removed: false,
|
|
UpdateClock: 234,
|
|
},
|
|
ChainShortNames: "eth:arb:",
|
|
ENSName: "test.stateofus.eth",
|
|
IsTest: false,
|
|
}
|
|
|
|
err = manager.upsertSavedAddress(sa1, nil)
|
|
require.NoError(t, err)
|
|
|
|
dbSavedAddresses, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(dbSavedAddresses))
|
|
require.Equal(t, sa1.Address, dbSavedAddresses[0].Address)
|
|
|
|
// Add simple saved address without sync metadata
|
|
sa2 := SavedAddress{
|
|
Address: common.Address{2},
|
|
Name: "Simple",
|
|
Favourite: false,
|
|
IsTest: false,
|
|
}
|
|
|
|
var sa2UpdatedClock uint64
|
|
sa2UpdatedClock, err = manager.UpdateMetadataAndUpsertSavedAddress(sa2)
|
|
require.NoError(t, err)
|
|
|
|
dbSavedAddresses, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 2, len(dbSavedAddresses))
|
|
// The order is not guaranteed check raw entry to decide
|
|
rawIndex := 0
|
|
simpleIndex := 1
|
|
if dbSavedAddresses[0] != sa1 {
|
|
rawIndex = 1
|
|
simpleIndex = 0
|
|
}
|
|
require.Equal(t, sa1.Address, dbSavedAddresses[simpleIndex].Address)
|
|
require.Equal(t, sa2.Address, dbSavedAddresses[rawIndex].Address)
|
|
require.Equal(t, sa2.Name, dbSavedAddresses[rawIndex].Name)
|
|
require.Equal(t, sa2.Favourite, dbSavedAddresses[rawIndex].Favourite)
|
|
require.Equal(t, sa2.IsTest, dbSavedAddresses[rawIndex].IsTest)
|
|
|
|
// Check the default values
|
|
require.False(t, dbSavedAddresses[rawIndex].Removed)
|
|
require.Equal(t, dbSavedAddresses[rawIndex].UpdateClock, sa2UpdatedClock)
|
|
require.Greater(t, dbSavedAddresses[rawIndex].UpdateClock, uint64(0))
|
|
|
|
sa2Older := sa2
|
|
sa2Older.Favourite = true
|
|
sa2Older.IsTest = false
|
|
|
|
sa2Newer := sa2
|
|
sa2Newer.Favourite = false
|
|
sa2Newer.IsTest = false
|
|
|
|
// Try to add an older entry
|
|
updated := false
|
|
updated, err = manager.AddSavedAddressIfNewerUpdate(sa2Older, dbSavedAddresses[rawIndex].UpdateClock-1)
|
|
require.NoError(t, err)
|
|
require.False(t, updated)
|
|
|
|
dbSavedAddresses, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
|
|
rawIndex = 0
|
|
simpleIndex = 1
|
|
if dbSavedAddresses[0] != sa1 {
|
|
rawIndex = 1
|
|
simpleIndex = 0
|
|
}
|
|
|
|
require.Equal(t, 2, len(dbSavedAddresses))
|
|
require.True(t, haveSameElements([]SavedAddress{sa1, sa2}, dbSavedAddresses, savedAddressDataIsEqual))
|
|
require.Equal(t, sa1.savedAddressMeta, dbSavedAddresses[simpleIndex].savedAddressMeta)
|
|
|
|
// Try to update sa2 with a newer entry
|
|
updatedClock := dbSavedAddresses[rawIndex].UpdateClock + 1
|
|
updated, err = manager.AddSavedAddressIfNewerUpdate(sa2Newer, updatedClock)
|
|
require.NoError(t, err)
|
|
require.True(t, updated)
|
|
|
|
dbSavedAddresses, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
|
|
require.Equal(t, 2, len(dbSavedAddresses))
|
|
require.True(t, haveSameElements([]SavedAddress{sa1, sa2Newer}, dbSavedAddresses, savedAddressDataIsEqual))
|
|
require.Equal(t, updatedClock, dbSavedAddresses[rawIndex].UpdateClock)
|
|
|
|
// Try to delete the sa2 newer entry
|
|
updatedDeleteClock := updatedClock + 1
|
|
updated, err = manager.DeleteSavedAddress(sa2Newer.Address, sa2Newer.ENSName, sa2Newer.IsTest, updatedDeleteClock)
|
|
require.NoError(t, err)
|
|
require.True(t, updated)
|
|
|
|
dbSavedAddresses, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
|
|
require.Equal(t, 2, len(dbSavedAddresses))
|
|
require.True(t, dbSavedAddresses[rawIndex].Removed)
|
|
|
|
// Check that deleted entry is not returned with the regular API (non-raw)
|
|
dbSavedAddresses, err = manager.GetSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(dbSavedAddresses))
|
|
}
|
|
|
|
func TestSavedAddressesCleanSoftDeletes(t *testing.T) {
|
|
manager, stop := setupTestSavedAddressesDB(t)
|
|
defer stop()
|
|
|
|
firstTimestamp := 10
|
|
for i := 0; i < 5; i++ {
|
|
sa := SavedAddress{
|
|
Address: common.Address{byte(i)},
|
|
Name: "Test" + strconv.Itoa(i),
|
|
Favourite: false,
|
|
savedAddressMeta: savedAddressMeta{
|
|
Removed: true,
|
|
UpdateClock: uint64(firstTimestamp + i),
|
|
},
|
|
}
|
|
|
|
err := manager.upsertSavedAddress(sa, nil)
|
|
require.NoError(t, err)
|
|
}
|
|
|
|
err := manager.DeleteSoftRemovedSavedAddresses(uint64(firstTimestamp + 3))
|
|
require.NoError(t, err)
|
|
|
|
dbSavedAddresses, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 2, len(dbSavedAddresses))
|
|
require.True(t, haveSameElements([]uint64{dbSavedAddresses[0].UpdateClock,
|
|
dbSavedAddresses[1].UpdateClock}, []uint64{uint64(firstTimestamp + 3), uint64(firstTimestamp + 4)},
|
|
func(a, b uint64) bool {
|
|
return a == b
|
|
},
|
|
))
|
|
}
|
|
|
|
func TestSavedAddressesGet(t *testing.T) {
|
|
manager, stop := setupTestSavedAddressesDB(t)
|
|
defer stop()
|
|
|
|
sa := SavedAddress{
|
|
Address: common.Address{1},
|
|
ENSName: "test.ens.eth",
|
|
IsTest: false,
|
|
savedAddressMeta: savedAddressMeta{
|
|
Removed: true,
|
|
},
|
|
}
|
|
|
|
err := manager.upsertSavedAddress(sa, nil)
|
|
require.NoError(t, err)
|
|
|
|
dbSavedAddresses, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(dbSavedAddresses))
|
|
|
|
require.True(t, savedAddressDataIsEqual(sa, dbSavedAddresses[0]))
|
|
|
|
dbSavedAddresses, err = manager.GetSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 0, len(dbSavedAddresses))
|
|
}
|
|
|
|
func TestSavedAddressesDelete(t *testing.T) {
|
|
manager, stop := setupTestSavedAddressesDB(t)
|
|
defer stop()
|
|
|
|
sa0 := SavedAddress{
|
|
Address: common.Address{1},
|
|
IsTest: false,
|
|
}
|
|
|
|
err := manager.upsertSavedAddress(sa0, nil)
|
|
require.NoError(t, err)
|
|
|
|
rst, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(rst))
|
|
|
|
require.True(t, savedAddressDataIsEqual(sa0, rst[0]))
|
|
|
|
// Modify IsTest flag, insert
|
|
sa1 := sa0
|
|
sa1.IsTest = !sa1.IsTest
|
|
|
|
err = manager.upsertSavedAddress(sa1, nil)
|
|
require.NoError(t, err)
|
|
|
|
// Delete s0, test that only s1 is left
|
|
updateClock := uint64(time.Now().Unix())
|
|
_, err = manager.DeleteSavedAddress(sa0.Address, sa0.ENSName, sa0.IsTest, updateClock)
|
|
require.NoError(t, err)
|
|
|
|
rst, err = manager.GetSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(rst))
|
|
require.True(t, savedAddressDataIsEqual(sa1, rst[0]))
|
|
|
|
// Test that we still have both addresses
|
|
rst, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 2, len(rst))
|
|
|
|
// Delete s0 one more time with the same timestamp
|
|
deleted, err := manager.DeleteSavedAddress(sa0.Address, sa0.ENSName, sa0.IsTest, updateClock)
|
|
require.NoError(t, err)
|
|
require.False(t, deleted)
|
|
}
|
|
|
|
func testInsertSameAddressWithOneChange(t *testing.T, member int) {
|
|
manager, stop := setupTestSavedAddressesDB(t)
|
|
defer stop()
|
|
|
|
// Insert one address
|
|
sa := SavedAddress{
|
|
Address: common.Address{1},
|
|
ENSName: "test.ens.eth",
|
|
IsTest: true,
|
|
}
|
|
|
|
err := manager.upsertSavedAddress(sa, nil)
|
|
require.NoError(t, err)
|
|
|
|
rst, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(rst))
|
|
|
|
require.True(t, savedAddressDataIsEqual(sa, rst[0]))
|
|
|
|
sa2 := sa
|
|
|
|
if member == isTestMember {
|
|
sa2.IsTest = !sa2.IsTest
|
|
} else if member == addressMember {
|
|
sa2.Address = common.Address{7}
|
|
} else if member == ensMember {
|
|
sa2.ENSName += "_"
|
|
} else {
|
|
t.Error("Unsupported member change. Please add it to the list")
|
|
}
|
|
|
|
err = manager.upsertSavedAddress(sa2, nil)
|
|
require.NoError(t, err)
|
|
|
|
rst, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 2, len(rst))
|
|
|
|
// The order of records returned by GetRawSavedAddresses is not
|
|
// guaranteed to be the same as insertions, so swap indices if first record does not match
|
|
firstIndex := 0
|
|
secondIndex := 1
|
|
if rst[firstIndex] != sa {
|
|
firstIndex = 1
|
|
secondIndex = 0
|
|
}
|
|
require.True(t, savedAddressDataIsEqual(sa, rst[firstIndex]))
|
|
require.True(t, savedAddressDataIsEqual(sa2, rst[secondIndex]))
|
|
}
|
|
|
|
func TestSavedAddressesAddDifferentIsTest(t *testing.T) {
|
|
testInsertSameAddressWithOneChange(t, isTestMember)
|
|
}
|
|
|
|
func TestSavedAddressesAddSame(t *testing.T) {
|
|
manager, stop := setupTestSavedAddressesDB(t)
|
|
defer stop()
|
|
|
|
// Insert one address
|
|
sa := SavedAddress{
|
|
Address: common.Address{1},
|
|
ENSName: "test.ens.eth",
|
|
IsTest: true,
|
|
}
|
|
|
|
err := manager.upsertSavedAddress(sa, nil)
|
|
require.NoError(t, err)
|
|
|
|
rst, err := manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(rst))
|
|
|
|
require.True(t, savedAddressDataIsEqual(sa, rst[0]))
|
|
|
|
sa2 := sa
|
|
err = manager.upsertSavedAddress(sa2, nil)
|
|
require.NoError(t, err)
|
|
|
|
rst, err = manager.GetRawSavedAddresses()
|
|
require.NoError(t, err)
|
|
require.Equal(t, 1, len(rst))
|
|
}
|