import {
  Document, Packer, Paragraph, TextRun, Table, TableRow, TableCell,
  HeadingLevel, AlignmentType, WidthType, ShadingType,
} from 'docx'
import type { EnrichedUserStory, EnrichedEpic } from '@/stores/workitems'
import { getSessionsByProject, getSessionSummary, getProjectState } from '@/services/transcriptions-db'

export interface ReportData {
  projectId: number
  projectName: string
  epicCount: number
  huCount: number
  inProgressCount: number
  doneCount: number
  blockedCount: number
  epics: EnrichedEpic[]
  hus: EnrichedUserStory[]
  totalSessions: number
  metrics: {
    totalSpPlanned: number
    totalSpCompleted: number
    velocityPerWeek: number
    spi: number
    estimatedEndDate: string
    clientBlockedHours: number
    totalBlockedHours: number
  }
  generatedAt: string
}

function cell(text: string, bold = false, shading?: string): TableCell {
  return new TableCell({
    children: [new Paragraph({
      children: [new TextRun({ text, bold, size: '20pt' })],
      spacing: { before: 40, after: 40 },
    })],
    shading: shading ? { type: ShadingType.CLEAR, fill: shading } : undefined,
  })
}

function headerRow(...headers: string[]): TableRow {
  return new TableRow({ children: headers.map(h => cell(h, true, 'F2F2F2')) })
}

function dataRow(...values: string[]): TableRow {
  return new TableRow({ children: values.map(v => cell(v)) })
}

