Add ntfy authentication support (username/password and API key)

- Settings table gets ntfy_username, ntfy_password, ntfy_api_key columns
- Backend applies Basic or Bearer auth header when sending notifications
- Settings page UI lets you toggle between no auth, basic, or token auth
- Masked credential display on load to avoid exposing stored secrets
- README updated with auth modes documentation

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-03-08 23:49:54 -07:00
parent 1ff44e4276
commit 1bed02ebb5
8 changed files with 109 additions and 16 deletions

View File

@@ -1,3 +1,4 @@
import base64
from datetime import date, timedelta
from fastapi import APIRouter, Depends, HTTPException
from sqlalchemy.orm import Session
@@ -96,16 +97,25 @@ async def send_ntfy(settings: Settings, title: str, message: str, db: Session, p
server = (settings.ntfy_server or "https://ntfy.sh").rstrip("/")
url = f"{server}/{settings.ntfy_topic}"
headers = {
"Title": title,
"Priority": priority,
"Tags": "seedling",
}
if settings.ntfy_api_key:
headers["Authorization"] = f"Bearer {settings.ntfy_api_key}"
elif settings.ntfy_username:
creds = base64.b64encode(
f"{settings.ntfy_username}:{settings.ntfy_password or ''}".encode()
).decode()
headers["Authorization"] = f"Basic {creds}"
try:
async with httpx.AsyncClient(timeout=10) as client:
resp = await client.post(
url,
content=message.encode("utf-8"),
headers={
"Title": title,
"Priority": priority,
"Tags": "seedling",
},
headers=headers,
)
resp.raise_for_status()