BUG: proper exception for already paid internal invoices (#1593)

* BUG: proper exception for paid interal invoices

* test should now fail, because we pay invoice twice, and should also work in regtest

* sorting

* unpack check_internal

* introduce another crud fn for checking internal paid payment

* rename

---------

Co-authored-by: callebtc <93376500+callebtc@users.noreply.github.com>
This commit is contained in:
dni ⚡ 2023-04-03 14:44:17 +02:00 committed by GitHub
parent a9bdf24425
commit fe9e821af5
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 23 additions and 4 deletions

View File

@ -604,6 +604,22 @@ async def check_internal(
return row["checking_id"]
async def check_internal_pending(
payment_hash: str, conn: Optional[Connection] = None
) -> bool:
row = await (conn or db).fetchone(
"""
SELECT pending FROM apipayments
WHERE hash = ? AND amount > 0
""",
(payment_hash,),
)
if not row:
return False
else:
return row["pending"]
# balance_check
# -------------

View File

@ -27,6 +27,7 @@ from lnbits.wallets.base import PaymentResponse, PaymentStatus
from . import db
from .crud import (
check_internal,
check_internal_pending,
create_account,
create_admin_settings,
create_payment,
@ -153,6 +154,9 @@ async def pay_invoice(
extra=extra,
)
if not await check_internal_pending(invoice.payment_hash, conn=conn):
raise PaymentFailure("Internal invoice already paid.")
# check_internal() returns the checking_id of the invoice we're waiting for
internal_checking_id = await check_internal(invoice.payment_hash, conn=conn)
if internal_checking_id:

View File

@ -6,7 +6,7 @@ from lnbits import bolt11
from lnbits.core.views.api import api_payment
from lnbits.settings import get_wallet_class
from ...helpers import get_random_invoice_data, is_fake, is_regtest
from ...helpers import get_random_invoice_data, is_fake
WALLET = get_wallet_class()
@ -170,16 +170,15 @@ async def test_pay_invoice_invoicekey(client, invoice, inkey_headers_from):
assert response.status_code >= 300 # should fail
# check POST /api/v1/payments: payment with admin key [should pass]
# check POST /api/v1/payments: payment with admin key, trying to pay twice [should fail]
@pytest.mark.asyncio
@pytest.mark.skipif(is_regtest, reason="this only works in fakewallet")
async def test_pay_invoice_adminkey(client, invoice, adminkey_headers_from):
data = {"out": True, "bolt11": invoice["payment_request"]}
# try payment with admin key
response = await client.post(
"/api/v1/payments", json=data, headers=adminkey_headers_from
)
assert response.status_code < 300 # should pass
assert response.status_code > 300 # should fail
# check POST /api/v1/payments/decode