mirror of
https://github.com/aljazceru/nutshell.git
synced 2025-12-21 02:54:20 +01:00
NUT-04/05: add amount, unit, request to melt and mint quote responses (#719)
* add amount, unit, request to melt and mint responses * make new fields optional to not break compat with old mints * make new flags optional for backwards compat
This commit is contained in:
@@ -141,6 +141,8 @@ class PostMintQuoteRequest(BaseModel):
|
|||||||
class PostMintQuoteResponse(BaseModel):
|
class PostMintQuoteResponse(BaseModel):
|
||||||
quote: str # quote id
|
quote: str # quote id
|
||||||
request: str # input payment request
|
request: str # input payment request
|
||||||
|
amount: Optional[int] # output amount (optional for backwards compat pre 0.16.6)
|
||||||
|
unit: Optional[str] # output unit (optional for backwards compat pre 0.16.6)
|
||||||
state: Optional[str] # state of the quote (optional for backwards compat)
|
state: Optional[str] # state of the quote (optional for backwards compat)
|
||||||
expiry: Optional[int] # expiry of the quote
|
expiry: Optional[int] # expiry of the quote
|
||||||
pubkey: Optional[str] = None # NUT-20 quote lock pubkey
|
pubkey: Optional[str] = None # NUT-20 quote lock pubkey
|
||||||
@@ -222,6 +224,10 @@ class PostMeltQuoteRequest(BaseModel):
|
|||||||
class PostMeltQuoteResponse(BaseModel):
|
class PostMeltQuoteResponse(BaseModel):
|
||||||
quote: str # quote id
|
quote: str # quote id
|
||||||
amount: int # input amount
|
amount: int # input amount
|
||||||
|
unit: Optional[str] # input unit (optional for backwards compat pre 0.16.6)
|
||||||
|
request: Optional[
|
||||||
|
str
|
||||||
|
] # output payment request (optional for backwards compat pre 0.16.6)
|
||||||
fee_reserve: int # input fee reserve
|
fee_reserve: int # input fee reserve
|
||||||
paid: Optional[bool] = (
|
paid: Optional[bool] = (
|
||||||
None # whether the request has been paid # DEPRECATED as per NUT PR #136
|
None # whether the request has been paid # DEPRECATED as per NUT PR #136
|
||||||
|
|||||||
@@ -667,7 +667,10 @@ class Ledger(LedgerVerification, LedgerSpendingConditions, LedgerTasks, LedgerFe
|
|||||||
if not payment_quote.checking_id:
|
if not payment_quote.checking_id:
|
||||||
raise Exception("quote has no checking id")
|
raise Exception("quote has no checking id")
|
||||||
# verify that payment quote amount is as expected
|
# verify that payment quote amount is as expected
|
||||||
if melt_quote.is_mpp and melt_quote.mpp_amount != payment_quote.amount.to(Unit.msat).amount:
|
if (
|
||||||
|
melt_quote.is_mpp
|
||||||
|
and melt_quote.mpp_amount != payment_quote.amount.to(Unit.msat).amount
|
||||||
|
):
|
||||||
raise TransactionError("quote amount not as requested")
|
raise TransactionError("quote amount not as requested")
|
||||||
# make sure the backend returned the amount with a correct unit
|
# make sure the backend returned the amount with a correct unit
|
||||||
if not payment_quote.amount.unit == unit:
|
if not payment_quote.amount.unit == unit:
|
||||||
@@ -759,6 +762,8 @@ class Ledger(LedgerVerification, LedgerSpendingConditions, LedgerTasks, LedgerFe
|
|||||||
return PostMeltQuoteResponse(
|
return PostMeltQuoteResponse(
|
||||||
quote=quote.quote,
|
quote=quote.quote,
|
||||||
amount=quote.amount,
|
amount=quote.amount,
|
||||||
|
unit=quote.unit,
|
||||||
|
request=quote.request,
|
||||||
fee_reserve=quote.fee_reserve,
|
fee_reserve=quote.fee_reserve,
|
||||||
paid=quote.paid, # deprecated
|
paid=quote.paid, # deprecated
|
||||||
state=quote.state.value,
|
state=quote.state.value,
|
||||||
|
|||||||
@@ -163,8 +163,10 @@ async def mint_quote(
|
|||||||
logger.trace(f"> POST /v1/mint/quote/bolt11: payload={payload}")
|
logger.trace(f"> POST /v1/mint/quote/bolt11: payload={payload}")
|
||||||
quote = await ledger.mint_quote(payload)
|
quote = await ledger.mint_quote(payload)
|
||||||
resp = PostMintQuoteResponse(
|
resp = PostMintQuoteResponse(
|
||||||
request=quote.request,
|
|
||||||
quote=quote.quote,
|
quote=quote.quote,
|
||||||
|
request=quote.request,
|
||||||
|
amount=quote.amount,
|
||||||
|
unit=quote.unit,
|
||||||
paid=quote.paid, # deprecated
|
paid=quote.paid, # deprecated
|
||||||
state=quote.state.value,
|
state=quote.state.value,
|
||||||
expiry=quote.expiry,
|
expiry=quote.expiry,
|
||||||
@@ -190,6 +192,8 @@ async def get_mint_quote(request: Request, quote: str) -> PostMintQuoteResponse:
|
|||||||
resp = PostMintQuoteResponse(
|
resp = PostMintQuoteResponse(
|
||||||
quote=mint_quote.quote,
|
quote=mint_quote.quote,
|
||||||
request=mint_quote.request,
|
request=mint_quote.request,
|
||||||
|
amount=mint_quote.amount,
|
||||||
|
unit=mint_quote.unit,
|
||||||
paid=mint_quote.paid, # deprecated
|
paid=mint_quote.paid, # deprecated
|
||||||
state=mint_quote.state.value,
|
state=mint_quote.state.value,
|
||||||
expiry=mint_quote.expiry,
|
expiry=mint_quote.expiry,
|
||||||
@@ -290,6 +294,8 @@ async def get_melt_quote(request: Request, quote: str) -> PostMeltQuoteResponse:
|
|||||||
resp = PostMeltQuoteResponse(
|
resp = PostMeltQuoteResponse(
|
||||||
quote=melt_quote.quote,
|
quote=melt_quote.quote,
|
||||||
amount=melt_quote.amount,
|
amount=melt_quote.amount,
|
||||||
|
unit=melt_quote.unit,
|
||||||
|
request=melt_quote.request,
|
||||||
fee_reserve=melt_quote.fee_reserve,
|
fee_reserve=melt_quote.fee_reserve,
|
||||||
paid=melt_quote.paid,
|
paid=melt_quote.paid,
|
||||||
state=melt_quote.state.value,
|
state=melt_quote.state.value,
|
||||||
|
|||||||
@@ -469,6 +469,8 @@ class LedgerAPI(LedgerAPIDeprecated, SupportsAuth):
|
|||||||
return PostMeltQuoteResponse(
|
return PostMeltQuoteResponse(
|
||||||
quote=quote_id,
|
quote=quote_id,
|
||||||
amount=amount_sat,
|
amount=amount_sat,
|
||||||
|
unit=unit.name,
|
||||||
|
request=payment_request,
|
||||||
fee_reserve=ret.fee or 0,
|
fee_reserve=ret.fee or 0,
|
||||||
paid=False,
|
paid=False,
|
||||||
state=MeltQuoteState.unpaid.value,
|
state=MeltQuoteState.unpaid.value,
|
||||||
@@ -550,6 +552,8 @@ class LedgerAPI(LedgerAPIDeprecated, SupportsAuth):
|
|||||||
return PostMeltQuoteResponse(
|
return PostMeltQuoteResponse(
|
||||||
quote=quote,
|
quote=quote,
|
||||||
amount=0,
|
amount=0,
|
||||||
|
unit="sat",
|
||||||
|
request="lnbc0",
|
||||||
fee_reserve=0,
|
fee_reserve=0,
|
||||||
paid=ret.paid or False,
|
paid=ret.paid or False,
|
||||||
state=(
|
state=(
|
||||||
|
|||||||
@@ -257,9 +257,12 @@ class LedgerAPIDeprecated(SupportsHttpxClient, SupportsMintURL):
|
|||||||
return_dict = resp.json()
|
return_dict = resp.json()
|
||||||
mint_response = GetMintResponse_deprecated.parse_obj(return_dict)
|
mint_response = GetMintResponse_deprecated.parse_obj(return_dict)
|
||||||
decoded_invoice = bolt11.decode(mint_response.pr)
|
decoded_invoice = bolt11.decode(mint_response.pr)
|
||||||
|
assert decoded_invoice.amount_msat, Exception("no amount in invoice")
|
||||||
return PostMintQuoteResponse(
|
return PostMintQuoteResponse(
|
||||||
quote=mint_response.hash,
|
quote=mint_response.hash,
|
||||||
request=mint_response.pr,
|
request=mint_response.pr,
|
||||||
|
amount=decoded_invoice.amount_msat // 1000,
|
||||||
|
unit="sat",
|
||||||
paid=False,
|
paid=False,
|
||||||
state=MintQuoteState.unpaid.value,
|
state=MintQuoteState.unpaid.value,
|
||||||
expiry=decoded_invoice.date + (decoded_invoice.expiry or 0),
|
expiry=decoded_invoice.date + (decoded_invoice.expiry or 0),
|
||||||
|
|||||||
@@ -202,6 +202,9 @@ async def test_mint_quote(ledger: Ledger):
|
|||||||
resp_quote = PostMintQuoteResponse(**result)
|
resp_quote = PostMintQuoteResponse(**result)
|
||||||
assert resp_quote.quote == result["quote"]
|
assert resp_quote.quote == result["quote"]
|
||||||
assert resp_quote.state == MintQuoteState.unpaid.value
|
assert resp_quote.state == MintQuoteState.unpaid.value
|
||||||
|
assert resp_quote.amount == 100
|
||||||
|
assert resp_quote.unit == "sat"
|
||||||
|
assert resp_quote.request == result["request"]
|
||||||
|
|
||||||
# check if DEPRECATED paid flag is also returned
|
# check if DEPRECATED paid flag is also returned
|
||||||
assert result["paid"] is False
|
assert result["paid"] is False
|
||||||
@@ -230,6 +233,9 @@ async def test_mint_quote(ledger: Ledger):
|
|||||||
resp_quote = PostMintQuoteResponse(**result2)
|
resp_quote = PostMintQuoteResponse(**result2)
|
||||||
assert resp_quote.quote == result["quote"]
|
assert resp_quote.quote == result["quote"]
|
||||||
assert resp_quote.state == MintQuoteState.paid.value
|
assert resp_quote.state == MintQuoteState.paid.value
|
||||||
|
assert resp_quote.amount == 100
|
||||||
|
assert resp_quote.unit == "sat"
|
||||||
|
assert resp_quote.request == result["request"]
|
||||||
|
|
||||||
# check if DEPRECATED paid flag is also returned
|
# check if DEPRECATED paid flag is also returned
|
||||||
assert result2["paid"] is True
|
assert result2["paid"] is True
|
||||||
@@ -338,6 +344,9 @@ async def test_melt_quote_internal(ledger: Ledger, wallet: Wallet):
|
|||||||
assert resp_quote.payment_preimage is None
|
assert resp_quote.payment_preimage is None
|
||||||
assert resp_quote.change is None
|
assert resp_quote.change is None
|
||||||
assert resp_quote.state == MeltQuoteState.unpaid.value
|
assert resp_quote.state == MeltQuoteState.unpaid.value
|
||||||
|
assert resp_quote.amount == 64
|
||||||
|
assert resp_quote.unit == "sat"
|
||||||
|
assert resp_quote.request == request
|
||||||
|
|
||||||
# check if DEPRECATED paid flag is also returned
|
# check if DEPRECATED paid flag is also returned
|
||||||
assert result["paid"] is False
|
assert result["paid"] is False
|
||||||
@@ -446,6 +455,9 @@ async def test_melt_internal(ledger: Ledger, wallet: Wallet):
|
|||||||
assert resp_quote.payment_preimage is None
|
assert resp_quote.payment_preimage is None
|
||||||
assert resp_quote.change == []
|
assert resp_quote.change == []
|
||||||
assert resp_quote.state == MeltQuoteState.paid.value
|
assert resp_quote.state == MeltQuoteState.paid.value
|
||||||
|
assert resp_quote.amount == 64
|
||||||
|
assert resp_quote.unit == "sat"
|
||||||
|
assert resp_quote.request == invoice_payment_request
|
||||||
|
|
||||||
# check if DEPRECATED paid flag is also returned
|
# check if DEPRECATED paid flag is also returned
|
||||||
assert result["paid"] is True
|
assert result["paid"] is True
|
||||||
@@ -504,6 +516,9 @@ async def test_melt_external(ledger: Ledger, wallet: Wallet):
|
|||||||
# deserialize the response
|
# deserialize the response
|
||||||
resp_quote = PostMeltQuoteResponse(**result)
|
resp_quote = PostMeltQuoteResponse(**result)
|
||||||
assert resp_quote.quote == quote.quote
|
assert resp_quote.quote == quote.quote
|
||||||
|
assert resp_quote.amount == 62
|
||||||
|
assert resp_quote.unit == "sat"
|
||||||
|
assert resp_quote.request == invoice_payment_request
|
||||||
assert resp_quote.payment_preimage is not None
|
assert resp_quote.payment_preimage is not None
|
||||||
assert len(resp_quote.payment_preimage) == 64
|
assert len(resp_quote.payment_preimage) == 64
|
||||||
assert resp_quote.change is not None
|
assert resp_quote.change is not None
|
||||||
|
|||||||
Reference in New Issue
Block a user