CREATE TABLE IF NOT EXISTS datasets (
    id          TEXT PRIMARY KEY,
    name        TEXT NOT NULL UNIQUE,
    schema_json TEXT NOT NULL,
    created_at  TEXT NOT NULL,
    description TEXT
);

CREATE TABLE IF NOT EXISTS dataset_versions (
    id           TEXT PRIMARY KEY,
    dataset_id   TEXT NOT NULL REFERENCES datasets(id),
    version_tag  TEXT,
    created_at   TEXT NOT NULL,
    schema_hash  TEXT NOT NULL,
    row_count    INTEGER NOT NULL,
    time_start   TEXT NOT NULL,
    time_end     TEXT NOT NULL,
    symbols_json TEXT NOT NULL,
    source_hash  TEXT NOT NULL,
    parquet_root TEXT NOT NULL,
    is_active    BOOLEAN NOT NULL DEFAULT FALSE,
    metadata     TEXT
);

CREATE TABLE IF NOT EXISTS symbols (
    id              INTEGER PRIMARY KEY,
    ticker          TEXT NOT NULL,
    asset_class     TEXT NOT NULL,
    exchange        TEXT NOT NULL,
    base_currency   TEXT NOT NULL,
    quote_currency  TEXT NOT NULL,
    tick_size       REAL NOT NULL,
    lot_size        REAL NOT NULL,
    margin_required REAL,
    active_from     TEXT,
    active_to       TEXT,
    metadata        TEXT
);

CREATE TABLE IF NOT EXISTS symbol_mappings (
    provider    TEXT NOT NULL,
    raw_symbol  TEXT NOT NULL,
    symbol_id   INTEGER NOT NULL REFERENCES symbols(id),
    valid_from  TEXT NOT NULL,
    valid_to    TEXT,
    PRIMARY KEY (provider, raw_symbol, valid_from)
);

CREATE TABLE IF NOT EXISTS runs (
    id              TEXT PRIMARY KEY,
    created_at      TEXT NOT NULL,
    user_id         TEXT,
    strategy_name   TEXT NOT NULL,
    strategy_hash   TEXT NOT NULL,
    config_json     TEXT NOT NULL,
    params_json     TEXT NOT NULL,
    data_versions   TEXT NOT NULL,
    rng_seed        INTEGER NOT NULL,
    engine_version  TEXT NOT NULL,
    status          TEXT NOT NULL,
    duration_ms     INTEGER,
    metrics_json    TEXT,
    manifest_json   TEXT NOT NULL
);

CREATE TABLE IF NOT EXISTS quality_reports (
    id             TEXT PRIMARY KEY,
    dataset_id     TEXT NOT NULL REFERENCES datasets(id),
    version_id     TEXT NOT NULL REFERENCES dataset_versions(id),
    created_at     TEXT NOT NULL,
    symbol_id      INTEGER NOT NULL,
    report_json    TEXT NOT NULL
);

CREATE INDEX IF NOT EXISTS idx_dataset_versions_dataset_id
    ON dataset_versions(dataset_id);

CREATE INDEX IF NOT EXISTS idx_dataset_versions_active
    ON dataset_versions(dataset_id, is_active);

CREATE INDEX IF NOT EXISTS idx_symbol_mappings_lookup
    ON symbol_mappings(provider, raw_symbol, valid_to);

CREATE INDEX IF NOT EXISTS idx_quality_reports_dataset_version
    ON quality_reports(dataset_id, version_id);
