package com.ningdatech.carapi.car.equipment.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.http.HttpStatus;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.google.common.collect.Maps;
import com.ningdatech.basic.exception.BaseUncheckedException;
import com.ningdatech.basic.exception.BizException;
import com.ningdatech.basic.exception.code.ExceptionCode;
import com.ningdatech.carapi.car.equipment.model.dto.EquipmentSaveDTO;
import com.ningdatech.carapi.car.equipment.model.dto.EquipmentUpdateDTO;
import com.ningdatech.carapi.car.equipment.model.res.SipApiResponse;
import com.ningdatech.carapi.car.equipment.model.res.SipEquipmentRes;
import com.ningdatech.carapi.car.position.contants.PositionContant;
import com.ningdatech.carapi.car.vehicle.model.NdVehicleBaseInfo;
import com.ningdatech.carapi.car.equipment.model.NdVehicleEquipmentChannels;
import com.ningdatech.carapi.car.equipment.model.NdVehicleEquipmentInfo;
import com.ningdatech.carapi.archives.enums.AuditStateEnum;
import com.ningdatech.carapi.car.equipment.mapper.NdVehicleEquipmentChannelsMapper;
import com.ningdatech.carapi.car.equipment.mapper.NdVehicleEquipmentInfoMapper;
import com.ningdatech.carapi.car.vehicle.mapper.VehicleBaseInfoMapper;
import com.ningdatech.carapi.car.equipment.service.INdVehicleEquipmentInfoService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.client.RestTemplate;

import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Objects;

