/**
 * LSP CLI 命令
 * 提供语言服务器的查询和安装功能
 */

import { execSync, spawnSync } from 'child_process';
import { getUniqueServers, type ServerConfig, type InstallConfig } from './server.js';
import type { LanguageId } from './language.js';

// 服务器状态
export interface ServerStatus {
  id: string;
  displayName: string;
  description: string;
  command: string;
  installed: boolean;
  languages: LanguageId[];
  install: InstallConfig;
}

/**
 * 检查命令是否存在
 */
function commandExists(command: string): boolean {
  try {
    execSync(`which ${command}`, { stdio: 'ignore' });
    return true;
  } catch {
    return false;
  }
}

/**
 * 检查包管理器是否可用
 */
function hasPackageManager(manager: string): boolean {
  return commandExists(manager);
}

/**
 * 获取所有服务器状态
 */
export function listServers(): ServerStatus[] {
  const servers = getUniqueServers();

  return servers.map((server) => ({
    id: server.id,
    displayName: server.config.displayName,
    description: server.config.description,
    command: server.config.command,
    installed: commandExists(server.config.command),
    languages: server.languages,
    install: server.config.install,
  }));
}

/**
 * 打印服务器列表
 */
export function printServerList(): void {
  const servers = listServers();

  console.log('\n语言服务器状态:\n');
  console.log('  状态  | 服务器                          | 支持语言');
  console.log('  ------+--------------------------------+------------------');

  for (const server of servers) {
    const status = server.installed ? ' ✓ ' : ' ✗ ';
    const statusColor = server.installed ? '\x1b[32m' : '\x1b[31m';
    const reset = '\x1b[0m';
    const name = server.displayName.padEnd(30);
    const langs = server.languages.slice(0, 3).join(', ') + (server.languages.length > 3 ? '...' : '');

    console.log(`  ${statusColor}${status}${reset}   | ${name} | ${langs}`);
  }

  const installed = servers.filter((s) => s.installed).length;
  console.log(`\n  已安装: ${installed}/${servers.length}\n`);
}

/**
 * 获取安装命令
 */
function getInstallCommand(install: InstallConfig): { command: string; description: string } | null {
  // 优先使用 npm
  if (install.npm && hasPackageManager('npm')) {
    return {
      command: `npm install -g ${install.npm}`,
      description: 'npm',
    };
  }

  // pip
  if (install.pip && hasPackageManager('pip3')) {
    return {
      command: `pip3 install ${install.pip}`,
      description: 'pip3',
    };
  }
  if (install.pip && hasPackageManager('pip')) {
    return {
      command: `pip install ${install.pip}`,
      description: 'pip',
    };
  }

  // go
  if (install.go && hasPackageManager('go')) {
    return {
      command: `go install ${install.go}`,
      description: 'go install',
    };
  }

  // rustup
  if (install.rustup && hasPackageManager('rustup')) {
    return {
      command: `rustup component add ${install.rustup}`,
      description: 'rustup',
    };
  }

  // cargo
  if (install.cargo && hasPackageManager('cargo')) {
    return {
      command: `cargo install ${install.cargo}`,
      description: 'cargo',
    };
  }

  // brew
  if (install.brew && hasPackageManager('brew')) {
    return {
      command: `brew install ${install.brew}`,
      description: 'Homebrew',
    };
  }

  // gem
  if (install.gem && hasPackageManager('gem')) {
    return {
      command: `gem install ${install.gem}`,
      description: 'RubyGems',
    };
  }

  // custom
  if (install.custom) {
    return {
      command: install.custom,
      description: '自定义命令',
    };
  }

  return null;
}

/**
 * 安装服务器
 */
export async function installServer(serverId: string): Promise<boolean> {
  const servers = listServers();
  const server = servers.find(
    (s) => s.id === serverId || s.displayName.toLowerCase() === serverId.toLowerCase()
  );

  if (!server) {
    console.error(`\x1b[31m错误: 未找到服务器 "${serverId}"\x1b[0m`);
    console.log('\n可用的服务器:');
    servers.forEach((s) => console.log(`  - ${s.displayName} (${s.id})`));
    return false;
  }

  if (server.installed) {
    console.log(`\x1b[32m✓ ${server.displayName} 已安装\x1b[0m`);
    return true;
  }

  const installCmd = getInstallCommand(server.install);

  if (!installCmd) {
    console.error(`\x1b[31m无法自动安装 ${server.displayName}\x1b[0m`);
    if (server.install.manual) {
      console.log('\n手动安装说明:');
      console.log(server.install.manual);
    }
    return false;
  }

  console.log(`\n正在安装 ${server.displayName}...`);
  console.log(`使用 ${installCmd.description}: ${installCmd.command}\n`);

  try {
    const result = spawnSync(installCmd.command, {
      shell: true,
      stdio: 'inherit',
    });

    if (result.status === 0) {
      console.log(`\n\x1b[32m✓ ${server.displayName} 安装成功\x1b[0m`);
      return true;
    } else {
      console.error(`\n\x1b[31m✗ ${server.displayName} 安装失败\x1b[0m`);
      if (server.install.manual) {
        console.log('\n手动安装说明:');
        console.log(server.install.manual);
      }
      return false;
    }
  } catch (error) {
    console.error(`\n\x1b[31m安装出错: ${error}\x1b[0m`);
    return false;
  }
}

/**
 * 安装所有服务器
 */
export async function installAllServers(): Promise<void> {
  const servers = listServers();
  const notInstalled = servers.filter((s) => !s.installed);

  if (notInstalled.length === 0) {
    console.log('\x1b[32m所有语言服务器都已安装\x1b[0m');
    return;
  }

  console.log(`\n将安装 ${notInstalled.length} 个语言服务器:\n`);
  notInstalled.forEach((s) => console.log(`  - ${s.displayName}`));
  console.log('');

  let success = 0;
  let failed = 0;

  for (const server of notInstalled) {
    const result = await installServer(server.id);
    if (result) {
      success++;
    } else {
      failed++;
    }
    console.log('');
  }

  console.log(`\n安装完成: ${success} 成功, ${failed} 失败`);
}

/**
 * 显示服务器详细信息
 */
export function showServerInfo(serverId: string): void {
  const servers = listServers();
  const server = servers.find(
    (s) => s.id === serverId || s.displayName.toLowerCase() === serverId.toLowerCase()
  );

  if (!server) {
    console.error(`\x1b[31m错误: 未找到服务器 "${serverId}"\x1b[0m`);
    return;
  }

  const status = server.installed ? '\x1b[32m已安装\x1b[0m' : '\x1b[31m未安装\x1b[0m';

  console.log(`\n${server.displayName}`);
  console.log('='.repeat(40));
  console.log(`状态: ${status}`);
  console.log(`命令: ${server.command}`);
  console.log(`描述: ${server.description}`);
  console.log(`支持语言: ${server.languages.join(', ')}`);

  if (!server.installed) {
    const installCmd = getInstallCommand(server.install);
    if (installCmd) {
      console.log(`\n安装命令 (${installCmd.description}):`);
      console.log(`  ${installCmd.command}`);
    }
    if (server.install.manual) {
      console.log('\n手动安装说明:');
      console.log(server.install.manual);
    }
  }

  console.log('');
}
