* Add a private member called `sentFuture` that completes when the broadcast
is "sent" (written to buffer) to the broadcast peers
* Update the broadcast() method to track success/failure of the individual
broadcast messages and update sentFuture when the individual messages complete.
(This is done by using `thenComposeAsync`/`whenComplete`)
* Add comments and TODOs
By using a CoinSelector that selects exactly the outputs that have been sent to us,
we make sure that
* we exactly send the value that has been sent to us, minus fee
* if the incoming transaction became invalid (e.g. due to a re-org),
our outgoing transaction would become invalid, too
Strictly speaking, after this change we would not need to wait for confirmations any
more.
* Simplifies the lambda in broadcast:
** shortens it by two lines of code
** makes `peers` effectively final
** doesn't mutate the list `peers` with `shuffle`
* chooseBroadastPeers() gets JavaDoc
* chooseBroadastPeers() is more testable
Rationale:
* The comment says that it is a "list"
* Immutable Lists are the collection that maps most easily/logically to and from Stream
* Lists are easier to enforce reproducibility (mainly for unit tests)
This will speed up synchronization because the .setMaxConnections() call
will occur before synchronization is finished and the necessary number of Peers
will be found sooner.
Also IMO this a better example because most apps should not block while syncing the chain.
* Use `startAsync()` for the blocking case, too. Since we were already
waiting on `downloadListner.await()`
* Make sure `installShutdownHook()` is called in both cases (bug fix)
* Add more comments
Remove the very long try/catch in startup that catches BlockStoreException
and rethrows it wrapped in an IOException.
The Guava service base class (`AbstractIdleService`) that we are extending
allows us to throw `Exception` so there is no reason to wrap the exception
and it can just be thrown directly.
LinuxSecureRandom used to be installed on Android because very old Android versions had a bug
in the random number generator. We don't support those old versions any more, so the workaround
has become unnecessary. It is still possible to initialize it manually if desired.
This means for mainnet and testnet, you don't have to provide the network name.
It will be inferred from the address. For signet and regtest however the network
name is still needed.
* Use `CompletableFuture` for all asynchronous operations
* Use `thenCompose` to chain them
* sendTransaction takes a SendRequest and returns a TransactionBroadcast
* The main "CoinsReceived" listener method uses one .thenCompose() for
completing/signing/preparing-to-broadcast the transaction and another for waiting
for it to be confirmed by peers.