package com.steerinfo.ems.mesemsdieseloil.service.impl;

import com.steerinfo.framework.mapper.IBaseMapper;
import com.steerinfo.framework.service.impl.BaseServiceImpl;
import com.steerinfo.ems.mesemsdieseloil.model.MesEmsDieseloil;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.steerinfo.ems.Utils.BigDecimalUtil;
import com.steerinfo.ems.Utils.HttpRequestMes;
import com.steerinfo.ems.formula.service.IFormulaService;
import com.steerinfo.ems.ifmesemsproductorder.model.IfMesEmsProductorder;
import com.steerinfo.ems.mesemsdieseloil.mapper.MesEmsDieseloilMapper;
import com.steerinfo.ems.mesemsdieseloil.service.IMesEmsDieseloilService;
import com.steerinfo.ems.trmactitem.mapper.TRmActItemMapper;
import com.steerinfo.ems.trmactitem.model.TRmActItem;
import com.steerinfo.ems.trmcalpoint.mapper.TRmCalpointMapper;
import com.steerinfo.ems.trmcalpoint.model.TRmCalpoint;
import com.steerinfo.ems.trmcalpointvalue.mapper.TRmCalpointValueMapper;
import com.steerinfo.ems.trmcalpointvalue.model.TRmCalpointValue;
import com.steerinfo.ems.trmcalpointvalue.service.ITRmCalpointValueService;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.text.ParseException;
import java.text.SimpleDateFormat;

/**
 * MesEmsDieseloil服务实现：
 * @author generator
 * @version 1.0-SNAPSHORT 2020-04-08 04:41
 * 类描述
 * 修订历史：
 * 日期：2020-04-08
 * 作者：generator
 * 参考：
 * 描述：MesEmsDieseloil服务实现
 * @see null
 * @Copyright 湖南视拓信息技术股份有限公司. All rights reserved.
 */
@Service(value = "mesEmsDieseloilService")
public class MesEmsDieseloilServiceImpl extends BaseServiceImpl<MesEmsDieseloil, String> implements IMesEmsDieseloilService {
	
	private static final Logger logger = LoggerFactory.getLogger(MesEmsDieseloilServiceImpl.class);

	@Autowired
    private MesEmsDieseloilMapper mesEmsDieseloilMapper;
    
    @Autowired
    private TRmCalpointMapper tRmCalpointMapper;
    
    @Autowired
    private TRmCalpointValueMapper tRmCalpointValueMapper;
    
    @Autowired
    ITRmCalpointValueService tRmCalpointValueService;
    
    @Autowired
    private TRmActItemMapper tRmActItemMapper;
    
    @Autowired
    IFormulaService formulaService;

    @Override
    protected IBaseMapper<MesEmsDieseloil, String> getMapper() {
        return mesEmsDieseloilMapper;
    }

	@Override
	public String synchronousMesEmsData() {
		int addSize = 0;
		int updateSize = 0;
		int errorSize = 0;
		String businessDate = "";
		logger.info("开始同步MES柴油数据");
		String url = "http://172.16.100.91:8093/mes_interface/dieseloildata"; // 柴油数据
		while (true) {
			String res = HttpRequestMes.httpRequestMes(url, "get", null);
			JSONArray ja = JSONArray.parseArray(res);
			if (ja != null && !ja.isEmpty()) {
				logger.info("获取柴油数据条数：" + ja.size());
				businessDate = ((JSONObject) ja.get(0)).getString("businessDate");
				for (int i = 0; i < ja.size(); i++) {
					JSONObject jo = (JSONObject) ja.get(i);
					if(!jo.containsKey("id")){
						errorSize += 1;
						continue;
					}
					MesEmsDieseloil model = new MesEmsDieseloil();
					model.jsonobjectToMesEmsDieseloil(jo);
					if (mesEmsDieseloilMapper.updateByPrimaryKeySelective(model) == 0){
						addSize += mesEmsDieseloilMapper.insert(model);
					}else{
						updateSize +=1;
					}
					HttpRequestMes.httpRequestMes(url, "post", "[{\"id\":\"" + jo.getString("id") + "\",\"state\":\"1\"}]");
				}
			} else {
				break;
			}
		}
		if(!businessDate.isEmpty()){
			// 处理柴油数据到计量点
			this.reCalData(businessDate);
		}
		logger.info("本次总共新增柴油数据条数：" + addSize);
		logger.info("本次总共更新柴油数据条数：" + updateSize);
		logger.info("本次总共错误柴油数据条数：" + errorSize);
        return "本次新增" + addSize + "条,更新" + updateSize + "条,失败" + errorSize + "条。";
	}

