novela/containers/novela/routers/settings.py

105 lines
3.5 KiB
Python

import re
from fastapi import APIRouter, Request
from fastapi.responses import HTMLResponse
from fastapi.templating import Jinja2Templates
from db import get_db_conn
templates = Jinja2Templates(directory="templates")
router = APIRouter()
@router.get("/settings", response_class=HTMLResponse)
async def settings_page(request: Request):
return templates.TemplateResponse(request, "settings.html", {"active": "settings"})
@router.get("/api/break-patterns")
async def get_break_patterns():
with get_db_conn() as conn:
with conn.cursor() as cur:
cur.execute(
"SELECT id, pattern_type, pattern, enabled, is_default FROM break_patterns ORDER BY id"
)
return [
{
"id": r[0],
"pattern_type": r[1],
"pattern": r[2],
"enabled": r[3],
"is_default": r[4],
}
for r in cur.fetchall()
]
@router.post("/api/break-patterns")
async def add_break_pattern(request: Request):
body = await request.json()
ptype = (body.get("pattern_type") or "").strip()
pattern = (body.get("pattern") or "").strip()
if ptype not in ("regex", "css_class") or not pattern:
return {"error": "Invalid input"}
if ptype == "regex":
try:
re.compile(pattern)
except re.error as e:
return {"error": f"Invalid regex: {e}"}
with get_db_conn() as conn:
with conn:
with conn.cursor() as cur:
cur.execute(
"""
INSERT INTO break_patterns (pattern_type, pattern)
VALUES (%s, %s)
ON CONFLICT (pattern_type, pattern) DO NOTHING
RETURNING id
""",
(ptype, pattern),
)
row = cur.fetchone()
if not row:
return {"error": "Pattern already exists"}
return {"ok": True, "id": row[0]}
@router.patch("/api/break-patterns/{pid}")
async def update_break_pattern(pid: int, request: Request):
body = await request.json()
with get_db_conn() as conn:
with conn:
with conn.cursor() as cur:
if "enabled" in body:
cur.execute("UPDATE break_patterns SET enabled = %s WHERE id = %s", (bool(body["enabled"]), pid))
if "pattern" in body:
new_pat = (body.get("pattern") or "").strip()
cur.execute("SELECT pattern_type FROM break_patterns WHERE id = %s", (pid,))
row = cur.fetchone()
if row and row[0] == "regex":
try:
re.compile(new_pat)
except re.error as e:
return {"error": f"Invalid regex: {e}"}
cur.execute("UPDATE break_patterns SET pattern = %s WHERE id = %s", (new_pat, pid))
return {"ok": True}
@router.delete("/api/break-patterns/{pid}")
async def delete_break_pattern(pid: int):
with get_db_conn() as conn:
with conn:
with conn.cursor() as cur:
cur.execute("DELETE FROM break_patterns WHERE id = %s", (pid,))
return {"ok": True}
@router.delete("/api/reading-history")
async def reset_reading_history():
with get_db_conn() as conn:
with conn:
with conn.cursor() as cur:
cur.execute("DELETE FROM reading_sessions")
return {"ok": True}