This commit is contained in:
counterweight 2023-12-09 19:27:21 +01:00
commit 896f2b76aa
204 changed files with 4845 additions and 0 deletions

View file

@ -0,0 +1,176 @@
# System
The entire system is called bisq arbitrage system (bas for friends).
bas is composed of several independent daemons, libraries, human-operators, etc. It works in a mostly automated way, with the exception of manual input for fiat bank-related tasks and confirmations.
bas components communicate through a pub-sub broker. This broker also acts as the single point of truth to keep state and data. The entire balances are re-buildable from it, as well as other statistics about the trades.
This documents shows the main components of the system and how they interact with each other.
- bisq daemon
- TheFilter
- TheComposer
- TheTrader
- TheLedger
- TheTeller
## Components Summary
### bisq daemon
The bisq daemon is the actual bisq client + wallet. It handles the relationship with the network and holds BTC. It exposes itself as a grpc API which the other components of the system leverage to interact with the network and obtain information.
### TheFilter
TheFilter is a daemon that is constantly pulling the available and relevant TradeOffers from bisq markets. The high level logic looks roughly like this:
```python
while True:
all_offers = get_all_offers()
relevant_offers = filter_only_relevant_offers(all_offers)
store_offers(relevant_offers)
sleep(5000)
```
The definition of what is a relevant TradeOffer can be configured.
TheFilter stores the relevant offer snapshot on TheLedger on each iteration in a file, making it accessible to other services.
### TheComposer
TheComposer is a daemon that tries to build ArbitrageComboPlans and store them in TheLedger. The high level logic looks roughly like this:
```python
while True:
if not new_offers_available():
sleep(5000)
next
last_offers_snapshot = get_last_offers_snapshot()
juicy_combos = compose_combos_from_offers(last_offers_snapshot)
if juicy_combos:
store_combos(juicy_combos)
```
TheComposer is tasked with a hard optimization problem. To come up with the combos, it needs three pieces of information: the TradeOffers, the JuicyDefinition and the state of the fiat and BTC balances.
The TradeOffers come from TheFilter.
The JuicyDefinition is a configuration that specifies certain conditions that an ArbitrageComboPlan must meet in order to be considered "juicy" (lucrative) enough to be worth pursuing.
To obtain the state of fiat and BTC balances, TheComposers sends requests to TheTeller.
If a juicy ArbitrageComboPlan is obtained, it is sent to TheLedger. TheComposer itself does not take action to execute it.
### TheTrader
TheTrader is a daemon that executes trades. It reads proposed ArbitrageComboPlans from TheLedger and interacts with the bisq deamon to commit the trades.
The high level logic looks roughly like this for commiting trades:
```python
while True:
while not available_combo():
sleep(5000)
next
combo_to_execute = get_combo_to_execute()
if trade_offers_still_available(combo_to_execute):
commit_combo(combo_to_execute)
```
And like this for confirming fiat payments:
```python
while True:
while not pending_payment_confirmations():
sleep(5000)
next
pending_payment_confirmation = get_pending_payment_confirmation()
confirm_payment(pending_payment_confirmation)
```
TheTrader acts as the interaction layer with the actual trading in bisq. It is responsible both for initially commiting the TradeOffers, as well as for sending confirming of fiat payments to the trading peers.
### TheLedger
The Ledger is a pub/sub message broker that acts both as a communication tool between the different components of bas, as well as the data storage solution. It records all relevant events of the system.
It contains the following topics:
- TradeOffers: where all the available snapshots of the relevant TradeOffers in the market are shared.
- ArbitrageComboPlans: where all the combos composed from different TradeOffers are shared.
- TradeStates
- ComboStates
- EURBalance: where all the events that modify the balance of euros are shared. The final state of the balance can be reconstructed from this.
- BTCBalance: where all the events that modify the balance of (free) bitcoin are shared. The final state of the balance can be reconstructed from this.
- LockedBTCBalance: where all the events that modify the balance of (locked) bitcoin are shared. Locked bitcoin is the amount that gets stuck in escrow while
- BSQBalance: where all the events that modify the balance of BSQ are shared. The final state of the balance can be reconstructed from this.
### TheOperator
TheOperator is not a piece of software, but a human being.
In all the arbitrage combos that happen, there will be some fiat payments to make and to receive. These need human intervention: in the case of the fiat payment, someone needs to actually make the payment and confirm this has been done, and someone needs to be monitoring the arrival of the received fiat and confirm once it reaches.
Paying and monitoring received payments is outside of the scope of bas, but the system needs to know about these events to update the state of trades and balances.
To achieve this, TheOperator delivers messages in TheLedger. How this should be done is still not specified, although some kind of CLI seems like the best idea.
### TheTeller
TheTeller is a small library that can be used to query the state of balances. Balances need to be built by sequentially running through the relevant events in TheLedger. TheTeller encapsules this behaviour and provides a unified view on how much is there in each balance.
## Data flow
Although the system does not have a linear nature, looking at the flow of data in a naive, linear way helps understanding all the moving parts.
All the data flow, from beginning to end, looks like this:
- The bisq daemon is constantly running and interacting with the bisq network.
- TheFilter polls the bisq daemon frequently to obtain all the available TradeOffers. It then sends back to TheLedger the relevant ones.
- TheComposer picks up the relevant TradeOffers from TheLedger and attempts to compose ArbitrageComboPlans. When it succeeds in doing so, it sends the ArbitrageComboPlan details back to TheLedger.
- TheTrader picks any ArbitrageComboPlan that appears in TheLedger ASAP. It publishes the state of the different trades and the combo as a whole in TheLedger. It also updates the BTCBalance, transfering the deposit bitcoin to the LockedBTCBalance.
- TheOperator posts confirmations of the fiat payments, both made and received, to TheLedger.
- TheTrader relays the confirmations to the bisq peers and keeps on updating the states of the trades and balances until the combo is finished.
- TheOperator can use TheTeller at any given time to check the state of the balances. If there is an mismatch between the balances and reality, it can also be used to include corrective entries to reconcile both.
## Configuration and decisions to be made
- Available payment accounts: bas can only operate on trades with the passed fiat payment accounts. These accounts are needed to limit the TradeOffers which are relevant.
- Fiat balance starting point: a first entry in TheLedger must define what is the starting balance.
- Prefered trades: a more complex definition which specifies which TradeOffers should be considered relevant and which ones should be ignored. These include:
- Minimum and maximum fiat value.
- Minimum premium %.
- Prefered combos: a series of conditions that an ArbitrageComboPlan must meet to be considered interesting enough to be executed.
- Prefered balance state: a series on restrictions on how should balances look like. This is to avoid the balance to shift completely into a single currency. This definition specifies thresholds that should not be exceeded by a specific currency in the system. For example, that the TotalPortfolioValue in BTC should stay between 25% and 75% percent of the CurrencyPortfolio. If an ArbitrageCombo shifts the balances outside of the allowed ranges, it won't be executed.
## Operation
## Risks and mitigations
- Trades becoming unavailable
- Combo not being executed atomically
- Failure to perform fiat payment
## Glossary
- **TradeOffer**: A TradeOffer is a public commitment from a bisq participant (the maker) to engage in a trade with certain conditions. The trade is binding, meaning that once someone takes it (the taker), the maker is forced into executing it. You can picture the maker's offer as a contract with his signature on it. Anyone can sign the taker spot and start the binding transaction.
A trade offer contains, at least, the following details:
- A BTC amount.
- A secondary currency amount.
- A price (which is obviously the proportion between the previous two)
- The role for each currency (what is the maker giving away and what is taker giving away)
- A payment method for the secondary currency
- A taker security deposit in BTC, which gets returned after the trade is succesful
- A bisq trading fee, which can be paid in either BSQ or BTC
- A mining fee, which can only be paid in BTC
- **ArbitrageCombo**: An ArbritrageCombo is a series of buys and sells in one or several BTC-XXX markets executed with the hope that TotalPortfolioValue is larger at the end of the ArbitrageCombo.
If markets were perfect, it would be impossible to run a profitable ArbitrageCombo. The expected gain of any ArbitrageCombo would be 0 (ignoring fees. If fees are taken into account, it would be negative). Given that we know that markets are definetely not perfect, there should be a certain degree of hope in finding profitable. Whether market imperfection is enough to make a nice amount of money out of it is uncertain.
- **ArbitrageComboPlan**: an ArbitrageComboPlan is simply a possible ArbitrageCombo that hasn't been committed yet.

