rebuild(runtime): govern market operations and job truth

This commit is contained in:
leefer
2026-07-30 10:14:29 +08:00
parent 4fc8691eee
commit d8f0dd930c
39 changed files with 2224 additions and 79 deletions
@@ -0,0 +1,75 @@
from __future__ import annotations
import sqlite3
from backend.database.migrations.runner import Migration
def upgrade(connection: sqlite3.Connection) -> None:
statements = (
"""
CREATE TABLE job_runs (
id INTEGER PRIMARY KEY AUTOINCREMENT,
kind TEXT NOT NULL,
run_key TEXT NOT NULL,
requested_date TEXT NOT NULL DEFAULT '',
trigger TEXT NOT NULL,
status TEXT NOT NULL CHECK (status IN ('running','completed','failed')),
attempt INTEGER NOT NULL CHECK (attempt >= 1),
started_at TEXT NOT NULL,
finished_at TEXT,
duration_ms INTEGER,
coverage REAL CHECK (coverage BETWEEN 0 AND 1),
source_set_json TEXT NOT NULL DEFAULT '[]',
output_version TEXT NOT NULL DEFAULT '',
payload_json TEXT NOT NULL DEFAULT '{}',
error_code TEXT NOT NULL DEFAULT '',
error_message TEXT NOT NULL DEFAULT '',
UNIQUE(kind, run_key, attempt)
)
""",
"""
CREATE UNIQUE INDEX job_runs_active_kind_idx
ON job_runs(kind) WHERE status = 'running'
""",
"""
CREATE INDEX job_runs_kind_started_idx
ON job_runs(kind, started_at DESC, id DESC)
""",
"""
CREATE TABLE market_event_revisions (
id INTEGER PRIMARY KEY AUTOINCREMENT,
trade_date TEXT NOT NULL,
identifier TEXT NOT NULL,
event_type TEXT NOT NULL CHECK (event_type IN ('limit_up','broken','limit_down')),
reason TEXT NOT NULL DEFAULT '',
first_time TEXT NOT NULL DEFAULT '',
last_time TEXT NOT NULL DEFAULT '',
open_times INTEGER CHECK (open_times IS NULL OR open_times >= 0),
source TEXT NOT NULL CHECK (source IN ('tushare','ifind','admin')),
priority INTEGER NOT NULL CHECK (priority >= 0),
created_by INTEGER REFERENCES users(id) ON DELETE SET NULL,
created_at TEXT NOT NULL
)
""",
"""
CREATE INDEX market_event_revisions_lookup_idx
ON market_event_revisions(trade_date, identifier, event_type, priority DESC, id DESC)
""",
)
for statement in statements:
connection.execute(statement)
def downgrade(connection: sqlite3.Connection) -> None:
connection.execute("DROP TABLE market_event_revisions")
connection.execute("DROP TABLE job_runs")
MIGRATION = Migration(
version=11,
name="create_operations_audit",
signature="operations:v1:jobs-event-revisions",
upgrade=upgrade,
downgrade=downgrade,
)