package com.xxfc.platform.vehicle.biz;

import com.ace.cache.annotation.Cache;
import com.ace.cache.annotation.CacheClear;
import com.github.wxiaoqi.security.common.biz.BaseBiz;
import com.github.wxiaoqi.security.common.msg.ObjectRestResponse;
import com.google.common.collect.Maps;
import com.xxfc.platform.vehicle.common.CustomIllegalParamException;
import com.xxfc.platform.vehicle.entity.VehicleBookHourInfo;
import com.xxfc.platform.vehicle.mapper.VehicleBookHourInfoMapper;
import com.xxfc.platform.vehicle.pojo.VehicleBookHourInfoDto;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.joda.time.DateTime;
import org.joda.time.format.DateTimeFormat;
import org.joda.time.format.DateTimeFormatter;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Map;

@Slf4j
@Service
public class VehicleBookHourInfoBiz extends BaseBiz<VehicleBookHourInfoMapper, VehicleBookHourInfo> {

    public static final DateTimeFormatter DEFAULT_DATE_TIME_FORMATTER = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss");
    public static final DateTimeFormatter DATE_TIME_FORMATTER = DateTimeFormat.forPattern("yyyy-MM-dd");

    public static  Map<String, Integer>  getPredictableHours(String bookStartDate, String bookEndDate) {
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date startDate = null;
        Date endDate = null;
        try{
            startDate = simpleDateFormat.parse(bookStartDate);
            endDate = simpleDateFormat.parse(bookEndDate);
        }catch (Exception e) {

        }

        //判定时间是否合法
        if (bookStartDate.compareTo(DateTime.now().toString(DEFAULT_DATE_TIME_FORMATTER)) < 0) {
            throw new CustomIllegalParamException("you can only book from today");
        }
        if (bookStartDate.compareTo(bookEndDate) > 0) {
            throw new CustomIllegalParamException("预定开始日期不能大于结束日期！");
        }
        Map<String, Integer> predictableHours = Maps.newHashMap();
        //预定开始小时
        int hour = new DateTime(startDate).hourOfDay().get();
        int endHour = new DateTime(endDate).hourOfDay().get();
        //获取开始天的预定小时
        int startPredictableHour = 0;
        if(hour > 0 ) {
            for (int curentHour = hour; curentHour <= 24; curentHour++) {
                startPredictableHour |= 1 << (curentHour - 1);
            }
        }

        //获取结束天的预定小时
        int endPredictableHour = 0;
        if(endHour > 0) {
            for (int curentHour = 0; curentHour < endHour; curentHour++) {
                endPredictableHour |= 1 << (curentHour);
            }
        }

        predictableHours.put(DateTime.parse(bookStartDate, DEFAULT_DATE_TIME_FORMATTER).toString(DATE_TIME_FORMATTER), startPredictableHour);
        predictableHours.put(DateTime.parse(bookEndDate, DEFAULT_DATE_TIME_FORMATTER).toString(DATE_TIME_FORMATTER), endPredictableHour);
        DateTime startDay = DateTime.parse(DateTime.parse(bookStartDate, DEFAULT_DATE_TIME_FORMATTER).toString(DATE_TIME_FORMATTER), DATE_TIME_FORMATTER);
        DateTime endDay = DateTime.parse(DateTime.parse(bookEndDate, DEFAULT_DATE_TIME_FORMATTER).toString(DATE_TIME_FORMATTER), DATE_TIME_FORMATTER);

        if(endDay.getDayOfMonth() - startDay.getDayOfMonth() >1){ //
            for (DateTime curDate = startDay.plusDays(1); curDate.compareTo(endDay) < 0; curDate = curDate.plusDays(1)) {
                String curDateStr = curDate.toString(DATE_TIME_FORMATTER);
                //全天预定
                predictableHours.put(curDateStr, 16777215);
            }
        }
        return predictableHours;
    }

    public List<VehicleBookHourInfo> selectByVehicleAndDate(VehicleBookHourInfoDto vehicleBookHourInfoDto) {
        return mapper.selectByVehicleAndDate(vehicleBookHourInfoDto);
    }

    @Cache(key = "vehicle.hourInfo")
    public VehicleBookHourInfo selectByVehicleAndId(VehicleBookHourInfoDto vehicleBookHourInfoDto) {
        return mapper.selectByVehicleAndId(vehicleBookHourInfoDto);
    }

    @Cache(key = "vehicle.hourInfo")
    public List<VehicleBookHourInfo> getAll() {
        return mapper.selectAll();
    }

    @Transactional
    @CacheClear(key = "vehicle.hourInfo")
    public ObjectRestResponse save(VehicleBookHourInfoDto vehicleBookHourInfoDto) {
        if(vehicleBookHourInfoDto == null) {
            return ObjectRestResponse.createFailedResult(502, "参数为空");
        }
        List<VehicleBookHourInfo> vehicleBookHourInfos = mapper.selectByVehicleAndDate(vehicleBookHourInfoDto);
        //有数据直接更新
        if(vehicleBookHourInfos.size() >=1) {
            for(VehicleBookHourInfo vehicleBookHourInfo : vehicleBookHourInfos) {
                if(vehicleBookHourInfo.getBookedHour().equals(vehicleBookHourInfoDto.getBookedHour())) {
                    return ObjectRestResponse.createFailedResult(504, "当天时间段已经被预定");
                } else {
                    vehicleBookHourInfo.setBookedHour(vehicleBookHourInfo.getBookedHour() | vehicleBookHourInfoDto.getBookedHour());
                    updateSelectiveByIdRe(vehicleBookHourInfo);
                }
            }
            return ObjectRestResponse.succ();
        }
        //没有数据直接添加
        insertSelectiveRe(vehicleBookHourInfoDto);
        return ObjectRestResponse.succ();
    }

    /**
     * 删除预定车辆小时记录信息
     * @param vehicleId 车辆Id
     * @param dateList  日期列表
     * @return
     */
    @Transactional
    @CacheClear(key = "vehicle.hourInfo")
    public ObjectRestResponse delete(String vehicleId, List<String> dateList) {
            if(StringUtils.isBlank(vehicleId) || dateList.size() <= 0) {
                return ObjectRestResponse.createFailedResult(502, "删除信息车辆Id为空");
            }
            Map<String, Object> param = Maps.newHashMap();
            param.put("vehicleId", vehicleId);
            param.put("list", dateList);
            List<VehicleBookHourInfo> list = mapper.selectByVehicleAndDateList(param);
            list.forEach((a) -> mapper.delete(a));
         return ObjectRestResponse.succ();
    }

    public static void main(String[] args) throws Exception{
        String result = Integer.toBinaryString(16777200);
        String newString = new StringBuilder(result).reverse().toString();
        int i=newString.length()-result.replace("1", "").length();
       System.out.println(i);

        Map<String, Integer> map = getPredictableHours("2019-07-28 00:00:00","2019-07-29 00:00:00");
        for (Map.Entry<String, Integer> entry : map.entrySet()) {
            log.info(entry.getKey());
            log.info(entry.getValue() + "");
        }


    }

}
