-
Notifications
You must be signed in to change notification settings - Fork 13
/
share.go
114 lines (93 loc) · 2.92 KB
/
share.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
// SPDX-License-Identifier: ISC
// Copyright (c) 2014-2020 Bitmark Inc.
// Use of this source code is governed by an ISC
// license that can be found in the LICENSE file.
package rpccalls
import (
"golang.org/x/crypto/ed25519"
"github.com/bitmark-inc/bitmarkd/command/bitmark-cli/configuration"
"github.com/bitmark-inc/bitmarkd/fault"
"github.com/bitmark-inc/bitmarkd/merkle"
"github.com/bitmark-inc/bitmarkd/pay"
"github.com/bitmark-inc/bitmarkd/rpc/share"
"github.com/bitmark-inc/bitmarkd/transactionrecord"
)
// ShareData - data for a share request
type ShareData struct {
Owner *configuration.Private
NewOwner *configuration.Private
TxId string
Quantity uint64
}
// ShareReply - JSON data to output after transfer completes
type ShareReply struct {
TxId merkle.Digest `json:"txId"`
ShareId merkle.Digest `json:"shareId"`
PayId pay.PayId `json:"payId"`
Payments map[string]transactionrecord.PaymentAlternative `json:"payments"`
Commands map[string]string `json:"commands,omitempty"`
}
// Share - perform a share request
func (client *Client) Share(shareConfig *ShareData) (*ShareReply, error) {
var link merkle.Digest
err := link.UnmarshalText([]byte(shareConfig.TxId))
if nil != err {
return nil, err
}
sh, err := makeShare(client.testnet, link, shareConfig.Quantity, shareConfig.Owner)
if nil != err {
return nil, err
}
if nil == sh {
return nil, fault.MakeShareFailed
}
client.printJson("Share Request", sh)
var reply share.CreateReply
err = client.client.Call("Share.Create", sh, &reply)
if err != nil {
return nil, err
}
tpid, err := reply.PayId.MarshalText()
if nil != err {
return nil, err
}
commands := make(map[string]string)
for _, payment := range reply.Payments {
currency := payment[0].Currency
commands[currency.String()] = paymentCommand(client.testnet, currency, string(tpid), payment)
}
client.printJson("Share Reply", reply)
// make response
response := ShareReply{
TxId: reply.TxId,
ShareId: reply.ShareId,
PayId: reply.PayId,
Payments: reply.Payments,
Commands: commands,
}
return &response, nil
}
func makeShare(testnet bool, link merkle.Digest, quantity uint64, owner *configuration.Private) (*transactionrecord.BitmarkShare, error) {
r := transactionrecord.BitmarkShare{
Link: link,
Quantity: quantity,
Signature: nil,
}
ownerAccount := owner.PrivateKey.Account()
// pack without signature
packed, err := r.Pack(ownerAccount)
if nil == err {
return nil, fault.MakeShareFailed
} else if fault.InvalidSignature != err {
return nil, err
}
// attach signature
signature := ed25519.Sign(owner.PrivateKey.PrivateKeyBytes(), packed)
r.Signature = signature[:]
// check that signature is correct by packing again
_, err = r.Pack(ownerAccount)
if nil != err {
return nil, err
}
return &r, nil
}