import { drizzle } from 'drizzle-orm/node-postgres';
import { Pool } from 'pg';
import { migrate } from 'drizzle-orm/node-postgres/migrator';
import * as schema from '../shared/schema.js';
import { sql } from 'drizzle-orm';

let db: ReturnType<typeof drizzle> | null = null;
export let pool: Pool | null = null;

export function getDatabase() {
  if (!db) {
    const databaseUrl = process.env.DATABASE_URL;

    if (!databaseUrl) {
      throw new Error('DATABASE_URL environment variable is not set');
    }

    // Configure SSL based on DATABASE_SSL environment variable
    // Values: 'true', 'false', or 'require'
    // Default: false (no SSL)
    let sslConfig: any = false;

    if (process.env.DATABASE_SSL === 'true') {
      sslConfig = { rejectUnauthorized: false };  // SSL with self-signed certs
    } else if (process.env.DATABASE_SSL === 'require') {
      sslConfig = { rejectUnauthorized: true };   // SSL with valid certs only
    }
    // Otherwise defaults to false (no SSL)

    pool = new Pool({
      connectionString: databaseUrl,
      ssl: sslConfig,
    });

    db = drizzle(pool, { schema });
  }

  return db;
}

export async function runMigrations() {
  try {
    const database = getDatabase();

    // Push schema to database (creates/updates tables as needed)
    // This is equivalent to running `drizzle-kit push`
    console.log('Checking database schema...');

    // Enable pgcrypto extension for gen_random_uuid()
    await database.execute(sql`CREATE EXTENSION IF NOT EXISTS "pgcrypto"`);

    // Create tables if they don't exist
    await database.execute(sql`
      CREATE TABLE IF NOT EXISTS users (
        id VARCHAR PRIMARY KEY DEFAULT gen_random_uuid(),
        username TEXT NOT NULL UNIQUE,
        password TEXT NOT NULL
      )
    `);

    await database.execute(sql`
      CREATE TABLE IF NOT EXISTS labels (
        id VARCHAR PRIMARY KEY DEFAULT gen_random_uuid(),
        name TEXT NOT NULL,
        color TEXT NOT NULL
      )
    `);

    await database.execute(sql`
      CREATE TABLE IF NOT EXISTS tasks (
        id VARCHAR PRIMARY KEY DEFAULT gen_random_uuid(),
        title TEXT NOT NULL,
        description TEXT,
        status TEXT NOT NULL DEFAULT 'todo',
        priority TEXT NOT NULL DEFAULT 'medium',
        due_date TIMESTAMP,
        time_tracked INTEGER NOT NULL DEFAULT 0,
        is_tracking BOOLEAN NOT NULL DEFAULT false,
        project_id TEXT,
        notes TEXT,
        label_id VARCHAR REFERENCES labels(id)
      )
    `);

    console.log('✓ Database schema is up to date');
  } catch (error) {
    console.error('Failed to run migrations:', error);
    throw error;
  }
}

export async function initializeDatabase() {
  try {
    // Run migrations first
    await runMigrations();

    const database = getDatabase();

    // Create default labels if they don't exist
    const existingLabels = await database.select().from(schema.labels);

    if (existingLabels.length === 0) {
      const defaultLabels = [
        { name: "Work", color: "#3B82F6" },
        { name: "Personal", color: "#10B981" },
        { name: "Urgent", color: "#EF4444" },
        { name: "Study", color: "#8B5CF6" },
      ];

      await database.insert(schema.labels).values(defaultLabels);
      console.log('✓ Created default labels');
    }

    console.log('✓ Database initialized successfully');
  } catch (error) {
    console.error('Failed to initialize database:', error);
    throw error;
  }
}

export async function closeDatabase() {
  if (pool) {
    await pool.end();
    pool = null;
    db = null;
    console.log('✓ Database connection closed');
  }
}
