package com.ffii.fpsms.modules.qc.service

import com.ffii.core.support.AbstractBaseEntityService
import com.ffii.core.support.JdbcDao
import com.ffii.fpsms.modules.master.entity.ItemsRepository
import com.ffii.fpsms.modules.master.entity.QcItemRepository
import com.ffii.fpsms.modules.master.web.models.MessageResponse
import com.ffii.fpsms.modules.purchaseOrder.entity.PurchaseOrderLineRepository
import com.ffii.fpsms.modules.qc.entity.QcResult
import com.ffii.fpsms.modules.qc.entity.QcResultRepository
import com.ffii.fpsms.modules.qc.entity.projection.QcResultInfo
import com.ffii.fpsms.modules.qc.web.model.SaveQcResultRequest
import com.ffii.fpsms.modules.stock.entity.StockInLine
import com.ffii.fpsms.modules.stock.entity.StockInLineRepository
import com.ffii.fpsms.modules.stock.entity.StockOutLIneRepository
import org.springframework.stereotype.Service
import org.springframework.transaction.annotation.Transactional
import java.io.IOException

@Service
open class QcResultService(
    private val jdbcDao: JdbcDao,
    private val qcResultRepository: QcResultRepository,
    private val qcItemRepository: QcItemRepository,
    private val itemRepository: ItemsRepository,
    private val stockInLineRepository: StockInLineRepository,
    private val stockOutLIneRepository: StockOutLIneRepository,
): AbstractBaseEntityService<QcResult, Long, QcResultRepository>(jdbcDao, qcResultRepository) {
    @Throws(IOException::class)
    @Transactional
    open fun createOrUpdate(request: SaveQcResultRequest): MessageResponse {
        val qcResult = if (request.id != null) qcResultRepository.findById(request.id).orElseThrow() else QcResult()
        val qcItem = qcItemRepository.findById(request.qcItemId).orElseThrow()
        val item = itemRepository.findById(request.itemId).orElseThrow()
        val stockInLine = if (request.stockInLineId != null) stockInLineRepository.findById(request.stockInLineId).orElseThrow() else null
        val stockOutLine = if (request.stockOutLineId != null) stockOutLIneRepository.findById(request.stockOutLineId).orElseThrow() else null

        qcResult.apply {
            this.qcItem = qcItem
            this.item = item
            this.stockInLine = stockInLine
            this.stockOutLine = stockOutLine
            this.failQty = request.failQty
            this.type = request.type
            this.remarks = request.remarks
        }
        val savedQcResult = saveAndFlush(qcResult)
        return MessageResponse(
            id = savedQcResult.id,
            name = savedQcResult.qcItem!!.name,
            code = savedQcResult.qcItem!!.code,
            type = savedQcResult.type,
            message = null,
            errorPosition = null
        )
    }

    fun getAllQcResultInfoByStockInLineId(stockInLineId: Long): List<QcResultInfo> {
        return qcResultRepository.findAllQcResultInfoByStockInLineIdAndDeletedFalse(stockInLineId)
    }
}