	@Override
	public void reCalData(String clock) {
		List<Map<String, Object>> wts = mesEmsDieseloilMapper.getMesEmsDieseloils(clock);
		Map<String, Object> m = new HashMap<String, Object>();
		m.put("useflag", "1");
		m.put("tagTable", "MES_EMS_DIESELOIL");
		// 查询需要统计的计量点信息
		List<TRmCalpoint> l = tRmCalpointMapper.selectCalpoints(m);
		for(TRmCalpoint tRmCalpoint : l){
			String itemid = tRmCalpoint.getItemid();
			String itemname = tRmCalpoint.getItemname();
			String tagCol = tRmCalpoint.getTagCol(); // 对应的factory_code
			BigDecimal mod = tRmCalpoint.getTagModulus() == null? new BigDecimal("1") : tRmCalpoint.getTagModulus(); // 倍率
			Short digits = tRmCalpoint.getDigits() == null ? 3 : tRmCalpoint.getDigits(); // 精度
			// 计算值
            BigDecimal ac = BigDecimal.ZERO;
			for(int i=0;i<wts.size();i++){
				Map<String, Object> mv = wts.get(i);
				if(mv.get("FACTORY_CODE")!=null && mv.get("FACTORY_CODE").toString().equals(tagCol)){
					ac = new BigDecimal(mv.get("WEIGHT").toString()).multiply(mod).setScale(digits, RoundingMode.HALF_UP);
					break;
				}
			}
			HashMap<String, Object> id = new HashMap<String, Object>();
			id.put("clock", clock);
			id.put("timegranid", "MONTH");
			id.put("itemid", itemid);
			// 获取原数据
			TRmCalpointValue t = tRmCalpointValueMapper.selectByPrimaryKey(id);
			if(t!=null){
				t.setActualvalue(ac); // 计算值
				t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
				if(t.getCorrectvalue()!=null){
					t.setApportvalue(ac.add(t.getCorrectvalue()));
				}else{
					t.setApportvalue(ac);
				}
				tRmCalpointValueMapper.updateByPrimaryKeySelective(t);
			}else{
				t = new TRmCalpointValue();
				t.setActualvalue(ac); // 计算值
				t.setClock(clock);
				t.setTimegranid("MONTH");
				t.setItemid(itemid);
				t.setItemname(itemname);
				t.setApportvalue(ac); // 最终值
				t.setCorrectvalue(BigDecimal.ZERO); // 修正值
				t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
				tRmCalpointValueMapper.insertSelective(t);
			}
			// 平摊数据到日粒度
			Date startDay = null; // 计算开始日期
			Date endDay = null; // 计算结束日期
			Date lastDay = null; // 计算最后一天
			try {
				startDay = new SimpleDateFormat("yyyy-MM").parse(clock);
			} catch (ParseException e) {
				e.printStackTrace();
			}
			// 非当月，统计到月底
			Calendar c = Calendar.getInstance();
			c.setTime(startDay);
			c.add(Calendar.MONTH, 1);
			c.add(Calendar.DAY_OF_YEAR, -1);
			lastDay = c.getTime();
			c.add(Calendar.DAY_OF_YEAR, -1);
			endDay  = c.getTime();
			// 这个月的天数
			int n = c.getActualMaximum(Calendar.DAY_OF_MONTH);
			// 日计算值
            BigDecimal avc = BigDecimalUtil.divide(ac.doubleValue(), Double.valueOf(n+""), 5).setScale(digits, RoundingMode.DOWN);
			// 最后一天计算值,总值ac-其他天数据之和
            BigDecimal lavc = ac.subtract(avc.multiply(new BigDecimal((n-1) + ""))).setScale(digits, RoundingMode.HALF_UP);
            while(!startDay.after(endDay)){
				String clk = new SimpleDateFormat("yyyy-MM-dd").format(startDay);
				HashMap<String, Object> did = new HashMap<String, Object>();
				did.put("clock", clk);
				did.put("timegranid", "DAY");
				did.put("itemid", itemid);
				// 获取原数据
				TRmCalpointValue dt = tRmCalpointValueMapper.selectByPrimaryKey(did);
				if(dt!=null){
					dt.setActualvalue(avc); // 计算值
					dt.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
					if(dt.getCorrectvalue()!=null){
						dt.setApportvalue(avc.add(dt.getCorrectvalue()));
					}else{
						dt.setApportvalue(avc);
					}
					tRmCalpointValueMapper.updateByPrimaryKeySelective(dt);
				}else{
					t = new TRmCalpointValue();
					t.setActualvalue(avc); // 计算值
					t.setClock(clk);
					t.setTimegranid("DAY");
					t.setItemid(itemid);
					t.setItemname(itemname);
					t.setApportvalue(avc); // 最终值
					t.setCorrectvalue(BigDecimal.ZERO); // 修正值
					t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
					tRmCalpointValueMapper.insertSelective(t);
				}
				startDay = new Date(startDay.getTime() + 3600*24*1000L);
			}
            // 最后一天
            HashMap<String, Object> did = new HashMap<String, Object>();
			did.put("clock", new SimpleDateFormat("yyyy-MM-dd").format(lastDay));
			did.put("timegranid", "DAY");
			did.put("itemid", itemid);
			TRmCalpointValue dt = tRmCalpointValueMapper.selectByPrimaryKey(did);
			if(dt!=null){
				dt.setActualvalue(lavc); // 计算值
				dt.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
				if(dt.getCorrectvalue()!=null){
					dt.setApportvalue(lavc.add(dt.getCorrectvalue()));
				}else{
					dt.setApportvalue(lavc);
				}
				tRmCalpointValueMapper.updateByPrimaryKeySelective(dt);
			}else{
				t = new TRmCalpointValue();
				t.setActualvalue(lavc); // 计算值
				t.setClock(new SimpleDateFormat("yyyy-MM-dd").format(lastDay));
				t.setTimegranid("DAY");
				t.setItemid(itemid);
				t.setItemname(itemname);
				t.setApportvalue(lavc); // 最终值
				t.setCorrectvalue(BigDecimal.ZERO); // 修正值
				t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
				tRmCalpointValueMapper.insertSelective(t);
			}
			// 年时间粒度处理，不是今年，重新计算年数据
			if(c.get(Calendar.YEAR) <  Calendar.getInstance().get(Calendar.YEAR)){
				String clk = c.get(Calendar.YEAR) + "";
				tRmCalpointValueService.restatCalData(tRmCalpoint, clk, "YEAR", "系统");
			}
		}
		// 生成相关实绩数据
		HashMap<String, Object> parmas = new HashMap<String, Object>();
		parmas.put("mintimegranid", "DAY");
		parmas.put("energyid", "'X014'");
		// 查询需要统计的计量点信息
		List<TRmActItem> rl = tRmActItemMapper.selectActr(parmas);
		String clocke = "";
		try {
			Date bd = new SimpleDateFormat("yyyy-MM-dd").parse(clock+"-01");
			Calendar cal = Calendar.getInstance();
			cal.setTime(bd);
			cal.add(Calendar.MONTH, 1);
			cal.add(Calendar.DAY_OF_MONTH, -1);
			clocke = new SimpleDateFormat("yyyy-MM-dd").format(cal.getTime());
		} catch (ParseException e) {
			logger.error("businessDate格式错误：" + clock);
			e.printStackTrace();
		}
		for(int i = 0; i<rl.size(); i++){
			TRmActItem t = rl.get(i);
			formulaService.reItemVal(t.getItemid(),clock+"-01","DAY",clocke);
		}
	}

