cestina, UI, UX
This commit is contained in:
+37
-29
@@ -39,7 +39,15 @@ def render_job_status(status: str | None) -> str:
|
||||
else:
|
||||
class_name = "pill pill-muted"
|
||||
|
||||
return f'<span class="{class_name}">{html.escape(status_value)}</span>'
|
||||
labels = {
|
||||
"queued": "čeká",
|
||||
"running": "běží",
|
||||
"cancelled_requested": "žádost o zrušení",
|
||||
"cancelled": "zrušeno",
|
||||
"success": "úspěšné",
|
||||
"failed": "selhalo",
|
||||
}
|
||||
return f'<span class="{class_name}">{html.escape(labels.get(normalized, status_value))}</span>'
|
||||
|
||||
|
||||
def pretty_json(value: str | None) -> str:
|
||||
@@ -195,7 +203,7 @@ def jobs_page(
|
||||
"""
|
||||
|
||||
if not rows:
|
||||
rows = '<tr><td colspan="9">Zatím nejsou evidované žádné joby.</td></tr>'
|
||||
rows = '<tr><td colspan="9">Zatím nejsou evidované žádné úlohy.</td></tr>'
|
||||
|
||||
status_options = render_options(JOB_FILTER_STATUSES, selected_status, "Všechny statusy")
|
||||
type_options = render_options(JOB_FILTER_TYPES, selected_type, "Všechny typy")
|
||||
@@ -225,19 +233,19 @@ def jobs_page(
|
||||
"""
|
||||
|
||||
return page(
|
||||
"Joby",
|
||||
"Úlohy",
|
||||
f"""
|
||||
{refresh}
|
||||
<div class="card">
|
||||
<h2>Joby</h2>
|
||||
<h2>Úlohy</h2>
|
||||
<p class="muted">Fronta portálových a webhook úloh připravená pro centrální worker.</p>
|
||||
</div>
|
||||
|
||||
<div class="stats-grid">
|
||||
<div class="stat-card stat-warning"><span>Queued</span><strong data-live-count="jobs.queued">{stats.get("queued") or 0}</strong></div>
|
||||
<div class="stat-card stat-warning"><span>Running</span><strong data-live-count="jobs.running">{stats.get("running") or 0}</strong></div>
|
||||
<div class="stat-card stat-danger"><span>Failed (24h)</span><strong data-live-count="jobs.failed_24h">{stats.get("failed_24h") or 0}</strong></div>
|
||||
<div class="stat-card stat-success"><span>Success (24h)</span><strong data-live-count="jobs.success_24h">{stats.get("success_24h") or 0}</strong></div>
|
||||
<div class="stat-card stat-warning"><span>Čekající</span><strong data-live-count="jobs.queued">{stats.get("queued") or 0}</strong></div>
|
||||
<div class="stat-card stat-warning"><span>Běžící</span><strong data-live-count="jobs.running">{stats.get("running") or 0}</strong></div>
|
||||
<div class="stat-card stat-danger"><span>Selhané (24 h)</span><strong data-live-count="jobs.failed_24h">{stats.get("failed_24h") or 0}</strong></div>
|
||||
<div class="stat-card stat-success"><span>Úspěšné (24 h)</span><strong data-live-count="jobs.success_24h">{stats.get("success_24h") or 0}</strong></div>
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
@@ -245,7 +253,7 @@ def jobs_page(
|
||||
<form method="get" action="/portal/jobs" class="filter-form">
|
||||
<select name="status">{status_options}</select>
|
||||
<select name="type">{type_options}</select>
|
||||
<input name="target" value="{target_value}" placeholder="Target">
|
||||
<input name="target" value="{target_value}" placeholder="Cíl">
|
||||
<input type="hidden" name="page" value="1">
|
||||
<button type="submit">Filtrovat</button>
|
||||
<a class="btn btn-secondary" href="/portal/jobs">Reset</a>
|
||||
@@ -253,15 +261,15 @@ def jobs_page(
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<h2>Recent Jobs</h2>
|
||||
<h2>Poslední úlohy</h2>
|
||||
<table>
|
||||
<tr>
|
||||
<th>ID</th>
|
||||
<th>Status</th>
|
||||
<th>Type</th>
|
||||
<th>Target</th>
|
||||
<th>Source</th>
|
||||
<th>Created At</th>
|
||||
<th>Typ</th>
|
||||
<th>Cíl</th>
|
||||
<th>Zdroj</th>
|
||||
<th>Vytvořeno</th>
|
||||
</tr>
|
||||
<tbody data-live-table="jobs.recent"></tbody>
|
||||
</table>
|
||||
@@ -274,10 +282,10 @@ def jobs_page(
|
||||
<tr>
|
||||
<th>ID</th>
|
||||
<th>Status</th>
|
||||
<th>Source</th>
|
||||
<th>Target</th>
|
||||
<th>Created by</th>
|
||||
<th>Created at</th>
|
||||
<th>Zdroj</th>
|
||||
<th>Cíl</th>
|
||||
<th>Vytvořil</th>
|
||||
<th>Vytvořeno</th>
|
||||
<th>Started at</th>
|
||||
<th>Finished at</th>
|
||||
<th>Akce</th>
|
||||
@@ -300,7 +308,7 @@ def job_detail_page(job_id: int, request: Request, user=Depends(require_user)):
|
||||
|
||||
status_value = (job.get("status") or "").lower()
|
||||
refresh = ""
|
||||
title = f"Job #{html.escape(str(job.get('id', job_id)))}"
|
||||
title = f"Úloha #{html.escape(str(job.get('id', job_id)))}"
|
||||
status = render_job_status(job.get("status"))
|
||||
target_type = job.get("target_type", "") or ""
|
||||
target_id = job.get("target_id", "") or ""
|
||||
@@ -315,7 +323,7 @@ def job_detail_page(job_id: int, request: Request, user=Depends(require_user)):
|
||||
if status_value == "failed" and can_retry_job(job):
|
||||
actions += f"""
|
||||
<form method="post" action="/portal/jobs/{html.escape(str(job_id))}/retry" onsubmit="return confirm('Retry job #{html.escape(str(job_id))}?');">
|
||||
<button type="submit">Retry Job</button>
|
||||
<button type="submit">Spustit znovu</button>
|
||||
</form>
|
||||
"""
|
||||
elif status_value == "failed" and (job.get("target_id") or "") in IGNORED_RETRY_REPOSITORIES:
|
||||
@@ -323,7 +331,7 @@ def job_detail_page(job_id: int, request: Request, user=Depends(require_user)):
|
||||
if status_value in {"queued", "running"}:
|
||||
actions += f"""
|
||||
<form method="post" action="/portal/jobs/{html.escape(str(job_id))}/cancel" onsubmit="return confirm('Cancel job #{html.escape(str(job_id))}?');">
|
||||
<button type="submit" class="danger">Cancel Job</button>
|
||||
<button type="submit" class="danger">Zrušit úlohu</button>
|
||||
</form>
|
||||
"""
|
||||
if actions:
|
||||
@@ -420,8 +428,8 @@ def job_detail_page(job_id: int, request: Request, user=Depends(require_user)):
|
||||
<div class="card">
|
||||
<h2>{title}</h2>
|
||||
<p>
|
||||
<a class="btn" href="/portal/jobs">← Zpět na joby</a>
|
||||
<a class="btn btn-secondary" href="{target_url}">Detail targetu</a>
|
||||
<a class="btn" href="/portal/jobs">← Zpět na úlohy</a>
|
||||
<a class="btn btn-secondary" href="{target_url}">Detail cíle</a>
|
||||
</p>
|
||||
{retry_blocked_notice}
|
||||
{actions}
|
||||
@@ -432,10 +440,10 @@ def job_detail_page(job_id: int, request: Request, user=Depends(require_user)):
|
||||
<table>
|
||||
<tr><th>Typ</th><td>{html.escape(job.get("type", "") or "")}</td></tr>
|
||||
<tr><th>Status</th><td>{status}</td></tr>
|
||||
<tr><th>Source</th><td>{html.escape(job.get("source", "") or "")}</td></tr>
|
||||
<tr><th>Target</th><td>{html.escape(target_type)}: {target_id_html}</td></tr>
|
||||
<tr><th>Created by</th><td>{html.escape(job.get("created_by_display_name") or job.get("created_by_username") or "")}</td></tr>
|
||||
<tr><th>Created at</th><td>{html.escape(job.get("created_at", "") or "")}</td></tr>
|
||||
<tr><th>Zdroj</th><td>{html.escape(job.get("source", "") or "")}</td></tr>
|
||||
<tr><th>Cíl</th><td>{html.escape(target_type)}: {target_id_html}</td></tr>
|
||||
<tr><th>Vytvořil</th><td>{html.escape(job.get("created_by_display_name") or job.get("created_by_username") or "")}</td></tr>
|
||||
<tr><th>Vytvořeno</th><td>{html.escape(job.get("created_at", "") or "")}</td></tr>
|
||||
<tr><th>Started at</th><td>{html.escape(job.get("started_at", "") or "")}</td></tr>
|
||||
<tr><th>Finished at</th><td>{html.escape(job.get("finished_at", "") or "")}</td></tr>
|
||||
<tr><th>Duration</th><td>{duration}</td></tr>
|
||||
@@ -456,8 +464,8 @@ def job_detail_page(job_id: int, request: Request, user=Depends(require_user)):
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<h2>Live logy</h2>
|
||||
<p class="muted">WebSocket: <span id="live-log-status">Connecting</span></p>
|
||||
<h2>Živé logy</h2>
|
||||
<p class="muted">WebSocket: <span id="live-log-status">Připojování</span></p>
|
||||
<div id="live-log-panel" class="log-viewer log-stdout"></div>
|
||||
</div>
|
||||
|
||||
|
||||
Reference in New Issue
Block a user