package browser

import (
	"encoding/base64"
	"fmt"
)

// CdpPrintPDFOpts configura la generacion del PDF via Page.printToPDF.
type CdpPrintPDFOpts struct {
	// Landscape orienta la pagina en horizontal cuando es true (vertical por defecto).
	Landscape bool
	// PrintBackground incluye los graficos de fondo (colores e imagenes CSS) cuando es true.
	PrintBackground bool
	// Scale es el factor de escala del renderizado (1.0 = tamano natural).
	// Si es <= 0 se usa 1.0. Chrome acepta el rango [0.1, 2].
	Scale float64
	// PaperWidthIn es el ancho del papel en pulgadas. 0 deja el default del navegador (8.5in).
	PaperWidthIn float64
	// PaperHeightIn es el alto del papel en pulgadas. 0 deja el default del navegador (11in).
	PaperHeightIn float64
}

// CdpPrintPDF genera un PDF de la pagina actual via el metodo CDP Page.printToPDF
// y devuelve los bytes del PDF ya decodificados, sin tocar el disco.
//
// Usa transferMode "ReturnAsBase64" (el default de CDP): Chrome devuelve el PDF
// completo como string base64 en el campo "data" de la respuesta, que esta
// funcion decodifica a []byte. Es robusto ante paginas grandes porque sendCDP
// espera la respuesta completa por el WebSocket antes de decodificar.
//
// Las opciones se traducen a los params de Page.printToPDF: Landscape,
// PrintBackground y Scale siempre se envian (con Scale forzado a 1.0 si opts pide
// <= 0). PaperWidthIn/PaperHeightIn solo se envian cuando son > 0, dejando el
// tamano de papel por defecto del navegador en caso contrario.
//
// Es la primitiva reutilizable de impresion a PDF: util para devolver el PDF al
// LLM como document content (bytes) o para que un caller lo persista a disco.
func CdpPrintPDF(c *CDPConn, opts CdpPrintPDFOpts) ([]byte, error) {
	if c == nil {
		return nil, fmt.Errorf("cdp print pdf: conexion nula")
	}

	scale := opts.Scale
	if scale <= 0 {
		scale = 1.0
	}

	params := map[string]any{
		"transferMode":    "ReturnAsBase64",
		"landscape":       opts.Landscape,
		"printBackground": opts.PrintBackground,
		"scale":           scale,
	}
	if opts.PaperWidthIn > 0 {
		params["paperWidth"] = opts.PaperWidthIn
	}
	if opts.PaperHeightIn > 0 {
		params["paperHeight"] = opts.PaperHeightIn
	}

	result, err := c.sendCDP("Page.printToPDF", params)
	if err != nil {
		return nil, fmt.Errorf("cdp print pdf: %w", err)
	}

	dataStr, ok := result["data"].(string)
	if !ok {
		return nil, fmt.Errorf("cdp print pdf: campo data ausente en respuesta")
	}

	pdfData, err := base64.StdEncoding.DecodeString(dataStr)
	if err != nil {
		return nil, fmt.Errorf("cdp print pdf: decodificar base64: %w", err)
	}

	return pdfData, nil
}
