package com.lukouguoji.gjc.viewModel

import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.viewModelScope
import com.lukouguoji.gjc.R
import com.lukouguoji.gjc.dialog.IntExpLoadDeleteDialogModel
import com.lukouguoji.gjc.dialog.IntExpLoadResetDialogModel
import com.lukouguoji.gjc.holder.IntExpLoadViewHolder
import com.lukouguoji.module_base.base.BasePageViewModel
import com.lukouguoji.module_base.bean.GjcCheckInPage
import com.lukouguoji.module_base.bean.GjcDeclareParam
import com.lukouguoji.module_base.bean.GjcExportLoad
import com.lukouguoji.module_base.common.Constant
import com.lukouguoji.module_base.common.ConstantEvent
import com.lukouguoji.module_base.http.net.NetApply
import com.lukouguoji.module_base.impl.FlowBus
import com.lukouguoji.module_base.ktx.commonAdapter
import com.lukouguoji.module_base.ktx.launchCollect
import com.lukouguoji.module_base.ktx.launchLoadingCollect
import com.lukouguoji.module_base.ktx.noNull
import com.lukouguoji.module_base.ktx.showToast
import com.lukouguoji.module_base.ktx.toRequestBody
import com.lukouguoji.module_base.model.ScanModel
import dev.utils.app.info.KeyValue
import dev.utils.common.DateUtils
import com.lukouguoji.module_base.ktx.formatDate
import kotlinx.coroutines.launch

/**
 * 国际出港-出港装载 ViewModel
 */
class IntExpLoadViewModel : BasePageViewModel() {

    // ========== 搜索条件 ==========
    val flightDate = MutableLiveData<String>(DateUtils.getCurrentTime().formatDate())        // 航班日期
    val flightNo = MutableLiveData("")          // 航班号
    val waybillNo = MutableLiveData("")         // 运单号
    val depPort = MutableLiveData("")           // 始发站（航班查询自动填充，锁定不可编辑）
    val destPort = MutableLiveData("")          // 目的站（下拉选择）
    val destPortList = MutableLiveData<List<KeyValue>>(emptyList())  // 目的站下拉列表（目的港 + 经停港）

    // ========== 航班级联查询 ==========
    private var lastQueriedFlight = ""          // 避免重复查询

    /**
     * 航班日期输入完成回调
     */
    fun onFlightDateInputComplete() {
        lastQueriedFlight = ""
        queryFlightIfReady()
    }

    /**
     * 航班号输入完成回调
     */
    fun onFlightNoInputComplete() {
        queryFlightIfReady()
    }

    /**
     * 航班日期 + 航班号 均有值时，查询航班并填充始发站/目的站
     * 出港：始发站自动填充且锁定(始发港)，目的站下拉可选(目的港+经停港)
     */
    private fun queryFlightIfReady() {
        val fdate = flightDate.value
        val fno = flightNo.value
        if (fdate.isNullOrEmpty() || fno.isNullOrEmpty()) return

        val key = "$fdate-$fno"
        if (key == lastQueriedFlight) return
        lastQueriedFlight = key

        launchCollect({
            NetApply.api.getGjFlightBean(
                mapOf(
                    "fdate" to fdate,
                    "fno" to fno,
                    "ieFlag" to "E",  // 出港
                ).toRequestBody()
            )
        }) {
            onSuccess = {
                if (it.verifySuccess() && it.data != null) {
                    val flight = it.data!!
                    // 始发站：航班查询返回，自动填充并锁定
                    depPort.value = flight.fdep.noNull()
                    // 目的站下拉：目的港 + 经停港(可逗号分隔多个)
                    val list = mutableListOf(KeyValue(flight.fdest.noNull(), flight.fdest.noNull()))
                    flight.jtz.split(",").forEach { stop ->
                        val s = stop.trim()
                        if (s.isNotEmpty()) list.add(KeyValue(s, s))
                    }
                    destPortList.value = list
                    destPort.value = flight.fdest.noNull()
                } else {
                    destPortList.value = emptyList()
                    depPort.value = ""
                    destPort.value = ""
                }
            }

            onFailed = { _, _ ->
                destPortList.value = emptyList()
                depPort.value = ""
                destPort.value = ""
            }
        }
    }

    // ========== 统计信息 ==========
    val totalCount = MutableLiveData("0")       // 合计票数
    val totalPc = MutableLiveData("0")          // 总件数
    val totalWeight = MutableLiveData("0")      // 总重量

    // ========== 全选状态 ==========
    val isAllChecked = MutableLiveData(false)

    fun onItemCheckChanged() {
        updateCheckAllStatus()
    }

    fun updateCheckAllStatus() {
        val list = pageModel.rv?.commonAdapter()?.items as? List<GjcExportLoad> ?: return
        isAllChecked.value = list.isNotEmpty() && list.all { it.checked.get() }
    }

    // ========== 适配器配置 ==========
    val itemViewHolder = IntExpLoadViewHolder::class.java
    val itemLayoutId = R.layout.item_int_exp_load

    /**
     * 搜索按钮点击
     */
    fun searchClick() {
        refresh()
    }

    /**
     * 全选按钮点击 (切换全选状态)
     */
    fun checkAllClick() {
        val list = pageModel.rv?.commonAdapter()?.items as? List<GjcExportLoad> ?: return

        // 切换全选状态
        val shouldCheckAll = !isAllChecked.value!!
        list.forEach { it.checked.set(shouldCheckAll) }
        isAllChecked.value = shouldCheckAll

        pageModel.rv?.commonAdapter()?.notifyDataSetChanged()
    }

