forked from hashgraph/hedera-sdk-go
-
Notifications
You must be signed in to change notification settings - Fork 0
/
main.go
212 lines (175 loc) · 6.51 KB
/
main.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
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
package main
import (
"fmt"
"os"
"github.com/hashgraph/hedera-sdk-go/v2"
)
func main() {
var client *hedera.Client
var err error
// Retrieving network type from environment variable HEDERA_NETWORK
client, err = hedera.ClientForName(os.Getenv("HEDERA_NETWORK"))
if err != nil {
println(err.Error(), ": error creating client")
return
}
// Retrieving operator ID from environment variable OPERATOR_ID
operatorAccountID, err := hedera.AccountIDFromString(os.Getenv("OPERATOR_ID"))
if err != nil {
println(err.Error(), ": error converting string to AccountID")
return
}
// Retrieving operator key from environment variable OPERATOR_KEY
operatorKey, err := hedera.PrivateKeyFromString(os.Getenv("OPERATOR_KEY"))
if err != nil {
println(err.Error(), ": error converting string to PrivateKey")
return
}
// Setting the client operator ID and key
client.SetOperator(operatorAccountID, operatorKey)
keys := make([]hedera.PrivateKey, 3)
pubKeys := make([]hedera.PublicKey, 3)
fmt.Println("threshold key example")
fmt.Println("Keys: ")
// Loop to generate keys for the KeyList
for i := range keys {
newKey, err := hedera.GeneratePrivateKey()
if err != nil {
println(err.Error(), ": error generating PrivateKey}")
return
}
fmt.Printf("Key %v:\n", i)
fmt.Printf("private = %v\n", newKey)
fmt.Printf("public = %v\n", newKey.PublicKey())
keys[i] = newKey
pubKeys[i] = newKey.PublicKey()
}
// A threshold key with a threshold of 2 and length of 3 requires
// at least 2 of the 3 keys to sign anything modifying the account
keyList := hedera.NewKeyList().
AddAllPublicKeys(pubKeys)
// We are using all of these keys, so the scheduled transaction doesn't automatically go through
// It works perfectly fine with just one key
createResponse, err := hedera.NewAccountCreateTransaction().
// The key that must sign each transfer out of the account. If receiverSigRequired is true, then
// it must also sign any transfer into the account.
SetKey(keyList).
SetInitialBalance(hedera.NewHbar(10)).
Execute(client)
if err != nil {
println(err.Error(), ": error executing create account transaction")
return
}
// Make sure the transaction succeeded
transactionReceipt, err := createResponse.GetReceipt(client)
if err != nil {
println(err.Error(), ": error getting receipt")
return
}
// Pre-generating transaction id for the scheduled transaction so we can track it
transactionID := hedera.TransactionIDGenerate(client.GetOperatorAccountID())
println("transactionId for scheduled transaction = ", transactionID.String())
// Not really necessary as its client.GetOperatorAccountID()
newAccountID := *transactionReceipt.AccountID
fmt.Printf("account = %v\n", newAccountID)
// Creating a non frozen transaction for the scheduled transaction
// In this case its TransferTransaction
transferTx := hedera.NewTransferTransaction().
SetTransactionID(transactionID).
AddHbarTransfer(newAccountID, hedera.HbarFrom(-1, hedera.HbarUnits.Hbar)).
AddHbarTransfer(client.GetOperatorAccountID(), hedera.HbarFrom(1, hedera.HbarUnits.Hbar))
// Scheduling it, this gives us hedera.ScheduleCreateTransaction
scheduled, err := transferTx.Schedule()
if err != nil {
println(err.Error(), ": error scheduling Transfer Transaction")
return
}
// Executing the scheduled transaction
scheduleResponse, err := scheduled.Execute(client)
if err != nil {
println(err.Error(), ": error executing schedule create")
return
}
// Make sure it executed successfully
scheduleReceipt, err := scheduleResponse.GetReceipt(client)
if err != nil {
println(err.Error(), ": error getting schedule create receipt")
return
}
// Taking out the schedule ID
scheduleID := *scheduleReceipt.ScheduleID
// Using the schedule ID to get the schedule transaction info, which contains the whole scheduled transaction
info, err := hedera.NewScheduleInfoQuery().
SetNodeAccountIDs([]hedera.AccountID{createResponse.NodeID}).
SetScheduleID(scheduleID).
Execute(client)
if err != nil {
println(err.Error(), ": error getting schedule info")
return
}
// Taking out the TransferTransaction from earlier
transfer, err := info.GetScheduledTransaction()
if err != nil {
println(err.Error(), ": error getting transaction from schedule info")
return
}
// Converting it from interface to hedera.TransferTransaction() and retrieving the amount of transfers
// to check if we have the right one, and that it's not empty
var transfers map[hedera.AccountID]hedera.Hbar
switch tx := transfer.(type) {
case *hedera.TransferTransaction:
transfers = tx.GetHbarTransfers()
}
if len(transfers) != 2 {
println("more transfers than expected")
return
}
// Checking if the Hbar values are correct
if transfers[newAccountID].AsTinybar() != -hedera.NewHbar(1).AsTinybar() {
println("transfer for ", newAccountID.String(), " is not whats is expected")
}
// Checking if the Hbar values are correct
if transfers[client.GetOperatorAccountID()].AsTinybar() != hedera.NewHbar(1).AsTinybar() {
println("transfer for ", client.GetOperatorAccountID().String(), " is not whats is expected")
}
println("sending schedule sign transaction")
// Creating a scheduled sign transaction, we have to sign with all of the keys in the KeyList
signTransaction, err := hedera.NewScheduleSignTransaction().
SetNodeAccountIDs([]hedera.AccountID{createResponse.NodeID}).
SetScheduleID(scheduleID).
FreezeWith(client)
if err != nil {
println(err.Error(), ": error freezing sign transaction")
return
}
// Signing the scheduled transaction
signTransaction.Sign(keys[0])
signTransaction.Sign(keys[1])
signTransaction.Sign(keys[2])
resp, err := signTransaction.Execute(client)
if err != nil {
println(err.Error(), ": error executing schedule sign transaction")
return
}
// Getting the receipt to make sure the signing executed properly
_, err = resp.GetReceipt(client)
if err != nil {
println(err.Error(), ": error executing schedule sign receipt")
return
}
// Making sure the scheduled transaction executed properly with schedule info query
info, err = hedera.NewScheduleInfoQuery().
SetScheduleID(scheduleID).
SetNodeAccountIDs([]hedera.AccountID{createResponse.NodeID}).
Execute(client)
if err != nil {
println(err.Error(), ": error retrieving schedule info after signing")
return
}
// Checking if the scheduled transaction was executed and signed, and retrieving the signatories
if !info.ExecutedAt.IsZero() {
println("Singing success, signed at: ", info.ExecutedAt.String())
println("Signatories: ", info.Signatories.String())
return
}
}