add admin stuff

This commit is contained in:
2026-08-20 10:43:19 +02:00
parent 7108d446d8
commit 91758a2701
19 changed files with 2514 additions and 85 deletions

View File

@ -67,7 +67,7 @@ def _assert_no_inline_script(html: str, page: str) -> None:
@pytest.mark.asyncio
@pytest.mark.parametrize(
"path",
["/", "/dashboard", "/terminal/1", "/rdp/1"],
["/", "/dashboard", "/terminal/1", "/rdp/1", "/admin"],
)
async def test_rendered_pages_contain_no_inline_style_or_script(client, path):
resp = await client.get(path)
@ -77,6 +77,40 @@ async def test_rendered_pages_contain_no_inline_style_or_script(client, path):
_assert_no_inline_script(html, path)
@pytest.mark.asyncio
async def test_api_docs_page_contains_no_inline_style_or_script(client):
"""/docs (siehe test_admin_groups_tokens.py fuer den Admin-Zugriffsschutz
selbst) ist bewusst KEIN vendored/CDN-bezogenes Swagger-UI-Bundle, sondern
eine selbstgebaute, CSP-konforme Ansicht -- muss also denselben
Inline-Regeln genuegen wie alle anderen Seiten."""
from app.db import get_db
from app.security.passwords import hash_password
conn = get_db()
await conn.execute(
"INSERT INTO users (username, password_hash, is_admin, must_change_password) "
"VALUES ('docsadmin', ?, 1, 0)",
(hash_password("Correct-Horse-Battery-Staple-Docs"),),
)
await conn.commit()
resp = await client.post(
"/auth/login", json={"username": "docsadmin", "password": "Correct-Horse-Battery-Staple-Docs"}
)
pending = resp.json()["pending_token"]
import pyotp
resp = await client.post("/auth/totp/enroll/start", json={"pending_token": pending})
provisioning_uri = resp.json()["provisioning_uri"]
secret = dict(part.split("=") for part in provisioning_uri.split("?", 1)[1].split("&"))["secret"]
code = pyotp.TOTP(secret).now()
await client.post("/auth/totp/enroll/confirm", json={"pending_token": pending, "code": code})
resp = await client.get("/docs")
assert resp.status_code == 200, resp.text
html = resp.text
_assert_no_inline_style(html, "/docs")
_assert_no_inline_script(html, "/docs")
@pytest.mark.asyncio
async def test_login_page_hidden_sections_use_css_class_not_inline_style(client):
"""Die anfangs versteckten Login-Bereiche muessen ueber die `.hidden`