AutomaticSch.java 14.5 KB
package com.bsth.data.zndd;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.bsth.data.BasicData;
import com.bsth.data.adjg.domain.LargeGap;
import com.bsth.data.directive.DayOfDirectives;
import com.bsth.data.directive.GatewayHttpUtils;
import com.bsth.data.directive.MsgIdGenerator;
import com.bsth.data.gpsdata_v2.GpsRealData;
import com.bsth.data.gpsdata_v2.entity.GpsEntity;
import com.bsth.data.schedule.DayOfSchedule;
import com.bsth.data.schedule.ScheduleComparator;
import com.bsth.entity.StationRoute;
import com.bsth.entity.directive.D60;
import com.bsth.entity.realcontrol.LineConfig;
import com.bsth.entity.realcontrol.ScheduleRealInfo;
import com.bsth.repository.StationRouteRepository;
import com.bsth.service.directive.DirectiveService;
import com.bsth.service.realcontrol.ScheduleRealInfoService;
import com.bsth.util.HttpClientUtils;
import org.apache.commons.lang3.StringUtils;
import org.joda.time.format.DateTimeFormat;
import org.joda.time.format.DateTimeFormatter;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import javax.xml.crypto.Data;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;

/**
 * 自动检测调度异常
 */
@Component
public class AutomaticSch {

    Logger logger = LoggerFactory.getLogger(this.getClass());
    @Autowired
    GpsRealData gpsRealData;
    @Autowired
    DayOfSchedule dayOfSchedule;
    @Autowired
    DayOfDirectives dayOfDirectives;
    @Autowired
    ScheduleRealInfoService scheduleRealInfoService;
    @Autowired
    DirectiveService directiveService;
    @Autowired
    StationRouteRepository stationRouteRepository;
    @Autowired
    OutEntrance outEntrance;
    
    private static DateTimeFormatter fmtHHmmss = DateTimeFormat.forPattern("HHmmss");
    private static SimpleDateFormat sdfMonth = new SimpleDateFormat("yyyy-MM-dd");
    private static DateTimeFormatter fmtyyyyMMddHHmmss = DateTimeFormat.forPattern("yyyy-MM-ddHHmmss");
    private static SimpleDateFormat sdfHHmm = new SimpleDateFormat("HH:mm");
    SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm");
    
    private Map<String,String> drivreMap =new HashMap<>(); //自动重发map
    // 当日60指令缓存
    private   ConcurrentMap<Integer, D60> d60Map = new ConcurrentHashMap<>();//d60map
    
    String urldkl = "http://10.10.200.202:5580/monitor/api/getMonitorInfoByDay?key=1&solt=1111&t=1&dayStr=2024-07-23"; //大间隔接口

    //http://10.10.200.201:8083/wxk-prod-api/service-api/lggj/schedule/drByInfo  维修接口

    private Map<String,Long> SFMAP = new HashMap<>();
    
    //满载
    public  void mz(){
        try {
            ScheduleRealInfo sr = dayOfSchedule.executeCurr("S0R-054");
            ts(addStationPeople(sr, "MZ", 0L));//第二种 设备未离线 出站时间内未出站 
        }
        catch (Exception e){
            logger.error("满载------------------",e);
        }
    }
    
    //大间隔的情况
    public void dfTz(){
        try{
            StringBuilder sb = HttpClientUtils.get(urldkl /*+ sdfMonth.format(new Date())*/);
            if (sb == null)
                return;
            JSONObject obj = JSON.parseObject(sb.toString());
            List<LargeGap> lgs = JSON.parseArray(obj.getString("largeGap"), LargeGap.class);
            Long its = 0l;
            //数据转换 并推送
            for (LargeGap lg : lgs){
                 if(dayOfSchedule.executeCurr(lg.getNbbm()) != null){
                     its= dayOfSchedule.executeCurr(lg.getNbbm()).getId();
                 }else {
                     continue;
                 }
                ts(ConvertDJK(lg,its.toString()));
            }
            
        }catch (Exception e){
            logger.error("大间隔推送失败------------------",e);
        }
    }
    
    //撤销班次  检测人员或者车辆故障  --//换人换车或烂班 //路牌对调
    public void cxJC(){


    }
    
    //撤销撤销班次  检测人员或者车辆故障  --//换人换车或烂班 //路牌对调
    public void cxJCX(){

    }
    