/**
 * <p>
 *  服务实现类
 * </p>
 *
 * @author PoffyZhang
 * @since 2022-10-12
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class NdVehicleEquipmentInfoServiceImpl extends ServiceImpl<NdVehicleEquipmentInfoMapper, NdVehicleEquipmentInfo> implements INdVehicleEquipmentInfoService {

    private final NdVehicleEquipmentChannelsMapper equipmentChannelsMapper;
    private final VehicleBaseInfoMapper vehicleBaseInfoMapper;

    private final NdVehicleEquipmentInfoMapper equipmentInfoMapper;

    private final RestTemplate restTemplate;

    @Value("${vedio.host}")
    private String HOST;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean removeByIdWithCache(List<Long> ids) {
        if (ids.isEmpty()) {
            return true;
        }
        // 车辆设备
        boolean removeFlag = removeByIds(ids);

        if(removeFlag){
            ids.forEach(id -> {
                //删除通道信息
                equipmentChannelsMapper.delete(Wrappers.lambdaQuery(NdVehicleEquipmentChannels.class)
                        .eq(NdVehicleEquipmentChannels::getEquipmentId,id));
            });
        }

        return removeFlag;
    }

    @Override
    public List<SipEquipmentRes> getSipEquipmentsByCarPlate(String carPlate) {
        SipApiResponse res = null;
        Map<String, Object> map = Maps.newConcurrentMap();
        map.put(PositionContant.FIELD_CAR_PLATE, carPlate);
        map.put(PositionContant.HOST_FEILD, HOST);
        res = restTemplate.getForObject(PositionContant.VEHICLE_DEVICE_URL, SipApiResponse.class, map);
        log.info("request equipment 【{}】:", JSON.toJSONString(res));
        Integer statusCode = res.getStatus_code();
        if (null == statusCode || 0 != statusCode) {
            return Collections.emptyList();
//            throw new BizException(ExceptionCode.BAD_REQUEST.getCode(), res.getMessage());
        }
        return res.getResult();
    }

    @Override
    public Boolean insertBatch(List<NdVehicleEquipmentInfo> toAddEp) {
        return equipmentInfoMapper.insertBatch(toAddEp);
    }


    /**
     * 保存车辆
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void save(List<EquipmentSaveDTO> datas, Long userId) {
        if(CollUtil.isEmpty(datas)){
            return;
        }

        Long vehicleId = datas.get(0).getVehicleId();
        List<NdVehicleEquipmentInfo> equipments = equipmentInfoMapper.selectList(Wrappers.lambdaQuery(NdVehicleEquipmentInfo.class)
                .eq(NdVehicleEquipmentInfo::getVehicleId,vehicleId));
        for(NdVehicleEquipmentInfo equipment : equipments){
            //先删除设备和通道信息
            removeById(equipment.getId());
            equipmentChannelsMapper.delete(Wrappers.lambdaQuery(NdVehicleEquipmentChannels.class)
                    .eq(NdVehicleEquipmentChannels::getEquipmentId,equipment.getId()));
        }

        for(EquipmentSaveDTO data : datas){
            if(Objects.isNull(data.getVehicleId())){
                throw new BizException(ExceptionCode.OPERATION_EX.getCode(),String.format("添加车辆id %d 为空",data.getVehicleId()));
            }
            NdVehicleBaseInfo vehicleBaseInfo = vehicleBaseInfoMapper.selectById(data.getVehicleId());
            if(Objects.isNull(vehicleBaseInfo)){
                throw new BaseUncheckedException(HttpStatus.HTTP_OK,String.format("车辆不存在",data.getVehicleId()));
            }
            if(!AuditStateEnum.AUDIT_SUCCESS.getCode().equals(vehicleBaseInfo.getAuditState())){
                throw new BaseUncheckedException(HttpStatus.HTTP_OK,String.format("车辆审核成功才能添加设备",data.getVehicleId()));
            }

            NdVehicleEquipmentInfo equipmentInfo = BeanUtil.toBean(data, NdVehicleEquipmentInfo.class);
            equipmentInfo.setCarPlate(vehicleBaseInfo.getCarPlate());
            //创建人 最后修改人
            equipmentInfo.setCreateBy(userId);
            equipmentInfo.setUpdateBy(userId);
            save(equipmentInfo);

            if(CollUtil.isNotEmpty(data.getChannels())){
                data.getChannels().forEach(channel ->{
                    NdVehicleEquipmentChannels equipmentChannel = BeanUtil.toBean(channel, NdVehicleEquipmentChannels.class);
                    equipmentChannel.setEquipmentId(equipmentInfo.getId());
                    equipmentChannel.setCreateBy(userId);
                    equipmentChannel.setUpdateBy(userId);
                    equipmentChannelsMapper.insert(equipmentChannel);
                });
            }
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void update(EquipmentUpdateDTO data, Long userId) {
        NdVehicleEquipmentInfo equipmentInfo = getById(data.getId());
        if (Objects.isNull(equipmentInfo)) {
            throw new BaseUncheckedException(HttpStatus.HTTP_OK, String.format("修改车辆设备%d 为空", data.getId()));
        }
        NdVehicleBaseInfo vehicleBaseInfo = vehicleBaseInfoMapper.selectById(data.getVehicleId());
        if (Objects.isNull(vehicleBaseInfo)) {
            throw new BaseUncheckedException(HttpStatus.HTTP_OK, String.format("车辆不存在", data.getVehicleId()));
        }
        if (!AuditStateEnum.AUDIT_SUCCESS.getCode().equals(vehicleBaseInfo.getAuditState())) {
            throw new BaseUncheckedException(HttpStatus.HTTP_OK, String.format("车辆审核成功才能修改设备", data.getVehicleId()));
        }
        NdVehicleEquipmentInfo equipment = BeanUtil.toBean(data, NdVehicleEquipmentInfo.class);
        //最后修改人
        equipment.setUpdateBy(userId);
        updateById(equipment);

        if (CollUtil.isNotEmpty(data.getChannels())) {
            //先删除通道信息
            equipmentChannelsMapper.delete(Wrappers.lambdaQuery(NdVehicleEquipmentChannels.class)
                    .eq(NdVehicleEquipmentChannels::getEquipmentId, equipmentInfo.getId()));
            data.getChannels().forEach(channel -> {
                channel.setEquipmentId(equipmentInfo.getId());
                channel.setCreateBy(userId);
                channel.setUpdateBy(userId);
                equipmentChannelsMapper.insert(channel);
            });
        }
    }
}
