Implementována portálová část SQLite job queue.
Přidán DB helper pro jobs a job_logs bez ORM.
Přidána idempotentní migrace pro job tabulky včetně created_by_display_name.
Přidány stránky /portal/jobs a /portal/jobs/{id}.
Jobs page zobrazuje status, type, target, source, created_by, created_at, started_at, finished_at.
Job detail zobrazuje payload, result/error a job_logs.
Queued/running joby mají auto-refresh po 5 s.
Navigace portálu obsahuje odkaz na Joby.
App redeploy už nespouští deploy script přímo; vytváří queued job deploy_app s prázdným payloadem.
Po redeploy se uživatel přesměruje na detail jobu.
Přidán audit event app.redeploy.queued s metadata={"job_id": job_id}.
Přidána ochrana proti duplicitnímu aktivnímu deploy jobu pro stejnou appku.
This commit is contained in:
@@ -0,0 +1,57 @@
|
||||
from app.db.database import get_connection
|
||||
|
||||
|
||||
def run_migrations():
|
||||
con = get_connection()
|
||||
|
||||
con.execute(
|
||||
"""
|
||||
CREATE TABLE IF NOT EXISTS jobs (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
type TEXT NOT NULL,
|
||||
target_type TEXT NOT NULL,
|
||||
target_id TEXT NOT NULL,
|
||||
payload_json TEXT NOT NULL DEFAULT '{}',
|
||||
status TEXT NOT NULL DEFAULT 'queued',
|
||||
created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
started_at TEXT,
|
||||
finished_at TEXT,
|
||||
created_by_user_id INTEGER,
|
||||
created_by_username TEXT,
|
||||
created_by_display_name TEXT,
|
||||
source TEXT NOT NULL DEFAULT 'portal',
|
||||
worker_id TEXT,
|
||||
result_json TEXT,
|
||||
error_text TEXT
|
||||
)
|
||||
"""
|
||||
)
|
||||
con.execute(
|
||||
"""
|
||||
CREATE TABLE IF NOT EXISTS job_logs (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
job_id INTEGER NOT NULL,
|
||||
stream TEXT NOT NULL,
|
||||
message TEXT NOT NULL,
|
||||
created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
FOREIGN KEY(job_id) REFERENCES jobs(id)
|
||||
)
|
||||
"""
|
||||
)
|
||||
|
||||
con.execute("CREATE INDEX IF NOT EXISTS idx_jobs_status_created ON jobs(status, created_at)")
|
||||
con.execute("CREATE INDEX IF NOT EXISTS idx_jobs_target_status ON jobs(target_type, target_id, status)")
|
||||
con.execute("CREATE INDEX IF NOT EXISTS idx_job_logs_job_id ON job_logs(job_id, id)")
|
||||
|
||||
try:
|
||||
con.execute("ALTER TABLE jobs ADD COLUMN created_by_display_name TEXT")
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
try:
|
||||
con.execute("ALTER TABLE deployments ADD COLUMN job_id INTEGER")
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
con.commit()
|
||||
con.close()
|
||||
Reference in New Issue
Block a user