import type {
  AgentPermission,
  AgentFilePermission,
  AgentBashPermission,
  AgentGitPermission,
  PermissionAction,
  PermissionRule,
} from './types.js';

/**
 * 系统默认权限配置
 */
export const SYSTEM_DEFAULT_PERMISSION: AgentPermission = {
  file: {
    read: 'allow',
    write: 'ask',
    edit: 'ask',
    delete: 'ask',
  },
  bash: {
    enabled: true,
    default: 'ask',
    rules: [
      // 安全命令
      { pattern: 'ls *', action: 'allow' },
      { pattern: 'pwd', action: 'allow' },
      { pattern: 'cat *', action: 'allow' },
      { pattern: 'head *', action: 'allow' },
      { pattern: 'tail *', action: 'allow' },
      { pattern: 'wc *', action: 'allow' },
      { pattern: 'echo *', action: 'allow' },
      { pattern: 'which *', action: 'allow' },
      { pattern: 'type *', action: 'allow' },
      // 危险命令
      { pattern: 'rm -rf *', action: 'deny' },
      { pattern: 'rm -fr *', action: 'deny' },
      { pattern: 'sudo *', action: 'deny' },
      { pattern: 'chmod 777 *', action: 'deny' },
    ],
  },
  web: 'ask',
  git: {
    read: 'allow',
    write: 'ask',
    dangerous: 'deny',
  },
};

/**
 * 合并单个权限值
 * 优先级: agent > global > system
 */
function mergeAction(
  system: PermissionAction | undefined,
  global: PermissionAction | undefined,
  agent: PermissionAction | undefined
): PermissionAction {
  return agent ?? global ?? system ?? 'ask';
}

/**
 * 合并规则数组
 * Agent 规则优先，然后是 global，最后是 system
 */
function mergeRules(
  system: PermissionRule[] | undefined,
  global: PermissionRule[] | undefined,
  agent: PermissionRule[] | undefined
): PermissionRule[] {
  return [
    ...(agent ?? []),
    ...(global ?? []),
    ...(system ?? []),
  ];
}

/**
 * 合并文件权限配置
 */
function mergeFilePermission(
  system: AgentFilePermission | undefined,
  global: AgentFilePermission | undefined,
  agent: AgentFilePermission | undefined
): AgentFilePermission {
  return {
    read: mergeAction(system?.read, global?.read, agent?.read),
    write: mergeAction(system?.write, global?.write, agent?.write),
    edit: mergeAction(system?.edit, global?.edit, agent?.edit),
    delete: mergeAction(system?.delete, global?.delete, agent?.delete),
    sensitivePaths: mergeRules(
      system?.sensitivePaths,
      global?.sensitivePaths,
      agent?.sensitivePaths
    ),
  };
}

/**
 * 合并 Bash 权限配置
 */
function mergeBashPermission(
  system: AgentBashPermission | undefined,
  global: AgentBashPermission | undefined,
  agent: AgentBashPermission | undefined
): AgentBashPermission {
  // 如果 agent 显式禁用，直接返回
  if (agent?.enabled === false) {
    return { enabled: false };
  }

  // 如果 global 禁用且 agent 没有覆盖
  if (global?.enabled === false && agent?.enabled === undefined) {
    return { enabled: false };
  }

  return {
    enabled: agent?.enabled ?? global?.enabled ?? system?.enabled ?? true,
    rules: mergeRules(system?.rules, global?.rules, agent?.rules),
    default: mergeAction(system?.default, global?.default, agent?.default),
  };
}

/**
 * 合并 Git 权限配置
 */
function mergeGitPermission(
  system: AgentGitPermission | undefined,
  global: AgentGitPermission | undefined,
  agent: AgentGitPermission | undefined
): AgentGitPermission {
  return {
    read: mergeAction(system?.read, global?.read, agent?.read),
    write: mergeAction(system?.write, global?.write, agent?.write),
    dangerous: mergeAction(system?.dangerous, global?.dangerous, agent?.dangerous),
  };
}

/**
 * 合并完整的权限配置
 * 优先级: Agent 配置 > 全局默认 > 系统默认
 */
export function mergePermissions(
  systemDefault: AgentPermission,
  globalConfig: AgentPermission | undefined,
  agentConfig: AgentPermission | undefined
): AgentPermission {
  return {
    file: mergeFilePermission(
      systemDefault.file,
      globalConfig?.file,
      agentConfig?.file
    ),
    bash: mergeBashPermission(
      systemDefault.bash,
      globalConfig?.bash,
      agentConfig?.bash
    ),
    web: mergeAction(systemDefault.web, globalConfig?.web, agentConfig?.web),
    git: mergeGitPermission(
      systemDefault.git,
      globalConfig?.git,
      agentConfig?.git
    ),
  };
}

/**
 * 检查命令是否匹配规则
 * 支持通配符 * 匹配任意字符
 */
export function matchRule(command: string, pattern: string): boolean {
  // 将通配符模式转换为正则表达式
  const regexPattern = pattern
    .replace(/[.+^${}()|[\]\\]/g, '\\$&') // 转义特殊字符
    .replace(/\*/g, '.*')                  // * 转换为 .*
    .replace(/\?/g, '.');                  // ? 转换为 .

  const regex = new RegExp(`^${regexPattern}$`, 'i');
  return regex.test(command);
}

/**
 * 根据规则列表检查命令权限
 */
export function checkBashPermission(
  command: string,
  permission: AgentBashPermission
): PermissionAction {
  // 如果禁用，直接拒绝
  if (permission.enabled === false) {
    return 'deny';
  }

  // 按顺序检查规则
  for (const rule of permission.rules ?? []) {
    if (matchRule(command, rule.pattern)) {
      return rule.action;
    }
  }

  // 返回默认策略
  return permission.default ?? 'ask';
}

/**
 * 根据规则列表检查文件路径权限
 */
export function checkFilePathPermission(
  filePath: string,
  sensitivePaths: PermissionRule[] | undefined
): PermissionAction | null {
  if (!sensitivePaths) return null;

  for (const rule of sensitivePaths) {
    if (matchRule(filePath, rule.pattern)) {
      return rule.action;
    }
  }

  return null;
}
