import (
"context"
- "encoding/hex"
"encoding/json"
"github.com/bytom/blockchain/signers"
"github.com/bytom/common"
"github.com/bytom/consensus"
"github.com/bytom/crypto/ed25519/chainkd"
- chainjson "github.com/bytom/encoding/json"
"github.com/bytom/errors"
"github.com/bytom/protocol/bc"
"github.com/bytom/protocol/bc/types"
type spendUTXOAction struct {
accounts *Manager
- OutputID *bc.Hash `json:"output_id"`
- UseUnconfirmed bool `json:"use_unconfirmed"`
- Arguments []contractArgument `json:"arguments"`
-}
-
-// contractArgument for smart contract
-type contractArgument struct {
- Type string `json:"type"`
- RawData json.RawMessage `json:"raw_data"`
-}
-
-// rawTxSigArgument is signature-related argument for run contract
-type rawTxSigArgument struct {
- RootXPub chainkd.XPub `json:"xpub"`
- Path []chainjson.HexBytes `json:"derivation_path"`
-}
-
-// dataArgument is the other argument for run contract
-type dataArgument struct {
- Value string `json:"value"`
+ OutputID *bc.Hash `json:"output_id"`
+ UseUnconfirmed bool `json:"use_unconfirmed"`
+ Arguments []txbuilder.ContractArgument `json:"arguments"`
}
func (a *spendUTXOAction) Build(ctx context.Context, b *txbuilder.TemplateBuilder) error {
}
sigInst = &txbuilder.SigningInstruction{}
- for _, arg := range a.Arguments {
- switch arg.Type {
- case "raw_tx_signature":
- rawTxSig := &rawTxSigArgument{}
- if err = json.Unmarshal(arg.RawData, rawTxSig); err != nil {
- return err
- }
-
- // convert path form chainjson.HexBytes to byte
- var path [][]byte
- for _, p := range rawTxSig.Path {
- path = append(path, []byte(p))
- }
- sigInst.AddRawWitnessKeys([]chainkd.XPub{rawTxSig.RootXPub}, path, 1)
-
- case "data":
- data := &dataArgument{}
- if err = json.Unmarshal(arg.RawData, data); err != nil {
- return err
- }
-
- value, err := hex.DecodeString(data.Value)
- if err != nil {
- return err
- }
- sigInst.WitnessComponents = append(sigInst.WitnessComponents, txbuilder.DataWitness(value))
-
- default:
- return errors.New("contract argument type is not exist")
- }
+ if err := txbuilder.AddContractArgs(sigInst, a.Arguments); err != nil {
+ return err
}
+
return b.AddInput(txInput, sigInst)
}