package at.procon.dip.extraction.impl;

import at.procon.dip.domain.document.ContentRole;
import at.procon.dip.domain.document.DocumentType;
import at.procon.dip.extraction.spi.ExtractedStructuredPayload;
import at.procon.dip.extraction.spi.DocumentExtractor;
import at.procon.dip.extraction.spi.ExtractionRequest;
import at.procon.dip.extraction.spi.ExtractionResult;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;

@Component
public class HtmlDocumentExtractor implements DocumentExtractor {

    @Override
    public boolean supports(DocumentType documentType, String mimeType) {
        return documentType == DocumentType.HTML || "text/html".equalsIgnoreCase(mimeType)
                || "application/xhtml+xml".equalsIgnoreCase(mimeType);
    }

    @Override
    public ExtractionResult extract(ExtractionRequest extractionRequest) {
        String html = extractionRequest.textContent();
        if (!StringUtils.hasText(html) && extractionRequest.binaryContent() != null) {
            html = new String(extractionRequest.binaryContent(), StandardCharsets.UTF_8);
        }
        if (!StringUtils.hasText(html)) {
            return new ExtractionResult(Map.of(), List.of(), List.of("No HTML content available"));
        }

        Document parsed = Jsoup.parse(html);
        parsed.outputSettings().prettyPrint(false);
        String cleanText = parsed.text();

        Map<ContentRole, String> derivedText = new LinkedHashMap<>();
        derivedText.put(ContentRole.HTML_CLEAN, parsed.body() != null ? parsed.body().text() : cleanText);
        derivedText.put(ContentRole.NORMALIZED_TEXT, cleanText);

        Map<String, Object> payload = new LinkedHashMap<>();
        if (StringUtils.hasText(parsed.title())) {
            payload.put("title", parsed.title().trim());
        }
        if (parsed.body() != null) {
            payload.put("bodyTextLength", parsed.body().text().length());
        }
        List<String> warnings = new ArrayList<>();
        if (!StringUtils.hasText(parsed.title())) {
            warnings.add("HTML document has no <title> element");
        }

        return new ExtractionResult(derivedText, List.of(new ExtractedStructuredPayload("html-document", payload)), warnings);
    }
}
