zhubaomin
8 天以前 00d54db361d697cf8fdf2f15940f4650b21b3185
pipIrr-platform/pipIrr-mw/pipIrr-mw-rtu/src/main/java/com/dy/rtuMw/server/forTcp/TcpDownCommandObj.java
New file
@@ -0,0 +1,117 @@
package com.dy.rtuMw.server.forTcp;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import com.dy.common.queue.NodeObj;
import com.dy.common.mw.protocol.MidResultToRtu;
import com.dy.rtuMw.server.ServerProperties;
public class TcpDownCommandObj implements NodeObj{
   private static Logger log = LogManager.getLogger(TcpDownCommandObj.class.getName());
   public MidResultToRtu result ;//下行命令
   public Long cachTime ;//缓存时刻
   public Long lastSendStamp ;//上次发送时刻
   public byte sendedTimes ;//已经发送次数
   public boolean onceReceivedResult ;//已经收到命令应答
   public TcpDownCommandObj(MidResultToRtu result){
      this.result = result ;
      this.cachTime = System.currentTimeMillis() ;
      this.lastSendStamp = 0L ;
      this.sendedTimes = 0 ;
      this.onceReceivedResult = false ;
   }
   /**
    * 自己处理自己
    * @param now
    * @return
    */
   public boolean dealSelf(Long now){
      boolean removeNodeFromCach = false ;
      if(this.onceReceivedResult){
         //已经收到命令结果
         removeNodeFromCach = true ;
           //记录状态
           RtuStatusDealer.commandSuccess(this.result.rtuAddr, this.result.downCode, this.result.downCodeName);
         return removeNodeFromCach ;
      }
      if(this.sendedTimes >= this.result.maxSendTimes){
         //发送次数达到最大值
         if(now - this.lastSendStamp >= ServerProperties.cacheWaitResultTimeout){
            //超时
            removeNodeFromCach = true ;
              //记录状态
              RtuStatusDealer.commandFailure(this.result.rtuAddr, this.result.downCode, this.result.downCodeName);
         }
         return removeNodeFromCach ;
      }
      TcpSession tcpSe = TcpSessionCache.getTcpSession(this.result.rtuAddr) ;
      Boolean flag = TcpSessionCache.isConnect(this.result.rtuAddr) ;
      if(tcpSe == null || flag == null || !flag.booleanValue()){
         //未曾上线或不在线
         if(!this.result.isCachForOffLine){
            //不在线命令不缓存
            removeNodeFromCach = true ;
         }else{
            //不在线命令缓存
            if(now - this.cachTime >= ServerProperties.offLineCacheTimeout){
               //缓存超时
               removeNodeFromCach = true ;
            }
         }
         return removeNodeFromCach ;
      }
      if(tcpSe.lastUpDataTime != null){
         //说明上行数据时刻有效,即此时离上行数据时刻太近,还不能下行数据,延迟一下
         return false ;
      }
      boolean nowSend = false ;
      if(this.result.countdown4Send > 0){
         this.result.countdown4Send -= 1 ;
      }else{
         Long lastDownComTime = tcpSe.lastDownComTime ;
         if(this.result.isQuickSend){
            //在命令构建时,只有在低功耗情况下,才会把isQuickSend付值为true
            //未收到命令结果,未达到最大发送次数,RTU在线,离上行数据时刻不近,当前是速发命令,满足发送命令条件,执行发送命令
            nowSend = true ;
         }else if(lastDownComTime == null){
            //未收到命令结果,未达到最大发送次数,RTU在线,离上行数据时刻不近,当前RTU上线以来未曾下发过命令,满足发送命令条件,执行发送命令
            nowSend = true ;
         }else if(this.result.isFastCom && (now - lastDownComTime) >= ServerProperties.fastCommandSendInterval){
            //未收到命令结果,未达到最大发送次数,RTU在线,离上行数据时刻不近,RTU上线以来曾下发过命令,当前命令是快速命令且超过命令下发间隔,满足发送命令条件,执行发送命令
            nowSend = true ;
         }else if(!this.result.isFastCom && (now - lastDownComTime) >= ServerProperties.commandSendInterval){
            //未收到命令结果,未达到最大发送次数,RTU在线,离上行数据时刻不近,RTU上线以来曾下发过命令,当前命令非快速命令,RTU下发命令间隔超过命令下发间隔,满足发送命令条件,执行发送命令
            nowSend = true ;
         }
      }
      if(nowSend){
         tcpSe.ioSession.write(this.result.downBuffer) ;
         tcpSe.lastDownComTime = now ;
         if(!this.result.hasResponse){
            //无应答
            removeNodeFromCach = true ;
         }
         this.sendedTimes++ ;
         this.lastSendStamp = now ;
         //记录日志
         RtuLogDealer.log(this.result.rtuAddr, "下行数据 " + this.result.downCode + (this.result.downCodeName==null?"":("(" + this.result.downCodeName + ")")) + ":" + this.result.downBufHex);
         //记录状态
         RtuStatusDealer.downData(this.result.rtuAddr, this.result.downCode, this.result.downCodeName, this.result.downBuffer.length);
         log.info("下行RTU(地址=" + this.result.rtuAddr + ")命令[功能码=" + this.result.downCode + (this.result.downCodeName==null?"":("(" + this.result.downCodeName + ")")) + "] "  + this.result.downBufHex ) ;
      }
      return removeNodeFromCach ;
   }
}