depolymerization

wire gateway for Bitcoin/Ethereum
Log | Files | Refs | Submodules | README | LICENSE

commit 59faf13eaf2b552616c7aa1c69149c92506bc73d
parent 805718832f00999324dc1a606d4e8255a0d4f77d
Author: Antoine A <>
Date:   Mon, 24 Jan 2022 11:21:01 +0100

Improve docuementation and require maxtxfee bitcoin config

Diffstat:
M.gitignore | 5+++--
MREADME.md | 59+++++++++++++++++++++++++++++++++++++++++++++++++++++++++--
Mbtc-wire/README.md | 93+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++------------
Mbtc-wire/src/config.rs | 5+++++
Mbtc-wire/src/loops/worker.rs | 2+-
Mtaler-common/src/config.rs | 4++--
Mtest/common.sh | 1-
Mtest/conf/bitcoin.conf | 1+
Mtest/conf/bitcoin_auth.conf | 1+
Mtest/conf/bitcoin_auth1.conf | 1+
Mtest/conf/bitcoin_auth2.conf | 1+
Mtest/conf/bitcoin_auth3.conf | 1+
Mtest/conf/bitcoin_auth4.conf | 1+
Mtest/conf/bitcoin_auth5.conf | 1+
Mtest/conf/taler_lifetime.conf | 4++--
Mwire-gateway/README.md | 9+++++++--
16 files changed, 163 insertions(+), 26 deletions(-)