View file

@ -0,0 +1,3 @@
# TheFilter
TheFilter is the component of bas that polls the market to observe the available tradeoffers and brings back the relevant ones.

View file

@ -0,0 +1,32 @@
# Bisq Daemon
The bisq daemon is the daemon bisq client that interacts with the bisq network. It is developed by the bisq DAO, not by the bas team. We simply grab it as it is and deploy it, with backups and monitoring to ensure the best operation.
## Repo
All the code necessary to deploy, monitor and backup a bas bisq daemon instance.
## Deploy
The bisq daemon is deployed by downloading the already-built daemon executable that gets packaged along bisq's releases.
## Backup
The data folder gets backed-up in real time via syncthing with oli.
## Monitoring
The daemon is monitored by running the following command in cron in the daemon's host:
```bash
bisq_cli getversion && curl http://git.contrapeso.xyz:3001/api/push/5rs4qsvNPw?msg=OK&ping=
```
If a ping is not received within a 120 seconds window, a monitoring notification is sent.

View file

@ -0,0 +1,84 @@
A few first thoughts I drafted when discussing the idea with Dani.
# Definitions
## ArbitrageCombo
An ArbritrageCombo is a series of buys and sells in one or several BTC-XXX markets executed with the hope that TotalPortfolioValue is larger at the end of the ArbitrageCombo.
If markets were perfect, it would be impossible to run a profitable ArbitrageCombo. The expected gain of any ArbitrageCombo would be 0 (ignoring fees. If fees are taken into account, it would be negative). Given that we know that markets are definetely not perfect, there should be a certain degree of hope in finding profitable. Whether market imperfection is enough to make a nice amount of money out of it is uncertain.
## Balances
A balance is the available amount of a certain currency to execute trades. The bunch of different currencies at play compose the CurrencyPortfolio. Given that ArbitrageCombos consist on making several trades in different ExchangePairs and different ways, but...
- A perfect match of amounts will almost never available.
- bisq requires initial BTC deposits to execute operations
..., a certain amount of all the used currencies must always be available. The existing balances limit the amount of ArbitrageCombos that can be executed.
Assuming that the only goal of arbitrage is to maximize value, there should be a target Balance allocation for the CurrencyPortfolio. This means, there should be a conscious decision on how the the total wealth of the operation should be distributed across the different currencies. Otherwise, the allcoation may drift into one or other currency, possibly reaching a situation where no more arbitrage can be done because there is a shortage of one of the involved currencies. Furthermore, there are other motivations to have a target allocation in the CurrencyPortfolio (such as risk willing to be assumed or preference towards holding certain currencies).
For example, an arbitrage agent could have a target of having 0.1BTC and the rest of the value split as 50% € and 50% $. Whenever this balance gets broken, different strategies can be used to recover it. Mainly:
- Only executing ArbitrageCombos that, besides generating profit, tip the balance favourably towards the allocation target.
- Executing neutral trades (neutral as in, profit = 0)
The TotalPortfolioValue is the value, measured in €, of the CurrencyPortfolio. For example, balances in €, $ and BTC are converted to € because of its role as unit of account to measure value.
The end goal of the whole arbitrage operation is to increase the TotalPortfolioValue of the CurrencyPortfolio with no or very little risk.
## Exchange Pair
An ExchangePair is the combination of two currencies which can be traded in Bisq. Trades can happen in both ways (BTC -> Other currency / Other currency -> BTC).
## TradeOffer
A TradeOffer is a public commitment from a bisq participant (the maker) to engage in a trade with certain conditions. The trade is binding, meaning that once someone takes it (the taker), the maker is forced into executing it. You can picture the maker's offer as a contract with his signature on it. Anyone can sign the taker spot and start the binding transaction.
A trade offer contains, at least, the following details:
- A BTC amount.
- A secondary currency amount.
- A price (which is obviously the proportion between the previous two)
- The role for each currency (what is the maker giving away and what is taker giving away)
- A payment method for the secondary currency
- A taker security deposit in BTC, which gets returned after the trade is succesful
- A bisq trading fee, which can be paid in either BSQ or BTC
- A mining fee, which can only be paid in BTC
An offer is profitable, in the sense that it increases the Total
# Logic
## ArbitrageSeeker
An ArbitrageSeeker is a little script that monitors all available TradeOffers and tries to compose a profitable ArbitrageComboPlan. An ArbitrageComboPlan is simply a possible ArbitrageCombo that hasn't been committed yet.
The ArbitrageComboPlan is mostly a bunch of TradeOffers tied together. The execution of all of the included TradeOffers would result in a change in the Balances. Hence, we introduce the concept of PreArbitragePortfolio and PostArbitragePortfolio. Two metrics are used to measure the difference in the Pre and Post Balances:
- The TotalPortfolioValue. An ArbitrageComboPlan where the difference in TotalPortfolioValue is <= 0 is a stupidity, since no profit is gained.
- The weights of the different currencies in the CurrencyPortfolio change.
How to compose such a ArbitrageComboPlan, or the best one? A few intuitions:
- The only way any TradeOffer can generate profit is when the price of it is below market price. So, any ArbitrageCombo should have at least one TradeOffer below market rates.
- To balance things out so that the weights of the CurrencyPortfolio don't drift too hard, we should ideally find other TradeOffers with the same currency pair, but in the other way. The additional TradeOffers can improve or reduce profitability, depending on their distance to market prices.
- This poses the existence of a trade-off: when building an ArbitrageComboPlan, there might be the need to choose between profit and CurrencyPortfolio balancedness. Some rule needs to be specified to decide how to weight both.
With the previous ideas in mind, a pseudo-codish approach could be as follows:
I started trying to build a small logic to get this done, but once you get into it you end up realising how it's actually a pretty dense optimization problem. A few options on how to deal with it reasonably:
- Build a nasty, not so elegant heuristic with a few hardcodes in there to approximate how someone would try to build an ArbitrageComboPlan manually. Not too bad, probably the first thing that should be tried.
- Given that the volume of profitable trades should be relatively small (<50) a basic combinatorial heuristic could also go places easily I guess.
- In dreamland, a Genetic Algorithm could be a fun idea to try. My intuition is that, for small amounts of candidate TradeOffers, the combinatorial heuristic would be better and faster, but as the number increases, the Genetic Algorithm would end up being more efficient at some point.
# Other random thoughts
## Agile approach
- We discussed that the first step towards bringing this live would be to simply implement something roughly like the ArbitrageSeeker described above and let it run constantly for some time to assess how frequently opportunities arise. A new idea came to my mind. While the previous still holds true, I realised there is a possible additional step which might be very interesting and not take that much work: implementing a fake CurrencyPortfolio and simulating that offers are actually taken. Something similar to webpages that let you play on the real stock market with fake money. We would assign an initial balance to the agent and let it "take offers" in a fakish way. After running it for some time, we can actually see how well it did and have data to answer the question: if we had actually used this, how much would we have earned?
## Risks
- The larger the set of available currencies and payment methods is, the bigger the chance of securing profitable ArbitrageCombos.
- Small, illiquid currencies are probably where the heftiest opportunities will come from. I'm thinking about markets which have smallish volumes, but are not completely dead, such as the Brazilian Real or the Swiss Frank. The problem here is that both come with two risks: one is that exchange rates from-to € might chew up the profitability from the arbitrage (since these are not really currencies we want to hold mid-long term). The second one is that these exchange rates might not be so easy to include real-time into the calculation of the profitability of an ArbitrageComboPlan. My only idea on how this could be executed practically is using Revolut, which easily enables payments in many currencies with low fess, but AFAIK those guys don't provide an API service to simulate currency exchange rates and fees.
- Taking multiple offers is not an atomic operation. When we decide to execute an ArbitrageCombo, there is a risk that some offers are available at the time of taking and others stop being available or change conditions, making them unprofitable. This is very unlikely if the lag between designing an ArbitrageComboPlan and moving forward with it is short (seconds), but it is nevertheless possible. To optimize for this kind of issue, it might be a smart idea to take offers in a predefined sequence that tries to minimize the negative impact of one of them failing.

