public static (ExtKey ExtKey, string ExtPubKey) GenerateAccountKeys(Features.Wallet.Wallet wallet, string password, string keyPath) { var accountExtKey = new ExtKey(Key.Parse(wallet.EncryptedSeed, password, wallet.Network), wallet.ChainCode).Derive(new KeyPath(keyPath)); string accountExtendedPubKey = accountExtKey.Derive(new KeyPath(keyPath)).Neuter().ToString(wallet.Network); return(accountExtKey, accountExtendedPubKey); }
public void WalletCanCatchupWithBestChain() { using (NodeBuilder builder = NodeBuilder.Create(this)) { CoreNode stratisminer = builder.CreateStratisPowNode(); builder.StartAll(); stratisminer.NotInIBD(); // get a key from the wallet Mnemonic mnemonic = stratisminer.FullNode.WalletManager().CreateWallet("123456", "mywallet"); Assert.Equal(12, mnemonic.Words.Length); HdAddress addr = stratisminer.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("mywallet", "account 0")); Features.Wallet.Wallet wallet = stratisminer.FullNode.WalletManager().GetWalletByName("mywallet"); Key key = wallet.GetExtendedPrivateKeyForAddress("123456", addr).PrivateKey; stratisminer.SetDummyMinerSecret(key.GetBitcoinSecret(stratisminer.FullNode.Network)); stratisminer.GenerateStratis(10); // wait for block repo for block sync to work TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisminer)); // push the wallet back stratisminer.FullNode.Services.ServiceProvider.GetService <IWalletSyncManager>().SyncFromHeight(5); stratisminer.GenerateStratis(5); TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisminer)); } }
public void WalletCanRecoverOnStartup() { using (NodeBuilder builder = NodeBuilder.Create(this)) { CoreNode stratisNodeSync = builder.CreateStratisPowNode(); builder.StartAll(); stratisNodeSync.NotInIBD(); // get a key from the wallet Mnemonic mnemonic = stratisNodeSync.FullNode.WalletManager().CreateWallet("123456", "mywallet"); Assert.Equal(12, mnemonic.Words.Length); HdAddress addr = stratisNodeSync.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("mywallet", "account 0")); Features.Wallet.Wallet wallet = stratisNodeSync.FullNode.WalletManager().GetWalletByName("mywallet"); Key key = wallet.GetExtendedPrivateKeyForAddress("123456", addr).PrivateKey; stratisNodeSync.SetDummyMinerSecret(key.GetBitcoinSecret(stratisNodeSync.FullNode.Network)); stratisNodeSync.GenerateStratis(10); TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisNodeSync)); // set the tip of best chain some blocks in the apst stratisNodeSync.FullNode.Chain.SetTip(stratisNodeSync.FullNode.Chain.GetBlock(stratisNodeSync.FullNode.Chain.Height - 5)); // stop the node it will persist the chain with the reset tip stratisNodeSync.FullNode.Dispose(); CoreNode newNodeInstance = builder.CloneStratisNode(stratisNodeSync); // load the node, this should hit the block store recover code newNodeInstance.Start(); // check that store recovered to be the same as the best chain. Assert.Equal(newNodeInstance.FullNode.Chain.Tip.HashBlock, newNodeInstance.FullNode.WalletManager().WalletTipHash); } }
public static Transaction SetupValidTransaction(Features.Wallet.Wallet wallet, string password, HdAddress spendingAddress, PubKey destinationPubKey, HdAddress changeAddress, Money amount, Money fee) { TransactionData spendingTransaction = spendingAddress.Transactions.ElementAt(0); var coin = new Coin(spendingTransaction.Id, (uint)spendingTransaction.Index, spendingTransaction.Amount, spendingTransaction.ScriptPubKey); Key privateKey = Key.Parse(wallet.EncryptedSeed, password, wallet.Network); var builder = new TransactionBuilder(wallet.Network); Transaction tx = builder .AddCoins(new List <Coin> { coin }) .AddKeys(new ExtKey(privateKey, wallet.ChainCode).Derive(new KeyPath(spendingAddress.HdPath)).GetWif(wallet.Network)) .Send(destinationPubKey.ScriptPubKey, amount) .SetChange(changeAddress.ScriptPubKey) .SendFees(fee) .BuildTransaction(true); if (!builder.Verify(tx)) { throw new WalletException("Could not build transaction, please make sure you entered the correct data."); } return(tx); }
public void GetAllTransactionsByCoinTypeReturnsTransactionsFromWalletByCoinType() { var wallet = new Features.Wallet.Wallet(); var stratisAccountRoot = CreateAccountRootWithHdAccountHavingAddresses("StratisAccount", CoinType.Stratis); var bitcoinAccountRoot = CreateAccountRootWithHdAccountHavingAddresses("BitcoinAccount", CoinType.Bitcoin); var stratisAccountRoot2 = CreateAccountRootWithHdAccountHavingAddresses("StratisAccount2", CoinType.Stratis); var transaction1 = CreateTransaction(new uint256(1), new Money(15000), 1); var transaction2 = CreateTransaction(new uint256(2), new Money(91209), 1); var transaction3 = CreateTransaction(new uint256(3), new Money(32145), 1); var transaction4 = CreateTransaction(new uint256(4), new Money(654789), 1); var transaction5 = CreateTransaction(new uint256(5), new Money(52387), 1); var transaction6 = CreateTransaction(new uint256(6), new Money(879873), 1); stratisAccountRoot.Accounts.ElementAt(0).InternalAddresses.ElementAt(0).Transactions.Add(transaction1); stratisAccountRoot.Accounts.ElementAt(0).ExternalAddresses.ElementAt(0).Transactions.Add(transaction2); bitcoinAccountRoot.Accounts.ElementAt(0).InternalAddresses.ElementAt(0).Transactions.Add(transaction3); bitcoinAccountRoot.Accounts.ElementAt(0).ExternalAddresses.ElementAt(0).Transactions.Add(transaction4); stratisAccountRoot2.Accounts.ElementAt(0).InternalAddresses.ElementAt(0).Transactions.Add(transaction5); stratisAccountRoot2.Accounts.ElementAt(0).ExternalAddresses.ElementAt(0).Transactions.Add(transaction6); wallet.AccountsRoot.Add(stratisAccountRoot); wallet.AccountsRoot.Add(bitcoinAccountRoot); wallet.AccountsRoot.Add(stratisAccountRoot2); var result = wallet.GetAllTransactionsByCoinType(CoinType.Stratis).ToList(); Assert.Equal(4, result.Count); Assert.Equal(transaction2, result[0]); Assert.Equal(transaction6, result[1]); Assert.Equal(transaction1, result[2]); Assert.Equal(transaction5, result[3]); }
public void Create_WithFunds_Via_Controller() { using (NodeBuilder builder = NodeBuilder.Create(this)) { CoreNode scSender = builder.CreateSmartContractPowNode(); CoreNode scReceiver = builder.CreateSmartContractPowNode(); builder.StartAll(); scSender.NotInIBD(); scReceiver.NotInIBD(); scSender.FullNode.Network.Consensus.CoinbaseMaturity = 1L; scReceiver.FullNode.Network.Consensus.CoinbaseMaturity = 1L; int maturity = (int)scReceiver.FullNode.Network.Consensus.CoinbaseMaturity; scSender.FullNode.WalletManager().CreateWallet(Password, WalletName, Passphrase); scReceiver.FullNode.WalletManager().CreateWallet(Password, WalletName, Passphrase); HdAddress addr = scSender.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference(WalletName, AccountName)); Features.Wallet.Wallet wallet = scSender.FullNode.WalletManager().GetWalletByName(WalletName); Key key = wallet.GetExtendedPrivateKeyForAddress(Password, addr).PrivateKey; scSender.SetDummyMinerSecret(new BitcoinSecret(key, scSender.FullNode.Network)); scReceiver.SetDummyMinerSecret(new BitcoinSecret(key, scReceiver.FullNode.Network)); scSender.GenerateStratisWithMiner(2); TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(scSender)); var total = scSender.FullNode.WalletManager().GetSpendableTransactionsInWallet(WalletName).Sum(s => s.Transaction.Amount); Assert.Equal(Money.COIN * (maturity + 1) * 50, total); SmartContractsController senderSmartContractsController = scSender.FullNode.NodeService <SmartContractsController>(); SmartContractWalletController senderWalletController = scSender.FullNode.NodeService <SmartContractWalletController>(); SmartContractCompilationResult compilationResult = SmartContractCompiler.CompileFile("SmartContracts/StorageDemo.cs"); Assert.True(compilationResult.Success); var buildRequest = new BuildCreateContractTransactionRequest { AccountName = AccountName, Amount = "30", GasLimit = "10000", GasPrice = "1", ContractCode = compilationResult.Compilation.ToHexString(), FeeAmount = "0.001", Password = Password, WalletName = WalletName, Sender = addr.Address }; JsonResult result = (JsonResult)senderSmartContractsController.BuildCreateSmartContractTransaction(buildRequest); var response = (BuildCreateContractTransactionResponse)result.Value; scSender.CreateRPCClient().AddNode(scReceiver.Endpoint, true); SmartContractSharedSteps.SendTransactionAndMine(scSender, scReceiver, senderWalletController, response.Hex); ContractStateRepositoryRoot senderState = scSender.FullNode.NodeService <ContractStateRepositoryRoot>(); Assert.Equal((ulong)30 * 100_000_000, senderState.GetCurrentBalance(new Address(response.NewContractAddress).ToUint160(new SmartContractsRegTest()))); } }
public void GetAllTransactionsByCoinTypeWithoutAccountRootReturnsEmptyList() { var wallet = new Features.Wallet.Wallet(); var result = wallet.GetAllTransactionsByCoinType(CoinType.Stratis).ToList(); Assert.Equal(0, result.Count); }
public void GetAccountsByCoinTypeWithoutAccountsReturnsEmptyList() { var wallet = new Features.Wallet.Wallet(); var result = wallet.GetAccountsByCoinType(CoinType.Stratis); Assert.Equal(0, result.Count()); }
private void a_sending_and_a_receiving_wallet() { this.receiverAddress = this.receiverNode.FullNode.WalletManager().GetUnusedAddress(); this.sendingWallet = this.receiverNode.FullNode.WalletManager().GetWalletByName(this.walletName); this.senderAddress = this.senderNode.FullNode.WalletManager().GetUnusedAddress(); this.sendingWallet = this.senderNode.FullNode.WalletManager().GetWalletByName(this.walletName); }
public void SyncWithProofWorkNode() { this.posReceiverAddress = this.nodes[this.PosStaker].FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference(this.PosWallet, this.WalletAccount)); Features.Wallet.Wallet wallet = this.nodes[this.PosStaker].FullNode.WalletManager().GetWalletByName(this.PosWallet); this.posReceiverPrivateKey = wallet.GetExtendedPrivateKeyForAddress(this.PosWalletPassword, this.posReceiverAddress).PrivateKey; this.nodes[this.PosStaker].SetDummyMinerSecret(new BitcoinSecret(this.posReceiverPrivateKey, this.nodes[this.PosStaker].FullNode.Network)); this.nodeGroupBuilder.WithConnections().Connect(this.PowMiner, this.PosStaker); }
public void BuildTransferContext_SenderHasNoBalance_Fails() { string senderAddress = uint160.Zero.ToBase58Address(this.network); var reserveUtxoService = new ReserveUtxoService(this.loggerFactory, new Mock <ISignals>().Object); var service = new SmartContractTransactionService( this.network, this.walletManager.Object, this.walletTransactionHandler.Object, this.stringSerializer.Object, this.callDataSerializer.Object, this.addressGenerator.Object, this.stateRepository.Object, reserveUtxoService, this.blockStore.Object, this.chainIndexer, this.primitiveSerializer.Object, this.contractAssemblyCache.Object, this.receiptRepository.Object); var request = new BuildContractTransactionRequest { AccountName = "account 0", WalletName = "wallet", Password = "******", Sender = senderAddress, }; var wallet = new Features.Wallet.Wallet(); wallet.AccountsRoot.Add(new AccountRoot(wallet)); var account0 = new HdAccount(wallet.AccountsRoot.First().Accounts) { Name = request.AccountName }; account0.ExternalAddresses.Add(new HdAddress() { Address = senderAddress }); this.walletManager.Setup(x => x.GetWallet(request.WalletName)) .Returns(wallet); this.walletManager.Setup(x => x.GetAddressBalance(request.Sender)) .Returns(new AddressBalance { Address = request.Sender, AmountConfirmed = 0, AmountUnconfirmed = 0 }); BuildContractTransactionResult result = service.BuildTx(request); Assert.Equal(SmartContractTransactionService.InsufficientBalanceError, result.Error); Assert.NotNull(result.Message); Assert.Null(result.Response); }
private void a_miner_validating_blocks() { this.node.FullNode.WalletManager().CreateWallet(this.password, "miner"); this.miningWalletAccountReference = new WalletAccountReference("miner", "account 0"); this.minerAddress = this.node.FullNode.WalletManager().GetUnusedAddress(this.miningWalletAccountReference); this.miningWallet = this.node.FullNode.WalletManager().GetWalletByName("miner"); this.key = this.miningWallet.GetExtendedPrivateKeyForAddress(this.password, this.minerAddress).PrivateKey; this.node.SetDummyMinerSecret(new BitcoinSecret(this.key, this.node.FullNode.Network)); }
public void GetAllPubKeysByCoinTypeWithoutMatchingCoinTypeReturnsEmptyList() { var wallet = new Features.Wallet.Wallet(); var bitcoinAccountRoot = CreateAccountRootWithHdAccountHavingAddresses("BitcoinAccount", CoinType.Bitcoin); wallet.AccountsRoot.Add(bitcoinAccountRoot); var result = wallet.GetAllPubKeysByCoinType(CoinType.Stratis).ToList(); Assert.Equal(0, result.Count); }
private void a_sending_and_a_receiving_wallet() { this.receiverNode.FullNode.WalletManager().CreateWallet(this.password, "receiver"); this.receiverAddress = this.receiverNode.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("receiver", "account 0")); this.sendingWallet = this.receiverNode.FullNode.WalletManager().GetWalletByName("receiver"); this.senderNode.FullNode.WalletManager().CreateWallet(this.password, "sender"); this.sendingWalletAccountReference = new WalletAccountReference("sender", "account 0"); this.senderAddress = this.senderNode.FullNode.WalletManager().GetUnusedAddress(this.sendingWalletAccountReference); this.sendingWallet = this.senderNode.FullNode.WalletManager().GetWalletByName("sender"); }
public void ProofOfWorkNodeWithWallet() { this.nodes = this.nodeGroupBuilder .CreateStratisPowMiningNode(this.PowMiner) .Start() .NotInIBD() .WithWallet(this.PowWallet, this.PowWalletPassword) .Build(); this.powSenderAddress = this.nodes[this.PowMiner].FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference(this.PowWallet, this.WalletAccount)); Features.Wallet.Wallet wallet = this.nodes[this.PowMiner].FullNode.WalletManager().GetWalletByName(this.PowWallet); this.powSenderPrivateKey = wallet.GetExtendedPrivateKeyForAddress(this.PowWalletPassword, this.powSenderAddress).PrivateKey; }
public void GetAccountsByCoinTypeReturnsAccountsFromWalletByCoinType() { var wallet = new Features.Wallet.Wallet(); wallet.AccountsRoot.Add(CreateAccountRootWithHdAccountHavingAddresses("StratisAccount", CoinType.Stratis)); wallet.AccountsRoot.Add(CreateAccountRootWithHdAccountHavingAddresses("BitcoinAccount", CoinType.Bitcoin)); wallet.AccountsRoot.Add(CreateAccountRootWithHdAccountHavingAddresses("StratisAccount2", CoinType.Stratis)); var result = wallet.GetAccountsByCoinType(CoinType.Stratis); Assert.Equal(2, result.Count()); Assert.Equal("StratisAccount", result.ElementAt(0).Name); Assert.Equal("StratisAccount2", result.ElementAt(1).Name); }
/// <summary> /// Creates a new wallet. /// </summary> /// <remarks> /// If it's the first time this wallet is created within this class, it is added to a collection for use by other tests. /// If the same parameters have already been used to create a wallet, the wallet will be retrieved from the internal collection and a copy of this wallet will be returned. /// </remarks> /// <param name="name">The name.</param> /// <param name="password">The password.</param> /// <returns>The generated wallet.</returns> public Features.Wallet.Wallet GenerateBlankWallet(string name, string password) { if (this.walletsGenerated.TryGetValue((name, password), out Features.Wallet.Wallet existingWallet)) { string serializedExistingWallet = JsonConvert.SerializeObject(existingWallet, Formatting.None); return(JsonConvert.DeserializeObject <Features.Wallet.Wallet>(serializedExistingWallet)); } Features.Wallet.Wallet newWallet = WalletTestsHelpers.GenerateBlankWallet(name, password); this.walletsGenerated.Add((name, password), newWallet); string serializedNewWallet = JsonConvert.SerializeObject(newWallet, Formatting.None); return(JsonConvert.DeserializeObject <Features.Wallet.Wallet>(serializedNewWallet)); }
public static Features.Wallet.Wallet CreateWallet(string name, IWalletRepository walletRepository = null) { Network network = walletRepository?.Network ?? KnownNetworks.Main; var wallet = new Features.Wallet.Wallet(name, walletRepository: walletRepository); wallet.Network = network; wallet.AccountsRoot = new List <AccountRoot> { new AccountRoot(wallet) { CoinType = (CoinType)network.Consensus.CoinType } }; return(wallet); }
public void BuildTransferContext_AccountNotInWallet_Fails() { string senderAddress = uint160.Zero.ToBase58Address(this.network); var reserveUtxoService = new ReserveUtxoService(this.loggerFactory, new Mock <ISignals>().Object); var service = new SmartContractTransactionService( this.network, this.walletManager.Object, this.walletTransactionHandler.Object, this.stringSerializer.Object, this.callDataSerializer.Object, this.addressGenerator.Object, this.stateRepository.Object, reserveUtxoService, this.blockStore.Object, this.chainIndexer, this.primitiveSerializer.Object, this.contractAssemblyCache.Object, this.receiptRepository.Object); var request = new BuildContractTransactionRequest { AccountName = "account 0", WalletName = "wallet", Password = "******", Sender = senderAddress, }; var wallet = new Features.Wallet.Wallet(); wallet.AccountsRoot.Add(new AccountRoot(wallet)); var account0 = new HdAccount(wallet.AccountsRoot.First().Accounts) { Name = "account 1" }; // Create a wallet but without the correct account name this.walletManager.Setup(x => x.GetWallet(request.WalletName)) .Returns(wallet); BuildContractTransactionResult result = service.BuildTx(request); Assert.Equal(SmartContractTransactionService.AccountNotInWalletError, result.Error); Assert.NotNull(result.Message); Assert.Null(result.Response); }
public void SmartContractsController_Builds_Transaction_With_Minimum_Inputs() { using (NodeBuilder builder = NodeBuilder.Create(this)) { CoreNode scSender = builder.CreateSmartContractPowNode(); builder.StartAll(); scSender.NotInIBD(); var maturity = (int)scSender.FullNode.Network.Consensus.CoinbaseMaturity; scSender.FullNode.WalletManager().CreateWallet(Password, WalletName, Passphrase); HdAddress addr = scSender.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference(WalletName, AccountName)); Features.Wallet.Wallet wallet = scSender.FullNode.WalletManager().GetWalletByName(WalletName); Key key = wallet.GetExtendedPrivateKeyForAddress(Password, addr).PrivateKey; scSender.SetDummyMinerSecret(new BitcoinSecret(key, scSender.FullNode.Network)); scSender.GenerateStratisWithMiner(maturity + 5); TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(scSender)); int spendableBlocks = GetSpendableBlocks(maturity + 5, maturity); var total = scSender.FullNode.WalletManager().GetSpendableTransactionsInWallet(WalletName).Sum(s => s.Transaction.Amount); Assert.Equal(Money.COIN * spendableBlocks * 50, total); SmartContractsController senderSmartContractsController = scSender.FullNode.NodeService <SmartContractsController>(); SmartContractWalletController senderWalletController = scSender.FullNode.NodeService <SmartContractWalletController>(); SmartContractCompilationResult compilationResult = SmartContractCompiler.CompileFile("SmartContracts/StorageDemo.cs"); Assert.True(compilationResult.Success); var buildRequest = new BuildCreateContractTransactionRequest { AccountName = AccountName, GasLimit = "10000", GasPrice = "1", ContractCode = compilationResult.Compilation.ToHexString(), FeeAmount = "0.001", Password = Password, WalletName = WalletName, Sender = addr.Address }; JsonResult result = (JsonResult)senderSmartContractsController.BuildCreateSmartContractTransaction(buildRequest); var response = (BuildCreateContractTransactionResponse)result.Value; var transaction = scSender.FullNode.Network.CreateTransaction(response.Hex); Assert.Single(transaction.Inputs); } }
public MockChainNode(CoreNode coreNode, MockChain chain) { this.CoreNode = coreNode; this.chain = chain; // Set up address and mining this.CoreNode.NotInIBD(); this.CoreNode.FullNode.WalletManager().CreateWallet(Password, WalletName); this.MinerAddress = this.CoreNode.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference(WalletName, AccountName)); Features.Wallet.Wallet wallet = this.CoreNode.FullNode.WalletManager().GetWalletByName(WalletName); Key key = wallet.GetExtendedPrivateKeyForAddress(Password, this.MinerAddress).PrivateKey; this.CoreNode.SetDummyMinerSecret(new BitcoinSecret(key, this.CoreNode.FullNode.Network)); // Set up services for later this.smartContractsController = this.CoreNode.FullNode.NodeService <SmartContractsController>(); this.stateRoot = this.CoreNode.FullNode.NodeService <ContractStateRepositoryRoot>(); this.blockStore = this.CoreNode.FullNode.NodeService <IBlockStoreCache>(); }
public void GetAllTransactionsByCoinTypeWithoutMatchingAccountReturnsEmptyList() { var wallet = new Features.Wallet.Wallet(); var bitcoinAccountRoot = CreateAccountRootWithHdAccountHavingAddresses("BitcoinAccount", CoinType.Bitcoin); var transaction1 = CreateTransaction(new uint256(3), new Money(32145), 1); var transaction2 = CreateTransaction(new uint256(4), new Money(654789), 1); bitcoinAccountRoot.Accounts.ElementAt(0).InternalAddresses.ElementAt(0).Transactions.Add(transaction1); bitcoinAccountRoot.Accounts.ElementAt(0).ExternalAddresses.ElementAt(0).Transactions.Add(transaction2); wallet.AccountsRoot.Add(bitcoinAccountRoot); var result = wallet.GetAllTransactionsByCoinType(CoinType.Stratis).ToList(); Assert.Equal(0, result.Count); }
public void GetAllPubKeysByCoinTypeReturnsPubkeysFromWalletByCoinType() { var wallet = new Features.Wallet.Wallet(); var stratisAccountRoot = CreateAccountRootWithHdAccountHavingAddresses("StratisAccount", CoinType.Stratis); var bitcoinAccountRoot = CreateAccountRootWithHdAccountHavingAddresses("BitcoinAccount", CoinType.Bitcoin); var stratisAccountRoot2 = CreateAccountRootWithHdAccountHavingAddresses("StratisAccount2", CoinType.Stratis); wallet.AccountsRoot.Add(stratisAccountRoot); wallet.AccountsRoot.Add(bitcoinAccountRoot); wallet.AccountsRoot.Add(stratisAccountRoot2); var result = wallet.GetAllPubKeysByCoinType(CoinType.Stratis).ToList(); Assert.Equal(4, result.Count); Assert.Equal(stratisAccountRoot.Accounts.ElementAt(0).ExternalAddresses.ElementAt(0).ScriptPubKey, result[0]); Assert.Equal(stratisAccountRoot2.Accounts.ElementAt(0).ExternalAddresses.ElementAt(0).ScriptPubKey, result[1]); Assert.Equal(stratisAccountRoot.Accounts.ElementAt(0).InternalAddresses.ElementAt(0).ScriptPubKey, result[2]); Assert.Equal(stratisAccountRoot2.Accounts.ElementAt(0).InternalAddresses.ElementAt(0).ScriptPubKey, result[3]); }
internal static (Features.Wallet.Wallet wallet, ExtKey key) GenerateBlankWalletWithExtKey(string name, string password) { Mnemonic mnemonic = new Mnemonic(Wordlist.English, WordCount.Twelve); ExtKey extendedKey = mnemonic.DeriveExtKey(password); Features.Wallet.Wallet walletFile = new Features.Wallet.Wallet { Name = name, EncryptedSeed = extendedKey.PrivateKey.GetEncryptedBitcoinSecret(password, Network.Main).ToWif(), ChainCode = extendedKey.ChainCode, CreationTime = DateTimeOffset.Now, Network = Network.Main, AccountsRoot = new List <AccountRoot> { new AccountRoot { Accounts = new List <HdAccount>(), CoinType = (CoinType)Network.Main.Consensus.CoinType } }, }; return(walletFile, extendedKey); }
public static (Features.Wallet.Wallet wallet, ExtKey key) GenerateBlankWalletWithExtKey(string name, string password, IWalletRepository walletRepository = null) { var mnemonic = new Mnemonic(Wordlist.English, WordCount.Twelve); ExtKey extendedKey = mnemonic.DeriveExtKey(password); Network network = walletRepository?.Network ?? KnownNetworks.Main; string encryptedSeed = extendedKey.PrivateKey.GetEncryptedBitcoinSecret(password, network).ToWif(); var wallet = new Features.Wallet.Wallet(name, encryptedSeed, extendedKey.ChainCode, walletRepository: walletRepository) { Network = network }; wallet.AccountsRoot = new List <AccountRoot> { new AccountRoot(wallet) { CoinType = (CoinType)network.Consensus.CoinType } }; return(wallet, extendedKey); }
public static void AddAddressesToWallet(Features.Wallet.Wallet wallet, int count) { if (wallet.AccountsRoot.Count == 0) { wallet.AccountsRoot.Add(new AccountRoot(wallet) { CoinType = CoinType.Bitcoin }); } HdAccount account0 = wallet.AddNewAccount((ExtPubKey)null); HdAccount account1 = wallet.AddNewAccount((ExtPubKey)null); for (int i = 0; i < count; i++) { account0.ExternalAddresses.Add(CreateAddress(false, account0, i)); account0.InternalAddresses.Add(CreateAddress(true, account0, i)); account1.ExternalAddresses.Add(CreateAddress(false, account1, i)); account1.InternalAddresses.Add(CreateAddress(true, account1, i)); } }
public static (Features.Wallet.Wallet wallet, ExtKey key) GenerateBlankWalletWithExtKey(string name, string password) { var mnemonic = new Mnemonic("grass industry beef stereo soap employ million leader frequent salmon crumble banana"); ExtKey extendedKey = mnemonic.DeriveExtKey(password); var walletFile = new Features.Wallet.Wallet { Name = name, EncryptedSeed = extendedKey.PrivateKey.GetEncryptedBitcoinSecret(password, KnownNetworks.Main).ToWif(), ChainCode = extendedKey.ChainCode, CreationTime = DateTimeOffset.Now, Network = KnownNetworks.Main, AccountsRoot = new List <AccountRoot> { new AccountRoot() { Accounts = new List <HdAccount>(), CoinType = KnownNetworks.Main.Consensus.CoinType } }, }; return(walletFile, extendedKey); }
public void WalletCanReceiveAndSendCorrectly() { using (NodeBuilder builder = NodeBuilder.Create(this)) { CoreNode stratisSender = builder.CreateStratisPowNode(this.network); CoreNode stratisReceiver = builder.CreateStratisPowNode(this.network); builder.StartAll(); stratisSender.NotInIBD(); stratisReceiver.NotInIBD(); // get a key from the wallet Mnemonic mnemonic1 = stratisSender.FullNode.WalletManager().CreateWallet("123456", "mywallet"); Mnemonic mnemonic2 = stratisReceiver.FullNode.WalletManager().CreateWallet("123456", "mywallet"); Assert.Equal(12, mnemonic1.Words.Length); Assert.Equal(12, mnemonic2.Words.Length); HdAddress addr = stratisSender.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("mywallet", "account 0")); Features.Wallet.Wallet wallet = stratisSender.FullNode.WalletManager().GetWalletByName("mywallet"); Key key = wallet.GetExtendedPrivateKeyForAddress("123456", addr).PrivateKey; stratisSender.SetDummyMinerSecret(new BitcoinSecret(key, stratisSender.FullNode.Network)); int maturity = (int)stratisSender.FullNode.Network.Consensus.CoinbaseMaturity; stratisSender.GenerateStratisWithMiner(maturity + 5); // wait for block repo for block sync to work TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisSender)); // the mining should add coins to the wallet long total = stratisSender.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Sum(s => s.Transaction.Amount); Assert.Equal(Money.COIN * 105 * 50, total); // sync both nodes stratisSender.CreateRPCClient().AddNode(stratisReceiver.Endpoint, true); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisSender)); // send coins to the receiver HdAddress sendto = stratisReceiver.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("mywallet", "account 0")); Transaction trx = stratisSender.FullNode.WalletTransactionHandler().BuildTransaction(CreateContext(stratisSender.FullNode.Network, new WalletAccountReference("mywallet", "account 0"), "123456", sendto.ScriptPubKey, Money.COIN * 100, FeeType.Medium, 101)); // broadcast to the other node stratisSender.FullNode.NodeService <WalletController>().SendTransaction(new SendTransactionRequest(trx.ToHex())); // wait for the trx to arrive TestHelper.WaitLoop(() => stratisReceiver.CreateRPCClient().GetRawMempool().Length > 0); TestHelper.WaitLoop(() => stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Any()); long receivetotal = stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Sum(s => s.Transaction.Amount); Assert.Equal(Money.COIN * 100, receivetotal); Assert.Null(stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").First().Transaction.BlockHeight); // generate two new blocks do the trx is confirmed stratisSender.GenerateBlockManually(new List <Transaction>(new[] { stratisSender.FullNode.Network.CreateTransaction(trx.ToBytes()) })); stratisSender.GenerateStratisWithMiner(1); // wait for block repo for block sync to work TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisSender)); TestHelper.WaitLoop(() => maturity + 6 == stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").First().Transaction.BlockHeight); } }
public void WalletCanReorg() { // this test has 4 parts: // send first transaction from one wallet to another and wait for it to be confirmed // send a second transaction and wait for it to be confirmed // connected to a longer chain that couse a reorg back so the second trasnaction is undone // mine the second transaction back in to the main chain using (NodeBuilder builder = NodeBuilder.Create(this)) { CoreNode stratisSender = builder.CreateStratisPowNode(this.network); CoreNode stratisReceiver = builder.CreateStratisPowNode(this.network); CoreNode stratisReorg = builder.CreateStratisPowNode(this.network); builder.StartAll(); stratisSender.NotInIBD(); stratisReceiver.NotInIBD(); stratisReorg.NotInIBD(); // get a key from the wallet Mnemonic mnemonic1 = stratisSender.FullNode.WalletManager().CreateWallet("123456", "mywallet"); Mnemonic mnemonic2 = stratisReceiver.FullNode.WalletManager().CreateWallet("123456", "mywallet"); Assert.Equal(12, mnemonic1.Words.Length); Assert.Equal(12, mnemonic2.Words.Length); HdAddress addr = stratisSender.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("mywallet", "account 0")); Features.Wallet.Wallet wallet = stratisSender.FullNode.WalletManager().GetWalletByName("mywallet"); Key key = wallet.GetExtendedPrivateKeyForAddress("123456", addr).PrivateKey; stratisSender.SetDummyMinerSecret(new BitcoinSecret(key, stratisSender.FullNode.Network)); stratisReorg.SetDummyMinerSecret(new BitcoinSecret(key, stratisSender.FullNode.Network)); int maturity = (int)stratisSender.FullNode.Network.Consensus.CoinbaseMaturity; stratisSender.GenerateStratisWithMiner(maturity + 15); int currentBestHeight = maturity + 15; // wait for block repo for block sync to work TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisSender)); // the mining should add coins to the wallet long total = stratisSender.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Sum(s => s.Transaction.Amount); Assert.Equal(Money.COIN * currentBestHeight * 50, total); // sync all nodes stratisReceiver.CreateRPCClient().AddNode(stratisSender.Endpoint, true); stratisReceiver.CreateRPCClient().AddNode(stratisReorg.Endpoint, true); stratisSender.CreateRPCClient().AddNode(stratisReorg.Endpoint, true); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisReorg)); // Build Transaction 1 // ==================== // send coins to the receiver HdAddress sendto = stratisReceiver.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("mywallet", "account 0")); Transaction transaction1 = stratisSender.FullNode.WalletTransactionHandler().BuildTransaction(CreateContext(stratisSender.FullNode.Network, new WalletAccountReference("mywallet", "account 0"), "123456", sendto.ScriptPubKey, Money.COIN * 100, FeeType.Medium, 101)); // broadcast to the other node stratisSender.FullNode.NodeService <WalletController>().SendTransaction(new SendTransactionRequest(transaction1.ToHex())); // wait for the trx to arrive TestHelper.WaitLoop(() => stratisReceiver.CreateRPCClient().GetRawMempool().Length > 0); Assert.NotNull(stratisReceiver.CreateRPCClient().GetRawTransaction(transaction1.GetHash(), false)); TestHelper.WaitLoop(() => stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Any()); long receivetotal = stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Sum(s => s.Transaction.Amount); Assert.Equal(Money.COIN * 100, receivetotal); Assert.Null(stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").First().Transaction.BlockHeight); // generate two new blocks so the trx is confirmed stratisSender.GenerateStratisWithMiner(1); int transaction1MinedHeight = currentBestHeight + 1; stratisSender.GenerateStratisWithMiner(1); currentBestHeight = currentBestHeight + 2; // wait for block repo for block sync to work TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisReorg)); Assert.Equal(currentBestHeight, stratisReceiver.FullNode.Chain.Tip.Height); TestHelper.WaitLoop(() => transaction1MinedHeight == stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").First().Transaction.BlockHeight); // Build Transaction 2 // ==================== // remove the reorg node stratisReceiver.CreateRPCClient().RemoveNode(stratisReorg.Endpoint); stratisSender.CreateRPCClient().RemoveNode(stratisReorg.Endpoint); TestHelper.WaitLoop(() => !TestHelper.IsNodeConnected(stratisReorg)); ChainedHeader forkblock = stratisReceiver.FullNode.Chain.Tip; // send more coins to the wallet sendto = stratisReceiver.FullNode.WalletManager().GetUnusedAddress(new WalletAccountReference("mywallet", "account 0")); Transaction transaction2 = stratisSender.FullNode.WalletTransactionHandler().BuildTransaction(CreateContext(stratisSender.FullNode.Network, new WalletAccountReference("mywallet", "account 0"), "123456", sendto.ScriptPubKey, Money.COIN * 10, FeeType.Medium, 101)); stratisSender.FullNode.NodeService <WalletController>().SendTransaction(new SendTransactionRequest(transaction2.ToHex())); // wait for the trx to arrive TestHelper.WaitLoop(() => stratisReceiver.CreateRPCClient().GetRawMempool().Length > 0); Assert.NotNull(stratisReceiver.CreateRPCClient().GetRawTransaction(transaction2.GetHash(), false)); TestHelper.WaitLoop(() => stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Any()); long newamount = stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Sum(s => s.Transaction.Amount); Assert.Equal(Money.COIN * 110, newamount); Assert.Contains(stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet"), b => b.Transaction.BlockHeight == null); // mine more blocks so its included in the chain stratisSender.GenerateStratisWithMiner(1); int transaction2MinedHeight = currentBestHeight + 1; stratisSender.GenerateStratisWithMiner(1); currentBestHeight = currentBestHeight + 2; TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisSender)); Assert.Equal(currentBestHeight, stratisReceiver.FullNode.Chain.Tip.Height); TestHelper.WaitLoop(() => stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Any(b => b.Transaction.BlockHeight == transaction2MinedHeight)); // create a reorg by mining on two different chains // ================================================ // advance both chains, one chin is longer stratisSender.GenerateStratisWithMiner(2); stratisReorg.GenerateStratisWithMiner(10); currentBestHeight = forkblock.Height + 10; TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisSender)); TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisReorg)); // connect the reorg chain stratisReceiver.CreateRPCClient().AddNode(stratisReorg.Endpoint, true); stratisSender.CreateRPCClient().AddNode(stratisReorg.Endpoint, true); // wait for the chains to catch up TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisReorg)); Assert.Equal(currentBestHeight, stratisReceiver.FullNode.Chain.Tip.Height); // ensure wallet reorg complete TestHelper.WaitLoop(() => stratisReceiver.FullNode.WalletManager().WalletTipHash == stratisReorg.CreateRPCClient().GetBestBlockHash()); // check the wallet amount was rolled back long newtotal = stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Sum(s => s.Transaction.Amount); Assert.Equal(receivetotal, newtotal); TestHelper.WaitLoop(() => maturity + 16 == stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").First().Transaction.BlockHeight); // ReBuild Transaction 2 // ==================== // After the reorg transaction2 was returned back to mempool stratisSender.FullNode.NodeService <WalletController>().SendTransaction(new SendTransactionRequest(transaction2.ToHex())); TestHelper.WaitLoop(() => stratisReceiver.CreateRPCClient().GetRawMempool().Length > 0); // mine the transaction again stratisSender.GenerateStratisWithMiner(1); transaction2MinedHeight = currentBestHeight + 1; stratisSender.GenerateStratisWithMiner(1); currentBestHeight = currentBestHeight + 2; TestHelper.WaitLoop(() => TestHelper.IsNodeSynced(stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisSender)); TestHelper.WaitLoop(() => TestHelper.AreNodesSynced(stratisReceiver, stratisReorg)); Assert.Equal(currentBestHeight, stratisReceiver.FullNode.Chain.Tip.Height); long newsecondamount = stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Sum(s => s.Transaction.Amount); Assert.Equal(newamount, newsecondamount); TestHelper.WaitLoop(() => stratisReceiver.FullNode.WalletManager().GetSpendableTransactionsInWallet("mywallet").Any(b => b.Transaction.BlockHeight == transaction2MinedHeight)); } }
public void BuildTransferContextCorrectly() { const int utxoIndex = 0; uint256 utxoId = uint256.Zero; uint256 utxoIdUnused = uint256.One; string senderAddress = uint160.Zero.ToBase58Address(this.network); string recipientAddress = uint160.One.ToBase58Address(this.network); string changeAddress = new uint160(2).ToBase58Address(this.network); var amount = 1234.567M; var request = new BuildContractTransactionRequest { AccountName = "account 0", FeeAmount = "0.01", WalletName = "wallet", Password = "******", Sender = senderAddress, ShuffleOutputs = true, AllowUnconfirmed = true, ChangeAddress = changeAddress, Recipients = new List <RecipientModel> { // In locales that use a , for the decimal point this would fail to be parsed unless we use the invariant culture new RecipientModel { Amount = amount.ToString(CultureInfo.InvariantCulture), DestinationAddress = recipientAddress } } }; var reserveUtxoService = new ReserveUtxoService(this.loggerFactory, new Mock <ISignals>().Object); var service = new SmartContractTransactionService( this.network, this.walletManager.Object, this.walletTransactionHandler.Object, this.stringSerializer.Object, this.callDataSerializer.Object, this.addressGenerator.Object, this.stateRepository.Object, reserveUtxoService); var senderHdAddress = new HdAddress { Address = senderAddress }; var wallet = new Features.Wallet.Wallet(); wallet.AccountsRoot.Add(new AccountRoot(wallet)); var account0 = new HdAccount(wallet.AccountsRoot.First().Accounts) { Name = request.AccountName }; account0.ExternalAddresses.Add(new HdAddress() { Address = senderAddress }); this.walletManager.Setup(x => x.GetWallet(request.WalletName)) .Returns(wallet); this.walletManager.Setup(x => x.GetAddressBalance(request.Sender)) .Returns(new AddressBalance { Address = request.Sender, AmountConfirmed = Money.FromUnit(amount, MoneyUnit.BTC), AmountUnconfirmed = 0 }); var outputs = new List <UnspentOutputReference> { new UnspentOutputReference { Address = new HdAddress { Address = senderAddress }, Transaction = new TransactionData { Id = utxoId, Index = utxoIndex, } }, new UnspentOutputReference { Address = new HdAddress { Address = senderAddress }, Transaction = new TransactionData { Id = utxoIdUnused, Index = utxoIndex, } } }; this.walletManager.Setup(x => x.GetSpendableTransactionsInWallet(It.IsAny <string>(), 0)).Returns(outputs); this.walletTransactionHandler.Setup(x => x.BuildTransaction(It.IsAny <TransactionBuildContext>())) .Returns(new Transaction()); BuildContractTransactionResult result = service.BuildTx(request); // Check that the transaction builder is invoked, and that we: // - Ignore shuffleOutputs, // - Set inputs from sender // - Set recipients, // - Set change to sender this.walletTransactionHandler.Verify(w => w.BuildTransaction(It.Is <TransactionBuildContext>(context => context.AllowOtherInputs == false && context.Shuffle == false && context.SelectedInputs.All(i => outputs.Select(o => o.Transaction.Id).Contains(i.Hash)) && context.Recipients.Single().Amount == Money.FromUnit(amount, MoneyUnit.BTC) && context.ChangeAddress.Address == senderHdAddress.Address ))); }