/**
 * /watch command implementation
 *
 * Watches .takt/tasks.yaml for pending tasks and executes them automatically.
 * Stays resident until Ctrl+C (SIGINT).
 */

import { TaskRunner, type TaskInfo, TaskWatcher } from '../../../infra/task/index.js';
import { getCurrentPiece } from '../../../infra/config/index.js';
import {
  header,
  info,
  success,
  status,
  blankLine,
} from '../../../shared/ui/index.js';
import { executeAndCompleteTask } from '../execute/taskExecution.js';
import { DEFAULT_PIECE_NAME } from '../../../shared/constants.js';
import { EXIT_SIGINT } from '../../../shared/exitCodes.js';
import { ShutdownManager } from '../execute/shutdownManager.js';
import type { TaskExecutionOptions } from '../execute/types.js';

/**
 * Watch for tasks and execute them as they appear.
 * Runs until Ctrl+C.
 */
export async function watchTasks(cwd: string, options?: TaskExecutionOptions): Promise<void> {
  const pieceName = getCurrentPiece(cwd) || DEFAULT_PIECE_NAME;
  const taskRunner = new TaskRunner(cwd);
  const watcher = new TaskWatcher(cwd);
  const recovered = taskRunner.recoverInterruptedRunningTasks();

  let taskCount = 0;
  let successCount = 0;
  let failCount = 0;

  header('TAKT Watch Mode');
  info(`Piece: ${pieceName}`);
  info(`Watching: ${taskRunner.getTasksDir()}`);
  if (recovered > 0) {
    info(`Recovered ${recovered} interrupted running task(s) to pending.`);
  }
  info('Waiting for tasks... (Ctrl+C to stop)');
  blankLine();

  const shutdownManager = new ShutdownManager({
    callbacks: {
      onGraceful: () => {
        blankLine();
        info('Stopping watch...');
        watcher.stop();
      },
      onForceKill: () => {
        watcher.stop();
        process.exit(EXIT_SIGINT);
      },
    },
  });
  shutdownManager.install();

  try {
    await watcher.watch(async (task: TaskInfo) => {
      taskCount++;
      blankLine();
      info(`=== Task ${taskCount}: ${task.name} ===`);
      blankLine();

      const taskSuccess = await executeAndCompleteTask(task, taskRunner, cwd, pieceName, options);

      if (taskSuccess) {
        successCount++;
      } else {
        failCount++;
      }

      blankLine();
      info('Waiting for tasks... (Ctrl+C to stop)');
    });
  } finally {
    shutdownManager.cleanup();
  }

  // Summary on exit
  if (taskCount > 0) {
    blankLine();
    header('Watch Summary');
    status('Total', String(taskCount));
    status('Success', String(successCount), successCount === taskCount ? 'green' : undefined);
    if (failCount > 0) {
      status('Failed', String(failCount), 'red');
    }
  }

  success('Watch stopped.');
}