    /**
     * 扫码运单号
     */
    fun scanWaybill() {
        ScanModel.startScan(getTopActivity(), Constant.RequestCode.WAYBILL)
    }

    /**
     * 状态重置 (批量操作) — 弹框选状态后调接口
     */
    fun resetDeclare() {
        val list = pageModel.rv?.commonAdapter()?.items as? List<GjcExportLoad> ?: return
        val selectedItems = list.filter { it.isSelected }

        if (selectedItems.isEmpty()) {
            showToast("请选择要重置的记录")
            return
        }

        val dialog = IntExpLoadResetDialogModel { dialogModel ->
            val params = mutableMapOf<String, Any?>(
                "loadList" to selectedItems
            )
            if (dialogModel.resetStatusCode != null) {
                params["restStatus"] = dialogModel.resetStatusCode
            }
            val requestData = params.toRequestBody()

            launchLoadingCollect({ NetApply.api.resetDeclare(requestData) }) {
                onSuccess = {
                    showToast("状态重置成功")
                    viewModelScope.launch {
                        FlowBus.with<String>(ConstantEvent.EVENT_REFRESH).emit("refresh")
                    }
                    refresh()
                }
            }
        }
        dialog.show()
    }

    /**
     * 装载申报 (批量操作)
     */
    fun declareLoad() {
        val list = pageModel.rv?.commonAdapter()?.items as? List<GjcExportLoad> ?: return
        val selectedItems = list.filter { it.isSelected }

        if (selectedItems.isEmpty()) {
            showToast("请选择要申报的记录")
            return
        }

        val param = GjcDeclareParam(loadList = selectedItems)
        val requestData = param.toRequestBody()

        launchLoadingCollect({ NetApply.api.declareLoad(requestData) }) {
            onSuccess = {
                showToast("装载申报成功")
                viewModelScope.launch {
                    FlowBus.with<String>(ConstantEvent.EVENT_REFRESH).emit("refresh")
                }
                refresh()
            }
        }
    }

    /**
     * 删除申报 (批量操作)
     */
    fun deleteLoad() {
        val list = pageModel.rv?.commonAdapter()?.items as? List<GjcExportLoad> ?: return
        val selectedItems = list.filter { it.isSelected }

        if (selectedItems.isEmpty()) {
            showToast("请选择要删除申报的记录")
            return
        }

        // 校验申报状态：只有装载申报状态为 01 的记录才能删除申报
        if (selectedItems.any { it.loadStatus != "01" }) {
            showToast("只能删除申报状态为01的运单")
            return
        }

        // 从接口获取删除原因列表
        launchLoadingCollect({ NetApply.api.getDelReasonList() }) {
            onSuccess = { result ->
                val changeReasonList = result.data?.map { it.toKeyValue() } ?: emptyList()

                // 创建并显示弹框
                val dialog = IntExpLoadDeleteDialogModel(changeReasonList) { dialogModel ->
                    // 弹框确认后的回调
                    val param = GjcDeclareParam(
                        dcode = dialogModel.changeReason.value,
                        dcontactsName = dialogModel.contactName.value,
                        dcontactsTel = dialogModel.contactPhone.value,
                        loadList = selectedItems
                    )

                    val requestData = param.toRequestBody()

                    // 调用删除接口
                    launchLoadingCollect({ NetApply.api.deleteLoadDeclare(requestData) }) {
                        onSuccess = {
                            showToast("删除申报成功")
                            viewModelScope.launch {
                                FlowBus.with<String>(ConstantEvent.EVENT_REFRESH).emit("refresh")
                            }
                            refresh()
                        }
                    }
                }

                dialog.show()
            }
        }
    }

    /**
     * 获取数据 (重写BasePageViewModel)
     */
    override fun getData() {
        // 构建查询参数对象
        val pageParams = GjcCheckInPage(
            fdate = flightDate.value?.ifEmpty { null },
            fno = flightNo.value?.ifEmpty { null },
            wbNo = waybillNo.value?.ifEmpty { null },
            dep = depPort.value?.ifEmpty { null },
            dest = destPort.value?.ifEmpty { null },
            pageNum = pageModel.page,
            pageSize = pageModel.limit
        )

        // 列表参数 (含分页)
        val listParams = pageParams.toRequestBody()

        // 统计参数 (无分页)
        val totalParams = GjcCheckInPage(
            fdate = flightDate.value?.ifEmpty { null },
            fno = flightNo.value?.ifEmpty { null },
            wbNo = waybillNo.value?.ifEmpty { null },
            dep = depPort.value?.ifEmpty { null },
            dest = destPort.value?.ifEmpty { null }
        ).toRequestBody()

        // 获取列表 (带Loading)
        launchLoadingCollect({ NetApply.api.getIntExpLoadList(listParams) }) {
            onSuccess = { pageModel.handleListBean(it) { updateCheckAllStatus() } }
        }

        // 获取统计信息 (后台请求,不阻塞列表)
        launchCollect({ NetApply.api.getIntExpLoadTotal(totalParams) }) {
            onSuccess = { result ->
                val data = result.data
                totalCount.value = (data?.wbNumber ?: 0).toString()
                totalPc.value = (data?.totalPc ?: 0).toString()
                totalWeight.value = (data?.totalWeight ?: 0.0).toString()
            }
        }
    }
}
