import type { RoleProgress } from './derive';
import type { Stage, Role } from './stage';
import { calcDelayStatus, calcOverallProgress } from './risk';

export interface RiskTag {
  key: string;
  label: string;
  severity: 'critical' | 'high' | 'medium';
  reason?: string;
  suggestion?: string;
}

export type HealthLevel = 'healthy' | 'good' | 'attention' | 'risk' | 'critical';

const STAGE_ROLE_MAP: Record<string, Role[]> = {
  requirement: ['product'],
  product_design: ['product'],
  ui_design: ['ui'],
  dev: ['frontend', 'backend'],
  testing: ['testing'],
  bug: [],
  released: [],
};

export function calcHealthScore(
  status: string,
  startDate?: string | null,
  expectedReleaseDate?: string | null,
  progress?: RoleProgress[],
): number {
  if (status === 'released' || status === 'closed') return 100;
  if (status === 'planned') return 100;

  let score = 100;

  // 暂停扣分
  if (status === 'paused') score -= 20;

  // 进度落后扣分
  if (startDate && expectedReleaseDate) {
    const now = new Date();
    now.setHours(0, 0, 0, 0);
    const start = new Date(startDate);
    start.setHours(0, 0, 0, 0);
    const end = new Date(expectedReleaseDate);
    end.setHours(0, 0, 0, 0);

    const totalDuration = end.getTime() - start.getTime();
    if (totalDuration > 0) {
      const elapsed = now.getTime() - start.getTime();
      const timeProgress = Math.min(100, Math.max(0, (elapsed / totalDuration) * 100));
      const actualProgress = calcOverallProgress(progress);
      const gap = Math.max(0, timeProgress - actualProgress);
      score -= gap * 0.8;
    }
  }

  // 延期扣分
  if (expectedReleaseDate && status !== 'released' && status !== 'closed') {
    const now = new Date();
    now.setHours(0, 0, 0, 0);
    const deadline = new Date(expectedReleaseDate);
    deadline.setHours(0, 0, 0, 0);
    const diffDays = (deadline.getTime() - now.getTime()) / (1000 * 60 * 60 * 24);

    if (diffDays < 0) {
      score -= Math.min(40, Math.abs(diffDays) * 5);
    } else if (diffDays <= 3) {
      score -= 15;
    }
  }

  return Math.max(0, Math.min(100, Math.round(score)));
}

export function getHealthLevel(score: number): HealthLevel {
  if (score >= 90) return 'healthy';
  if (score >= 75) return 'good';
  if (score >= 60) return 'attention';
  if (score >= 35) return 'risk';
  return 'critical';
}

export const HEALTH_LEVEL_LABEL: Record<HealthLevel, string> = {
  healthy: '健康',
  good: '良好',
  attention: '关注',
  risk: '风险',
  critical: '严重',
};

export const HEALTH_LEVEL_COLOR: Record<HealthLevel, string> = {
  healthy: 'text-emerald-600',
  good: 'text-blue-600',
  attention: 'text-amber-600',
  risk: 'text-orange-600',
  critical: 'text-red-600',
};

export const HEALTH_LEVEL_DOT: Record<HealthLevel, string> = {
  healthy: 'bg-emerald-500',
  good: 'bg-blue-500',
  attention: 'bg-amber-500',
  risk: 'bg-orange-500',
  critical: 'bg-red-500',
};

const TAG_SEVERITY_STYLE: Record<string, string> = {
  critical: 'bg-red-50 text-red-600 border-red-200',
  high: 'bg-orange-50 text-orange-600 border-orange-200',
  medium: 'bg-amber-50 text-amber-600 border-amber-200',
};

export function getTagStyle(severity: string): string {
  return TAG_SEVERITY_STYLE[severity] || TAG_SEVERITY_STYLE.medium;
}

