package com.testor.module.contractor.manage.controller;

import cn.hutool.core.date.DateUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.testor.common.model.UpdateProcessStatusReq;
import com.testor.common.util.BeanConverUtil;
import com.testor.module.contractor.common.model.constant.ContractorProcessStatus;
import com.testor.module.contractor.ledger.model.domain.TContractorProject;
import com.testor.module.contractor.ledger.model.dto.TContractorLedgerDto;
import com.testor.module.contractor.ledger.service.TContractorLedgerService;
import com.testor.module.contractor.ledger.service.TContractorProjectService;
import com.testor.module.contractor.manage.model.domain.TContractorAllow;
import com.testor.module.contractor.manage.model.domain.TContractorAllowPerson;
import com.testor.module.contractor.manage.model.domain.TContractorPreparation;
import com.testor.module.contractor.manage.model.dto.ContractorPreparationDto;
import com.testor.module.contractor.manage.model.dto.TContractorAllowPersonParam;
import com.testor.module.contractor.manage.model.dto.TContractorPreparationDelParam;
import com.testor.module.contractor.manage.model.dto.TContractorPreparationParam;
import com.testor.module.contractor.manage.service.TContractorAllowPersonService;
import com.testor.module.contractor.manage.service.TContractorAllowService;
import com.testor.module.contractor.manage.service.TContractorPreparationService;
import com.testor.module.sys.service.NewSysOrgService;
import com.tongtech.tfw.backend.common.biz.constants.BizConstants;
import com.tongtech.tfw.backend.common.biz.models.BaseResponse;
import com.tongtech.tfw.backend.common.biz.models.BaseResponseList;
import com.tongtech.tfw.backend.common.biz.models.BizGeneralResponse;
import com.tongtech.tfw.backend.common.context.ContextUtils;
import com.tongtech.tfw.backend.common.models.supers.SuperController;
import com.tongtech.tfw.backend.common.models.sys.UserInfo;
import com.tongtech.tfw.backend.core.helper.IdHelper;
import com.tongtech.tfw.backend.core.helper.ObjectHelper;
import com.tongtech.tfw.backend.core.helper.StringHelper;
import com.tongtech.tfw.backend.core.helper.TypeHelper;
import com.tongtech.tfw.backend.core.helper.bean.BeanHelper;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.List;

/**
 * 开工准备Controller
 *
 * @author testor-framework
 * @date 2024-11-24 13:19:04
 */
@RestController
@RequestMapping("/contractorManage/preparation")
@Api(value = "TContractorPreparation", tags = "开工准备")
@Slf4j
public class TContractorPreparationController extends SuperController {
    @Autowired
    private TContractorPreparationService tContractorPreparationService;

    @Autowired
    private TContractorLedgerService tContractorLedgerService;

    @Autowired
    private TContractorProjectService tContractorProjectService;

    @Autowired
    private TContractorAllowService tContractorAllowService;

    @Autowired
    private TContractorAllowPersonService tContractorAllowPersonService;

    @Autowired
    private NewSysOrgService newSysOrgService;

    /* Generated Method*/
    @ApiOperation(value = "新增 开工准备", notes = "Add TContractorPreparation")
    @PostMapping(value = "/add")
    public BaseResponse<TContractorPreparation> addEntity(@RequestBody TContractorPreparation addRequest) {
        BaseResponse<TContractorPreparation> baseResponse = new BaseResponse<>();
        if (ObjectHelper.isNotEmpty(addRequest)) {
            // TODO 按需求添加数据去重，特殊值设定，业务异常
            String id = IdHelper.getId32bit();
            TContractorPreparation data = BeanHelper.beanToBean(addRequest, TContractorPreparation.class);
            data.setId(id);
            data.setProcessStatus(ContractorProcessStatus.PENDING_SUBMISSION.getValue());
            boolean result = tContractorPreparationService.save(data);
            if (result) {
                TContractorPreparation newEntity = new TContractorPreparation();
                newEntity.setId(id);
                baseResponse.setData(newEntity);
            }
        }
        return baseResponse;
    }

    @ApiOperation(value = "获取 开工准备 ", notes = "Get TContractorPreparation By Id")
    @GetMapping(value = "/get")
    public BaseResponse<ContractorPreparationDto> getById(String id) {
        BaseResponse<ContractorPreparationDto> baseResponse = new BaseResponse<>();
        if (StringHelper.isEmpty(id)) {
            return baseResponse;
        }
        // TODO 按需求添加业务异常判断
        TContractorPreparation data = tContractorPreparationService.getById(id);
        if (data == null) {
            return baseResponse;
        }
        TContractorLedgerDto ledgerDto = tContractorLedgerService.getLedgerById(data.getContractorId());
        TContractorProject project = tContractorProjectService.getById(data.getProjId());
        ContractorPreparationDto dto = BeanConverUtil.conver(data, ContractorPreparationDto.class);
        if (ledgerDto != null && ledgerDto.getTContractorInfo() != null) {
            dto.setContractorName(ledgerDto.getTContractorInfo().getName());
        }
        if (project != null) {
            dto.setProjectName(project.getName());
            if (dto.getPlanStartTime() == null) {
                dto.setPlanStartTime(project.getPlanStartTime());
            }
            if (dto.getPlanEndTime() == null) {
                dto.setPlanEndTime(project.getPlanEndTime());
            }
        }

        baseResponse.setData(dto);
        return baseResponse;
    }