View file

@ -0,0 +1,14 @@
When using the `getpaymentacctform` method from bisq cli, I saw the following text:
```
"_COMMENTS_": [
"Do not manually edit the paymentMethodId field.",
"Edit the salt field only if you are recreating a payment account on a new installation and wish to preserve the account age."
]
```
So I understand that it is possible to restore my payment accounts from my persona GUI instance in the daemon by filling in the form properly.
I also asked about this topic in bisq's matrix chat and I got told that the structure of the data in bisq-gui and bisq-daemon should be the hence, and that means that copying the `UserPayload` file could do the trick.
Update: yes, the above trick works. I checked myself in a test environment.

View file

@ -0,0 +1,87 @@
# Installation of bisq daemon and CLI
## Installing
### Java
```bash
apt update
apt install default-jdk
java -version
```
Java must be installed.
### Daemon and CLI
```bash
cd
mkdir bisq
cd bisq
BISQ_VERSION="1.9.4"
wget "https://github.com/bisq-network/bisq/releases/download/v${BISQ_VERSION}/bisq-daemon-${BISQ_VERSION}.zip"
wget "https://github.com/bisq-network/bisq/releases/download/v${BISQ_VERSION}/bisq-cli-${BISQ_VERSION}.zip"
unzip bisq-daemon-${BISQ_VERSION}.zip
unzip bisq-cli-${BISQ_VERSION}.zip
rm bisq-daemon-${BISQ_VERSION}.zip
rm bisq-cli-${BISQ_VERSION}.zip
```
1. Copy the pre-built bisq cli from github
2. Copy the pre-built bisq daemon from github
3. Unzip both
```bash
cd ~/bisq/bisq-daemon-1.9.4
java -jar daemon.jar --apiPassword=noesfacilvivirsinbisq
# Give it some time to start up
cd ~/bisq/bisq-cli-1.9.4
java -jar cli.jar --password=noesfacilvivirsinbisq getversion
```
4. Run the bisq-daemon
5. Make a test call from the CLI to test
NOTE: the daemon consumes some RAM. Ensure that there is at least a 2Gb of RAM ready for the daemon to use, otherwise Java runs out of memory and behaves weird.
### Payment Accounts
To copy over existing payment accounts from another instance, one has to copy the `UserPayload` file, located in `$BISQ_DATA/btc_mainnet/db/UserPayload` into the bisq daemon data folder.
---
A few CLI calls to practice:
- Get BSQ balance
```shell
java -jar cli.jar --password=noesfacilvivirsinbisq getbalance --currency-code=BSQ
```
- Get BTC balance
``` bash
java -jar cli.jar --password=noesfacilvivirsinbisq getbalance --currency-code=BTC
```
- Set a password on the wallet
```bash
java -jar cli.jar --password=noesfacilvivirsinbisq setwalletpassword --wallet-password="noesfacilvivirsinbisq"
```
- Unlock the wallet for 60 seconds
```bash
java -jar cli.jar --password=noesfacilvivirsinbisq unlockwallet --wallet-password="noesfacilvivirsinbisq" --timeout=60
```
- Get EUR/BTC price
```bash
java -jar cli.jar --password=noesfacilvivirsinbisq getbtcprice --currency-code=EUR
```
- Get a funding address
```bash
java -jar cli.jar --password=noesfacilvivirsinbisq getfundingaddresses
```
- Get offers for a certain market and direction
```bash
java -jar cli.jar --password=noesfacilvivirsinbisq getoffers --direction=BUY --currency-code=EUR
```
- Stop the daemon
```bash
java -jar cli.jar --password=noesfacilvivirsinbisq stop
```

