Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -810,6 +810,7 @@ public void GetColdStakingInfoOnlyConfirmAccountExistenceOnceCreated()
/// Adds a spendable cold staking transaction to a wallet.
/// </summary>
/// <param name="wallet">Wallet to add the transaction to.</param>
/// <param name="script">Set to <c>true</c> to output to the <see cref="WitScriptId.ScriptPubKey"/>.</param>
/// <returns>The spendable transaction that was added to the wallet.</returns>
private Transaction AddSpendableColdstakingTransactionToWallet(Wallet.Wallet wallet, bool script = false)
{
Expand Down Expand Up @@ -855,6 +856,7 @@ private Transaction AddSpendableColdstakingTransactionToWallet(Wallet.Wallet wal
/// Adds a spendable cold staking transaction to a normal account, as oppose to dedicated special account.
/// </summary>
/// <param name="wallet">Wallet to add the transaction to.</param>
/// <param name="script">Set to <c>true</c> to output to the <see cref="WitScriptId.ScriptPubKey"/>.</param>
/// <returns>The spendable transaction that was added to the wallet.</returns>
private Transaction AddSpendableColdstakingTransactionToNormalWallet(Wallet.Wallet wallet, bool script = false)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,7 @@ public void ProcessTransactionWithValidColdStakingSetupLoadsTransactionsIntoWall
Assert.Single(spendingAddress.Transactions);
Assert.Equal(transaction.GetHash(), spentAddressResult.Transactions.ElementAt(0).SpendingDetails.TransactionId);
Assert.Equal(2, transaction.Outputs.Count);
Assert.True(spentAddressResult.Transactions.ElementAt(0).SpendingDetails.Payments.Any(p => p.DestinationScriptPubKey == transaction.Outputs[1].ScriptPubKey && p.Amount == transaction.Outputs[1].Value));
Assert.Contains(spentAddressResult.Transactions.ElementAt(0).SpendingDetails.Payments, p => p.DestinationScriptPubKey == transaction.Outputs[1].ScriptPubKey && p.Amount == transaction.Outputs[1].Value);

Assert.Single(wallet.AccountsRoot.ElementAt(0).Accounts.ElementAt(0).InternalAddresses.ElementAt(0).Transactions);
TransactionData changeAddressResult = wallet.AccountsRoot.ElementAt(0).Accounts.ElementAt(0).InternalAddresses.ElementAt(0).Transactions.ElementAt(0);
Expand Down
11 changes: 11 additions & 0 deletions src/Stratis.Bitcoin.Features.ColdStaking/ColdStakingManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,7 @@ public class ColdStakingManager : WalletManager, IWalletManager
/// <param name="scriptAddressReader">A reader for extracting an address from a <see cref="Script"/>.</param>
/// <param name="loggerFactory">The logger factory to use to create the custom logger.</param>
/// <param name="dateTimeProvider">Provider of time functions.</param>
/// <param name="walletRepository">The wallet repository.</param>
/// <param name="broadcasterManager">The broadcaster manager.</param>
public ColdStakingManager(
Network network,
Expand Down Expand Up @@ -194,6 +195,7 @@ internal HdAccount GetColdStakingAccount(Wallet.Wallet wallet, bool isColdWallet
/// <param name="walletName">The name of the wallet where we wish to create the account.</param>
/// <param name="isColdWalletAccount">Indicates whether we need the cold wallet account (versus the hot wallet account).</param>
/// <param name="walletPassword">The wallet password which will be used to create the account.</param>
/// <param name="extPubKey">The <see cref="ExtPubKey"/> of the wallet account. Can be <c>null</c> for watch-only wallets.</param>
/// <returns>The new or existing cold staking account.</returns>
internal HdAccount GetOrCreateColdStakingAccount(string walletName, bool isColdWalletAccount, string walletPassword, ExtPubKey extPubKey)
{
Expand Down Expand Up @@ -457,6 +459,14 @@ internal Money EstimateSetupTransactionFee(IWalletTransactionHandler walletTrans
/// Builds an unsigned transaction template for a cold staking withdrawal transaction.
/// This requires specialised logic due to the lack of a private key for the cold account.
/// </summary>
/// <param name="walletTransactionHandler">The <see cref="IWalletTransactionHandler"/>.</param>
/// <param name="receivingAddress">The receiving address.</param>
/// <param name="walletName">The spending wallet name.</param>
/// <param name="accountName">The spending account name.</param>
/// <param name="amount">The amount to spend.</param>
/// <param name="feeAmount">The fee amount.</param>
/// <param name="subtractFeeFromAmount">Set to <c>true</c> to subtract the <paramref name="feeAmount"/> from the <paramref name="amount"/>.</param>
/// <returns>See <see cref="BuildOfflineSignResponse"/>.</returns>
public BuildOfflineSignResponse BuildOfflineColdStakingWithdrawalRequest(IWalletTransactionHandler walletTransactionHandler, string receivingAddress,
string walletName, string accountName, Money amount, Money feeAmount, bool subtractFeeFromAmount)
{
Expand Down Expand Up @@ -552,6 +562,7 @@ private TransactionBuildContext GetOfflineWithdrawalBuildContext(string receivin
/// <param name="walletPassword">The wallet password.</param>
/// <param name="amount">The amount to remove from cold staking.</param>
/// <param name="feeAmount">The fee to pay for cold staking transaction withdrawal.</param>
/// <param name="subtractFeeFromAmount">Set to <c>true</c> to subtract the <paramref name="feeAmount"/> from the <paramref name="amount"/>.</param>
/// <returns>The <see cref="Transaction"/> for cold staking withdrawal.</returns>
/// <exception cref="WalletException">Thrown if the receiving address is in a cold staking account in this wallet.</exception>
/// <exception cref="ArgumentNullException">Thrown if the receiving address is invalid.</exception>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,9 +100,11 @@ public Script GenerateScriptPubKey(KeyId hotPubKeyHash, KeyId coldPubKeyHash)
return new Script(
// Duplicates the last stack entry resulting in:
// <scriptSig> 0/1 <coldPubKey/hotPubKey> <coldPubKey/hotPubKey>.
#pragma warning disable SA1114 // Parameter list must follow declaration
OP_DUP,
// Replaces the last stack entry with its hash resulting in:
// <scriptSig> 0/1 <coldPubKey/hotPubKey> <coldPubKeyHash/hotPubKeyHash>.
#pragma warning restore SA1114 // Parameter list must follow declaration
// Replaces the last stack entry with its hash resulting in:
// <scriptSig> 0/1 <coldPubKey/hotPubKey> <coldPubKeyHash/hotPubKeyHash>.
OP_HASH160,
// Rotates the top 3 stack entries resulting in:
// <scriptSig> <coldPubKey/hotPubKey> <coldPubKeyHash/hotPubKeyHash> 0/1.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -76,17 +76,17 @@ public override async Task<WalletBuildTransactionModel> OfflineSignRequest(Offli
$"Could not resolve address from UTXO's scriptPubKey '{scriptPubKey.ToHex()}'.");
}

var accounts = this.walletManager.GetAccounts(request.WalletName);
var addresses = accounts.SelectMany(hdAccount => hdAccount.GetCombinedAddresses());
IEnumerable<HdAccount> accounts = this.walletManager.GetAccounts(request.WalletName);
IEnumerable<HdAddress> addresses = accounts.SelectMany(hdAccount => hdAccount.GetCombinedAddresses());

HdAddress hdAddress = addresses.FirstOrDefault(a => a.Address == address || a.Bech32Address == address);

if (coldStakingWithdrawal && hdAddress == null)
{
var coldStakingManager = this.walletManager as ColdStakingManager;
var wallet = coldStakingManager.GetWallet(request.WalletName);
var coldAccount = coldStakingManager.GetColdStakingAccount(wallet, true);
var coldAccountAddresses = coldAccount.GetCombinedAddresses();
Wallet.Wallet wallet = coldStakingManager.GetWallet(request.WalletName);
HdAccount coldAccount = coldStakingManager.GetColdStakingAccount(wallet, true);
IEnumerable<HdAddress> coldAccountAddresses = coldAccount.GetCombinedAddresses();
hdAddress = coldAccountAddresses.FirstOrDefault(a => a.Address == address || a.Bech32Address == address);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@

namespace Stratis.Bitcoin.Features.Wallet.Interfaces
{
/// <summary>
/// A handler that has various functionalities related to transaction operations.
/// </summary>
public interface IWalletTransactionHandler
{
/// <summary>
Expand Down