feat: nwc#2150
Conversation
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #2150 +/- ##
==========================================
+ Coverage 71.55% 71.65% +0.10%
==========================================
Files 356 359 +3
Lines 73999 75095 +1096
==========================================
+ Hits 52950 53813 +863
- Misses 21049 21282 +233 ☔ View full report in Codecov by Harness. 🚀 New features to boost your workflow:
|
|
closes #2106 |
|
I have tested this with https://nwc-playground.vercel.app/ |
There was a problem hiding this comment.
I see there is a nwc crate https://github.com/rust-nostr/nostr/tree/master/crates/nwc for the client side of this. I think it would be good to use that to add some end to end tests in for this or maybe just an example would suffice.
| return Ok(false); | ||
| } | ||
|
|
||
| handle_request(&service_keys, &client, handler.as_ref(), &event).await; |
There was a problem hiding this comment.
Right now handle_request(...).await runs inside the relay notification callback, so requests are processed serially. For a pay_invoice request this can take a while: we need to get a melt quote, pay it, and wait for the LN invoice/payment flow to complete. While that is happening, other requests from the client will not be processed.
I wonder if we eventually want to spawn request handling here, probably with a bounded concurrency limit. That said, I think it is fine to leave the implementation serial for now since this only becomes noticeable if a client sends many zaps/requests at once and payments are slow.
| /// A [`cdk_nwc::NwcRequestHandler`] backed by a Cashu [`Wallet`]. | ||
| #[derive(Debug, Clone)] | ||
| pub struct WalletNwcHandler { | ||
| wallet: Wallet, |
There was a problem hiding this comment.
| wallet: Wallet, | |
| wallet: Arc<Wallet>, |
We should make this an Arc<> as we eventually want to remove clone from the Wallet. And I think the FFI aligns with this already
| #[instrument(skip(self))] | ||
| async fn make_invoice( | ||
| &self, | ||
| request: MakeInvoiceRequest, |
There was a problem hiding this comment.
MakeInvoiceRequest accepts a description_hash but we can't support this in cashu so I think we should error if this is set.
| .mint_quote( | ||
| PaymentMethod::Known(KnownMethod::Bolt11), | ||
| Some(amount), | ||
| request.description.clone(), |
There was a problem hiding this comment.
Not all mints support setting the description as its optional https://github.com/cashubtc/nuts/blob/main/23.md#mint-quote. So to avoid silently attempting to create an invoice without the correct description I think we should check the mint info before getting the quote if the description is set in the request.
This is important for ZAPs as the invoice description has to be set to the zap receipt I believe.
| #[derive(Debug, Clone)] | ||
| pub struct WalletNwcHandler { | ||
| wallet: Wallet, | ||
| budget_msat: Option<u64>, |
There was a problem hiding this comment.
I would rename this to max_payment_msat. budget made me think it was some sort of cumulatively daily budget, which would maybe something useful we could add later, I think many nostr apps allow you to set things like hourly, daily zap budgets?
| } | ||
| } | ||
|
|
||
| /// Convert millisatoshis to a wallet [`Amount`] for the given unit. |
There was a problem hiding this comment.
Could we use the cdk Amount type we have to_sat and to_msat fns instead of having the logic here as well?
cdk/crates/cashu/src/amount.rs
Lines 569 to 583 in 04d39a6
So I think we could use that internally and convert at the boundary?
| created_at: Timestamp::from(quote.expiry), | ||
| expires_at: Some(Timestamp::from(quote.expiry)), |
There was a problem hiding this comment.
Should these both be the expiry?
Description
Notes to the reviewers
Suggested CHANGELOG Updates
CHANGED
ADDED
REMOVED
FIXED
Checklist
just quick-checkbefore committingcrates/cdk-ffi)