View file

@ -0,0 +1,170 @@
I am going to perform a manual trade through the bisq daemon with the bisq cli in order to get familiar with a full trade flow. I'll carefully describe below:
- The plan
- The execution log, with each output and response
- The flow of funds throughout.
----
# The plan
The plan is simply to buy some BTC by taking a small offer. The steps would be:
0. Unlock wallet with `unlockwallet`.
1. Fund the wallet
1. Get a BTC address from the CLI with `getfundingaddresses`.
2. Send 0.01 BTC to the address.
3. Check the balance of the BTC address with `getbalance` and `getaddressbalance`.
2. Buy a small amount of BSQ
1. Check the available offers with `getoffers --direction=BUY --currency-code=BSQ`
2. Pick one and take it with `takeoffer`. Payment must come from `BsqSwapAccount` payment account.
3. Check the change in BSQ and BTC balances with `getbalance --currency-code=BTC` and `getbalance --currency-code=BSQ`. The BTC balance should comply with BTC = starting_btc + purchased_btc - mining_fee. The BSQ balance should comply with BSQ = starting_bsq - trading_fee.
3. Buy a small amount of BTC
1. Check the available offers with `getoffers --direction=BUY --currency-code=BSQ`.
2. Pick one (preferably revolut since it's fast) and take it with `takeoffer`.
3. Check it on the list of open trades with `gettrades --category=open`.
4. Send the payment through the fiat system.
5. Confirm the payment with `confirmpaymentstarted`.
6. Regularly check `gettrade` until the trade is finished.
7. Once it appears finished, verify that it appears in `gettrades --category=closed`.
4. Review balances and empty the wallet.
1. Check the change in BSQ and BTC balances with `getbalance --currency-code=BTC` and `getbalance --currency-code=BSQ`. The BTC balance should comply with BTC = starting_btc - (purchased_bsq * price) - trading_fee - mining_fee.
2. Send the remaining BSQ to my main wallet with `sendbsq`
3. Check the change in BSQ and BTC balances with `getbalance --currency-code=BTC` and `getbalance --currency-code=BSQ`. The BTC balance should comply with BTC = starting_btc - mining_fee. The BSQ balance should be zero.
4. Send the remaining BTC to my main wallet with `sendbtc`.
5. Check that the BTC balance is zero.
# Log
*Note: `bisq_cli` is an alias to call the bisq cli with the password included. Simply syntactic sugar.*
0. Unlock wallet with `unlockwallet`.
command: `bisq_cli unlockwallet --wallet-password=noesfacilvivirsinbisq --timeout=3600`
output: `wallet unlocked`
1. Fund the wallet
1.1 Get a BTC address from the CLI with `getfundingaddresses`.
- command: `bisq_cli getfundingaddresses`
- output:
```bash
BTC Address Available Balance Confirmations Is Used
bc1qnafthlvmfknywypgjvg6l04rxg30w740s7p2px 0.00000000 0 NO
```
1.2 Send 0.01 BTC to the address.
1.3 Check the balance of the BTC address with `getbalance` and `getaddressbalance`.
- command: `bisq_cli getbalance`
- output:
```bash
BTC
Available Balance Reserved Balance Total Available Balance Locked Balance
0.01000000 0.00000000 0.01000000 0.00000000
BSQ
Available Confirmed Balance Unverified Balance Unconfirmed Change Balance Locked For Voting Balance Lockup Bonds Balance Unlocking Bonds Balance
0.00 0.00 0.00 0.00 0.00 0.00
```
with `getaddressbalance`:
- command: `bisq_cli getaddressbalance --address=bc1qnafthlvmfknywypgjvg6l04rxg30w740s7p2px`
- output:
```bash
BTC Address Available Balance Confirmations Is Used
bc1qnafthlvmfknywypgjvg6l04rxg30w740s7p2px 0.01000000 0 YES
```
2. Buy a small amount of BSQ
2.1 Check the available offers with `getoffers --direction=BUY --currency-code=BSQ`
- command: `bisq_cli getoffers --direction=BUY --currency-code=BSQ`
- output:
```bash
Buy/Sell Price in BTC for 1 BSQ BTC(min - max) BSQ(min - max) Payment Method Creation Date (UTC) ID
Sell BSQ (Buy BTC) 0.00003848 0.00490000 - 0.03850000 127.34 - 1000.52 BSQ Swap 2022-08-30T14:36:35Z 14389-ec20aa00-c9eb-41e0-9e3a-5340b371b8e2-194
Sell BSQ (Buy BTC) 0.00003849 0.00500000 - 0.05000000 129.90 - 1299.04 BSQ Swap 2022-08-30T11:41:56Z zwievr-085f03d1-94d6-4501-8010-242cd29199d2-195
Sell BSQ (Buy BTC) 0.00003938 0.00610000 - 0.01560000 154.90 - 396.14 BSQ Swap 2022-08-30T11:57:27Z TZITsBb-f137baac-2f6f-48ca-8d4f-34f790097d23-195
Sell BSQ (Buy BTC) 0.00003940 0.01500000 - 0.04000000 380.71 - 1015.23 BSQ Swap 2022-08-29T05:34:22Z kmxvby-f8c31feb-2c1c-46bb-ad66-059914a89b64-194
Sell BSQ (Buy BTC) 0.00003950 0.03950000 1000.00 BSQ Swap 2022-08-30T07:04:16Z 35879170-8cc6f257-f25c-464d-9f71-ceccb44d9c89-195
Sell BSQ (Buy BTC) 0.00003950 0.00060000 - 0.00400000 15.19 - 101.27 BSQ Swap 2022-08-30T11:41:51Z 714117-59608f03-963f-4336-baab-64d43338e4c7-192
Sell BSQ (Buy BTC) 0.00004000 0.00080000 20.00 BSQ Swap 2022-08-30T07:14:57Z ue9sdp-dc7323d8-2731-4247-a058-030996d067af-195
Sell BSQ (Buy BTC) 0.00004000 0.00080000 20.00 BSQ Swap 2022-08-30T07:14:27Z SKCKVQDP-d4623ad7-bebc-4aed-93da-53a8ac3ff514-195
Sell BSQ (Buy BTC) 0.00004048 0.00100000 - 0.00810000 24.70 - 200.10 BSQ Swap 2022-08-29T19:41:39Z HrOuNo-58302776-5319-4818-af00-213d0973375f-194
Sell BSQ (Buy BTC) 0.00004049 0.00060000 - 0.00610000 14.82 - 150.65 BSQ Swap 2022-08-28T16:40:05Z 6KxJh-e4ee2a5a-64e9-46b5-951d-6c6c9f17e0c3-194
Sell BSQ (Buy BTC) 0.00004050 0.00060000 - 0.00400000 14.81 - 98.77 BSQ Swap 2022-07-03T16:05:01Z NJBASBFF-d92a6fe1-ca9c-4fd0-9b46-6af997df8062-192
Sell BSQ (Buy BTC) 0.00004100 0.01000000 - 0.03500000 243.90 - 853.66 BSQ Swap 2022-07-20T16:32:42Z 4KWYFJP-bb86953f-3eaf-46f8-8746-83f9e548f7ed-194
Sell BSQ (Buy BTC) 0.00004399 0.00040000 - 0.00290000 9.09 - 65.92 BSQ Swap 2022-08-29T19:43:42Z 175293-8435740d-5985-49e7-9db8-36f033a9eebd-194
Sell BSQ (Buy BTC) 0.00004438 0.00250000 56.33 BSQ Swap 2022-08-03T21:01:34Z oA9oj0GO-5c9b7e5e-de84-4ca2-a387-58486f5b5935-192
Sell BSQ (Buy BTC) 0.00004648 0.00200000 43.03 BSQ Swap 2022-08-03T19:24:12Z edwjc-94213efc-7cd0-4140-a0ae-0641e29179e2-192
Sell BSQ (Buy BTC) 0.00004655 0.00070000 15.04 BSQ Swap 2022-07-20T20:53:08Z asxly-427893e8-6d6b-4a12-97cc-3463cc217bdf-192
Sell BSQ (Buy BTC) 0.00004660 0.00150000 32.19 BSQ Swap 2022-08-03T21:06:37Z ypW2V-b690bc2e-de32-4176-a7b9-27ebc7f72e14-192
Sell BSQ (Buy BTC) 0.00004679 0.00080000 17.10 BSQ Swap 2022-08-03T19:28:24Z hgsZP-e7a80f22-7a06-416c-82aa-b4f5c8cbf798-192
Sell BSQ (Buy BTC) 0.00004680 0.00060000 12.82 BSQ Swap 2022-07-20T20:49:31Z PJNjEX-0461e540-c6ed-49f7-b1f7-8584f8aefb69-192
Sell BSQ (Buy BTC) 0.00004724 0.00090000 19.05 BSQ Swap 2022-07-29T02:01:58Z Fejwzd-1e0d10c9-8612-4001-b04e-fae90af42dc7-192
Sell BSQ (Buy BTC) 0.00004990 0.00050000 10.02 BSQ Swap 2022-07-29T02:02:54Z pcokkua-06cdeb10-c423-4ef4-87f7-d711d4d23bf1-192
Sell BSQ (Buy BTC) 0.00005000 0.00040000 8.00 BSQ Swap 2022-08-03T20:55:05Z 6ensso-15e41f4b-5444-4394-830d-199c8d2efc93-192
Sell BSQ (Buy BTC) 0.00005610 0.00040000 7.13 BSQ Swap 2022-07-29T01:59:34Z 3741221-a4290129-059b-47c6-a62b-e78e8613ecb9-192
```
2.2. Pick one and take it with `takeoffer`. Payment must come from `BsqSwapAccount` payment account.
- command: `bisq_cli takeoffer --offer-id=PJNjEX-0461e540-c6ed-49f7-b1f7-8584f8aefb69-192 --fee-currency=BTC`
- output:
```bash
trade PJNjEX-0461e540-c6ed-49f7-b1f7-8584f8aefb69-192 successfully taken
```
2.3. Check the change in BSQ and BTC balances with `getbalance --currency-code=BTC` and `getbalance --currency-code=BSQ`.
- command: `bisq_cli getbalance --currency-code=btc`
- output:
```bash
Available Balance Reserved Balance Total Available Balance Locked Balance
0.00938658 0.00000000 0.00938658 0.00000000
```
And then for BSQ:
- command: `bisq_cli getbalance --currency-code=bsq`
- output:
```bash
Available Confirmed Balance Unverified Balance Unconfirmed Change Balance Locked For Voting Balance Lockup Bonds Balance Unlocking Bonds Balance
12.74 0.00 0.00 0.00 0.00 0.00
```
Let's see the trades details as well:
- command: `bisq_cli gettrades --category=closed`
- output:
```bash
Trade ID Date/Time (UTC) Market Price Deviation Amount in BTC Amount Currency Tx Fee (BTC) Trade Fee Buyer Deposit (BTC) Seller Deposit (BTC) Offer Type Status
PJNjEX-0461e540-c6ed-49f7-b1f7-8584f8aefb69-192 2022-09-08T19:20:22Z BSQ/BTC 0.00004680 N/A 0.0006 12.82 BSQ 0.00001342 0.00 BSQ 0.00000000 0.00000000 SELL BSQ Confirmed
```
Now for the numbers:
- BTC
- My expected balance and the reality
```
paid_btc = bsq_amount * btc_per_bisq_price
final_btc_balance = starting_btc - paid_btc - mining_fee = 0.01 - (0.00004680 * 12.82) - 0.00001342 = 0.009386604
reality = 0.00938658
There is a difference of 24 sats that can be attributed to how bisq rounds the price to 8 decimal positions (so that it's counted only up to sats).
final_bsq_balance = 12.82
reality = 12.74
Where did my 0.08 BSQ go to???
```
```
4. Check the change in BSQ and BTC balances with `getbalance --currency-code=BTC` and `getbalance --currency-code=BSQ`. The BTC balance should comply with BTC = starting_btc + purchased_btc - mining_fee. The BSQ balance should comply with BSQ = starting_bsq - trading_fee.
2. Buy a small amount of BTC
1. Check the available offers with `getoffers --direction=BUY --currency-code=BSQ`.
2. Pick one (preferably revolut since it's fast) and take it with `takeoffer`.
3. Check it on the list of open trades with `gettrades --category=open`.
4. Send the payment through the fiat system.
5. Confirm the payment with `confirmpaymentstarted`.
6. Regularly check `gettrade` until the trade is finished.
7. Once it appears finished, verify that it appears in `gettrades --category=closed`.
3. Review balances and empty the wallet.
1. Check the change in BSQ and BTC balances with `getbalance --currency-code=BTC` and `getbalance --currency-code=BSQ`. The BTC balance should comply with BTC = starting_btc - (purchased_bsq * price) - trading_fee - mining_fee.
2. Send the remaining BSQ to my main wallet with `sendbsq`
3. Check the change in BSQ and BTC balances with `getbalance --currency-code=BTC` and `getbalance --currency-code=BSQ`. The BTC balance should comply with BTC = starting_btc - mining_fee. The BSQ balance should be zero.
4. Send the remaining BTC to my main wallet with `sendbtc`.
5. Check that the BTC balance is zero.

View file

@ -0,0 +1,17 @@
# bas-dev
`bas-dev` is the development machine. It also contains a couple of other utilities like a private git server and a private docker registry.
usr bas
pwd noesfacilvivirsinbas
usr git
pwd noesfacilvivirsingit
gitea details
pablo
noesfacilvivirenunmundo...

View file

@ -0,0 +1,4 @@
# Ports
The bisq daemon GRPC server listens on port 9998 by default. So, if it's running within a container, you need to map it to access the GRPC server.