Merge branch 'lnbits:main' into main

This commit is contained in:
blackcoffeexbt
2022-11-14 10:29:23 +00:00
committed by GitHub
10 changed files with 87 additions and 36 deletions

View File

@@ -220,8 +220,8 @@ You need to edit the `.env` file.
```sh
# add the database connection string to .env 'nano .env' LNBITS_DATABASE_URL=
# postgres://<user>:<myPassword>@<host>/<lnbits> - alter line bellow with your user, password and db name
LNBITS_DATABASE_URL="postgres://postgres:postgres@localhost/lnbits"
# postgres://<user>:<myPassword>@<host>:<port>/<lnbits> - alter line bellow with your user, password and db name
LNBITS_DATABASE_URL="postgres://postgres:postgres@localhost:5432/lnbits"
# save and exit
```

View File

@@ -1,7 +1,11 @@
import asyncio
from fastapi import APIRouter
from lnbits.db import Database
from lnbits.helpers import template_renderer
from lnbits.tasks import catch_everything_and_restart
db = Database("ext_events")
@@ -13,5 +17,11 @@ def events_renderer():
return template_renderer(["lnbits/extensions/events/templates"])
from .tasks import wait_for_paid_invoices
from .views import * # noqa
from .views_api import * # noqa
def events_start():
loop = asyncio.get_event_loop()
loop.create_task(catch_everything_and_restart(wait_for_paid_invoices))

View File

@@ -0,0 +1,39 @@
import asyncio
import json
from http import HTTPStatus
from urllib.parse import urlparse
import httpx
from fastapi import HTTPException
from lnbits import bolt11
from lnbits.core.models import Payment
from lnbits.core.services import pay_invoice
from lnbits.helpers import get_current_extension_name
from lnbits.tasks import register_invoice_listener
from .views_api import api_ticket_send_ticket
from loguru import logger
from lnbits.extensions.events.models import CreateTicket
async def wait_for_paid_invoices():
invoice_queue = asyncio.Queue()
register_invoice_listener(invoice_queue, get_current_extension_name())
while True:
payment = await invoice_queue.get()
await on_invoice_paid(payment)
async def on_invoice_paid(payment: Payment) -> None:
# (avoid loops)
if (
"events" == payment.extra.get("tag")
and payment.extra.get("name")
and payment.extra.get("email")
):
CreateTicket.name = str(payment.extra.get("name"))
CreateTicket.email = str(payment.extra.get("email"))
await api_ticket_send_ticket(payment.memo, payment.payment_hash, CreateTicket)
return

View File

