feat: Fetch community data for tokens (#4497)
This commit is contained in:
parent
54f3cf8af0
commit
dac7a0daf9
|
@ -455,7 +455,7 @@ func NewMessenger(
|
|||
if c.tokenManager != nil {
|
||||
managerOptions = append(managerOptions, communities.WithTokenManager(c.tokenManager))
|
||||
} else if c.rpcClient != nil {
|
||||
tokenManager := token.NewTokenManager(c.walletDb, c.rpcClient, community.NewManager(database, c.httpServer), c.rpcClient.NetworkManager, database, c.httpServer)
|
||||
tokenManager := token.NewTokenManager(c.walletDb, c.rpcClient, community.NewManager(database, c.httpServer, nil), c.rpcClient.NetworkManager, database, c.httpServer)
|
||||
managerOptions = append(managerOptions, communities.WithTokenManager(communities.NewDefaultTokenManager(tokenManager)))
|
||||
}
|
||||
|
||||
|
|
|
@ -2,22 +2,39 @@ package community
|
|||
|
||||
import (
|
||||
"database/sql"
|
||||
"encoding/json"
|
||||
|
||||
"github.com/ethereum/go-ethereum/event"
|
||||
"github.com/ethereum/go-ethereum/log"
|
||||
"github.com/status-im/status-go/server"
|
||||
"github.com/status-im/status-go/services/wallet/thirdparty"
|
||||
"github.com/status-im/status-go/services/wallet/walletevent"
|
||||
)
|
||||
|
||||
// These events are used to notify the UI of state changes
|
||||
const (
|
||||
EventCommmunityDataUpdated walletevent.EventType = "wallet-community-data-updated"
|
||||
)
|
||||
|
||||
type Manager struct {
|
||||
db *DataDB
|
||||
communityInfoProvider thirdparty.CommunityInfoProvider
|
||||
mediaServer *server.MediaServer
|
||||
feed *event.Feed
|
||||
}
|
||||
|
||||
func NewManager(db *sql.DB, mediaServer *server.MediaServer) *Manager {
|
||||
type Data struct {
|
||||
ID string `json:"id"`
|
||||
Name string `json:"name"`
|
||||
Color string `json:"color"`
|
||||
Image string `json:"image,omitempty"`
|
||||
}
|
||||
|
||||
func NewManager(db *sql.DB, mediaServer *server.MediaServer, feed *event.Feed) *Manager {
|
||||
return &Manager{
|
||||
db: NewDataDB(db),
|
||||
mediaServer: mediaServer,
|
||||
feed: feed,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -58,7 +75,43 @@ func (cm *Manager) FetchCommunityInfo(communityID string) (*thirdparty.Community
|
|||
}
|
||||
return nil, err
|
||||
}
|
||||
|
||||
err = cm.setCommunityInfo(communityID, communityInfo)
|
||||
return communityInfo, err
|
||||
}
|
||||
|
||||
func (cm *Manager) FetchCommunityMetadataAsync(communityID string) {
|
||||
go func() {
|
||||
communityInfo, err := cm.FetchCommunityInfo(communityID)
|
||||
if err != nil {
|
||||
log.Error("FetchCommunityInfo failed", "communityID", communityID, "err", err)
|
||||
return
|
||||
}
|
||||
|
||||
cm.signalUpdatedCommunityMetadata(communityID, communityInfo)
|
||||
}()
|
||||
}
|
||||
|
||||
func (cm *Manager) signalUpdatedCommunityMetadata(communityID string, communityInfo *thirdparty.CommunityInfo) {
|
||||
if communityInfo == nil {
|
||||
return
|
||||
}
|
||||
data := Data{
|
||||
ID: communityID,
|
||||
Name: communityInfo.CommunityName,
|
||||
Color: communityInfo.CommunityColor,
|
||||
Image: communityInfo.CommunityImage, // TODO make media server url after merging community token media server changes
|
||||
}
|
||||
|
||||
payload, err := json.Marshal(data)
|
||||
if err != nil {
|
||||
log.Error("Error marshaling response: %v", err)
|
||||
return
|
||||
}
|
||||
|
||||
event := walletevent.Event{
|
||||
Type: EventCommmunityDataUpdated,
|
||||
Message: string(payload),
|
||||
}
|
||||
|
||||
cm.feed.Send(event)
|
||||
}
|
||||
|
|
|
@ -14,6 +14,7 @@ import (
|
|||
"github.com/status-im/status-go/params"
|
||||
"github.com/status-im/status-go/rpc"
|
||||
"github.com/status-im/status-go/services/wallet/async"
|
||||
"github.com/status-im/status-go/services/wallet/community"
|
||||
"github.com/status-im/status-go/services/wallet/market"
|
||||
"github.com/status-im/status-go/services/wallet/thirdparty"
|
||||
"github.com/status-im/status-go/services/wallet/transfer"
|
||||
|
@ -46,11 +47,12 @@ func belongsToMandatoryTokens(symbol string) bool {
|
|||
return false
|
||||
}
|
||||
|
||||
func NewReader(rpcClient *rpc.Client, tokenManager *token.Manager, marketManager *market.Manager, accountsDB *accounts.Database, persistence *Persistence, walletFeed *event.Feed) *Reader {
|
||||
func NewReader(rpcClient *rpc.Client, tokenManager *token.Manager, marketManager *market.Manager, communityManager *community.Manager, accountsDB *accounts.Database, persistence *Persistence, walletFeed *event.Feed) *Reader {
|
||||
return &Reader{
|
||||
rpcClient: rpcClient,
|
||||
tokenManager: tokenManager,
|
||||
marketManager: marketManager,
|
||||
communityManager: communityManager,
|
||||
accountsDB: accountsDB,
|
||||
persistence: persistence,
|
||||
walletFeed: walletFeed,
|
||||
|
@ -62,6 +64,7 @@ type Reader struct {
|
|||
rpcClient *rpc.Client
|
||||
tokenManager *token.Manager
|
||||
marketManager *market.Manager
|
||||
communityManager *community.Manager
|
||||
accountsDB *accounts.Database
|
||||
persistence *Persistence
|
||||
walletFeed *event.Feed
|
||||
|
@ -103,7 +106,7 @@ type Token struct {
|
|||
PegSymbol string `json:"pegSymbol"`
|
||||
Verified bool `json:"verified"`
|
||||
Image string `json:"image,omitempty"`
|
||||
CommunityData *token.CommunityData `json:"community_data,omitempty"`
|
||||
CommunityData *community.Data `json:"community_data,omitempty"`
|
||||
}
|
||||
|
||||
func splitVerifiedTokens(tokens []*token.Token) ([]*token.Token, []*token.Token) {
|
||||
|
@ -389,6 +392,8 @@ func (r *Reader) GetWalletToken(ctx context.Context, addresses []common.Address)
|
|||
return nil, err
|
||||
}
|
||||
|
||||
communities := make(map[string]bool)
|
||||
|
||||
for address, tokens := range result {
|
||||
for index, token := range tokens {
|
||||
marketValuesPerCurrency := make(map[string]TokenMarketValues)
|
||||
|
@ -409,6 +414,10 @@ func (r *Reader) GetWalletToken(ctx context.Context, addresses []common.Address)
|
|||
}
|
||||
}
|
||||
|
||||
if token.CommunityData != nil {
|
||||
communities[token.CommunityData.ID] = true
|
||||
}
|
||||
|
||||
if _, ok := tokenDetails[token.Symbol]; !ok {
|
||||
continue
|
||||
}
|
||||
|
@ -422,6 +431,10 @@ func (r *Reader) GetWalletToken(ctx context.Context, addresses []common.Address)
|
|||
|
||||
r.lastWalletTokenUpdateTimestamp.Store(time.Now().Unix())
|
||||
|
||||
for communityID := range communities {
|
||||
r.communityManager.FetchCommunityMetadataAsync(communityID)
|
||||
}
|
||||
|
||||
return result, r.persistence.SaveTokens(result)
|
||||
}
|
||||
|
||||
|
|
|
@ -99,7 +99,7 @@ func NewService(
|
|||
})
|
||||
})
|
||||
|
||||
communityManager := community.NewManager(db, mediaServer)
|
||||
communityManager := community.NewManager(db, mediaServer, feed)
|
||||
balanceCacher := balance.NewCacherWithTTL(5 * time.Minute)
|
||||
tokenManager := token.NewTokenManager(db, rpcClient, communityManager, rpcClient.NetworkManager, appDB, mediaServer)
|
||||
savedAddressesManager := &SavedAddressesManager{db: db}
|
||||
|
@ -110,7 +110,7 @@ func NewService(
|
|||
cryptoCompare := cryptocompare.NewClient()
|
||||
coingecko := coingecko.NewClient()
|
||||
marketManager := market.NewManager(cryptoCompare, coingecko, feed)
|
||||
reader := NewReader(rpcClient, tokenManager, marketManager, accountsDB, NewPersistence(db), feed)
|
||||
reader := NewReader(rpcClient, tokenManager, marketManager, communityManager, accountsDB, NewPersistence(db), feed)
|
||||
history := history.NewService(db, accountsDB, feed, rpcClient, tokenManager, marketManager, balanceCacher.Cache())
|
||||
currency := currency.NewService(db, feed, tokenManager, marketManager)
|
||||
blockChainState := NewBlockChainState(rpcClient, accountsDB)
|
||||
|
|
|
@ -49,16 +49,9 @@ type Token struct {
|
|||
PegSymbol string `json:"pegSymbol"`
|
||||
Image string `json:"image,omitempty"`
|
||||
|
||||
CommunityData *CommunityData `json:"community_data,omitempty"`
|
||||
Verified bool `json:"verified"`
|
||||
TokenListID string `json:"tokenListId"`
|
||||
}
|
||||
|
||||
type CommunityData struct {
|
||||
ID string `json:"id"`
|
||||
Name string `json:"name"`
|
||||
Color string `json:"color"`
|
||||
Image string `json:"image,omitempty"`
|
||||
CommunityData *community.Data `json:"community_data,omitempty"`
|
||||
Verified bool `json:"verified"`
|
||||
TokenListID string `json:"tokenListId"`
|
||||
}
|
||||
|
||||
func (t *Token) IsNative() bool {
|
||||
|
@ -551,7 +544,7 @@ func (tm *Manager) getTokensFromDB(query string, args ...any) ([]*Token, error)
|
|||
break
|
||||
}
|
||||
|
||||
token.CommunityData = &CommunityData{
|
||||
token.CommunityData = &community.Data{
|
||||
ID: communityID,
|
||||
}
|
||||
}
|
||||
|
|
|
@ -8,6 +8,7 @@ import (
|
|||
"github.com/ethereum/go-ethereum/common"
|
||||
|
||||
"github.com/status-im/status-go/params"
|
||||
"github.com/status-im/status-go/services/wallet/community"
|
||||
"github.com/status-im/status-go/t/helpers"
|
||||
"github.com/status-im/status-go/walletdatabase"
|
||||
)
|
||||
|
@ -97,7 +98,7 @@ func TestCommunityTokens(t *testing.T) {
|
|||
Symbol: "COM",
|
||||
Decimals: 12,
|
||||
ChainID: 777,
|
||||
CommunityData: &CommunityData{
|
||||
CommunityData: &community.Data{
|
||||
ID: "random_community_id",
|
||||
},
|
||||
}
|
||||
|
|
|
@ -937,7 +937,8 @@ func TestFindBlocksCommand(t *testing.T) {
|
|||
}
|
||||
client, _ := statusRpc.NewClient(nil, 1, params.UpstreamRPCConfig{Enabled: false, URL: ""}, []params.Network{}, db)
|
||||
client.SetClient(tc.NetworkID(), tc)
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
|
||||
tokenManager.SetTokens([]*token.Token{
|
||||
{
|
||||
Address: tokenTXXAddress,
|
||||
|
@ -1062,7 +1063,7 @@ func TestFetchTransfersForLoadedBlocks(t *testing.T) {
|
|||
|
||||
client, _ := statusRpc.NewClient(nil, 1, params.UpstreamRPCConfig{Enabled: false, URL: ""}, []params.Network{}, db)
|
||||
client.SetClient(tc.NetworkID(), tc)
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
|
||||
tokenManager.SetTokens([]*token.Token{
|
||||
{
|
||||
|
@ -1182,7 +1183,7 @@ func TestFetchNewBlocksCommand_findBlocksWithEthTransfers(t *testing.T) {
|
|||
|
||||
client, _ := statusRpc.NewClient(nil, 1, params.UpstreamRPCConfig{Enabled: false, URL: ""}, []params.Network{}, db)
|
||||
client.SetClient(tc.NetworkID(), tc)
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
|
||||
tokenManager.SetTokens([]*token.Token{
|
||||
{
|
||||
|
@ -1259,8 +1260,7 @@ func TestFetchNewBlocksCommand(t *testing.T) {
|
|||
|
||||
client, _ := statusRpc.NewClient(nil, 1, params.UpstreamRPCConfig{Enabled: false, URL: ""}, []params.Network{}, db)
|
||||
client.SetClient(tc.NetworkID(), tc)
|
||||
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
tokenManager := token.NewTokenManager(db, client, community.NewManager(appdb, nil, nil), network.NewManager(appdb), appdb, mediaServer)
|
||||
|
||||
tokenManager.SetTokens([]*token.Token{
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue