Skip to content
This repository was archived by the owner on Feb 3, 2025. It is now read-only.

Commit eafa9ab

Browse files
Merge pull request #894 from johncantrell97/lightning-liquidity
Add LSPS support via `lightning-liquidity` crate
2 parents 26d7fee + 190873f commit eafa9ab

File tree

17 files changed

+1190
-224
lines changed

17 files changed

+1190
-224
lines changed

Cargo.lock

Lines changed: 15 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

mutiny-core/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ lightning-invoice = { version = "0.26.0", features = ["serde"] }
3232
lightning-rapid-gossip-sync = { version = "0.0.118" }
3333
lightning-background-processor = { version = "0.0.118", features = ["futures"] }
3434
lightning-transaction-sync = { version = "0.0.118", features = ["esplora-async-https"] }
35+
lightning-liquidity = { git = "https://github.com/lightningdevkit/lightning-liquidity.git", rev = "e00d917a8bb17e29493497538c7a4dda00bef151" }
3536
chrono = "0.4.22"
3637
futures-util = { version = "0.3", default-features = false }
3738
reqwest = { version = "0.11", default-features = false, features = ["json"] }

mutiny-core/src/error.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,9 @@ pub enum MutinyError {
6969
/// LSP indicated it was not connected to the client node.
7070
#[error("Failed to have a connection to the LSP node.")]
7171
LspConnectionError,
72+
/// LSP required an invoice and none was provided.
73+
#[error("Failed to provide an invoice to the LSP.")]
74+
LspInvoiceRequired,
7275
/// Subscription Client Not Configured
7376
#[error("Subscription Client Not Configured")]
7477
SubscriptionClientNotConfigured,

mutiny-core/src/event.rs

Lines changed: 24 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ use crate::fees::MutinyFeeEstimator;
22
use crate::keymanager::PhantomKeysManager;
33
use crate::ldkstorage::{MutinyNodePersister, PhantomChannelManager};
44
use crate::logging::MutinyLogger;
5+
use crate::lsp::{AnyLsp, Lsp};
56
use crate::node::BumpTxEventHandler;
67
use crate::nodemanager::ChannelClosure;
78
use crate::onchain::OnChainWallet;
@@ -85,7 +86,7 @@ pub struct EventHandler<S: MutinyStorage> {
8586
keys_manager: Arc<PhantomKeysManager<S>>,
8687
persister: Arc<MutinyNodePersister<S>>,
8788
bump_tx_event_handler: Arc<BumpTxEventHandler<S>>,
88-
lsp_client_pubkey: Option<PublicKey>,
89+
lsp_client: Option<AnyLsp<S>>,
8990
logger: Arc<MutinyLogger>,
9091
}
9192

@@ -98,15 +99,15 @@ impl<S: MutinyStorage> EventHandler<S> {
9899
keys_manager: Arc<PhantomKeysManager<S>>,
99100
persister: Arc<MutinyNodePersister<S>>,
100101
bump_tx_event_handler: Arc<BumpTxEventHandler<S>>,
101-
lsp_client_pubkey: Option<PublicKey>,
102+
lsp_client: Option<AnyLsp<S>>,
102103
logger: Arc<MutinyLogger>,
103104
) -> Self {
104105
Self {
105106
channel_manager,
106107
fee_estimator,
107108
wallet,
108109
keys_manager,
109-
lsp_client_pubkey,
110+
lsp_client,
110111
persister,
111112
bump_tx_event_handler,
112113
logger,
@@ -224,10 +225,24 @@ impl<S: MutinyStorage> EventHandler<S> {
224225
payment_hash,
225226
purpose,
226227
amount_msat,
228+
counterparty_skimmed_fee_msat,
227229
..
228230
} => {
229231
log_debug!(self.logger, "EVENT: PaymentReceived received payment from payment hash {} of {amount_msat} millisatoshis to {receiver_node_id:?}", payment_hash.0.to_hex());
230232

233+
let expected_skimmed_fee_msat = self
234+
.lsp_client
235+
.as_ref()
236+
.map(|lsp_client| {
237+
lsp_client.get_expected_skimmed_fee_msat(payment_hash, amount_msat)
238+
})
239+
.unwrap_or(0);
240+
241+
if counterparty_skimmed_fee_msat > expected_skimmed_fee_msat {
242+
log_error!(self.logger, "ERROR: Payment with hash {} skimmed a fee of {} millisatoshis when we expected a fee of {} millisatoshis", payment_hash, counterparty_skimmed_fee_msat, expected_skimmed_fee_msat);
243+
return;
244+
}
245+
231246
if let Some(payment_preimage) = match purpose {
232247
PaymentPurpose::InvoicePayment {
233248
payment_preimage, ..
@@ -376,7 +391,12 @@ impl<S: MutinyStorage> EventHandler<S> {
376391
Err(e) => log_debug!(self.logger, "EVENT: OpenChannelRequest error: {e:?}"),
377392
};
378393

379-
if self.lsp_client_pubkey.as_ref() != Some(&counterparty_node_id) {
394+
let lsp_pubkey = self
395+
.lsp_client
396+
.as_ref()
397+
.map(|client| client.get_lsp_pubkey());
398+
399+
if lsp_pubkey.as_ref() != Some(&counterparty_node_id) {
380400
// did not match the lsp pubkey, normal open
381401
let result = self.channel_manager.accept_inbound_channel(
382402
&temporary_channel_id,

mutiny-core/src/keymanager.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ use bitcoin::bech32::u5;
99
use bitcoin::secp256k1::ecdh::SharedSecret;
1010
use bitcoin::secp256k1::ecdsa::RecoverableSignature;
1111
use bitcoin::secp256k1::ecdsa::Signature;
12-
use bitcoin::secp256k1::{PublicKey, Scalar, Secp256k1, Signing};
12+
use bitcoin::secp256k1::{PublicKey, Scalar, Secp256k1, SecretKey, Signing};
1313
use bitcoin::util::bip32::{ChildNumber, DerivationPath, ExtendedPrivKey};
1414
use bitcoin::{PackedLockTime, Script, Transaction, TxOut};
1515
use lightning::ln::msgs::{DecodeError, UnsignedGossipMessage};
@@ -53,6 +53,10 @@ impl<S: MutinyStorage> PhantomKeysManager<S> {
5353
}
5454
}
5555

56+
pub(crate) fn get_node_secret_key(&self) -> SecretKey {
57+
self.inner.get_node_secret_key()
58+
}
59+
5660
/// See [`KeysManager::spend_spendable_outputs`] for documentation on this method.
5761
pub fn spend_spendable_outputs<C: Signing>(
5862
&self,

mutiny-core/src/lib.rs

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,8 @@ pub mod labels;
2121
mod ldkstorage;
2222
pub mod lnurlauth;
2323
pub mod logging;
24-
mod lspclient;
24+
mod lsp;
25+
mod messagehandler;
2526
mod networking;
2627
mod node;
2728
pub mod nodemanager;
@@ -79,6 +80,8 @@ pub struct MutinyWalletConfig {
7980
user_esplora_url: Option<String>,
8081
user_rgs_url: Option<String>,
8182
lsp_url: Option<String>,
83+
lsp_connection_string: Option<String>,
84+
lsp_token: Option<String>,
8285
auth_client: Option<Arc<MutinyAuthClient>>,
8386
subscription_url: Option<String>,
8487
scorer_url: Option<String>,
@@ -97,6 +100,8 @@ impl MutinyWalletConfig {
97100
user_esplora_url: Option<String>,
98101
user_rgs_url: Option<String>,
99102
lsp_url: Option<String>,
103+
lsp_connection_string: Option<String>,
104+
lsp_token: Option<String>,
100105
auth_client: Option<Arc<MutinyAuthClient>>,
101106
subscription_url: Option<String>,
102107
scorer_url: Option<String>,
@@ -112,6 +117,8 @@ impl MutinyWalletConfig {
112117
user_rgs_url,
113118
scorer_url,
114119
lsp_url,
120+
lsp_connection_string,
121+
lsp_token,
115122
auth_client,
116123
subscription_url,
117124
do_not_connect_peers: false,
@@ -695,6 +702,8 @@ mod tests {
695702
None,
696703
None,
697704
None,
705+
None,
706+
None,
698707
false,
699708
true,
700709
);
@@ -726,6 +735,8 @@ mod tests {
726735
None,
727736
None,
728737
None,
738+
None,
739+
None,
729740
false,
730741
true,
731742
);
@@ -763,6 +774,8 @@ mod tests {
763774
None,
764775
None,
765776
None,
777+
None,
778+
None,
766779
false,
767780
true,
768781
);
@@ -801,6 +814,8 @@ mod tests {
801814
None,
802815
None,
803816
None,
817+
None,
818+
None,
804819
false,
805820
true,
806821
);
@@ -827,6 +842,8 @@ mod tests {
827842
None,
828843
None,
829844
None,
845+
None,
846+
None,
830847
false,
831848
true,
832849
);

0 commit comments

Comments
 (0)