@@ -135,7 +135,7 @@
var self = this
axios
.get('/events/api/v1/tickets/' + '{{ event_id }}')
.get('/events/api/v1/tickets/' + '{{ event_id }}' + '/' + self.formDialog.data.name + '/' + self.formDialog.data.email)
.then(function (response) {
self.paymentReq = response.data.payment_request
self.paymentCheck = response.data.payment_hash

View File

@@ -10,6 +10,7 @@ from lnbits.core.services import create_invoice
from lnbits.core.views.api import api_payment
from lnbits.decorators import WalletTypeInfo, get_key_type
from lnbits.extensions.events.models import CreateEvent, CreateTicket
from loguru import logger
from . import events_ext
from .crud import (
@@ -96,8 +97,8 @@ async def api_tickets(
return [ticket.dict() for ticket in await get_tickets(wallet_ids)]
@events_ext.get("/api/v1/tickets/{event_id}")
async def api_ticket_make_ticket(event_id):
@events_ext.get("/api/v1/tickets/{event_id}/{name}/{email}")
async def api_ticket_make_ticket(event_id, name, email):
event = await get_event(event_id)
if not event:
raise HTTPException(
@@ -108,11 +109,10 @@ async def api_ticket_make_ticket(event_id):
wallet_id=event.wallet,
amount=event.price_per_ticket,
memo=f"{event_id}",
extra={"tag": "events"},
extra={"tag": "events", "name": name, "email": email},
)
except Exception as e:
raise HTTPException(status_code=HTTPStatus.INTERNAL_SERVER_ERROR, detail=str(e))
return {"payment_hash": payment_hash, "payment_request": payment_request}
@@ -156,7 +156,7 @@ async def api_ticket_delete(ticket_id, wallet: WalletTypeInfo = Depends(get_key_
)
await delete_ticket(ticket_id)
raise HTTPException(status_code=HTTPStatus.NO_CONTENT)
return "", HTTPStatus.NO_CONTENT
# Event Tickets

View File

@@ -105,9 +105,9 @@ async def lnurl_v1_params(
paymentcheck = await get_lnurlpayload(p)
if device.device == "atm":
if paymentcheck:
return {"status": "ERROR", "reason": f"Payment already claimed"}
if paymentcheck.payhash != "payment_hash":
return {"status": "ERROR", "reason": f"Payment already claimed"}
if device.device == "switch":
price_msat = (
await fiat_amount_as_satoshis(float(profit), device.currency)
if device.currency != "sat"
@@ -177,7 +177,7 @@ async def lnurl_v1_params(
"callback": request.url_for(
"lnurldevice.lnurl_callback", paymentid=lnurldevicepayment.id
),
"k1": lnurldevicepayment.id,
"k1": p,
"minWithdrawable": price_msat * 1000,
"maxWithdrawable": price_msat * 1000,
"defaultDescription": device.title,
@@ -227,14 +227,13 @@ async def lnurl_callback(
status_code=HTTPStatus.FORBIDDEN, detail="No payment request"
)
else:
if lnurldevicepayment.id != k1:
if lnurldevicepayment.payload != k1:
return {"status": "ERROR", "reason": "Bad K1"}
if lnurldevicepayment.payhash != "payment_hash":
return {"status": "ERROR", "reason": f"Payment already claimed"}
lnurldevicepayment = await update_lnurldevicepayment(
lnurldevicepayment_id=paymentid, payhash=lnurldevicepayment.payload
)
await pay_invoice(
wallet_id=device.wallet,
payment_request=pr,

View File

@@ -797,7 +797,7 @@
LNbits.utils.notifyApiError(error)
})
},
clearFormDialoglnurldevice () {
clearFormDialoglnurldevice() {
this.formDialoglnurldevice.data = {
lnurl_toggle: false,
show_message: false,

View File

@@ -63,10 +63,11 @@ async def get_usermanager_users(user_id: str) -> List[Users]:
return [Users(**row) for row in rows]
async def delete_usermanager_user(user_id: str) -> None:
wallets = await get_usermanager_wallets(user_id)
for wallet in wallets:
await delete_wallet(user_id=user_id, wallet_id=wallet.id)
async def delete_usermanager_user(user_id: str, delete_core: bool = True) -> None:
if delete_core:
wallets = await get_usermanager_wallets(user_id)
for wallet in wallets:
await delete_wallet(user_id=user_id, wallet_id=wallet.id)
await db.execute("DELETE FROM usermanager.users WHERE id = ?", (user_id,))
await db.execute("""DELETE FROM usermanager.wallets WHERE "user" = ?""", (user_id,))

View File

@@ -44,7 +44,7 @@
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
<code
>curl -X GET {{ request.base_url }}usermanager/api/v1/users -H
"X-Api-Key: {{ user.wallets[0].inkey }}"
"X-Api-Key: {{ user.wallets[0].adminkey }}"
</code>
</q-card-section>
</q-card>
@@ -57,13 +57,14 @@
/usermanager/api/v1/users/&lt;user_id&gt;</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
<h5 class="text-caption q-mt-sm q-mb-none">
Returns 200 OK (application/json)
</h5>
<code
>{"id": &lt;string&gt;, "name": &lt;string&gt;, "admin":
&lt;string&gt;, "email": &lt;string&gt;, "password": &lt;string&gt;}</code
&lt;string&gt;, "email": &lt;string&gt;, "password":
&lt;string&gt;}</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
@@ -80,7 +81,7 @@
<q-card-section>
<code
><span class="text-light-blue">GET</span>
/usermanager/api/v1/wallets/&lt;user_id&gt;</code
/usermanager/api/v1/wallets</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
<code>{"X-Api-Key": &lt;string&gt;}</code>
@@ -91,9 +92,8 @@
<code>JSON wallet data</code>
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
<code
>curl -X GET {{ request.base_url
}}usermanager/api/v1/wallets/&lt;user_id&gt; -H "X-Api-Key: {{
user.wallets[0].inkey }}"
>curl -X GET {{ request.base_url }}usermanager/api/v1/wallets -H
"X-Api-Key: {{ user.wallets[0].adminkey }}"
</code>
</q-card-section>
</q-card>
@@ -220,7 +220,7 @@
<code
>curl -X DELETE {{ request.base_url
}}usermanager/api/v1/users/&lt;user_id&gt; -H "X-Api-Key: {{
user.wallets[0].inkey }}"
user.wallets[0].adminkey }}"
</code>
</q-card-section>
</q-card>
@@ -238,7 +238,7 @@
<code
>curl -X DELETE {{ request.base_url
}}usermanager/api/v1/wallets/&lt;wallet_id&gt; -H "X-Api-Key: {{
user.wallets[0].inkey }}"
user.wallets[0].adminkey }}"
</code>
</q-card-section>
</q-card>
@@ -259,15 +259,15 @@
<code>{"X-Api-Key": &lt;string&gt;}</code>
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
<code
>curl -X POST {{ request.base_url }}usermanager/api/v1/extensions?extension=withdraw&userid=user_id&active=true -H "X-Api-Key: {{ user.wallets[0].inkey }}" -H
"Content-type: application/json"
>curl -X POST {{ request.base_url
}}usermanager/api/v1/extensions?extension=withdraw&userid=user_id&active=true
-H "X-Api-Key: {{ user.wallets[0].inkey }}" -H "Content-type:
application/json"
</code>
<h5 class="text-caption q-mt-sm q-mb-none">
Returns 200 OK (application/json)
</h5>
<code
>{"extension": "updated"}</code
>
<code>{"extension": "updated"}</code>
</q-card-section>
</q-card>
</q-expansion-item>

View File

@@ -52,15 +52,17 @@ async def api_usermanager_users_create(
@usermanager_ext.delete("/api/v1/users/{user_id}")
async def api_usermanager_users_delete(
user_id, wallet: WalletTypeInfo = Depends(require_admin_key)
user_id,
delete_core: bool = Query(True),
wallet: WalletTypeInfo = Depends(require_admin_key),
):
user = await get_usermanager_user(user_id)
if not user:
raise HTTPException(
status_code=HTTPStatus.NOT_FOUND, detail="User does not exist."
)
await delete_usermanager_user(user_id)
raise HTTPException(status_code=HTTPStatus.NO_CONTENT)
await delete_usermanager_user(user_id, delete_core)
return "", HTTPStatus.NO_CONTENT
# Activate Extension
@@ -124,4 +126,4 @@ async def api_usermanager_wallets_delete(
status_code=HTTPStatus.NOT_FOUND, detail="Wallet does not exist."
)
await delete_usermanager_wallet(wallet_id, get_wallet.user)
raise HTTPException(status_code=HTTPStatus.NO_CONTENT)
return "", HTTPStatus.NO_CONTENT