"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.listEntities = listEntities;
exports.listJobs = listJobs;
const db_1 = require("../../lib/db");
const hotmesh_utils_1 = require("../hotmesh-utils");
const sql_1 = require("./sql");
const SORTABLE_COLUMNS = new Set(['created_at', 'updated_at', 'entity', 'status']);
function buildOrderBy(sortBy, order) {
    if (!sortBy || !SORTABLE_COLUMNS.has(sortBy)) {
        return '(CASE WHEN j.status > 0 THEN 0 ELSE 1 END), j.created_at DESC';
    }
    const dir = order === 'asc' ? 'ASC' : 'DESC';
    const col = sortBy === 'status' ? '(CASE WHEN j.status > 0 THEN 0 WHEN j.status = 0 THEN 1 ELSE 2 END)' : `j.${sortBy}`;
    return `${col} ${dir}`;
}
/**
 * Return distinct entity names from job runs + yaml workflow graph_topics.
 */
async function listEntities(rawAppId) {
    const appId = (0, hotmesh_utils_1.sanitizeAppId)(rawAppId);
    const schema = (0, hotmesh_utils_1.quoteSchema)(appId);
    const pool = (0, db_1.getPool)();
    const [jobResult, yamlResult] = await Promise.all([
        pool.query((0, sql_1.DISTINCT_ENTITIES)(schema)).catch(() => ({ rows: [] })),
        pool.query(sql_1.ACTIVE_GRAPH_TOPICS, [rawAppId]).catch(() => ({ rows: [] })),
    ]);
    const entitySet = new Set();
    for (const r of jobResult.rows)
        entitySet.add(r.entity);
    for (const r of yamlResult.rows)
        entitySet.add(r.graph_topic);
    return [...entitySet].sort();
}
/**
 * List jobs with filtering, pagination, and status mapping.
 */
async function listJobs(params) {
    const { rawAppId } = params;
    const appId = (0, hotmesh_utils_1.sanitizeAppId)(rawAppId);
    const schema = (0, hotmesh_utils_1.quoteSchema)(appId);
    const limit = Math.min(params.limit ?? 20, 100);
    const offset = params.offset ?? 0;
    const pool = (0, db_1.getPool)();
    const conditions = [];
    const values = [];
    let idx = 1;
    if (params.entity) {
        conditions.push(`j.entity = $${idx++}`);
        values.push(params.entity);
    }
    if (params.search) {
        conditions.push(`j.key ILIKE $${idx++}`);
        values.push(`%${params.search}%`);
    }
    if (params.status === 'running') {
        conditions.push('j.status > 0');
    }
    else if (params.status === 'completed') {
        conditions.push('j.status = 0');
    }
    else if (params.status === 'failed') {
        conditions.push('j.status < 0');
    }
    const where = conditions.length > 0 ? `WHERE ${conditions.join(' AND ')}` : '';
    const keyPrefix = `hmsh:${appId}:j:`;
    const orderBy = buildOrderBy(params.sort_by, params.order);
    const [countResult, dataResult] = await Promise.all([
        pool.query((0, sql_1.COUNT_JOBS)(schema, where), values),
        pool.query((0, sql_1.LIST_JOBS)(schema, appId, where, idx++, idx++, orderBy), [...values, limit, offset]),
    ]);
    const jobs = dataResult.rows.map((row) => ({
        workflow_id: row.key.startsWith(keyPrefix) ? row.key.slice(keyPrefix.length) : row.key,
        entity: row.entity,
        status: row.status > 0 ? 'running' : row.status === 0 ? 'completed' : 'failed',
        is_live: row.is_live,
        created_at: row.created_at,
        updated_at: row.updated_at,
    }));
    return { jobs, total: parseInt(countResult.rows[0].count, 10) };
}
