mirror of
https://github.com/lightningnetwork/lnd.git
synced 2025-09-14 18:30:52 +02:00
rpcwallet: forward FinalizePsbt call over RPC
This commit is contained in:
@@ -15,6 +15,7 @@ import (
|
|||||||
"github.com/btcsuite/btcd/wire"
|
"github.com/btcsuite/btcd/wire"
|
||||||
"github.com/btcsuite/btcutil"
|
"github.com/btcsuite/btcutil"
|
||||||
"github.com/btcsuite/btcutil/hdkeychain"
|
"github.com/btcsuite/btcutil/hdkeychain"
|
||||||
|
"github.com/btcsuite/btcutil/psbt"
|
||||||
"github.com/btcsuite/btcwallet/waddrmgr"
|
"github.com/btcsuite/btcwallet/waddrmgr"
|
||||||
btcwallet "github.com/btcsuite/btcwallet/wallet"
|
btcwallet "github.com/btcsuite/btcwallet/wallet"
|
||||||
"github.com/lightningnetwork/lnd/input"
|
"github.com/lightningnetwork/lnd/input"
|
||||||
@@ -350,6 +351,56 @@ func (r *RPCKeyRing) SendOutputs(outputs []*wire.TxOut,
|
|||||||
return tx, r.WalletController.PublishTransaction(tx, label)
|
return tx, r.WalletController.PublishTransaction(tx, label)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// FinalizePsbt expects a partial transaction with all inputs and outputs fully
|
||||||
|
// declared and tries to sign all inputs that belong to the specified account.
|
||||||
|
// Lnd must be the last signer of the transaction. That means, if there are any
|
||||||
|
// unsigned non-witness inputs or inputs without UTXO information attached or
|
||||||
|
// inputs without witness data that do not belong to lnd's wallet, this method
|
||||||
|
// will fail. If no error is returned, the PSBT is ready to be extracted and the
|
||||||
|
// final TX within to be broadcast.
|
||||||
|
//
|
||||||
|
// NOTE: This method does NOT publish the transaction after it's been
|
||||||
|
// finalized successfully.
|
||||||
|
//
|
||||||
|
// This is a part of the WalletController interface.
|
||||||
|
func (r *RPCKeyRing) FinalizePsbt(packet *psbt.Packet, accountName string) error {
|
||||||
|
ctxt, cancel := context.WithTimeout(context.Background(), r.rpcTimeout)
|
||||||
|
defer cancel()
|
||||||
|
|
||||||
|
var buf bytes.Buffer
|
||||||
|
if err := packet.Serialize(&buf); err != nil {
|
||||||
|
return fmt.Errorf("error serializing PSBT: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
resp, err := r.walletClient.FinalizePsbt(
|
||||||
|
ctxt, &walletrpc.FinalizePsbtRequest{
|
||||||
|
FundedPsbt: buf.Bytes(),
|
||||||
|
Account: accountName,
|
||||||
|
},
|
||||||
|
)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("error finalizing PSBT in remote signer "+
|
||||||
|
"instance: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
signedPacket, err := psbt.NewFromRawBytes(
|
||||||
|
bytes.NewReader(resp.SignedPsbt), false,
|
||||||
|
)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("error parsing signed PSBT: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
// The caller expects the packet to be modified instead of a new
|
||||||
|
// instance to be returned. So we just overwrite all fields in the
|
||||||
|
// original packet.
|
||||||
|
packet.UnsignedTx = signedPacket.UnsignedTx
|
||||||
|
packet.Inputs = signedPacket.Inputs
|
||||||
|
packet.Outputs = signedPacket.Outputs
|
||||||
|
packet.Unknowns = signedPacket.Unknowns
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
// DeriveNextKey attempts to derive the *next* key within the key family
|
// DeriveNextKey attempts to derive the *next* key within the key family
|
||||||
// (account in BIP43) specified. This method should return the next external
|
// (account in BIP43) specified. This method should return the next external
|
||||||
// child within this branch.
|
// child within this branch.
|
||||||
|
Reference in New Issue
Block a user