	@Override
	public String synchronousMesFromProd(Date d) {
		Calendar calendar = Calendar.getInstance();
		calendar.setTime(d);
		calendar.add(Calendar.MONTH, -1); // 减1月获得上月
		String clock = new SimpleDateFormat("yyyy-MM").format(calendar.getTime());
		String url = "http://ems.sxzygc.com.cn/zhongsteel.pass.web/pass/ems/v1/mesemsdieseloils/?pageNum=1&pageSize=2000&businessDate=" + clock; // 柴油月数据
		String res = HttpRequestMes.httpRequestMes(url, "get", null);
		JSONObject jo = JSONObject.parseObject(res);
		boolean reCalData = false;
		if (jo != null && !jo.isEmpty() && jo.getString("code").equals("0")){
			JSONObject jo2 = (JSONObject)jo.get("data");
			JSONArray ja = (JSONArray)jo2.get("list");
			if (ja != null && !ja.isEmpty()) {
				for (int i = 0; i < ja.size(); i++) {
					JSONObject jo3 = (JSONObject) ja.get(i);
					if(mesEmsDieseloilMapper.selectByPrimaryKey(jo3.getString("id"))==null){
						reCalData = true;
						MesEmsDieseloil model = new MesEmsDieseloil();
						model.setId(jo3.getString("id"));
						model.setFactoryCode(jo3.getString("factoryCode"));
						model.setFactoryName(jo3.getString("factoryName"));
						model.setMaterialcode(jo3.getString("materialcode"));
						model.setMaterialname(jo3.getString("materialname"));
						model.setMaterialspec(jo3.getString("materialspec"));
						model.setBusinessDate(jo3.getString("businessDate"));
						model.setVolume(jo3.getBigDecimal("volume"));
						model.setWeight(jo3.getBigDecimal("weight"));
						model.setState(jo3.getString("state"));
						model.setUnit(jo3.getString("unit"));
						mesEmsDieseloilMapper.insert(model);
					}
				}
			}
		}
		if(reCalData){
			// 处理柴油数据到计量点
			this.reCalData(clock);
		}
		logger.info("从正式环境同步MES柴油数据--执行完毕--");
		return null;
	}

