package com.ffii.fpsms.modules.master.service

import com.ffii.core.utils.PdfUtils
import com.ffii.core.utils.QrCodeUtil
import com.ffii.fpsms.modules.master.entity.EquipmentDetailRepository
import com.ffii.fpsms.modules.master.web.ExportEquipmentQrCodeRequest
import net.sf.jasperreports.engine.JasperCompileManager
import net.sf.jasperreports.engine.JasperPrint
import org.springframework.core.io.ClassPathResource
import org.springframework.stereotype.Service
import java.io.FileNotFoundException
import java.awt.GraphicsEnvironment
import kotlinx.serialization.json.Json
import kotlinx.serialization.encodeToString

@Service
class EquipmentQrCodeService(
    private val equipmentDetailRepository: EquipmentDetailRepository
) {

    fun exportEquipmentQrCode(request: ExportEquipmentQrCodeRequest): Map<String, Any> {
        val QRCODE_HANDLE_PDF = "qrCodeHandle/equipment_QrHandle.jrxml"
        val resource = ClassPathResource(QRCODE_HANDLE_PDF)
        if (!resource.exists()) {
            throw FileNotFoundException("Report file not found: $QRCODE_HANDLE_PDF")
        }
        
        val inputStream = resource.inputStream
        val qrCodeHandleReport = JasperCompileManager.compileReport(inputStream)
        
        val equipmentDetails = equipmentDetailRepository.findAllById(request.equipmentDetailIds)
        if (equipmentDetails.isEmpty()) {
            throw IllegalArgumentException("No equipment details found for the provided equipment detail IDs: ${request.equipmentDetailIds}")
        }
        
        val fields = mutableListOf<MutableMap<String, Any>>()
        
        for (equipmentDetail in equipmentDetails) {
            val field = mutableMapOf<String, Any>()
            
            val code = equipmentDetail.code ?: ""
            val equipmentCodeFromDetail = equipmentDetail.equipmentCode ?: ""
            
            if (code.isBlank() && equipmentCodeFromDetail.isBlank()) {
                continue
            }
            
            val qrContentMap = mapOf("equipmentCode" to equipmentCodeFromDetail)
            val qrCodeContent = Json.encodeToString(qrContentMap)
            
            val qrCodeImage = QrCodeUtil.generateQRCodeImage(qrCodeContent)
            
            field["username"] = code
            field["staffNo"] = code
            field["qrCode"] = qrCodeImage
            field["code"] = code
            
            fields.add(field)
        }
        
        if (fields.isEmpty()) {
            throw IllegalArgumentException("No valid equipment details found for the provided equipment detail IDs: ${request.equipmentDetailIds}")
        }
        
        val params: MutableMap<String, Any> = mutableMapOf()
        
        val availableFonts = GraphicsEnvironment.getLocalGraphicsEnvironment().availableFontFamilyNames
        val chineseFont = availableFonts.find { 
            it.contains("SimSun", ignoreCase = true) || 
            it.contains("Microsoft YaHei", ignoreCase = true) ||
            it.contains("STSong", ignoreCase = true) ||
            it.contains("SimHei", ignoreCase = true)
        } ?: "Arial Unicode MS"
        
        params["net.sf.jasperreports.default.pdf.encoding"] = "Identity-H"
        params["net.sf.jasperreports.default.pdf.embedded"] = true
        params["net.sf.jasperreports.default.pdf.font.name"] = chineseFont
        
        val firstEquipmentDetail = equipmentDetails.firstOrNull()
        
        return mapOf(
            "report" to PdfUtils.fillReport(qrCodeHandleReport, fields, params),
            "fileName" to (firstEquipmentDetail?.code ?: "equipment_qrcode")
        )
    }
}
