You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

276 lines
5.9 KiB

2 months ago
package grpc
import (
"encoding/json"
"errors"
"fmt"
"github.com/fbsobreira/gotron-sdk/pkg/address"
"github.com/fbsobreira/gotron-sdk/pkg/client"
"github.com/fbsobreira/gotron-sdk/pkg/proto/api"
"github.com/fbsobreira/gotron-sdk/pkg/proto/core"
"google.golang.org/grpc"
"math/big"
"strings"
"time"
"wallet-system/internal/pkg/logging/applogger"
)
type Client struct {
node string
GRPC *client.GrpcClient
}
// NewClient
//
// @Description:
// @param node
// @return *Client
// @return error
func NewClient(node string) (*Client, error) {
c := new(Client)
c.node = node
c.GRPC = client.NewGrpcClient(node)
err := c.GRPC.Start(grpc.WithInsecure())
if err != nil {
return nil, fmt.Errorf("grpc client start error:%v", err)
}
return c, nil
}
// SetTimeout
//
// @Description:
// @receiver c
// @param timeout
// @return error
func (c *Client) SetTimeout(timeout time.Duration) error {
if c == nil {
return errors.New("client is nil ptr")
}
c.GRPC = client.NewGrpcClientWithTimeout(c.node, timeout)
err := c.GRPC.Start()
if err != nil {
return fmt.Errorf("grpc start error: %v", err)
}
return nil
}
// keepConnect
//
// @Description:
// @receiver c
// @return error
func (c *Client) keepConnect() error {
_, err := c.GRPC.GetNodeInfo()
if err != nil {
if strings.Contains(err.Error(), "no such host") {
return c.GRPC.Reconnect(c.node)
}
return fmt.Errorf("node connect error: %v", err)
}
return nil
}
// Transfer
//
// @Description:
// @receiver c
// @param from
// @param to
// @param amount
// @return *api.TransactionExtention
// @return error
func (c *Client) Transfer(from, to string, amount int64) (*api.TransactionExtention, error) {
err := c.keepConnect()
if err != nil {
return nil, err
}
return c.GRPC.Transfer(from, to, amount)
}
// GetTrc10Balance
//
// @Description:
// @receiver c
// @param addr
// @param assetId
// @return int64
// @return error
func (c *Client) GetTrc10Balance(addr, assetId string) (int64, error) {
err := c.keepConnect()
if err != nil {
return 0, err
}
acc, err := c.GRPC.GetAccount(addr)
if err != nil || acc == nil {
return 0, fmt.Errorf("get %s account error:%v", addr, err)
}
for key, value := range acc.AssetV2 {
if key == assetId {
return value, nil
}
}
return 0, fmt.Errorf("%s do not find this assetID=%s amount", addr, assetId)
}
// GetTrxBalance
//
// @Description:
// @receiver c
// @param addr
// @return *core.Account
// @return error
func (c *Client) GetTrxBalance(addr string) (*core.Account, error) {
err := c.keepConnect()
if err != nil {
return nil, err
}
return c.GRPC.GetAccount(addr)
}
// GetTrc20Balance
//
// @Description:
// @receiver c
// @param addr
// @param contractAddress
// @return *big.Int
// @return error
func (c *Client) GetTrc20Balance(addr, contractAddress string) (*big.Int, error) {
err := c.keepConnect()
if err != nil {
return nil, err
}
return c.GRPC.TRC20ContractBalance(addr, contractAddress)
}
// TransferTrc10
//
// @Description:
// @receiver c
// @param from
// @param to
// @param assetId
// @param amount
// @return *api.TransactionExtention
// @return error
func (c *Client) TransferTrc10(from, to, assetId string, amount int64) (*api.TransactionExtention, error) {
err := c.keepConnect()
if err != nil {
return nil, err
}
fromAddr, err := address.Base58ToAddress(from)
if err != nil {
return nil, fmt.Errorf("from address is not equal")
}
toAddr, err := address.Base58ToAddress(to)
if err != nil {
return nil, fmt.Errorf("to address is not equal")
}
return c.GRPC.TransferAsset(fromAddr.String(), toAddr.String(), assetId, amount)
}
// TransferTrc20
//
// @Description:
// @receiver c
// @param from
// @param to
// @param contract
// @param amount
// @param feeLimit
// @return *api.TransactionExtention
// @return error
func (c *Client) TransferTrc20(from, to, contract string, amount *big.Int, feeLimit int64) (*api.TransactionExtention, error) {
err := c.keepConnect()
if err != nil {
applogger.Error("link failure:%v", err)
return nil, err
}
return c.GRPC.TRC20Send(from, to, contract, amount, feeLimit)
}
// BroadcastTransaction
//
// @Description:
// @receiver c
// @param transaction
// @return error
func (c *Client) BroadcastTransaction(transaction *core.Transaction) error {
err := c.keepConnect()
if err != nil {
return err
}
result, err := c.GRPC.Broadcast(transaction)
if err != nil {
return fmt.Errorf("broadcast transaction error:%v", err)
}
if result.Code != 0 {
return fmt.Errorf("bad transaction:%v", string(result.GetMessage()))
}
if result.Result == true {
return nil
}
d, _ := json.Marshal(result)
return fmt.Errorf("tx send fail:%s", string(d))
}
// TRC20Approve
//
// @Description:
// @receiver c
// @param from
// @param to
// @param contract
// @param amount
// @param feeLimit
// @return *api.TransactionExtention
// @return error
func (c *Client) TRC20Approve(from, to, contract string, amount *big.Int, feeLimit int64) (*api.TransactionExtention, error) {
err := c.keepConnect()
if err != nil {
applogger.Error("link failure:%v", err)
return nil, err
}
return c.GRPC.TRC20Approve(from, to, contract, amount, feeLimit)
}
// GetContractABI .
//
// @Description:
// @receiver c
// @param contractAddress
// @return *core.SmartContract_ABI
// @return error
func (c *Client) GetContractABI(contractAddress string) (*core.SmartContract_ABI, error) {
err := c.keepConnect()
if err != nil {
applogger.Error("link failure:%v", err)
return nil, err
}
return c.GRPC.GetContractABI(contractAddress)
}
// TransferAsset from to base58 address
//
// @Description:
// @receiver c
// @param from
// @param toAddress
// @param assetName
// @param amount
// @return *api.TransactionExtention
// @return error
func (c *Client) TransferAsset(from, toAddress, assetName string, amount int64) (*api.TransactionExtention, error) {
err := c.keepConnect()
if err != nil {
applogger.Error("link failure:%v", err)
return nil, err
}
return c.GRPC.TransferAsset(from, toAddress, assetName, amount)
}