export function calcRiskTags(
  status: string,
  startDate?: string | null,
  expectedReleaseDate?: string | null,
  progress?: RoleProgress[],
  currentStage?: Stage,
  members?: { role: Role; name: string }[],
): RiskTag[] {
  if (status === 'released' || status === 'closed' || status === 'planned') return [];

  const tags: RiskTag[] = [];

  // 延期类
  if (expectedReleaseDate) {
    const now = new Date();
    now.setHours(0, 0, 0, 0);
    const deadline = new Date(expectedReleaseDate);
    deadline.setHours(0, 0, 0, 0);
    const diffDays = (now.getTime() - deadline.getTime()) / (1000 * 60 * 60 * 24);

    if (diffDays > 7) {
      tags.push({ key: 'severe_delay', label: '严重延期', severity: 'critical', reason: `已超过截止日期 ${Math.round(diffDays)} 天`, suggestion: '立即与团队确认是否调整截止日期，评估是否需要缩减版本范围' });
    } else if (diffDays > 0) {
      tags.push({ key: 'delay_risk', label: '延期风险', severity: 'high', reason: `已超过截止日期 ${Math.round(diffDays)} 天`, suggestion: '排查阻塞原因，与相关负责人沟通加速或调整排期' });
    } else if (diffDays > -3) {
      tags.push({ key: 'delay_risk', label: '延期风险', severity: 'medium', reason: `距离截止日期仅剩 ${Math.round(-diffDays)} 天`, suggestion: '关注剩余工作量是否可按时完成，提前预警相关方' });
    }
  }

  // 进度落后
  if (startDate && expectedReleaseDate) {
    const now = new Date();
    now.setHours(0, 0, 0, 0);
    const start = new Date(startDate);
    start.setHours(0, 0, 0, 0);
    const end = new Date(expectedReleaseDate);
    end.setHours(0, 0, 0, 0);

    const totalDuration = end.getTime() - start.getTime();
    if (totalDuration > 0) {
      const elapsed = now.getTime() - start.getTime();
      const timeProgress = Math.min(100, Math.max(0, Math.round((elapsed / totalDuration) * 100)));
      const actualProgress = calcOverallProgress(progress);
      const gap = timeProgress - actualProgress;

      if (gap >= 30) {
        tags.push({ key: 'progress_behind', label: '进度落后', severity: 'high', reason: `整体进度 ${actualProgress}%，时间已过 ${timeProgress}%，落后 ${Math.round(gap)}%`, suggestion: '排查阻塞点，考虑增加资源投入或调整版本优先级' });
      }
    }
  }

  // 阶段超时
  if (currentStage && progress) {
    const roles = STAGE_ROLE_MAP[currentStage] || [];
    const stageItems = roles.map((r) => progress.find((p) => p.role === r)).filter(Boolean);
    const maxDays = stageItems.length > 0 ? Math.max(...stageItems.map((i) => i!.daysSpent)) : 0;
    if (maxDays > 14) {
      tags.push({ key: 'stage_timeout', label: '阶段超时', severity: 'medium', reason: `当前阶段已耗时 ${maxDays} 天，超过经验值（14天）`, suggestion: '确认是否存在技术难点或外部依赖阻塞，及时同步风险' });
    }
  }

  // 资源类
  if (!members || members.length < 2) {
    tags.push({ key: 'missing_owner', label: '负责人缺失', severity: 'high', reason: '版本参与人员不足 2 人', suggestion: '尽快分配各角色负责人，确保版本推进有明确责任人' });
  } else if (currentStage) {
    const neededRoles = STAGE_ROLE_MAP[currentStage] || [];
    const memberRoles = new Set(members.map((m) => m.role));
    const missing = neededRoles.filter((r) => !memberRoles.has(r));
    if (missing.length > 0) {
      tags.push({ key: 'key_role_missing', label: '关键角色缺失', severity: 'medium', reason: `当前阶段缺少对应角色人员`, suggestion: '补充缺失角色的负责人，避免阶段推进受阻' });
    }
  }

  // 按严重程度排序
  const severityOrder: Record<string, number> = { critical: 0, high: 1, medium: 2 };
  tags.sort((a, b) => severityOrder[a.severity] - severityOrder[b.severity]);

  return tags;
}
