use of co.rsk.bitcoinj.wallet.Wallet in project rskj by rsksmart.
the class ReleaseTransactionBuilder method buildWithConfiguration.
private Optional<BuildResult> buildWithConfiguration(SendRequestConfigurator sendRequestConfigurator, String operationDescription) {
// Build a tx and send request and configure it
BtcTransaction btcTx = new BtcTransaction(params);
if (activations.isActive(ConsensusRule.RSKIP201)) {
btcTx.setVersion(2);
}
SendRequest sr = SendRequest.forTx(btcTx);
// Default settings
defaultSettingsConfigurator.configure(sr);
// Specific settings
sendRequestConfigurator.configure(sr);
try {
wallet.completeTx(sr);
// Disconnect input from output because we don't need the reference and it interferes serialization
for (TransactionInput transactionInput : btcTx.getInputs()) {
transactionInput.disconnect();
}
List<UTXO> selectedUTXOs = wallet.getUTXOProvider().getOpenTransactionOutputs(wallet.getWatchedAddresses()).stream().filter(utxo -> btcTx.getInputs().stream().anyMatch(input -> input.getOutpoint().getHash().equals(utxo.getHash()) && input.getOutpoint().getIndex() == utxo.getIndex())).collect(Collectors.toList());
return Optional.of(new BuildResult(btcTx, selectedUTXOs));
} catch (InsufficientMoneyException e) {
logger.warn(String.format("Not enough BTC in the wallet to complete %s", operationDescription), e);
// panicProcessor.panic("nomoney", "Not enough confirmed BTC in the federation wallet to complete " + rskTxHash + " " + btcTx);
return Optional.empty();
} catch (Wallet.CouldNotAdjustDownwards e) {
logger.warn(String.format("A user output could not be adjusted downwards to pay tx fees %s", operationDescription), e);
// panicProcessor.panic("couldnotadjustdownwards", "A user output could not be adjusted downwards to pay tx fees " + rskTxHash + " " + btcTx);
return Optional.empty();
} catch (Wallet.ExceededMaxTransactionSize e) {
logger.warn(String.format("Tx size too big %s", operationDescription), e);
// panicProcessor.panic("exceededmaxtransactionsize", "Tx size too big " + rskTxHash + " " + btcTx);
return Optional.empty();
} catch (UTXOProviderException e) {
logger.warn(String.format("UTXO provider exception sending %s", operationDescription), e);
// panicProcessor.panic("utxoprovider", "UTXO provider exception " + rskTxHash + " " + btcTx);
return Optional.empty();
}
}
use of co.rsk.bitcoinj.wallet.Wallet in project rskj by rsksmart.
the class ReleaseTransactionBuilderTest method first_output_pay_fees.
@Test
public void first_output_pay_fees() {
NetworkParameters networkParameters = BridgeRegTestConstants.getInstance().getBtcParams();
Federation federation = new Federation(FederationMember.getFederationMembersFromKeys(Arrays.asList(new BtcECKey(), new BtcECKey(), new BtcECKey())), Instant.now(), 0, networkParameters);
List<UTXO> utxos = Arrays.asList(new UTXO(Sha256Hash.of(new byte[] { 1 }), 0, Coin.COIN, 0, false, federation.getP2SHScript()), new UTXO(Sha256Hash.of(new byte[] { 1 }), 0, Coin.COIN, 0, false, federation.getP2SHScript()));
Wallet thisWallet = BridgeUtils.getFederationSpendWallet(Context.getOrCreate(networkParameters), federation, utxos, false, mock(BridgeStorageProvider.class));
ReleaseTransactionBuilder rtb = new ReleaseTransactionBuilder(networkParameters, thisWallet, federation.address, Coin.SATOSHI.multiply(1000), activations);
Address pegoutRecipient = mockAddress(123);
Coin pegoutAmount = Coin.COIN.add(Coin.SATOSHI);
Optional<ReleaseTransactionBuilder.BuildResult> result = rtb.buildAmountTo(pegoutRecipient, pegoutAmount);
Assert.assertTrue(result.isPresent());
ReleaseTransactionBuilder.BuildResult builtTx = result.get();
Coin inputsValue = builtTx.getSelectedUTXOs().stream().map(UTXO::getValue).reduce(Coin.ZERO, Coin::add);
TransactionOutput changeOutput = builtTx.getBtcTx().getOutput(1);
// Second output should be the change output to the Federation
Assert.assertEquals(federation.getAddress(), changeOutput.getAddressFromP2SH(networkParameters));
// And if its value is the spent UTXOs summatory minus the requested pegout amount
// we can ensure the Federation is not paying fees for pegouts
Assert.assertEquals(inputsValue.minus(pegoutAmount), changeOutput.getValue());
}
use of co.rsk.bitcoinj.wallet.Wallet in project rskj by rsksmart.
the class ReleaseTransactionBuilderTest method build_pegout_tx_from_erp_federation.
@Test
public void build_pegout_tx_from_erp_federation() {
ActivationConfig.ForBlock activations = mock(ActivationConfig.ForBlock.class);
when(activations.isActive(ConsensusRule.RSKIP284)).thenReturn(true);
// Use mainnet constants to test a real situation
BridgeConstants bridgeConstants = BridgeMainNetConstants.getInstance();
Federation erpFederation = new ErpFederation(FederationMember.getFederationMembersFromKeys(Arrays.asList(new BtcECKey(), new BtcECKey(), new BtcECKey())), Instant.now(), 0, bridgeConstants.getBtcParams(), bridgeConstants.getErpFedPubKeysList(), bridgeConstants.getErpFedActivationDelay(), activations);
List<UTXO> utxos = Arrays.asList(new UTXO(Sha256Hash.of(new byte[] { 1 }), 0, Coin.COIN, 0, false, erpFederation.getP2SHScript()), new UTXO(Sha256Hash.of(new byte[] { 1 }), 0, Coin.COIN, 0, false, erpFederation.getP2SHScript()));
Wallet thisWallet = BridgeUtils.getFederationSpendWallet(new Context(bridgeConstants.getBtcParams()), erpFederation, utxos, false, mock(BridgeStorageProvider.class));
ReleaseTransactionBuilder releaseTransactionBuilder = new ReleaseTransactionBuilder(bridgeConstants.getBtcParams(), thisWallet, erpFederation.address, Coin.SATOSHI.multiply(1000), activations);
Address pegoutRecipient = mockAddress(123);
Coin pegoutAmount = Coin.COIN.add(Coin.SATOSHI);
Optional<ReleaseTransactionBuilder.BuildResult> result = releaseTransactionBuilder.buildAmountTo(pegoutRecipient, pegoutAmount);
Assert.assertTrue(result.isPresent());
}
use of co.rsk.bitcoinj.wallet.Wallet in project rskj by rsksmart.
the class BridgeUtilsTest method testIsValidPegInTx.
@Test
public void testIsValidPegInTx() {
// Peg-in is for the genesis federation ATM
Context btcContext = new Context(networkParameters);
Federation federation = bridgeConstantsRegtest.getGenesisFederation();
Wallet wallet = new BridgeBtcWallet(btcContext, Collections.singletonList(federation));
Address federationAddress = federation.getAddress();
wallet.addWatchedAddress(federationAddress, federation.getCreationTime().toEpochMilli());
when(activations.isActive(any(ConsensusRule.class))).thenReturn(false);
// Tx sending less than the minimum allowed, not a peg-in tx
Coin minimumLockValue = bridgeConstantsRegtest.getLegacyMinimumPeginTxValueInSatoshis();
BtcTransaction tx = new BtcTransaction(networkParameters);
tx.addOutput(minimumLockValue.subtract(Coin.CENT), federationAddress);
tx.addInput(Sha256Hash.ZERO_HASH, 0, new Script(new byte[] {}));
assertFalse(BridgeUtils.isValidPegInTx(tx, federation, btcContext, bridgeConstantsRegtest, activations));
// Tx sending 1 btc to the federation, but also spending from the federation address,
// the typical peg-out tx, not a peg-in tx.
BtcTransaction tx2 = new BtcTransaction(networkParameters);
tx2.addOutput(Coin.COIN, federationAddress);
TransactionInput txIn = new TransactionInput(networkParameters, tx2, new byte[] {}, new TransactionOutPoint(networkParameters, 0, Sha256Hash.ZERO_HASH));
tx2.addInput(txIn);
signWithNecessaryKeys(bridgeConstantsRegtest.getGenesisFederation(), BridgeRegTestConstants.REGTEST_FEDERATION_PRIVATE_KEYS, txIn, tx2);
assertFalse(BridgeUtils.isValidPegInTx(tx2, federation, btcContext, bridgeConstantsRegtest, activations));
// Tx sending 1 btc to the federation, is a peg-in tx
BtcTransaction tx3 = new BtcTransaction(networkParameters);
tx3.addOutput(Coin.COIN, federationAddress);
tx3.addInput(Sha256Hash.ZERO_HASH, 0, new Script(new byte[] {}));
assertTrue(BridgeUtils.isValidPegInTx(tx3, federation, btcContext, bridgeConstantsRegtest, activations));
// Tx sending 50 btc to the federation, is a peg-in tx
BtcTransaction tx4 = new BtcTransaction(networkParameters);
tx4.addOutput(Coin.FIFTY_COINS, federationAddress);
tx4.addInput(Sha256Hash.ZERO_HASH, 0, new Script(new byte[] {}));
assertTrue(BridgeUtils.isValidPegInTx(tx4, federation, btcContext, bridgeConstantsRegtest, activations));
}
use of co.rsk.bitcoinj.wallet.Wallet in project rskj by rsksmart.
the class BridgeSupportTestPowerMock method getRetiringFederationWallet_nonEmpty.
@Test
public void getRetiringFederationWallet_nonEmpty() throws IOException {
Federation mockedNewFederation = new Federation(FederationTestUtils.getFederationMembers(2), Instant.ofEpochMilli(2000), 10L, NetworkParameters.fromID(NetworkParameters.ID_REGTEST));
Federation expectedFederation = new Federation(FederationTestUtils.getFederationMembersWithBtcKeys(Arrays.asList(new BtcECKey[] { BtcECKey.fromPublicOnly(Hex.decode("036bb9eab797eadc8b697f0e82a01d01cabbfaaca37e5bafc06fdc6fdd38af894a")), BtcECKey.fromPublicOnly(Hex.decode("031da807c71c2f303b7f409dd2605b297ac494a563be3b9ca5f52d95a43d183cc5")) })), Instant.ofEpochMilli(5005L), 0L, NetworkParameters.fromID(NetworkParameters.ID_REGTEST));
Block mockedBlock = mock(Block.class);
when(mockedBlock.getNumber()).thenReturn(25L);
BridgeSupport bridgeSupport = getBridgeSupportWithMocksForFederationTests(false, mockedNewFederation, null, expectedFederation, null, null, mockedBlock);
Context expectedContext = mock(Context.class);
Whitebox.setInternalState(bridgeSupport, "btcContext", expectedContext);
BridgeStorageProvider provider = (BridgeStorageProvider) Whitebox.getInternalState(bridgeSupport, "provider");
Object expectedUtxos = provider.getOldFederationBtcUTXOs();
final Wallet expectedWallet = mock(Wallet.class);
PowerMockito.mockStatic(BridgeUtils.class);
PowerMockito.when(BridgeUtils.getFederationSpendWallet(any(), any(), any(), anyBoolean(), any())).then((InvocationOnMock m) -> {
Assert.assertEquals(m.<Context>getArgument(0), expectedContext);
Assert.assertEquals(m.<Federation>getArgument(1), expectedFederation);
Assert.assertEquals(m.<Object>getArgument(2), expectedUtxos);
return expectedWallet;
});
Assert.assertSame(expectedWallet, bridgeSupport.getRetiringFederationWallet(false));
}
Aggregations