Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Store swap dynamic fees in separate table #355

Merged
merged 7 commits into from
Aug 1, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions libs/sdk-core/src/persist/migrations.rs
Original file line number Diff line number Diff line change
Expand Up @@ -428,6 +428,14 @@ pub(crate) fn current_migrations() -> Vec<&'static str> {
"
ALTER TABLE swaps_info ADD COLUMN channel_opening_fees TEXT;
",
// Swaps synchronization: Add sync table that stores the fees used in swaps
"
CREATE TABLE IF NOT EXISTS sync.swaps_fees (
bitcoin_address TEXT PRIMARY KEY NOT NULL,
created_at INTEGER DEFAULT CURRENT_TIMESTAMP NOT NULL,
channel_opening_fees TEXT NOT NULL
) STRICT;
"
]
}

Expand Down
34 changes: 32 additions & 2 deletions libs/sdk-core/src/persist/swap.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ use crate::models::{SwapInfo, SwapStatus};
use super::db::{SqliteStorage, StringArray};
use crate::OpeningFeeParams;
use anyhow::{anyhow, Result};
use rusqlite::{named_params, OptionalExtension, Params, Row};
use rusqlite::{named_params, OptionalExtension, Params, Row, Transaction};

impl SqliteStorage {
pub(crate) fn insert_swap(&self, swap_info: SwapInfo) -> Result<()> {
Expand Down Expand Up @@ -65,6 +65,13 @@ impl SqliteStorage {
":channel_opening_fees": swap_info.channel_opening_fees
},
)?;

Self::insert_swaps_fees(
&tx,
swap_info.bitcoin_address,
swap_info.channel_opening_fees,
)?;

tx.commit()?;
Ok(())
}
Expand Down Expand Up @@ -113,19 +120,42 @@ impl SqliteStorage {
Ok(())
}

fn insert_swaps_fees(
tx: &Transaction,
bitcoin_address: String,
channel_opening_fees: Option<OpeningFeeParams>,
) -> Result<()> {
tx.execute(
"INSERT OR REPLACE INTO sync.swaps_fees (bitcoin_address, channel_opening_fees) VALUES(:bitcoin_address, :channel_opening_fees)",
named_params! {
":bitcoin_address": bitcoin_address,
":channel_opening_fees": channel_opening_fees,
},
)?;

Ok(())
}

/// Update the dynamic fees associated with a swap
pub(crate) fn update_swap_fees(
&self,
bitcoin_address: String,
channel_opening_fees: Option<OpeningFeeParams>,
) -> Result<()> {
self.get_connection()?.execute(
let mut con = self.get_connection()?;
let tx = con.transaction()?;

tx.execute(
"UPDATE swaps_info SET channel_opening_fees=:channel_opening_fees where bitcoin_address=:bitcoin_address",
ok300 marked this conversation as resolved.
Show resolved Hide resolved
named_params! {
":channel_opening_fees": channel_opening_fees,
":bitcoin_address": bitcoin_address,
},
)?;

Self::insert_swaps_fees(&tx, bitcoin_address, channel_opening_fees)?;

tx.commit()?;
Ok(())
}

Expand Down
43 changes: 42 additions & 1 deletion libs/sdk-core/src/persist/sync.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ use crate::ReverseSwapStatus;

use super::db::SqliteStorage;
use anyhow::Result;
use rusqlite::{named_params, Row};
use rusqlite::{named_params, Row, Transaction};
use std::path::Path;

#[allow(dead_code)]
Expand Down Expand Up @@ -201,11 +201,52 @@ impl SqliteStorage {
[],
)?;

// Sync remote swaps_fees table, which contains dynamic fees used in swaps
// created_at is used to settle conflicts, since we assume small variations in the client local times
Self::sync_swaps_fees_local(&tx)?;
Self::sync_swaps_fees_remote(&tx)?;

tx.commit()?;
con.execute("DETACH DATABASE remote_sync", [])?;

Ok(())
}

/// Insert or update to local db all rows that have created_at larger than in the local
fn sync_swaps_fees_local(tx: &Transaction) -> Result<()> {
tx.execute(
"
INSERT OR REPLACE INTO sync.swaps_fees
(SELECT bitcoin_address, created_at, channel_opening_fees FROM remote_sync.swaps_fees
WHERE
bitcoin_address NOT IN (SELECT bitcoin_address from sync.swaps)
OR
created_at > (SELECT created_at FROM sync.swaps_fees WHERE bitcoin_address = remote_sync.bitcoin_address)
);
",
[],
)?;

Ok(())
}

/// Insert or update to remote db all rows that have created_at larger than in remote.
fn sync_swaps_fees_remote(tx: &Transaction) -> Result<()> {
tx.execute(
"
INSERT OR REPLACE INTO remote_sync.swaps_fees
(SELECT bitcoin_address, created_at, channel_opening_fees FROM sync.swaps_fees
WHERE
bitcoin_address NOT IN (SELECT bitcoin_address from remote_sync.swaps)
OR
created_at > (SELECT created_at FROM remote_sync.swaps_fees WHERE bitcoin_address = sync.bitcoin_address)
);
",
[],
)?;

Ok(())
}
}

#[test]
Expand Down
Loading