export async function generateReportDocx(data: ReportData): Promise<Blob> {
  const sessions = await getSessionsByProject(data.projectId)
  const state = await getProjectState(data.projectId)

  const summary = state?.summary || 'Sin resumen disponible'

  const doc = new Document({
    sections: [{
      children: [
        // ═══════════ TITLE ═══════════
        new Paragraph({
          text: `${data.projectName} — Informe de Avance del Proyecto`,
          heading: HeadingLevel.TITLE,
          alignment: AlignmentType.CENTER,
          spacing: { after: 100 },
        }),
        new Paragraph({
          spacing: { after: 400 },
          children: [
            new TextRun({ text: `Fecha de corte: ${data.generatedAt}`, size: '20pt' }),
          ],
        }),

        // ═══════════ 1. ESTADO GENERAL ═══════════
        new Paragraph({ text: '1. Estado General', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),

        new Table({
          rows: [
            headerRow('Métrica', 'Valor'),
            dataRow('Total Épicas', String(data.epicCount)),
            dataRow('Total HUs', String(data.huCount)),
            dataRow('En Progreso', String(data.inProgressCount)),
            dataRow('Completadas', String(data.doneCount)),
            dataRow('Bloqueadas', String(data.blockedCount)),
            dataRow('SP Planificados', String(data.metrics.totalSpPlanned)),
            dataRow('SP Completados', String(data.metrics.totalSpCompleted)),
          ],
          width: { size: 100, type: WidthType.PERCENTAGE },
        }),

        // ═══════════ 2. RESUMEN EJECUTIVO ═══════════
        new Paragraph({ text: '2. Resumen Ejecutivo', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),
        new Paragraph({
          spacing: { after: 200 },
          children: [new TextRun({ text: summary, size: '20pt' })],
        }),

        ...(data.metrics.totalBlockedHours > 0 ? [
          new Paragraph({
            spacing: { before: 100 },
            children: [new TextRun({
              text: `⏱ Horas bloqueadas: ${data.metrics.totalBlockedHours}h totales (${data.metrics.clientBlockedHours}h imputables al cliente)`,
              size: '20pt',
              bold: true,
            })],
          }),
        ] : []),

        // ═══════════ 3. ÉPICAS ═══════════
        new Paragraph({ text: '3. Épicas', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),
        ...data.epics.map(epic => new Paragraph({
          spacing: { before: 80, after: 40 },
          children: [
            new TextRun({ text: `📦 ${(epic as any)._epicCode || `EP-${epic.id}`}`, bold: true, size: '20pt' }),
            new TextRun({ text: `  ${(epic as any)._cleanName || epic.name || epic.title || ''}`, size: '20pt' }),
          ],
        })),

        // ═══════════ 4. HUs ═══════════
        new Paragraph({ text: '4. HUs — Resumen', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),
        new Table({
          rows: [
            headerRow('Código', 'Título', 'Estado', 'Prioridad', 'SP'),
            ...data.hus.slice(0, 50).map(hu => dataRow(
              hu.code || `#${hu.id}`,
              (hu._cleanTitle || hu.title).slice(0, 60),
              hu._statusName || String(hu.status || '—'),
              String(hu.priority || '—'),
              String(hu.story_points ?? '—'),
            )),
          ],
          width: { size: 100, type: WidthType.PERCENTAGE },
        }),
        new Paragraph({
          spacing: { before: 100 },
          children: [new TextRun({ text: `Mostrando 50 de ${data.huCount} HUs`, size: '20pt', italics: true, color: '888888' })],
        }),

        // ═══════════ 5. HUs BLOQUEADAS ═══════════
        ...(data.blockedCount > 0 ? [
          new Paragraph({ text: '5. HUs Bloqueadas', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),
          ...data.hus.filter(h => {
            const s = String(h.status ?? '').toLowerCase()
            return ['blocked', 'bloqueado'].includes(s)
          }).map(hu => new Paragraph({
            spacing: { before: 60, after: 60 },
            children: [new TextRun({ text: `⚠ ${hu._cleanTitle || hu.title}`, size: '20pt' })],
          })),
        ] : []),

        // ═══════════ 6. CURVA S ═══════════
        new Paragraph({ text: '6. Curva S del Proyecto', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),
        new Paragraph({
          children: [new TextRun({
            text: `La curva S muestra el avance planificado vs real. SPI actual: ${data.metrics.spi}. Velocidad: ${data.metrics.velocityPerWeek} SP/semana. Proyección de finalización: ${data.metrics.estimatedEndDate || 'N/A'}.`,
            size: '20pt',
          })],
          spacing: { after: 200 },
        }),

        // ═══════════ 7. CURVA S ═══════════
        new Paragraph({ text: '7. Carga de Trabajo Actual', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),
        new Paragraph({
          children: [new TextRun({
            text: `${data.inProgressCount} HUs en progreso · ${data.blockedCount} bloqueadas · ${data.doneCount} completadas de ${data.huCount} totales.`,
            size: '20pt',
          })],
        }),

        // ═══════════ 8. AVANCES DE LA SEMANA ═══════════
        ...(sessions.length > 0 ? [
          new Paragraph({ text: '8. Avances Registrados', heading: HeadingLevel.HEADING_1, spacing: { before: 400, after: 200 } }),
          ...(await Promise.all(sessions.slice(-10).reverse().map(async (s) => {
            const sum = await getSessionSummary(s.id!)
            return new Paragraph({
              spacing: { before: 60, after: 60 },
              children: [
                new TextRun({ text: `📅 ${s.date}`, bold: true, size: '20pt' }),
                new TextRun({ text: ` — ${s.title}`, size: '20pt' }),
                ...(sum?.summary ? [new TextRun({ text: `\n${sum.summary.slice(0, 300)}`, size: '20pt', italics: true, color: '555555' })] : []),
              ],
            })
          }))),
        ] : []),

        // ═══════════ FOOTER ═══════════
        new Paragraph({
          spacing: { before: 600 },
          alignment: AlignmentType.CENTER,
          children: [new TextRun({
            text: `Documento generado automáticamente por Alpha — ${data.generatedAt}`,
            size: '20pt', italics: true, color: '888888',
          })],
        }),
      ],
    }],
  })

  return await Packer.toBlob(doc)
}
