import readline from "readline";
import chalk from "chalk";

export interface Command {
  name: string;
  description: string;
  execute: (args: string[]) => void | Promise<void>;
}

class CommandHandler {
  private commands: Map<string, Command>;
  private rl: readline.Interface;

  constructor() {
    this.commands = new Map();
    this.rl = readline.createInterface({
      input: process.stdin,
      output: process.stdout,
      prompt: chalk.blue("> "),
    });

    this.registerCommand({
      name: "help",
      description: "Shows all available commands",
      execute: this.handleHelp.bind(this),
    });

    this.registerCommand({
      name: "exit",
      description: "Exits the application",
      execute: () => {
        console.log(chalk.yellow("Goodbye!"));
        this.rl.close();
        process.exit(0);
      },
    });
  }

  public registerCommand(command: Command): void {
    this.commands.set(command.name, command);
  }

  private handleHelp(): void {
    console.log(chalk.green("\nAvailable commands:"));
    this.commands.forEach((command) => {
      console.log(chalk.cyan(`${command.name}: `) + command.description);
    });
    console.log();
  }

  private async executeCommand(input: string): Promise<void> {
    const args = input.trim().split(/\s+/);
    const commandName = args.shift()?.toLowerCase();

    if (!commandName) {
      return;
    }

    const command = this.commands.get(commandName);

    if (!command) {
      console.log(chalk.red(`Unknown command: ${commandName}`));
      console.log(chalk.yellow('Type "help" to see available commands'));
      return;
    }

    try {
      await command.execute(args);
    } catch (error) {
      console.error(chalk.red("Error executing command:"), error);
    }
  }

  public start(): void {
    console.log(chalk.green("Welcome to the SkyMP LaunchServer CLI!"));
    console.log(chalk.yellow('Type "help" to see available commands\n'));

    this.rl.prompt();

    this.rl.on("line", async (input) => {
      await this.executeCommand(input.trim());
      this.rl.prompt();
    });

    this.rl.on("close", () => {
      console.log(chalk.yellow("Goodbye!"));
      process.exit(0);
    });
  }
}

export const commandHandler = new CommandHandler();