    @ApiOperation(value = "修改 开工准备 ", notes = "Update TContractorPreparation By Id")
    @PutMapping(value = "/update")
    public BaseResponse<BizGeneralResponse> updateEntity(@RequestBody TContractorPreparation updateRequest) {
        BaseResponse<BizGeneralResponse> baseResponse = new BaseResponse<>();
        if (ObjectHelper.isNotEmpty(updateRequest) && StringHelper.isNotEmpty(updateRequest.getId())) {
            // TODO 按需求添加数据去重，特殊值设定，业务异常
            TContractorPreparation data = BeanHelper.beanToBean(updateRequest, TContractorPreparation.class);
            boolean result = tContractorPreparationService.updateById(data);
            baseResponse.setData(
                    BizGeneralResponse.builder().result(TypeHelper.castToString(result)).build());
        }
        return baseResponse;
    }

    @ApiOperation(value = "删除 开工准备 ", notes = "delete TContractorPreparation By Id")
    @PutMapping(value = "/delete")
    public BaseResponse<BizGeneralResponse> deleteEntity(@RequestBody TContractorPreparationDelParam deleteRequest) {
        BaseResponse<BizGeneralResponse> baseResponse = new BaseResponse<>();
        if (ObjectHelper.isNotEmpty(deleteRequest) && StringHelper.isNotEmpty(deleteRequest.getId())) {
            // TODO 按需求添加数据去重，特殊值设定，业务异常
            TContractorPreparation data = new TContractorPreparation();
            data.setId(deleteRequest.getId());
            data.setStatus(BizConstants.STATUS_DELETE);
            boolean result = tContractorPreparationService.updateById(data);
            baseResponse.setData(
                    BizGeneralResponse.builder().result(TypeHelper.castToString(result)).build());
        }
        return baseResponse;
    }

    @ApiOperation(value = "批量删除开工准备", notes = "delete TContractorPreparation by batch Id")
    @PutMapping(value = "/batch_delete")
    public BaseResponse<BizGeneralResponse> deleteEntityBatch(
            @RequestBody TContractorPreparationDelParam deleteRequest) {
        BaseResponse<BizGeneralResponse> baseResponse = new BaseResponse<>();
        if (ObjectHelper.isNotEmpty(deleteRequest) && (!deleteRequest.getIds().isEmpty())) {
            /* 批量删除 */
            List<TContractorPreparation> tContractorPreparationList = new ArrayList<>();
            for (String id : deleteRequest.getIds()) {
                TContractorPreparation data = new TContractorPreparation();
                data.setId(id);
                data.setStatus(BizConstants.STATUS_DELETE);
                tContractorPreparationList.add(data);
            }
            boolean result = tContractorPreparationService.updateBatchById(tContractorPreparationList);
            baseResponse.setData(
                    BizGeneralResponse.builder().result(TypeHelper.castToString(result)).build());
        }
        return baseResponse;
    }

    @ApiOperation(value = "获取 开工准备 分页列表", notes = "List TContractorPreparation with page")
    @GetMapping(value = "/list")
    public BaseResponse<BaseResponseList<ContractorPreparationDto>> listEntity(TContractorPreparationParam param) {
        BaseResponse<BaseResponseList<ContractorPreparationDto>> baseResponse = new BaseResponse<>();
        Page<ContractorPreparationDto> resultList = tContractorPreparationService.pageList(param);
        BaseResponseList<ContractorPreparationDto> baseResponseList = new BaseResponseList<>();
        baseResponseList.setData(resultList.getRecords());
        baseResponseList.setTotal(resultList.getTotal());
        baseResponse.setData(baseResponseList);
        return baseResponse;
    }

    @ApiOperation(value = "获取 开工准备 列表", notes = "List TContractorPreparation all")
    @GetMapping(value = "/datas")
    public BaseResponse<BaseResponseList<TContractorPreparation>> listAllEntity(TContractorPreparationParam param) {
        BaseResponse<BaseResponseList<TContractorPreparation>> baseResponse = new BaseResponse<>();
        // TODO 根据需求修改查询条件及查询参数
        QueryWrapper<TContractorPreparation> queryWrapper = this.createQuery(param);
        List<TContractorPreparation> resultList = tContractorPreparationService.list(queryWrapper);
        BaseResponseList<TContractorPreparation> baseResponseList = new BaseResponseList<>();
        baseResponseList.setData(resultList);
        baseResponseList.setTotal(resultList.size());
        baseResponse.setData(baseResponseList);
        return baseResponse;
    }

    @ApiOperation(value = "更新流程状态", notes = "更新审批流程状态")
    @PostMapping(value = "/updateProcessStatus")
    public BaseResponse updateProcessStatus(@RequestBody UpdateProcessStatusReq updateProcessStatusReq) throws Exception {
        tContractorPreparationService.updateProcessStatus(updateProcessStatusReq);
        return BaseResponse.success();
    }

