/
chain.go
149 lines (124 loc) · 3.74 KB
/
chain.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
package eth
import (
"crypto/ecdsa"
"strings"
"github.com/coming-chat/wallet-SDK/core/base"
"github.com/ethereum/go-ethereum/crypto"
)
type Chain struct {
RpcUrl string
}
func NewChainWithRpc(rpcUrl string) *Chain {
return &Chain{
RpcUrl: rpcUrl,
}
}
// MARK - Implement the protocol Chain
func (c *Chain) MainToken() base.Token {
return &Token{chain: c}
}
func (c *Chain) MainEthToken() TokenProtocol {
return &Token{chain: c}
}
func (c *Chain) Erc20Token(contractAddress string) TokenProtocol {
return &Erc20Token{
Token: &Token{chain: c},
ContractAddress: contractAddress,
}
}
func (c *Chain) BalanceOfAddress(address string) (*base.Balance, error) {
b := base.EmptyBalance()
eip55Address, err := TransformEIP55Address(address)
if err != nil {
return b, err
}
chain, err := GetConnection(c.RpcUrl)
if err != nil {
return b, err
}
balance, err := chain.Balance(eip55Address)
if err != nil {
return b, err
}
return &base.Balance{
Total: balance,
Usable: balance,
}, nil
}
func (c *Chain) BalanceOfPublicKey(publicKey string) (*base.Balance, error) {
return c.BalanceOfAddress(publicKey)
}
func (c *Chain) BalanceOfAccount(account base.Account) (*base.Balance, error) {
return c.BalanceOfAddress(account.Address())
}
// Send the raw transaction on-chain
// @return the hex hash string
func (c *Chain) SendRawTransaction(signedTx string) (string, error) {
chain, err := GetConnection(c.RpcUrl)
if err != nil {
return "", err
}
return chain.SendRawTransaction(signedTx)
}
// Fetch transaction details through transaction hash
func (c *Chain) FetchTransactionDetail(hash string) (*base.TransactionDetail, error) {
chain, err := GetConnection(c.RpcUrl)
if err != nil {
return nil, err
}
return chain.FetchTransactionDetail(hash)
}
// Fetch transaction status through transaction hash
func (c *Chain) FetchTransactionStatus(hash string) base.TransactionStatus {
chain, err := GetConnection(c.RpcUrl)
if err != nil {
return base.TransactionStatusNone
}
return chain.FetchTransactionStatus(hash)
}
// Batch fetch the transaction status, the hash list and the return value,
// which can only be passed as strings separated by ","
// @param hashListString The hash of the transactions to be queried in batches, a string concatenated with ",": "hash1,hash2,hash3"
// @return Batch transaction status, its order is consistent with hashListString: "status1,status2,status3"
func (c *Chain) BatchFetchTransactionStatus(hashListString string) string {
chain, err := GetConnection(c.RpcUrl)
if err != nil {
return ""
}
return chain.SdkBatchTransactionStatus(hashListString)
}
func (c *Chain) BuildTransferTx(privateKey string, transaction *Transaction) (*base.OptionalString, error) {
privateKey = strings.TrimPrefix(privateKey, "0x")
privateKeyECDSA, err := crypto.HexToECDSA(privateKey)
if err != nil {
return nil, err
}
return c.buildTransfer(privateKeyECDSA, transaction)
}
func (c *Chain) BuildTransferTxWithAccount(account *Account, transaction *Transaction) (*base.OptionalString, error) {
return c.buildTransfer(account.privateKeyECDSA, transaction)
}
func (c *Chain) buildTransfer(privateKey *ecdsa.PrivateKey, transaction *Transaction) (*base.OptionalString, error) {
chain, err := GetConnection(c.RpcUrl)
if err != nil {
return nil, err
}
if transaction.Nonce == "" || transaction.Nonce == "0" {
address := crypto.PubkeyToAddress(privateKey.PublicKey).Hex()
nonce, err := chain.Nonce(address)
if err != nil {
nonce = "0"
err = nil
}
transaction.Nonce = nonce
}
rawTx, err := transaction.GetRawTx()
if err != nil {
return nil, err
}
txResult, err := chain.buildTxWithTransaction(rawTx, privateKey)
if err != nil {
return nil, err
}
return &base.OptionalString{Value: txResult.TxHex}, nil
}