/**备品智能化
 * 2023-11-2 Add by dzk 
 * OPD计划自动顺序排队且OPD计划下的备品申请进行重新排序
 * 获取下月14号——下下月13号,符合条件的OPD计划状态为计划中的备品申请数据
 */
global class OPDAutomaticSortBatch implements Database.Batchable<sObject> {
    private final List<String> sdcName = null;
    private BatchIF_Log__c iflog;
    public Boolean onlyMyselefy = false;
    global OPDAutomaticSortBatch(){
        iflog = new BatchIF_Log__c();
        iflog.Type__c = 'RentalAutomaticSortBatch';
        iflog.Log__c  = 'RentalAutomaticSortBatch start\n';
        iflog.ErrorLog__c = '';
        insert iflog;
    }

    global OPDAutomaticSortBatch(List<String> str){
        sdcName = str;
        iflog = new BatchIF_Log__c();
        iflog.Type__c = 'RentalAutomaticSortBatch';
        iflog.Log__c  = 'RentalAutomaticSortBatch start\n';
        iflog.ErrorLog__c = '';
        insert iflog;
    }

    global OPDAutomaticSortBatch(Boolean only){
        this.onlyMyselefy = only;
        iflog = new BatchIF_Log__c();
        iflog.Type__c = 'RentalAutomaticSortBatch';
        iflog.Log__c  = 'RentalAutomaticSortBatch start\n';
        iflog.ErrorLog__c = '';
        insert iflog;
    }
    
    global Database.QueryLocator start(Database.BatchableContext BC){
        String sql = 'SELECT Id,Name,type__c FROM opp2AuxiliarySort__c ';
        sql += ' WHERE Id != null ';
        if(sdcName <> null){
            sql += 'AND Name IN :sdcName ';
        }
        sql += ' AND (type__c = 1 OR type__c = 11)';
        sql += ' ORDER BY type__c';
        return Database.getQueryLocator(sql);

    }

    global void execute(Database.BatchableContext BC, List<opp2AuxiliarySort__c> opp2AuxiliarySortList) {
        try{
            Date today = Date.today();
            // 获取从次月14日至再次月13日的日期
            Date startDate = today.addMonths(1).toStartOfMonth().addDays(13);
            Date endDate = today.addMonths(2).toStartOfMonth().addDays(12);
            Map<String,Integer> provinceSortMap = new Map<String,Integer>();
            // 获取符合条件的已排序的OPD计划数据

            String soql = 'SELECT Id,SortDate__c,OPDPlanOCM_man_province_Rental__c,OPDLendSort__c,OPDLendSortDraft__c,SortOperator__c  FROM OPDPlan__c ';
            //拼接SQL  AccountType__c不一样 两种排序规则
            String soql01 = ' WHERE OPDPlanOCM_man_province_Rental__c = \'' + opp2AuxiliarySortList[0].Name + '\''; 
            // 2024-01-25 ssm 长假对应，增加计划中之后状态的判断
            soql01 += ' and (Status__c = \'计划中\' OR (Status__c in (\'完毕未报告\', \'待提交报告\', \'完毕\') and OPDLendSort__c = null))';
            soql01 += ' and OPDPlan_ImplementDate__c >=: startDate ' ;  
            soql01 += ' and OPDPlan_ImplementDate__c <=: endDate ';   
            soql01 += ' and AccountType__c = \'学会会议\' ';  
            // 20240227 ssm 备品可视化补充 start
            // 上月残留的就不进排序队列了，序号也不用
            soql01 += ' and Last_Month_Untreated__c = false ';
            // 20240227 ssm 备品可视化补充 end
            soql01 += ' order by OPDPlan_ImplementDate__c ASC,CreatedDate ASC ';

            String soql02 = ' WHERE OPDPlanOCM_man_province_Rental__c = \'' + opp2AuxiliarySortList[0].Name + '\''; 
            // 2024-01-25 ssm 长假对应，增加计划中之后状态的判断
            soql02 += ' and (Status__c = \'计划中\' OR (Status__c in (\'完毕未报告\', \'待提交报告\', \'完毕\') and OPDLendSort__c = null))';
            soql02 += ' and OPDPlan_ImplementDate__c >=: startDate ' ;  
            soql02 += ' and OPDPlan_ImplementDate__c <=: endDate ';  
            soql02 += ' and AccountType__c = \'医院\' ';  
            // 通过再申请生成的OPD计划 优先度最高，排在最前面
            // 20240227 ssm 备品可视化补充 start
            // 上月残留的就不进排序队列了，序号也不用
            soql02 += ' and Last_Month_Untreated__c = false ';
            // 20240227 ssm 备品可视化补充 end
            soql02 += ' order by Reapply__c DESC nulls last, OPDPlan_ImplementDate__c ASC, if_HaveEquipment__c ASC,';
            soql02 += ' if_Newest_HaveOpportunity__c DESC nulls last ,if_OPDTarget__c DESC nulls last,if_HaveSalestarget__c DESC nulls last';
            //分别查询结果后拼接 在遍历排序赋值
            List<OPDPlan__c> tempList01 = Database.query(soql+soql01);
            List<OPDPlan__c> tempList02 = Database.query(soql+soql02);
            tempList01.addAll(tempList02);
            // 省份与排序
            for(OPDPlan__c opdbefore : tempList01){
                provinceSortMap.put(opdbefore.OPDPlanOCM_man_province_Rental__c,0);  
            }

            // 获取符合条件的OPD计划下的出借备品申请   
            List<OPDPlan__c> opdUpdateList = new List<OPDPlan__c>();
            // for(OPDPlan__c opdp : sortedOPDList) {
            for(OPDPlan__c opdp : tempList01) {
                // if(opdp.OPDLendSort__c == null){ // 20240228 ssm 不看是否排过序，避免手动延期的数据无法正常排序
                String opdProvince = opdp.OPDPlanOCM_man_province_Rental__c;
                opdp.OPDLendSort__c = provinceSortMap.get(opdProvince) + 1;
                opdp.OPDLendSortDraft__c = provinceSortMap.get(opdProvince) + 1;
                provinceSortMap.put(opdProvince, Integer.valueOf(opdp.OPDLendSort__c));
                opdp.SortDate__c = Date.today();
                opdp.SortOperator__c = userInfo.getUserId();
                // 增加新的是否计划内排序标记
                opdp.If_AutoSort__c = 1;
                opdUpdateList.add(opdp);
                // }
            }

            // if (sortedOPDList != null && sortedOPDList.size() > 0) {
            //     update sortedOPDList;
            // }
            if (opdUpdateList != null && opdUpdateList.size() > 0) {
                update opdUpdateList;
            }

        }catch(Exception ex){
            iflog.ErrorLog__c = ex.getLineNumber()+'  行错误 :   '+ex.getMessage();

            return;
        }
        
    }

    global void finish(Database.BatchableContext BC) {
        iflog.Log__c += '\nOPDAutomaticSortBatch end' ;
        String tmp = iflog.ErrorLog__c;
        if (tmp.length() > 65000) {
            tmp = tmp.substring(0, 65000);
            tmp += ' ...have more lines...';
            iflog.ErrorLog__c = tmp;
        }
        update iflog;
        // 20231230 ljh add
        if(!onlyMyselefy && !Test.isRunningTest()){
            // 自动后续执行
            Id execBTId = Database.executebatch(new RentalAutomaticSortBatch(false, false),1);
        }        
}
       
}