	@Override
	public void reCalData2(String clock, TRmCalpoint tRmCalpoint) {
		List<Map<String, Object>> wts = mesEmsDieseloilMapper.getMesEmsDieseloils(clock);
		if(tRmCalpoint.getUseflag()==null || !tRmCalpoint.getUseflag().equals("1")){
			return;
		}
		if(tRmCalpoint.getTagTable()==null || !tRmCalpoint.getTagTable().equalsIgnoreCase("MES_EMS_DIESELOIL")){
			return;
		}
		if(tRmCalpoint.getTagCol()==null || tRmCalpoint.getTagCol().isEmpty()){
			return;
		}
		String itemid = tRmCalpoint.getItemid();
		String itemname = tRmCalpoint.getItemname();
		String tagCol = tRmCalpoint.getTagCol(); // 对应的factory_code
		BigDecimal mod = tRmCalpoint.getTagModulus() == null? new BigDecimal("1") : tRmCalpoint.getTagModulus(); // 倍率
		Short digits = tRmCalpoint.getDigits() == null ? 3 : tRmCalpoint.getDigits(); // 精度
		// 计算值
        BigDecimal ac = BigDecimal.ZERO;
		for(int i=0;i<wts.size();i++){
			Map<String, Object> mv = wts.get(i);
			if(mv.get("FACTORY_CODE")!=null && mv.get("FACTORY_CODE").toString().equals(tagCol)){
				ac = new BigDecimal(mv.get("WEIGHT").toString()).multiply(mod).setScale(digits, RoundingMode.HALF_UP);
				break;
			}
		}
		clock = clock.length()>7?clock.substring(0, 7):clock;
		HashMap<String, Object> id = new HashMap<String, Object>();
		id.put("clock", clock);
		id.put("timegranid", "MONTH");
		id.put("itemid", itemid);
		// 获取原数据
		TRmCalpointValue t = tRmCalpointValueMapper.selectByPrimaryKey(id);
		if(t!=null){
			t.setActualvalue(ac); // 计算值
			t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
			if(t.getCorrectvalue()!=null){
				t.setApportvalue(ac.add(t.getCorrectvalue()));
			}else{
				t.setApportvalue(ac);
			}
			tRmCalpointValueMapper.updateByPrimaryKeySelective(t);
		}else{
			t = new TRmCalpointValue();
			t.setActualvalue(ac); // 计算值
			t.setClock(clock);
			t.setTimegranid("MONTH");
			t.setItemid(itemid);
			t.setItemname(itemname);
			t.setApportvalue(ac); // 最终值
			t.setCorrectvalue(BigDecimal.ZERO); // 修正值
			t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
			tRmCalpointValueMapper.insertSelective(t);
		}
		// 平摊数据到日粒度
		Date startDay = null; // 计算开始日期
		Date endDay = null; // 计算结束日期
		Date lastDay = null; // 计算最后一天
		try {
			startDay = new SimpleDateFormat("yyyy-MM").parse(clock);
		} catch (ParseException e) {
			e.printStackTrace();
		}
		// 非当月，统计到月底
		Calendar c = Calendar.getInstance();
		c.setTime(startDay);
		c.add(Calendar.MONTH, 1);
		c.add(Calendar.DAY_OF_YEAR, -1);
		lastDay = c.getTime();
		c.add(Calendar.DAY_OF_YEAR, -1);
		endDay  = c.getTime();
		// 这个月的天数
		int n = c.getActualMaximum(Calendar.DAY_OF_MONTH);
		// 日计算值
        BigDecimal avc = BigDecimalUtil.divide(ac.doubleValue(), Double.valueOf(n+""), 5).setScale(digits, RoundingMode.DOWN);
		// 最后一天计算值,总值ac-其他天数据之和
        BigDecimal lavc = ac.subtract(avc.multiply(new BigDecimal((n-1) + ""))).setScale(digits, RoundingMode.HALF_UP);
        while(!startDay.after(endDay)){
			String clk = new SimpleDateFormat("yyyy-MM-dd").format(startDay);
			HashMap<String, Object> did = new HashMap<String, Object>();
			did.put("clock", clk);
			did.put("timegranid", "DAY");
			did.put("itemid", itemid);
			// 获取原数据
			TRmCalpointValue dt = tRmCalpointValueMapper.selectByPrimaryKey(did);
			if(dt!=null){
				dt.setActualvalue(avc); // 计算值
				dt.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
				if(dt.getCorrectvalue()!=null){
					dt.setApportvalue(avc.add(dt.getCorrectvalue()));
				}else{
					dt.setApportvalue(avc);
				}
				tRmCalpointValueMapper.updateByPrimaryKeySelective(dt);
			}else{
				t = new TRmCalpointValue();
				t.setActualvalue(avc); // 计算值
				t.setClock(clk);
				t.setTimegranid("DAY");
				t.setItemid(itemid);
				t.setItemname(itemname);
				t.setApportvalue(avc); // 最终值
				t.setCorrectvalue(BigDecimal.ZERO); // 修正值
				t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
				tRmCalpointValueMapper.insertSelective(t);
			}
			startDay = new Date(startDay.getTime() + 3600*24*1000L);
		}
        // 最后一天
        HashMap<String, Object> did = new HashMap<String, Object>();
		did.put("clock", new SimpleDateFormat("yyyy-MM-dd").format(lastDay));
		did.put("timegranid", "DAY");
		did.put("itemid", itemid);
		TRmCalpointValue dt = tRmCalpointValueMapper.selectByPrimaryKey(did);
		if(dt!=null){
			dt.setActualvalue(lavc); // 计算值
			dt.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
			if(dt.getCorrectvalue()!=null){
				dt.setApportvalue(lavc.add(dt.getCorrectvalue()));
			}else{
				dt.setApportvalue(lavc);
			}
			tRmCalpointValueMapper.updateByPrimaryKeySelective(dt);
		}else{
			t = new TRmCalpointValue();
			t.setActualvalue(lavc); // 计算值
			t.setClock(new SimpleDateFormat("yyyy-MM-dd").format(lastDay));
			t.setTimegranid("DAY");
			t.setItemid(itemid);
			t.setItemname(itemname);
			t.setApportvalue(lavc); // 最终值
			t.setCorrectvalue(BigDecimal.ZERO); // 修正值
			t.setRecTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
			tRmCalpointValueMapper.insertSelective(t);
		}
		// 年时间粒度处理，不是今年，重新计算年数据
		if(c.get(Calendar.YEAR) <  Calendar.getInstance().get(Calendar.YEAR)){
			String clk = c.get(Calendar.YEAR) + "";
			tRmCalpointValueService.restatCalData(tRmCalpoint, clk, "YEAR", "系统");
		}
		
	}
}
