Commit e865d202 authored by vicotor's avatar vicotor

add swap token config support.

parent b086b896
......@@ -54,6 +54,10 @@ func (s *ChainSync) ParseTokenConfigChanged(log *types.Log) (*bridge.BridgeContr
return s.bridgeCa.ParseTokenOutConfigChanged(*log)
}
func (s *ChainSync) ParseSwapConfigChanged(log *types.Log) (*bridge.BridgeContractSwapConfigChanged, error) {
return s.bridgeCa.ParseSwapConfigChanged(*log)
}
func (s *ChainSync) GetReceiveToken(token common.Address, toChainId int64) (string, error) {
callOpt := &bind.CallOpts{
BlockNumber: nil,
......@@ -206,6 +210,7 @@ func (s *ChainSync) SyncLogs(beginHeight, endHeight int64) error {
dao.TransferInRejectionEvent.ID.Hex(),
dao.TransferInExecutionEvent.ID.Hex(),
dao.TokenConfigChangedEvent.ID.Hex(),
dao.SwapConfigChangedEvent.ID.Hex(),
}
logs, err := s.d.GetLogs(s.chain, beginHeight, endHeight, topics, []string{
......
......@@ -46,6 +46,7 @@ const (
EVENT_TRANSFER_IN_REJECTION = "TransferInRejection"
EVENT_TRANSFER_IN_EXECUTION = "TransferInExecution"
EVENT_TOKENCONFIGCHANGED = "TokenOutConfigChanged"
EVENT_SWAPCONFIGCHANGED = "SwapConfigChanged"
)
type ValidatorOp int
......
This diff is collapsed.
[
{
"anonymous": false,
"inputs": [
{
"indexed": false,
"internalType": "address",
"name": "initialOwner",
"name": "previousAdmin",
"type": "address"
},
{
"indexed": false,
"internalType": "address",
"name": "newAdmin",
"type": "address"
}
],
"stateMutability": "nonpayable",
"type": "constructor"
"name": "AdminChanged",
"type": "event"
},
{
"anonymous": false,
"inputs": [
{
"indexed": true,
"internalType": "address",
"name": "owner",
"name": "beacon",
"type": "address"
}
],
"name": "OwnableInvalidOwner",
"type": "error"
"name": "BeaconUpgraded",
"type": "event"
},
{
"anonymous": false,
"inputs": [
{
"indexed": true,
"internalType": "address",
"name": "oldReceiver",
"type": "address"
},
{
"indexed": true,
"internalType": "address",
"name": "account",
"name": "newReceiver",
"type": "address"
}
],
"name": "OwnableUnauthorizedAccount",
"type": "error"
"name": "FeeReceiverChanged",
"type": "event"
},
{
"anonymous": false,
......@@ -70,6 +88,37 @@
"name": "RequirementChange",
"type": "event"
},
{
"anonymous": false,
"inputs": [
{
"indexed": true,
"internalType": "address",
"name": "fromToken",
"type": "address"
},
{
"indexed": true,
"internalType": "address",
"name": "toToken",
"type": "address"
},
{
"indexed": true,
"internalType": "address",
"name": "swap",
"type": "address"
},
{
"indexed": false,
"internalType": "address[]",
"name": "path",
"type": "address[]"
}
],
"name": "SwapConfigChanged",
"type": "event"
},
{
"anonymous": false,
"inputs": [
......@@ -211,19 +260,19 @@
"anonymous": false,
"inputs": [
{
"indexed": false,
"indexed": true,
"internalType": "uint256",
"name": "outId",
"type": "uint256"
},
{
"indexed": false,
"indexed": true,
"internalType": "uint256",
"name": "fromChainID",
"type": "uint256"
},
{
"indexed": false,
"indexed": true,
"internalType": "address",
"name": "sender",
"type": "address"
......@@ -349,6 +398,19 @@
"name": "TreasuryTransfer",
"type": "event"
},
{
"anonymous": false,
"inputs": [
{
"indexed": true,
"internalType": "address",
"name": "implementation",
"type": "address"
}
],
"name": "Upgraded",
"type": "event"
},
{
"anonymous": false,
"inputs": [
......@@ -560,6 +622,19 @@
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [],
"name": "feeReceiver",
"outputs": [
{
"internalType": "address",
"name": "",
"type": "address"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [
{
......@@ -686,6 +761,19 @@
"stateMutability": "view",
"type": "function"
},
{
"inputs": [
{
"internalType": "address",
"name": "initialOwner",
"type": "address"
}
],
"name": "initialize",
"outputs": [],
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [
{
......@@ -993,6 +1081,19 @@
"stateMutability": "view",
"type": "function"
},
{
"inputs": [],
"name": "proxiableUUID",
"outputs": [
{
"internalType": "bytes32",
"name": "",
"type": "bytes32"
}
],
"stateMutability": "view",
"type": "function"
},
{
"inputs": [
{
......@@ -1072,6 +1173,19 @@
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [
{
"internalType": "address",
"name": "newReceiver",
"type": "address"
}
],
"name": "setFeeReceiver",
"outputs": [],
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [
{
......@@ -1276,6 +1390,37 @@
"stateMutability": "view",
"type": "function"
},
{
"inputs": [
{
"internalType": "address",
"name": "newImplementation",
"type": "address"
}
],
"name": "upgradeTo",
"outputs": [],
"stateMutability": "nonpayable",
"type": "function"
},
{
"inputs": [
{
"internalType": "address",
"name": "newImplementation",
"type": "address"
},
{
"internalType": "bytes",
"name": "data",
"type": "bytes"
}
],
"name": "upgradeToAndCall",
"outputs": [],
"stateMutability": "payable",
"type": "function"
},
{
"inputs": [],
"name": "validRequired",
......
......@@ -23,6 +23,7 @@ type ChainInterface interface {
ParseTransferInRejection(log *types.Log) (*bridge.BridgeContractTransferInRejection, error)
ParseTransferInConfirmation(log *types.Log) (*bridge.BridgeContractTransferInConfirmation, error)
ParseTokenConfigChanged(log *types.Log) (*bridge.BridgeContractTokenOutConfigChanged, error)
ParseSwapConfigChanged(log *types.Log) (*bridge.BridgeContractSwapConfigChanged, error)
GetReceiveToken(token common.Address, toChainId int64) (string, error)
}
......@@ -34,6 +35,7 @@ var (
TransferInRejectionEvent = bridgeAbi.Events[EVENT_TRANSFER_IN_REJECTION]
TransferInConfirmationEvent = bridgeAbi.Events[EVENT_TRANSFER_IN_CONFIRMATION]
TokenConfigChangedEvent = bridgeAbi.Events[EVENT_TOKENCONFIGCHANGED]
SwapConfigChangedEvent = bridgeAbi.Events[EVENT_SWAPCONFIGCHANGED]
)
func (s *Dao) HandleEvents(chain ChainInterface, logs []types.Log) error {
......@@ -43,6 +45,7 @@ func (s *Dao) HandleEvents(chain ChainInterface, logs []types.Log) error {
var allTransferOut = make([]types.Log, 0)
var allTransferIn = make([]types.Log, 0)
var allTokenConfigChanged = make([]types.Log, 0)
var allSwapConfigChanged = make([]types.Log, 0)
var allExecuted = make([]types.Log, 0)
var allRejected = make([]types.Log, 0)
var allConfirmed = make([]types.Log, 0)
......@@ -55,6 +58,8 @@ func (s *Dao) HandleEvents(chain ChainInterface, logs []types.Log) error {
allTransferIn = append(allTransferIn, lg)
case TokenConfigChangedEvent.ID.Hex():
allTokenConfigChanged = append(allTokenConfigChanged, lg)
case SwapConfigChangedEvent.ID.Hex():
allSwapConfigChanged = append(allSwapConfigChanged, lg)
case TransferInExecutionEvent.ID.Hex():
allExecuted = append(allExecuted, lg)
case TransferInRejectionEvent.ID.Hex():
......@@ -70,6 +75,7 @@ func (s *Dao) HandleEvents(chain ChainInterface, logs []types.Log) error {
allLogs = append(allLogs, allRejected...)
allLogs = append(allLogs, allConfirmed...)
allLogs = append(allLogs, allExecuted...)
allLogs = append(allLogs, allSwapConfigChanged...)
// disable the code.
if false {
......@@ -128,6 +134,10 @@ func (s *Dao) HandleEvents(chain ChainInterface, logs []types.Log) error {
ormTxErr = err
break
}
if err := s.filterSwapConfigChanged(chain, txLog, ctx); err != nil {
ormTxErr = err
break
}
}
// commit or rollback.
......@@ -394,3 +404,44 @@ func (s *Dao) filterTokenConfigChanged(chain ChainInterface, txLog *types.Log, c
}
return nil
}
func (s *Dao) filterSwapConfigChanged(chain ChainInterface, txLog *types.Log, ctx context.Context) error {
if len(txLog.Topics) == 0 {
return nil
}
if txLog.Topics[0].Hex() == SwapConfigChangedEvent.ID.Hex() {
configure, err := chain.ParseSwapConfigChanged(txLog)
if err != nil {
return err
}
info := &dbModel.SwapTokenInfo{
ChainId: chain.GetChain().ChainId,
Contract: strings.ToLower(txLog.Address.String()),
Token: strings.ToLower(configure.FromToken.String()),
SwapContract: strings.ToLower(configure.Swap.String()),
ToToken: strings.ToLower(configure.ToToken.String()),
SwapPath: make([]string, 0),
}
for _, addr := range configure.Path {
info.SwapPath = append(info.SwapPath, strings.ToLower(addr.String()))
}
if tokenInfo, err := s.tokenRepo.RetriveTokenInfo(chain.GetChain().ChainId, configure.FromToken.Hex()); err == nil {
info.TokenName = tokenInfo.Symbol
}
err = s.CreateSwapTokenInfo(ctx, info)
if err != nil {
log.WithFields(log.Fields{
"chain": chain.Name(),
"token": configure.FromToken.Hex(),
"toToken": configure.ToToken.Hex(),
"swap": configure.Swap.Hex(),
"swapPath": info.SwapPath,
}).WithError(err).Error("db create or update token config failed")
return err
}
}
return nil
}
......@@ -191,3 +191,73 @@ func (d *Dao) GetHistoryInfo(user string) (history apiModel.History, err error)
return history, nil
}
func (d *Dao) GetSwapConfig(chainId int64) (config apiModel.SwapConfigs, err error) {
collection := d.db.Collection(new(dbModel.SwapTokenInfo).TableName())
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()
// Find all swap token info fillter by chain_id.
cursor, err := collection.Find(ctx, bson.M{})
if err != nil {
return config, err
}
defer cursor.Close(ctx)
var swaps []dbModel.SwapTokenInfo
err = cursor.All(ctx, &swaps)
if err != nil {
return config, err
}
config.SwapPairs = make(map[string]apiModel.SwapPair)
// Convert database model to API model
for _, info := range swaps {
if info.ChainId != chainId {
continue
}
swap := apiModel.SwapPair{
From: apiModel.TokenInfo{
Contract: info.Token,
Name: info.TokenName,
},
To: apiModel.TokenInfo{
Contract: info.ToToken,
Name: "",
},
SwapContract: info.SwapContract,
SwapPath: make([]string, 0),
}
for _, pathToken := range info.SwapPath {
swap.SwapPath = append(swap.SwapPath, pathToken)
}
if swap.From.Name == "" {
tokenInfo, err := d.tokenRepo.RetriveTokenInfo(info.ChainId, info.Token)
if err != nil {
log.WithFields(log.Fields{
"chain_id": info.ChainId,
"token": info.Token,
"error": err,
}).Error("not found token info with tokenrepo, skip symbol info")
} else {
swap.From.Name = tokenInfo.Symbol
}
}
if swap.To.Name == "" {
toTokenInfo, err := d.tokenRepo.RetriveTokenInfo(info.ChainId, info.ToToken)
if err != nil {
log.WithFields(log.Fields{
"chain_id": info.ChainId,
"token": info.ToToken,
"error": err,
}).Error("not found token info with tokenrepo, skip symbol info")
} else {
swap.To.Name = toTokenInfo.Symbol
}
}
config.SwapPairs[swap.From.Name] = swap
}
return config, nil
}
......@@ -228,3 +228,16 @@ func (d *Dao) GetTokenInfo(address string) (info dbModel.TokenInfo, err error) {
}
return info, err
}
func (d *Dao) CreateSwapTokenInfo(ctx context.Context, info *dbModel.SwapTokenInfo) error {
collection := d.db.Collection(info.TableName())
filter := bson.M{"chain_id": info.ChainId, "token": info.Token, "contract": info.Contract}
update := bson.D{
{"$set", info},
}
opts := options.Update().SetUpsert(true)
_, err := collection.UpdateOne(ctx, filter, update, opts)
return err
}
......@@ -15,6 +15,22 @@ type ChainConfig struct {
RpcUrl string `json:"rpc" bson:"rpc"`
}
type TokenInfo struct {
Name string `json:"name" bson:"name"`
Contract string `json:"contract" bson:"contract"`
}
type SwapPair struct {
From TokenInfo `json:"from" bson:"from"`
To TokenInfo `json:"to" bson:"to"`
SwapContract string `json:"swap_contract" bson:"swap_contract"`
SwapPath []string `json:"swap_path" bson:"swap_path"`
}
type SwapConfigs struct {
SwapPairs map[string]SwapPair `json:"swap_pairs" bson:"swap_pairs"`
}
type BridgeConfig struct {
Chains map[string]ChainConfig `json:"chains" bson:"chains"`
}
......@@ -42,5 +58,6 @@ type History struct {
type Querier interface {
GetBridgeConfig() (config BridgeConfig, err error)
GetSwapConfig(chainId int64) (config SwapConfigs, err error)
GetHistoryInfo(user string) (history History, err error)
}
......@@ -92,6 +92,21 @@ func (b *BridgeTokenInfo) TableName() string {
return "bridge_token_info"
}
type SwapTokenInfo struct {
ID primitive.ObjectID `bson:"_id,omitempty"`
ChainId int64 `bson:"chain_id"`
Contract string `bson:"contract"`
Token string `bson:"token"`
TokenName string `bson:"token_name"`
SwapContract string `bson:"swap_contract"`
ToToken string `bson:"to_token"`
SwapPath []string `bson:"swap_path"`
}
func (b *SwapTokenInfo) TableName() string {
return "swap_token_info"
}
type TokenInfo struct {
ID primitive.ObjectID `bson:"_id,omitempty"`
Address string `bson:"address"`
......
......@@ -4,6 +4,7 @@ import (
"code.wuban.net.cn/movabridge/bridge-backend/constant"
"github.com/ethereum/go-ethereum/common"
log "github.com/sirupsen/logrus"
"strconv"
"strings"
"github.com/gin-gonic/gin"
......@@ -45,3 +46,26 @@ func getHistory(c *gin.Context) {
}
c.JSON(200, withSuccess(history))
}
func getSwapConfig(c *gin.Context) {
chainIdStr := c.DefaultQuery("chain", "")
chainId, err := strconv.ParseInt(chainIdStr, 10, 64)
if err != nil {
log.Errorf("convert chainId(%s) to int error: %v", chainIdStr, err)
c.JSON(200, withError(constant.InvalidParam))
}
if _querier == nil {
log.Error("querier is nil")
c.JSON(500, withError(constant.InternalError))
return
}
configs, err := _querier.GetSwapConfig(chainId)
if err != nil {
log.Errorf("get swap config error: %v", err)
c.JSON(500, withError(constant.InternalError))
return
}
c.JSON(200, withSuccess(configs))
}
......@@ -16,4 +16,5 @@ func initRouter(conf *config.Config, e *gin.Engine) {
user.GET("/history", getHistory)
}
v1.GET("/params", getParam)
v1.GET("/swapconfig", getSwapConfig)
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment