package network

import io.ktor.client.*
import io.ktor.client.request.*
import io.ktor.client.statement.*
import java.io.ByteArrayInputStream
import java.io.File
import java.util.zip.ZipInputStream
import javax.xml.parsers.DocumentBuilderFactory

object DartCodeManager {
    private val corpCodeMap = mutableMapOf<String, String>()
    private const val DART_API_KEY = "61143d2af0759f6c28ce372d9e339d1e01687abc" // 지범님의 API 키 입력

    private fun saveXmlDebugFile(xmlBytes: ByteArray) {
        try {
            val debugFile = java.io.File("debug_CORPCODE.xml")
            debugFile.writeBytes(xmlBytes)
            println("💾 [디버그] XML 파일 저장 완료: ${debugFile.absolutePath}")
            // M3 Pro 환경에서는 파일 쓰기가 거의 즉시 완료됩니다.
        } catch (e: Exception) {
            println("⚠️ [디버그] 파일 저장 실패: ${e.message}")
        }
    }

    /**
     * 앱 실행 시 호출하여 매핑 테이블 업데이트
     */
    suspend fun updateCorpCodes(client: HttpClient) {
        println("📂 [DART] 법인코드 매핑 데이터 업데이트 시작...")

        try {
            val url = "https://opendart.fss.or.kr/api/corpCode.xml?crtfc_key=$DART_API_KEY"
            val response: HttpResponse = client.get(url)
            val zipBytes = response.readBytes()
            val zipFile = File("dart_corp_codes.zip")
            zipFile.writeBytes(zipBytes)
            println("💾 [디버그] 원본 ZIP 저장 완료: ${zipFile.absolutePath} (${zipBytes.size} bytes)")
            ZipInputStream(ByteArrayInputStream(zipBytes)).use { zis ->
                var entry = zis.nextEntry
                while (entry != null) {
                    if (entry.name == "CORPCODE.xml") {
                        saveXmlDebugFile(zipBytes)
                        parseXml(zis.readAllBytes())
                        break
                    }
                    entry = zis.nextEntry
                }
            }
            println("✅ [DART] 매핑 완료: ${corpCodeMap.size}개의 상장사 로드됨")
        } catch (e: Exception) {
            println("❌ [DART] 법인코드 업데이트 실패: ${e.message}")
        }
    }

    private fun parseXml(xmlBytes: ByteArray) {
        val factory = DocumentBuilderFactory.newInstance()
        val builder = factory.newDocumentBuilder()
        val doc = builder.parse(ByteArrayInputStream(xmlBytes))
        val nodeList = doc.getElementsByTagName("list")

        for (i in 0 until nodeList.length) {
            val element = nodeList.item(i) as org.w3c.dom.Element
            val stockCode = element.getElementsByTagName("stock_code").item(0)?.textContent?.trim() ?: ""
            val corpCode = element.getElementsByTagName("corp_code").item(0)?.textContent ?: ""
            println("stockCode: $stockCode , corpCode: $corpCode")
            // 종목코드(stock_code)가 있는 상장사만 매핑에 추가
            if (stockCode.isNotEmpty()) {
                corpCodeMap[stockCode] = corpCode
            }
        }
    }

    /**
     * 6자리 종목코드로 8자리 법인코드 반환
     */
    fun getCorpCode(stockCode: String): String? {
        // 1. 직접 매칭 시도
        corpCodeMap[stockCode]?.let { return it }

        // 2. 우선주 규칙 적용 (마지막 자리가 5, 7, 9인 경우 0으로 변경)
        if (stockCode.length == 6 && stockCode.last() in listOf('5', '7', '9')) {
            val commonStockCode = stockCode.substring(0, 5) + "0"
            corpCodeMap[commonStockCode]?.let {
                println("ℹ️ [DART] 우선주($stockCode)를 보통주($commonStockCode) 코드로 매핑 성공")
                return it
            }
        }

        return null
    }
}