<?php

namespace App\Services\Witness;

use App\Models\Witness\WitnessStatement;
use App\Services\PdfService;
use App\Support\Witness\WitnessQuestionnaire;
use Illuminate\Support\Facades\Storage;
use Spatie\Browsershot\Browsershot;
use Spatie\LaravelPdf\Facades\Pdf;

/**
 * Renders a witness statement to a PDF using the project's existing PDF
 * infrastructure (spatie/laravel-pdf → Browsershot, PdfService for merges).
 *
 * This is deliberately a thin, swappable collaborator: WitnessStatementService
 * depends on it, so tests can bind a fake and never invoke headless Chrome,
 * while production renders for real. It does the Chrome work only — the
 * service owns the Document row and the version snapshot.
 */
class WitnessStatementRenderer
{
    public function __construct(
        private readonly PdfService $pdf,
        private readonly WitnessQuestionnaire $questionnaire,
    ) {}

    /**
     * Build the statement PDF and return storage metadata.
     *
     * @param  array<string, array{value:mixed,origin:string,review_status:string}>  $answers  keyed "section.question"
     * @param  array<int, array<string, mixed>>  $exhibits
     * @param  array<string, bool>  $options
     * @return array{disk:string, path:string, file_name:string, file_size:int}
     */
    public function render(WitnessStatement $ws, int $versionNumber, array $answers, array $exhibits, array $options): array
    {
        $ws->loadMissing(['client', 'claim.bankDetail', 'solicitor']);

        $disk = 'public';
        $dir = trim($ws->claim->getDocumentStoragePath(), '/');
        $fileName = 'Witness-Statement-v'.$versionNumber.'.pdf';
        $storagePath = $dir.'/'.$fileName;

        if (! Storage::disk($disk)->exists($dir)) {
            Storage::disk($disk)->makeDirectory($dir);
        }

        $absolute = Storage::disk($disk)->path($storagePath);

        Pdf::view('pdfs.witness-statement', [
            'ws' => $ws,
            'client' => $ws->client,
            'claim' => $ws->claim,
            'solicitor' => $ws->solicitor,
            'questionnaire' => $this->questionnaire,
            'answers' => $answers,
            'exhibits' => $exhibits,
            'options' => $options,
            'versionNumber' => $versionNumber,
            'coverLetter' => (bool) ($options['cover_letter'] ?? false),
        ])
            ->margins(40, 40, 40, 40)
            ->withBrowsershot(function (Browsershot $browsershot) {
                $this->pdf->configureBrowsershot($browsershot);
            })
            ->save($absolute);

        return [
            'disk' => $disk,
            'path' => $storagePath,
            'file_name' => $fileName,
            'file_size' => Storage::disk($disk)->exists($storagePath)
                ? (int) Storage::disk($disk)->size($storagePath)
                : 0,
        ];
    }
}
