/*
**20220507 LJH 提交申请到备品出库时长 历史数据处理
**SFDC-CC6CLJ phase5上线课题131 提交申请到备品出库时长
** ApplyToShipmentWorkTimeHDBatchTest
*/
global class rentalApplyToShipmentWorkTimeHDBatch implements Database.Batchable<sObject> {
    public String query;
    public String sId;
    global rentalApplyToShipmentWorkTimeHDBatch() {
        this.query = query;
    }
    global rentalApplyToShipmentWorkTimeHDBatch(String sId) {
        this.query = query;
        this.sId = sId;
    }

    global Database.QueryLocator start(Database.BatchableContext bc) {

        HistoryData__mdt hData = [SELECT DatetimeStart__c,DatetimeEnd__c  FROM HistoryData__mdt  limit 1];        
        Datetime startT = hData.DatetimeStart__c;
        Datetime endT = hData.DatetimeEnd__c;
        query = 'select id,name,Rental_Apply__c';
        query += ' , Rental_Apply__r.Request_approval_time__c ,Shippment_loaner_time__c,Add_Request_approval_time__c ';
        query += ' from Rental_Apply_Equipment_Set_Detail__c ';
        query += ' where ApplyToShipmentWorkTime__c = NULL ';
        query += ' AND Shippment_loaner_time__c != NULL';
        if(startT != null){
            query += ' AND Rental_Apply__r.Request_approval_time__c >= :startT ';
        }
        if(endT != null){
            query += ' AND Rental_Apply__r.Request_approval_time__c < :endT ';
        }
        
        if(String.isNotBlank(sId)){
           query += ' AND Id = :sId '; 
        }
        query += 'order by Rental_Apply__c';
        System.debug('query'+query);
        return Database.getQueryLocator(query);
    }

    global void execute(Database.BatchableContext BC, list<Rental_Apply_Equipment_Set_Detail__c> eList) {
        system.debug('进来了');
        Map<String, List<Rental_Apply_Equipment_Set_Detail__c>> approvalMap = new Map<String, List<Rental_Apply_Equipment_Set_Detail__c>>();// 20220315 ljh SFDC-CC6CLJ phase5上线课题131 提交申请到备品出库时长
        //循环获取1.最大和最小时间 2.MAP<开始和结束时间,明细list>
        Datetime minStartDt;
        Datetime maxEndDt;
        for (Rental_Apply_Equipment_Set_Detail__c esd : eList) {
            Datetime keyStartDt = esd.Add_Request_approval_time__c != null?esd.Add_Request_approval_time__c:esd.Rental_Apply__r.Request_approval_time__c;
            Datetime keyEndDt = esd.Shippment_loaner_time__c;
            if(minStartDt != null){
                if(minStartDt > keyStartDt){
                    minStartDt = keyStartDt;
                }
            }else{
                minStartDt = keyStartDt;
            }
            if(maxEndDt != null){
                if(keyEndDt > maxEndDt){
                    maxEndDt = keyEndDt;
                }
            }else{
                maxEndDt = keyEndDt;
            }
            List<Rental_Apply_Equipment_Set_Detail__c> tempRaesdL;
            String key = keyStartDt.getTime()+';'+keyEndDt.getTime();
            if(approvalMap.containsKey(key)){
                tempRaesdL = approvalMap.get(key);
            }else{
                tempRaesdL = new List<Rental_Apply_Equipment_Set_Detail__c>();
            }
            tempRaesdL.add(esd);                        
            approvalMap.put(key,tempRaesdL);
        }
        map<String,Decimal> ApplyToShipmentMap = new map<String,Decimal>();
        if(approvalMap.size() > 0 ){
            List<String> dtList = new List<String>(approvalMap.keySet());
            List<OlympusCalendar__c> ocList = [SELECT Id, Date__c,IsWorkDay__c 
                             FROM OlympusCalendar__c
                            WHERE Date__c >= :minStartDt.date()
                              AND Date__c <= :maxEndDt.date()
                            ORDER BY Date__c ASC];
            Map<Date,String> ocMap = new Map<Date,String>();
            for(OlympusCalendar__c oc:ocList){
                String IsWorkDay = oc.IsWorkDay__c.format();
                ocMap.put(oc.Date__c,IsWorkDay);
            }              
            for(String dt:dtList){
                Boolean startFlag = false;
                Boolean endFlag = false;
                Long startDateL =  Long.valueOf(dt.split(';')[0]);
                Long endTimeL = Long.valueOf(dt.split(';')[1]);
                Datetime startTime = DateTime.newInstance(startDateL);
                Date startDate = Date.newInstance(startTime.year(),startTime.month(),startTime.day());
                Datetime endTime = DateTime.newInstance(endTimeL);
                Date endDate = Date.newInstance(endTime.year(),endTime.month(),endTime.day());
                // 审批时间是非奥林巴斯工作日  
                if(ocMap.get(startDate) == '0'){
                    for(OlympusCalendar__c oc:ocList){
                        if( startDate < oc.Date__c && oc.IsWorkDay__c == 1){
                            startTime = Datetime.newInstance(oc.Date__c.year(),oc.Date__c.month(),oc.Date__c.day(),0,0,0);
                            startDate = oc.Date__c;
                            startFlag = true;
                            break;
                        }
                    }
                }
                // 发货时间是非奥林巴斯工作日
                if(ocMap.get(endDate) == '0'){
                    for(Integer i = ocList.size() - 1; i >= 0;i--){
                        if(endDate > ocList[i].Date__c && ocList[i].IsWorkDay__c == 1){
                            endTime = Datetime.newInstance(ocList[i].Date__c.addDays(1).year(),ocList[i].Date__c.addDays(1).month(),ocList[i].Date__c.addDays(1).day(),0,0,0);
                            endDate = ocList[i].Date__c.addDays(1);
                            endFlag = true;
                            break;
                        }
                    }
                }
                Decimal timeDifLast;
                if(ocList[0].IsWorkDay__c == 0 && ocList[ocList.size() - 1].IsWorkDay__c == 0 && !startFlag && !endFlag){
                    timeDifLast = 0;
                }else{
                    Long startL = startTime.getTime();
                    Long tendL = endTime.getTime();
                    Long timeDif = tendL - startL;                            
                    Decimal time11 = timeDif*1.00;
                    Decimal time12 = 24*3600*1000*1.00;
                    timeDifLast = time11/time12;                            
                    Integer tempWeek = 0;
                    for(OlympusCalendar__c oc:ocList){
                        if(oc.IsWorkDay__c == 0 && startDate < oc.Date__c && oc.Date__c < endDate){
                            tempWeek++;
                        }
                    }
                    timeDifLast = timeDifLast - tempWeek;
                }
                // dtestLast 四舍五入 保留1位小数
                for(Rental_Apply_Equipment_Set_Detail__c raesd00:approvalMap.get(dt)){
                    ApplyToShipmentMap.put(raesd00.Id,timeDifLast.setScale(1));
                }
            }
        }
        List<Rental_Apply_Equipment_Set_Detail__c> upeList = new List<Rental_Apply_Equipment_Set_Detail__c>();
        for (Rental_Apply_Equipment_Set_Detail__c esd : eList) {
            if(ApplyToShipmentMap.containsKey(esd.Id)){
                Rental_Apply_Equipment_Set_Detail__c temp  = new Rental_Apply_Equipment_Set_Detail__c(); 
                temp.id = esd.Id;
                temp.ApplyToShipmentWorkTime__c = ApplyToShipmentMap.get(esd.Id);
                upeList.add(temp);
            }
        }
        update upeList;
    }

    global void finish(Database.BatchableContext BC) {

    }
    public static void justForTest() {
        Integer i = 0;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
        i++;
    }
}