    //实发调整检测 -- 车辆GPS掉线的情况下,车辆该出站了
    /**
     * 1。已过待发时间还没发车的
     * 2.设备离线
     * --上一班次还没有抵达终点不做操作
     */
    public void sftz(){
        logger.warn("实发调整扫描开始");
        try {
            //获取所有线路
            Map<String, String> lineMap =  BasicData.lineCode2NameMap;
            for (Map.Entry<String, String> t : lineMap.entrySet()){
                List<GpsEntity>  gpslist = gpsRealData.getByLine(t.getKey());
                List<ScheduleRealInfo> srList = dayOfSchedule.findByLineCode(t.getKey());
                for (ScheduleRealInfo sr : srList){
                    //1.离线 2.实发时间为空 3.已过待发时间还没发车的
                    long time = System.currentTimeMillis();//实际时间+2分钟
                    //超过待发时间  实发时间还是null的
                    if (sr.getFcsjT() + (1000*2) < time) {

                        //起点站实际到达时间为null的情况下
                        if (StringUtils.isEmpty(sr.getQdzArrDatesj())) {
                            ScheduleRealInfo prev = dayOfSchedule.prev(sr);
                            //上一个班次没有实际终点到达时间
                            if (prev != null && StringUtils.isEmpty(prev.getZdsjActual())) {
                                continue;
                            }
                        }
                        //第一种 设备离线的情况下改出站
                        Integer staus = 0; //状态
                        if (StringUtils.isEmpty(sr.getFcsjActual()) &&  sr.getRemarks() == null) {

                            GpsEntity gps =  gpsRealData.getByNbbm(sr.getClZbh());
                            //当前设备离线的情况  
                            //1。一直没收到gps
                            //2.gps长时间离线的情况下
                            //3.人为调整过的都跳过
                            if (gps == null || (gps.getAbnormalStatus() != null && gps.getAbnormalStatus().equals("offline"))){
                                ts(addStationPeople(sr, "SFTZ_1", 0L));
                                break;
                            }
                         /*   if (staus == 0)
                                ts(addStationPeople(sr, "SFTZ_2", 0L));//第二种 设备未离线 出站时间内未出站 */
                        }
                    }
                }
                                   
            }
        }catch (Exception e){
            logger.error("自动调度,实发调整推送失败---",e);
        }
        logger.warn("实发调整扫描结束");
    }
   
    //实发撤销检测 -- 出现快一慢三的情况  && 指令重发
    public void sfCX(){
        //查询所有班次
        //remark 人工干预过的的不检测
        try {
            Map<String, String> lineMap =  BasicData.lineCode2NameMap;
            List<ScheduleRealInfo>  oldSchDateList;
            String lineCode;
            for (Map.Entry<String, String> ts : lineMap.entrySet()){
                lineCode =ts.getKey();
                oldSchDateList = dayOfSchedule.findByLineCode(lineCode);
                //排序
                Collections.sort(oldSchDateList, new ScheduleComparator.FCSJ());
                for (ScheduleRealInfo t : oldSchDateList){
                    // 发车误点 
                    if (t.getFcsj() != null && t.getFcsjActual() != null && t.getRemarks() == null){
                        Long sst = ((t.getFcsjActualTime() - t.getFcsjT()) / 1000 / 60);
                        Long dfsj = t.getDfsjT() / 1000 ;
                        Long sfsj = t.getFcsjActualTime() / 1000;
                        //获取车辆状态 gps没有的情况下,或者车辆状态异常的情况
                        //判定gps发送时间和现在时间作对比
                        GpsEntity gps =  gpsRealData.getByNbbm(t.getClZbh());
                     /*   if (gps)*/
                        //1.gps一直掉后一直没上线
                        //2.车辆gps判断还在场站内
                        //3.车辆信号离线的
                        if (gps == null || gps.getInstation() == 2 ||
                                (gps.getAbnormalStatus() != null && gps.getAbnormalStatus().equals("offline"))){
                            //实发快一慢三   
                          /*  if (sst <= 3 && sst >= -1){*/
                                if(dfsj.equals(sfsj)) 
                                    continue;
                                //快1
                                if(sfsj < dfsj && dfsj - sfsj <=  60*4) 
                                    continue;
                                //慢3
                                if(dfsj < sfsj && sfsj - dfsj <= 60 *6) 
                                    continue;
                                
                                
                                //异常实发
                                ts(addStationPeople(t,"YCSF",sst));
                            }
                        /*}*/
                       
                    }
                }
            }
        }catch (Exception e){
            logger.error("实发撤销推送接口出错-----------",e);
        }
        
        
    }
    
    //发车信息微调检测  -- 车辆掉线后实发检测,重新计算时间发车时间
    public  void updatesf(){
        
    }
    
    //临加班次 -- 检测到大客流  //走落地屏客流接口
    public void ljbc(){
        
        
    }

