package cn.wise.sc.energy.power.plant.business.service.impl;

import cn.hutool.core.util.StrUtil;
import cn.wise.sc.energy.power.plant.business.bean.DataPower;
import cn.wise.sc.energy.power.plant.business.domain.CharacterParamInfo;
import cn.wise.sc.energy.power.plant.business.domain.DeviceInfo;
import cn.wise.sc.energy.power.plant.business.domain.PlantInfo;
import cn.wise.sc.energy.power.plant.business.domain.vo.CharacterParamInfoVo;
import cn.wise.sc.energy.power.plant.business.opentsdb.OpentsdbOkHttpClient;
import cn.wise.sc.energy.power.plant.business.opentsdb.bean.QueryExt;
import cn.wise.sc.energy.power.plant.business.opentsdb.bean.QueryRequestExt;
import cn.wise.sc.energy.power.plant.business.repository.DeviceInfoRepository;
import cn.wise.sc.energy.power.plant.business.service.ICharacterParamService;
import cn.wise.sc.energy.power.plant.business.service.IPlantInfoService;
import cn.wise.sc.energy.power.plant.common.core.bean.BaseResponse;
import cn.wise.sc.energy.power.plant.common.core.exception.ResponseEnum;
import com.alibaba.fastjson.JSON;
import lombok.Data;
import net.opentsdb.client.api.query.request.QueryLastRequest;
import net.opentsdb.client.api.query.response.QueryLastResponse;
import net.opentsdb.client.api.query.response.QueryResponse;
import net.opentsdb.client.bean.Aggregator;
import net.opentsdb.client.bean.LastDataPoint;
import net.opentsdb.client.bean.LastDataPointQuery;
import net.opentsdb.client.bean.QueryResult;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import java.io.IOException;
import java.net.URISyntaxException;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;

/**
 * @description: 电厂信息服务层实现
 * @author: qh
 * @create: 2020-07-14 16:38
 **/
@Service
public class PlantInfoServiceImpl extends BaseServiceImpl<String, PlantInfo> implements IPlantInfoService {

    final
    DeviceInfoRepository deviceInfoRepository;
    final
    ICharacterParamService iCharacterParamService;

    public PlantInfoServiceImpl(DeviceInfoRepository deviceInfoRepository,
                                ICharacterParamService iCharacterParamService) {
        this.deviceInfoRepository = deviceInfoRepository;
        this.iCharacterParamService = iCharacterParamService;
    }

    @Override
    public BaseResponse<Double> getTotalPower(String plantId) {

        List<DeviceInfo> deviceInfos = deviceInfoRepository.findAll((root, query, criteriaBuilder) -> criteriaBuilder.equal(root.get("plantId"), plantId));
        if (deviceInfos.size() == 0) {
            return BaseResponse.okData(10D);
        } else {
            //设备不为空
            double totalPower = 0D;
            for (DeviceInfo deviceInfo : deviceInfos) {
                ResponseEnum.LICENCE_NOT_FOUND.assertNotEmpty(deviceInfo.getDeviceParam());
                DeviceParam deviceParam = JSON.parseObject(deviceInfo.getDeviceParam(), DeviceParam.class);
                ResponseEnum.LICENCE_NOT_FOUND.assertNotEmpty(deviceParam.getRatepower());
                double power = Double.parseDouble(deviceParam.getRatepower().replace("MW", ""));
                totalPower += power;
            }
            return BaseResponse.okData(totalPower);
        }
    }

    public void a() {
        System.out.println("调用service");
    }

    @Override
    public DataPower getInitPower(String plantId, String deviceId) {

        ResponseEnum.LICENCE_NOT_FOUND.assertNotEmpty(plantId);

        if (StrUtil.isBlank(deviceId)) {
            deviceId = "";
        }

        List<String> cpName = new ArrayList<>(1);
        cpName.add("有功功率");
        List<CharacterParamInfoVo> characterParamInfoVos = iCharacterParamService
                .getCharacterByName(cpName, plantId, deviceId);
        try {
            //获取最后一个时间点
            Long lastTime = OpentsdbOkHttpClient.queryLast(characterParamInfoVos);
            if(lastTime==0){
                lastTime = System.currentTimeMillis();
            }
            //判断并获取最后一个时间点 1天前,每5min一个点
            QueryRequestExt queryRequestExt = QueryRequestExt.builder()
                    .start((lastTime - 1 * 24 * 3600 * 1000) + "")
                    .end(lastTime + "")
                    .build();
            for (CharacterParamInfoVo characterParamInfo : characterParamInfoVos) {
                QueryExt build = QueryExt.builder()
                        .aggregator(Aggregator.AVG)
                        .downsample("5m-max-zero")
                        .metric(characterParamInfo.getKksCode())
                        .build();
                queryRequestExt.addQuery(build);
            }
            QueryResponse response;

            response = OpentsdbOkHttpClient.query(queryRequestExt);
            if (response.getResults().size() == 0) {
                return null;
            }
            return buildDataPower(characterParamInfoVos, response);
        } catch (IOException e) {
            e.printStackTrace();
        } catch (URISyntaxException e) {
            e.printStackTrace();
        }
        return null;
    }

    private DataPower buildDataPower(List<CharacterParamInfoVo> characterParamInfos,
                                     QueryResponse response) {

        DataPower rts = new DataPower();
        List<Object> times = rts.getXAxis();
        List<QueryResult> results = response.getResults();
        //添加时间轴
        if (results.size() > 0) {
            times.addAll(results.get(0).getDps().keySet());
        }
        //关联kksCode和名字
        for (QueryResult queryResult : results) {
            Optional<CharacterParamInfoVo> first = characterParamInfos.stream()
                    .filter(arg -> arg.getKksCode().equals(queryResult.getMetric()))
                    .findFirst();
            if (!first.isPresent()) {
                continue;
            }
            String cpName = first.get().getCpName();
            DataPower.PowerPoints powerPoints = new DataPower.PowerPoints();
            powerPoints.setKksCode(queryResult.getMetric());
            powerPoints.setName(cpName);
            queryResult.getDps().keySet().forEach(arg -> {
                Number number = queryResult.getDps().get(arg);
                powerPoints.getValue().add(number + "");
            });
            rts.getDataList().add(powerPoints);
        }
        return rts;
    }


    @Data
    public static class DeviceParam {

        private String ratepower;

        private String raterpm;
    }
}
