[FEAT] Push notification integration into core (#1393)

* push notification integration into core

added missing component

fixed bell working on all pages
- made pubkey global template env var
- had to move `get_push_notification_pubkey` to `helpers.py` because of circular reference with `tasks.py`

formay

trying to fix mypy

added py-vapid to requirements

Trying to fix stub mypy issue

* removed key files

* webpush key pair is saved in db `webpush_settings`

* removed lnaddress extension changes

* support for multi user account subscriptions, subscriptions are stored user based

fixed syntax error

fixed syntax error

removed unused line

* fixed subscribed user storage with local storage, no get request required

* method is singular now

* cleanup unsubscribed or expired push subscriptions

fixed flake8 errors

fixed poetry errors

* updating to latest lnbits

formatting, rebase error

fix

* remove unused?

* revert

* relock

* remove

* do not create settings table use adminsettings

mypy

fix

* cleanup old code

* catch case when client tries to recreate existing webpush subscription e.g. on cleared local storage

* show notification bell on user related pages only

* use local storage with one key like array, some refactoring

* fixed crud import

* fixed too long line

* removed unused imports

* ruff

* make webpush editable

* fixed privkey encoding

* fix ruff

* fix migration

---------

Co-authored-by: schneimi <admin@schneimi.de>
Co-authored-by: schneimi <dev@schneimi.de>
Co-authored-by: dni  <office@dnilabs.com>
This commit is contained in:
schneimi
2023-09-11 14:48:49 +01:00
committed by GitHub
co-authored by schneimi schneimi dni ⚡
parent 8f0c1f6a80
commit fb98576431
17 changed files with 571 additions and 21 deletions
+43 -1
View File
@@ -1,11 +1,12 @@
import asyncio
import base64
import hashlib
import json
import uuid
from http import HTTPStatus
from io import BytesIO
from typing import Dict, List, Optional, Union
from urllib.parse import ParseResult, parse_qs, urlencode, urlparse, urlunparse
from urllib.parse import ParseResult, parse_qs, unquote, urlencode, urlparse, urlunparse
import httpx
import pyqrcode
@@ -33,12 +34,14 @@ from lnbits.core.models import (
CreateInvoice,
CreateLnurl,
CreateLnurlAuth,
CreateWebPushSubscription,
DecodePayment,
Payment,
PaymentFilters,
User,
Wallet,
WalletType,
WebPushSubscription,
)
from lnbits.db import Filters, Page
from lnbits.decorators import (
@@ -69,9 +72,11 @@ from .. import core_app, core_app_extra, db
from ..crud import (
add_installed_extension,
create_tinyurl,
create_webpush_subscription,
delete_dbversion,
delete_installed_extension,
delete_tinyurl,
delete_webpush_subscription,
drop_extension_db,
get_dbversions,
get_payments,
@@ -80,6 +85,7 @@ from ..crud import (
get_tinyurl,
get_tinyurl_by_url,
get_wallet_for_key,
get_webpush_subscription,
save_balance_check,
update_wallet,
)
@@ -986,3 +992,39 @@ async def api_tinyurl(tinyurl_id: str):
raise HTTPException(
status_code=HTTPStatus.NOT_FOUND, detail="unable to find tinyurl"
)
############################WEBPUSH##################################
@core_app.post("/api/v1/webpush", status_code=HTTPStatus.CREATED)
async def api_create_webpush_subscription(
request: Request,
data: CreateWebPushSubscription,
wallet: WalletTypeInfo = Depends(require_admin_key),
) -> WebPushSubscription:
subscription = json.loads(data.subscription)
endpoint = subscription["endpoint"]
host = urlparse(str(request.url)).netloc
subscription = await get_webpush_subscription(endpoint, wallet.wallet.user)
if subscription:
return subscription
else:
return await create_webpush_subscription(
endpoint,
wallet.wallet.user,
data.subscription,
host,
)
@core_app.delete("/api/v1/webpush", status_code=HTTPStatus.OK)
async def api_delete_webpush_subscription(
request: Request,
wallet: WalletTypeInfo = Depends(require_admin_key),
):
endpoint = unquote(
base64.b64decode(request.query_params.get("endpoint")).decode("utf-8")
)
await delete_webpush_subscription(endpoint, wallet.wallet.user)