    /**
     * 指令重发
     * 指令下发后设备未响应后  5分钟后重新发送一次 还未响应的话 未来一小时不自动发送该设备
     */
    public void drivresponse(){
        logger.warn("指令重发扫描开始");
        try {
            Map<String,Object> tempmap =new HashMap<>();
            //所有缓存指令
            Collection<D60> dptArray =  dayOfDirectives.all60();

            Map<String, String> lineMap =  BasicData.lineCode2NameMap;
            List<ScheduleRealInfo>  oldSchDateList;
            String lineCode;
            for (Map.Entry<String, String> ts : lineMap.entrySet()) {
                lineCode = ts.getKey();
                oldSchDateList = dayOfSchedule.findByLineCode(lineCode);
                for (ScheduleRealInfo t : oldSchDateList){
                    //指令重发
                    //1.待发时间是要超过当前时间的,2.当实际发车时间不为空的
                    //3.状态 驾驶员未响应的
                    if(t.getFcsjT() < new Date().getTime() && t.getFcsjActual() != null){

                    }
                    
                    
                }
            }
        }catch (Exception e){
            logger.error("自动调度,指令重发---",e);
        }
        logger.warn("指令重发扫描结束");
    }
    
    //误点检测 调度有的-LateAdjustHandle
    public Map wd(ScheduleRealInfo sch){
        //推送
        try{
            return addStationPeople(sch, "WD", 0L);
        }catch (Exception e){
            logger.error("自动调度,推送失败---",e);
        }
        return null;
    }
    
    
    
    public void ts(Map m) throws ParseException {
        //记录存一下  --超过当前时间的是否推送?
        String st = m.get("lineCode")+"_"+m.get("type")+"_"+m.get("rqStr");
        Long sj = sdf.parse(m.get("rqStr").toString() +" "+ m.get("rq")).getTime();
        Long dsj = new Date().getTime();
        List<Long> list = new ArrayList();
        //111_DJG_2024-06-24
        if (ZnddThread.ZNDDTYPEMAP.get(st) != null ) {
            list = ZnddThread.ZNDDTYPEMAP.get(st);
            int i = 0;
            
            for (Long s : list){ //推送过的同样情况1小时内  &&//超过当前时间的不推送&& sj < dsj
                if (Math.abs(s - sj) > (60 * 60 * 1000)){
                    i ++ ;
                }
            }
            outEntrance.Znddjk(m);//测试推送
            if (i == list.size()){
                list.add(sj);
                ZnddThread.ZNDDTYPEMAP.put(st,list);//存记录
                outEntrance.Znddjk(m);//推送
            }
            return;
        }else {
            list.add(sj);
            ZnddThread.ZNDDTYPEMAP.put(st,list);//存记录
            outEntrance.Znddjk(m);//推送
        }

    }




    //大间隔数据转换
    public Map ConvertDJK(LargeGap lg,String ids){
        Map sp = new HashMap();
        sp.put("uuid",UUID());
        sp.put("lineCode",lg.getLineCode());
        sp.put("lineName",lg.getLineName() );
        sp.put("rqStr",lg.getDateStr());
        sp.put("rq",sdfHHmm.format(lg.getTsTime()));
        sp.put("type","DJG");
        sp.put("xlDir",lg.getUpDown());
        sp.put("numType",lg.getIntervalMinute());
        sp.put("stationCode",lg.getStationName());
        sp.put("stationName",lg.getStationName());
        sp.put("clzbh",lg.getNbbm());
        sp.put("fcsj",lg.getBcfcsj());
        sp.put("ids",ids);
        sp.put("lg",lg);
        return sp;

    }

    //转换
    public Map addStationPeople(ScheduleRealInfo info,String type,Long sst) throws ParseException{
        Map sp = new HashMap();
        sp.put("uuid",UUID());
        sp.put("lineCode",info.getXlBm());
        sp.put("lineName",info.getXlName() );
        sp.put("rqStr",info.getScheduleDateStr());
        sp.put("rq",sdfHHmm.format(new Date())); //检测到时间
        sp.put("type",type);
        sp.put("xlDir",info.getXlDir());
        sp.put("numType",sst);
        sp.put("fcsj",info.getFcsj());
        sp.put("id",info.getId());
        sp.put("clzbh",info.getClZbh());
        sp.put("ids",info.getId());
        sp.put("sch",info);
        return sp;
    }
    //生成唯一id
    public String  UUID(){
        String uuid = UUID.randomUUID().toString().replaceAll("-", "");
        uuid=uuid.substring(0,10);
        StringBuilder builder=new StringBuilder();
        builder.append(uuid)
                .append(getRandom(3));
        return builder.toString();
    }


    private static long getRandom(long n) {
        long min = 1, max = 9;
        for (int i = 1; i < n; i++) {
            min *= 10;
            max *= 10;
        }
        long rangeLong = (((long) (new Random().nextDouble() * (max - min)))) + min;
        return rangeLong;
    }
}