diff --git a/.gitignore b/.gitignore @@ -1,2 +1,3 @@ /target -log -\ No newline at end of file +log +/.vscode +\ No newline at end of file diff --git a/README.md b/README.md @@ -6,4 +6,59 @@ - **btc-wire**: Taler wire implementation for [bitcoincore](https://bitcoincore.org/en/about/) node - **uri-pack**: Efficient probabilistic binary encoding for URI - **docs**: Documentation files -- **test**: Test scripts -\ No newline at end of file +- **test**: Test scripts + +## Configuration + +The configuration is based on [taler.conf](https://docs.taler.net/manpages/taler.conf.5.html). + +``` ini +# taler.conf - common config +[taler] +CURRENCY = ___ + +[exchange] +BASE_URL = https://___ + +[depolymerizer-___] +DB_URL = postgres://___ +PAYTO = payto://___ +``` + +### Process lifetime + +You may want to restart depolymerization processes regularly to improve +stability (ex. fix memory fragmentation). It is possible to configure lifetime +that trigger graceful shutdown every time a specific amount of work have been +done. + +``` ini +[depolymerizer-___] +# Number of requests to serve before gateway shutdown (0 mean never) +HTTP_LIFETIME = 0 +# Number of done worker's loops before wire implementation shutdown (0 mean never) +WIRE_LIFETIME = 0 +``` + +Modules have specific configuration: + +- [wire-gateway](wire-gateway/README.md#Configuration) +- [btc-wire](btc-wire/README.md#Configuration) + +## Architecture + +### Linking Taler to blockchains + +``` + ┌─────┐ ┌────────────────┐ ┌──────────┐ + │Taler├───┤Depolymerization├───┤Blockchain│ + └─────┘ └────────────────┘ └──────────┘ +``` + +### Depolymerization architecture + +``` + ┌────────────┐ ┌──────────┐ ┌────────┐ + │wire_gateway├───┤PostgreSQL├───┤###_wire│ + └────────────┘ └──────────┘ └────────┘ +``` +\ No newline at end of file diff --git a/btc-wire/README.md b/btc-wire/README.md @@ -16,21 +16,87 @@ Bitcoind version >= 22.0 is required The configuration is based on [taler.conf](https://docs.taler.net/manpages/taler.conf.5.html) +``` ini +# taler.conf - btc_wire config +[depolymerizer-___] +BTC_DATA_DIR = +CONFIRMATION = 6 +BOUNCE_FEE = 1000 +BUMP_DELAY = +``` + ### bitcoin.conf -btc-wire will automatically read the bitcoin configuration file to connect to the RPC server, -`txindex=1` is mandatory. +btc-wire will automatically read the bitcoin configuration file to connect to +the RPC server, `txindex=1` and `maxtxfee` are mandatory. ## Getting Started -1. Init bitcoincore node: - 1. Edit the default bitcoin.conf to add `txindex=1` - 2. Start a bitcoincore node on your machine -2. Init postgresql database - 1. Start a postgres database - 2. Load the database [schema](../db/btc.sql) -3. Init bitcoin wallet - 1. `bitcoin-cli createwallet wire` - 2. `bitcoin-cli -rpcwallet=wire getnewaddress` - 3. Edit taler.conf with wallet info -4. Run wire-gateway and btc-wire -\ No newline at end of file +1. Write configuration files +2. Start bitcoind +3. Start PostgreSQL +4. Initialize database `btc-wire-cli initdb` +5. Initialize wallet `btc-wire-cli initwallet` +6. Update taler.conf with wallet info +7. Run wire-gateway `wire-gateway` +8. Run btc-wire `btc-wire` + +## How it work ? + + +### Outgoing transaction lifecycle + +#### Transaction lifecycle + +``` + │ + ▼ + ┌─────────┐ + ┌─┤Requested├─┐ + │ └─────────┘ │ + ▼ ▼ + ┌────┐ ┌───────┐ + │Sent│◄────►│Delayed│ + └────┘ └───────┘ + + -> Requested API request +Requested -> Sent Sent in the blockchain +Requested -> Delayed Error while sending +Delayed -> Sent Sent in the blockchain +Send -> Delayed Conflicting transaction (reorg) +``` + +#### Bounce lifecycle + +``` + │ + ▼ + ┌─────────┐ + ┌─────┤Requested├────┐ + │ └────┬────┘ │ + ▼ ▼ ▼ + ┌────┐ ┌───────┐ ┌───────┐ + │Sent│◄─►│Delayed│ │Ignored│ + └────┘ └───────┘ └───────┘ + + -> Requested Transaction in wrong format +Requested -> Sent Sent in the blockchain +Requested -> Ignored Insufficient amount +Requested -> Delayed Error while sending +Delayed -> Sent Sent in the blockchain +Send -> Delayed Conflicting transaction (reorg) +``` + +### Stuck transaction + +When a transaction is sent with a fee too small compared to other transaction, +it can take an unlimited amount of time for this transaction to be mined. It is +possible to replace this transaction with another transaction with more fees +using [BIP 125](https://github.com/bitcoin/bips/blob/master/bip-0125.mediawiki). +btc-wire can be configured to do this automatically: + +``` ini +[depolymerizer-bitcoin] +# Delay in seconds before bumping an unconfirmed transaction fee +BUMP_DELAY = 10 +``` diff --git a/btc-wire/src/config.rs b/btc-wire/src/config.rs @@ -73,6 +73,11 @@ impl BitcoinConfig { exit(1); } + if !main.contains_key("maxtxfee") { + error!("btc_wire require a bitcoin core node running with 'maxtxfee' option"); + exit(1); + } + let network = if let Some("1") = main.get("testnet") { Network::Testnet } else if let Some("1") = main.get("signet") { diff --git a/btc-wire/src/loops/worker.rs b/btc-wire/src/loops/worker.rs @@ -51,7 +51,7 @@ pub fn worker( config: &Config, state: &WireState, ) { - let mut lifetime = config.btc_lifetime; + let mut lifetime = config.wire_lifetime; let mut status = true; // Alway start with a sync work diff --git a/taler-common/src/config.rs b/taler-common/src/config.rs @@ -49,7 +49,7 @@ pub struct Config { pub payto: Url, pub confirmation: u16, pub bounce_fee: u64, - pub btc_lifetime: Option<u32>, + pub wire_lifetime: Option<u32>, pub http_lifetime: Option<u32>, pub bump_delay: Option<u32>, } @@ -70,7 +70,7 @@ impl Config { payto: require(self_conf, "PAYTO", url), confirmation: nb(self_conf, "CONFIRMATION").unwrap_or(6), bounce_fee: nb(self_conf, "BOUNCE_FEE").unwrap_or(1000), - btc_lifetime: nb(self_conf, "BTC_LIFETIME") + wire_lifetime: nb(self_conf, "WIRE_LIFETIME") .and_then(|nb| (nb != 0).then(|| Some(nb))) .unwrap_or(None), http_lifetime: nb(self_conf, "HTTP_LIFETIME") diff --git a/test/common.sh b/test/common.sh @@ -196,7 +196,6 @@ function stress_btc_wire() { cargo build --bin btc-wire --release --features fail &> /dev/null target/release/btc-wire $CONF &>> log/btc_wire.log & target/release/btc-wire $CONF &>> log/btc_wire1.log & - target/release/btc-wire $CONF &>> log/btc_wire2.log & } # ----- Gateway ------ # diff --git a/test/conf/bitcoin.conf b/test/conf/bitcoin.conf @@ -1,5 +1,6 @@ regtest=1 txindex=1 +maxtxfee=0.00002000 fallbackfee=0.00000001 [regtest] diff --git a/test/conf/bitcoin_auth.conf b/test/conf/bitcoin_auth.conf @@ -1,5 +1,6 @@ regtest=1 txindex=1 +maxtxfee=0.1 fallbackfee=0.00000001 rpcuser=bob rpcpassword=password diff --git a/test/conf/bitcoin_auth1.conf b/test/conf/bitcoin_auth1.conf @@ -1,5 +1,6 @@ regtest=1 txindex=1 +maxtxfee=0.1 fallbackfee=0.00000001 rpcuser=bob rpcpassword=password diff --git a/test/conf/bitcoin_auth2.conf b/test/conf/bitcoin_auth2.conf @@ -1,5 +1,6 @@ regtest=1 txindex=1 +maxtxfee=0.1 fallbackfee=0.00000001 [regtest] diff --git a/test/conf/bitcoin_auth3.conf b/test/conf/bitcoin_auth3.conf @@ -1,5 +1,6 @@ regtest=1 txindex=1 +maxtxfee=0.1 fallbackfee=0.00000001 [regtest] diff --git a/test/conf/bitcoin_auth4.conf b/test/conf/bitcoin_auth4.conf @@ -1,5 +1,6 @@ regtest=1 txindex=1 +maxtxfee=0.1 fallbackfee=0.00000001 rpccookiefile=catch_me_if_you_can diff --git a/test/conf/bitcoin_auth5.conf b/test/conf/bitcoin_auth5.conf @@ -1,5 +1,6 @@ regtest=1 txindex=1 +maxtxfee=0.1 fallbackfee=0.00000001 rpccookiefile=catch_me_if_you_can diff --git a/test/conf/taler_lifetime.conf b/test/conf/taler_lifetime.conf @@ -11,4 +11,4 @@ PAYTO = payto://bitcoin/bcrt1qgkgxkjj27g3f7s87mcvjjsghay7gh34cx39prj CONFIRMATION = 3 BOUNCE_FEE = 1000 HTTP_LIFETIME = 10 -BTC_LIFETIME = 10 -\ No newline at end of file +WIRE_LIFETIME = 10 +\ No newline at end of file diff --git a/wire-gateway/README.md b/wire-gateway/README.md @@ -8,8 +8,13 @@ Rust server for [Taler Wire Gateway HTTP API](https://docs.taler.net/core/api-wi ## Configuration -Depend on the used wire implementation : -- [BTC](../btc-wire/README.md) +``` ini +# taler.conf - wire_gateway config +[depolymerizer-___] +PORT = 8080 +UNIXPATH = +``` + ## Database schema