/**
 * ETL Data Quality — Post-sync validation checks
 * Runs after each daily sync to verify data integrity
 */
const pool = require('../db-rds');
const analyticsDb = require('../db-analytics');

/**
 * Run data quality checks for a given date
 */
async function runDataQuality(dateStr) {
  const issues = [];
  console.log(`[DQ] Running data quality checks for ${dateStr}...`);

  // 1. Row count validation — SQLite should have 3 product rows per synced day
  const sqliteRows = analyticsDb.prepare(
    'SELECT COUNT(*) as c FROM daily_metrics WHERE date = ?'
  ).get(dateStr);

  if (!sqliteRows || sqliteRows.c !== 3) {
    issues.push(`Row count: expected 3 product rows, got ${sqliteRows?.c || 0}`);
  }

  // 2. Null / negative checks on SQLite aggregates
  const metrics = analyticsDb.prepare(
    'SELECT product, transactions, volume_usd, revenue, avg_spread FROM daily_metrics WHERE date = ?'
  ).all(dateStr);

  for (const m of metrics) {
    if (m.transactions < 0) issues.push(`${m.product}: negative transaction count (${m.transactions})`);
    if (m.volume_usd < 0) issues.push(`${m.product}: negative volume_usd (${m.volume_usd})`);
    if (m.revenue < 0 && m.product !== 'USD→USD') issues.push(`${m.product}: negative revenue (${m.revenue})`);
    if (m.avg_spread < 0 && m.product !== 'USD→USD') issues.push(`${m.product}: negative avg_spread (${m.avg_spread})`);
  }

  // 3. Revenue reconciliation — compare SQLite aggregates vs MySQL source
  let conn;
  try {
    conn = await pool.getConnection();

    // BRL→USD reconciliation
    const [mysqlBrlUsd] = await conn.execute(`
      SELECT COUNT(*) as tx_count,
        ROUND(COALESCE(SUM(amount_usd), 0), 2) as volume_usd
      FROM br_transaction_to_usa
      WHERE DATE(created_at) = ?
    `, [dateStr]);

    const sqliteBrlUsd = analyticsDb.prepare(
      "SELECT transactions, volume_usd FROM daily_metrics WHERE date = ? AND product = 'BRL→USD'"
    ).get(dateStr);

    if (mysqlBrlUsd[0] && sqliteBrlUsd) {
      const txDelta = Math.abs(Number(mysqlBrlUsd[0].tx_count) - sqliteBrlUsd.transactions);
      if (txDelta > 0) {
        issues.push(`BRL→USD tx count mismatch: MySQL=${mysqlBrlUsd[0].tx_count}, SQLite=${sqliteBrlUsd.transactions}`);
      }
      const volDelta = Math.abs(Number(mysqlBrlUsd[0].volume_usd) - sqliteBrlUsd.volume_usd);
      if (volDelta > 0.01) {
        issues.push(`BRL→USD volume mismatch: MySQL=${mysqlBrlUsd[0].volume_usd}, SQLite=${sqliteBrlUsd.volume_usd}, delta=${volDelta.toFixed(2)}`);
      }
    }

    // USD→BRL reconciliation
    const [mysqlUsdBrl] = await conn.execute(`
      SELECT COUNT(*) as tx_count,
        ROUND(COALESCE(SUM(valor), 0), 2) as volume_usd
      FROM pagamento_br
      WHERE DATE(created_at) = ?
        AND cotacao IS NOT NULL AND cotacao > 0
        AND (pgto IS NULL OR pgto != 'balance')
    `, [dateStr]);

    const sqliteUsdBrl = analyticsDb.prepare(
      "SELECT transactions, volume_usd FROM daily_metrics WHERE date = ? AND product = 'USD→BRL'"
    ).get(dateStr);

    if (mysqlUsdBrl[0] && sqliteUsdBrl) {
      const txDelta = Math.abs(Number(mysqlUsdBrl[0].tx_count) - sqliteUsdBrl.transactions);
      if (txDelta > 0) {
        issues.push(`USD→BRL tx count mismatch: MySQL=${mysqlUsdBrl[0].tx_count}, SQLite=${sqliteUsdBrl.transactions}`);
      }
      const volDelta = Math.abs(Number(mysqlUsdBrl[0].volume_usd) - sqliteUsdBrl.volume_usd);
      if (volDelta > 0.01) {
        issues.push(`USD→BRL volume mismatch: MySQL=${mysqlUsdBrl[0].volume_usd}, SQLite=${sqliteUsdBrl.volume_usd}, delta=${volDelta.toFixed(2)}`);
      }
    }

    // 4. Monthly revenue check — sum of client revenues should be positive if there are transactions
    const month = dateStr.slice(0, 7);
    const monthlySum = analyticsDb.prepare(
      'SELECT SUM(revenue) as total_rev, COUNT(*) as clients FROM monthly_revenue WHERE month = ?'
    ).get(month);

    const totalDayTx = metrics.reduce((s, m) => s + m.transactions, 0);
    if (totalDayTx > 0 && monthlySum && monthlySum.total_rev <= 0 && monthlySum.clients > 0) {
      issues.push(`Monthly revenue for ${month} is ${monthlySum.total_rev} despite ${totalDayTx} transactions on ${dateStr}`);
    }
  } finally {
    if (conn) conn.release();
  }

  // Report results
  if (issues.length === 0) {
    console.log(`[DQ] ${dateStr}: All checks passed`);
  } else {
    console.warn(`[DQ] ${dateStr}: ${issues.length} issue(s) found:`);
    issues.forEach(i => console.warn(`[DQ]   - ${i}`));
  }

  return { date: dateStr, passed: issues.length === 0, issues };
}

module.exports = { runDataQuality };