    @ApiOperation(value = "提交", notes = "启动流程")
    @PostMapping(value = "/submit")
    @Transactional(rollbackFor = Exception.class)
    public BaseResponse<BizGeneralResponse> startProcess(@RequestBody TContractorPreparationParam updateRequest) {
        BaseResponse<BizGeneralResponse> baseResponse = new BaseResponse<>();
        if (ObjectHelper.isNotEmpty(updateRequest) && StringHelper.isNotEmpty(updateRequest.getId())) {
            tContractorPreparationService.startProcess(updateRequest);
        }
        return baseResponse;
    }

    @ApiOperation(value = "完成流程", notes = "启动流程")
    @PostMapping(value = "/completeProcess")
    @Transactional(rollbackFor = Exception.class)
    public BaseResponse<BizGeneralResponse> completeProcess(@RequestBody TContractorPreparationParam updateRequest) {
        BaseResponse<BizGeneralResponse> baseResponse = new BaseResponse<>();
        if (ObjectHelper.isNotEmpty(updateRequest) && StringHelper.isNotEmpty(updateRequest.getId())) {
            tContractorPreparationService.completeProcess(updateRequest);
        }
        return baseResponse;
    }

    @ApiOperation(value = "开工准备-查询准入管理中的人员列表", notes = "查询准入管理中的人员列表")
    @GetMapping(value = "/personList")
    public BaseResponse<BaseResponseList<TContractorAllowPerson>> personList(TContractorPreparationParam param) {
        String contractorId = param.getContractorId();
        String projId = param.getProjId();
        String bizId = param.getBizId();
        TContractorAllow tContractorAllow =
                tContractorAllowService.getOne(new LambdaQueryWrapper<TContractorAllow>().eq(TContractorAllow::getContractorId, contractorId).eq(TContractorAllow::getProjId, projId).eq(TContractorAllow::getBizId, bizId).ne(TContractorAllow::getStatus, BizConstants.STATUS_DELETE), false);

        BaseResponse<BaseResponseList<TContractorAllowPerson>> baseResponse = new BaseResponse<>();
        if (tContractorAllow == null) {
            return baseResponse;
        }
        TContractorAllowPersonParam allowPersonParam = new TContractorAllowPersonParam();
        allowPersonParam.setAllowId(tContractorAllow.getId());
        List<TContractorAllowPerson> resultList = tContractorAllowPersonService.listAllEntity(allowPersonParam);
        BaseResponseList<TContractorAllowPerson> baseResponseList = new BaseResponseList<>();
        baseResponseList.setData(resultList);
        baseResponseList.setTotal(resultList.size());
        baseResponse.setData(baseResponseList);
        return baseResponse;
    }

    /* Private Methods */

    /**
     * 列表查询条件及查询参数
     */
    private QueryWrapper<TContractorPreparation> createQuery(TContractorPreparationParam queryParam) {
        QueryWrapper<TContractorPreparation> queryWrapper = new QueryWrapper<>();
        UserInfo loginUser = ContextUtils.getLoginUser();
        String orgId = loginUser.getOrgId();
        List<String> idsChildrenById = newSysOrgService.getIdsChildrenById(orgId);
        //查询下级机构id
        queryWrapper.in("org_id", idsChildrenById);
        if (StringHelper.isNotEmpty(queryParam.getContractorId())) {
            queryWrapper.eq(TContractorPreparation.CONTRACTOR_ID, queryParam.getContractorId());
        }
        if (StringHelper.isNotEmpty(queryParam.getProjId())) {
            queryWrapper.eq(TContractorPreparation.PROJ_ID, queryParam.getProjId());
        }
        if (StringHelper.isNotEmpty(queryParam.getProcessId())) {
            queryWrapper.eq(TContractorPreparation.PROCESS_ID, queryParam.getProcessId());
        }
        if (StringHelper.isNotEmpty(queryParam.getProcessStatus())) {
            queryWrapper.eq(TContractorPreparation.PROCESS_STATUS, queryParam.getProcessStatus());
        }
        if (StringHelper.isNotEmpty(queryParam.getBizId())) {
            queryWrapper.eq(TContractorPreparation.BIZ_ID, queryParam.getBizId());
        }
        if (StringHelper.isNotEmpty(queryParam.getStatus())) {
            queryWrapper.eq(TContractorPreparation.STATUS, queryParam.getStatus());
        } else {
            queryWrapper.ne(TContractorPreparation.STATUS, BizConstants.STATUS_DELETE);
        }
        if (StringHelper.isNotEmpty(queryParam.getOrderBy())) {
            if (StringHelper.isNotEmpty(queryParam.getOrderType())
                    && BizConstants.ASC.equals(queryParam.getOrderType())) {
                queryWrapper.orderByAsc(queryParam.getOrderBy());
            } else {
                queryWrapper.orderByDesc(queryParam.getOrderBy());
            }
        } else {
            queryWrapper.orderByDesc(TContractorPreparation.UPDATE_DATE);
        }
        return queryWrapper;
    }
}
