|
|
using System.Text.Json.Nodes;
|
|
|
using Autofac;
|
|
|
using AutoMapper;
|
|
|
using Entity.Api.Resp;
|
|
|
using Entity.Constant;
|
|
|
using Entity.DbModel.Station;
|
|
|
using HybirdFrameworkCore.Autofac;
|
|
|
using HybirdFrameworkCore.Autofac.Attribute;
|
|
|
using HybirdFrameworkCore.Entity;
|
|
|
using HybirdFrameworkDriver.Session;
|
|
|
using HybirdFrameworkDriver.TcpClient;
|
|
|
using log4net;
|
|
|
using Newtonsoft.Json;
|
|
|
using Repository.Station;
|
|
|
using Service.Charger.Client;
|
|
|
using Service.Charger.Codec;
|
|
|
using Service.Charger.Handler;
|
|
|
using Service.Charger.Msg.Host.Req;
|
|
|
using Service.Execute;
|
|
|
using Service.Plc.Msg.Host.Req;
|
|
|
|
|
|
namespace Service.Charger.Server;
|
|
|
|
|
|
[Scope]
|
|
|
public class PlcClient : TcpClient<IBaseHandler, Decoder, Encoder>
|
|
|
{
|
|
|
|
|
|
//0 待机 1:换电任务 2:移仓任务 3:消防任务
|
|
|
#region 属性
|
|
|
private long TaskNo = 0;
|
|
|
/// <summary>
|
|
|
/// Plc编号
|
|
|
/// </summary>
|
|
|
public string Sn { get; set; }
|
|
|
|
|
|
/// <summary>
|
|
|
///
|
|
|
/// </summary>
|
|
|
public bool SwapDone { get; set; }
|
|
|
|
|
|
/// <summary>
|
|
|
/// 换电开始标记
|
|
|
/// </summary>
|
|
|
public bool SwapStart { get; set; }
|
|
|
|
|
|
/// <summary>
|
|
|
/// 电池搬运结束
|
|
|
/// </summary>
|
|
|
public bool BatteryMoveDone { get; set; }
|
|
|
|
|
|
public bool DisassembleDone { get; set; }
|
|
|
|
|
|
//自动模式
|
|
|
public bool Auto { get; set; }
|
|
|
|
|
|
//远程模式
|
|
|
public bool Remote { get; set; }
|
|
|
|
|
|
//初始化完成
|
|
|
public bool Init { get; set; }
|
|
|
|
|
|
|
|
|
//9号仓是否有电池
|
|
|
public bool Is9Exist { get; set; }
|
|
|
|
|
|
private readonly BinInfoRepository _binInfoRepository;
|
|
|
|
|
|
public PlcClient(BinInfoRepository binInfoRepository)
|
|
|
{
|
|
|
_binInfoRepository = binInfoRepository;
|
|
|
}
|
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
//修改当前任务
|
|
|
public void ExChangeTaskNo(long taskNo)
|
|
|
{
|
|
|
Interlocked.Exchange(ref TaskNo, taskNo);
|
|
|
}
|
|
|
|
|
|
//重置当前任务
|
|
|
public void ResetTaskNo()
|
|
|
{
|
|
|
Interlocked.Exchange(ref TaskNo, 0);
|
|
|
}
|
|
|
|
|
|
public bool IsTaskFree()
|
|
|
{
|
|
|
return ReadTaskNo() == 0l;
|
|
|
}
|
|
|
|
|
|
//读取当前任务
|
|
|
public long ReadTaskNo()
|
|
|
{
|
|
|
return Interlocked.Read(ref TaskNo);
|
|
|
}
|
|
|
|
|
|
|
|
|
#region send
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送初始化命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendInitializeCommandReq()
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
InitializeCommandReq req = new InitializeCommandReq();
|
|
|
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
|
|
|
StationSoftMgr.PutDeviceLog((int)StationConstant.DeviceCode.Plc,SwapConstant.PlcProtocol.Init,
|
|
|
|
|
|
JsonConvert.SerializeObject(req),(int)SwapConstant.CommunicationType.Send);
|
|
|
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送出库命令
|
|
|
/// </summary>
|
|
|
/// <param name="outboundMode">出库方式</param>
|
|
|
/// <param name="takePositionNumber">取仓位号</param>
|
|
|
public Result<bool> SendOutboundCommandReq(byte outboundMode,byte takePositionNumber)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
OutboundCommandReq req = new OutboundCommandReq(outboundMode, takePositionNumber)
|
|
|
{
|
|
|
OutboundMode = outboundMode,
|
|
|
TakePositionNumber = takePositionNumber,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送红绿灯
|
|
|
/// </summary>
|
|
|
/// <param name="trafficLight">出库方式</param>
|
|
|
public Result<bool> SendTrafficLightReq(byte trafficLight)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
TrafficLightReq req = new TrafficLightReq(trafficLight)
|
|
|
{
|
|
|
TrafficLight = trafficLight,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送开始换电命令
|
|
|
/// </summary>
|
|
|
/// <param name="takePositionNumber">取仓位号</param>
|
|
|
/// <param name="positionNumber">存仓位号</param>
|
|
|
/// <returns></returns>
|
|
|
public Result<bool> SendStartBatterySwapReq(byte takePositionNumber,byte positionNumber)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
StartBatterySwapReq req = new StartBatterySwapReq(takePositionNumber, positionNumber)
|
|
|
{
|
|
|
TakePositionNumber = takePositionNumber,
|
|
|
PositionNumber = positionNumber,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送开始搬电命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendStartMovElectricityReq(byte takeBatteryShelfNumber,byte saveBatteryShelfNumber)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
StartMovElectricityReq req = new StartMovElectricityReq(takeBatteryShelfNumber, saveBatteryShelfNumber)
|
|
|
{
|
|
|
TakeBatteryShelfNumber = takeBatteryShelfNumber,
|
|
|
SaveBatteryShelfNumber = saveBatteryShelfNumber,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送车辆型号
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendVehicleModelReq(byte cartNo)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
VehicleModelReq req = new VehicleModelReq(cartNo)
|
|
|
{
|
|
|
CartNo = cartNo,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送移库命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendMoveCommandReq(byte takePositionNumber,byte positionNumber)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
MoveCommandReq req = new MoveCommandReq(takePositionNumber, positionNumber)
|
|
|
{
|
|
|
TakePositionNumber = takePositionNumber,
|
|
|
PositionNumber = positionNumber,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送继续命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendContinueCommandReq( )
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
ContinueCommandReq req = new ContinueCommandReq();
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送暂停命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendPauseCommandReq()
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
PauseCommandReq req = new PauseCommandReq();
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送入库命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendInboundCommandsReq(byte positionNumber)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
InboundCommandsReq req = new InboundCommandsReq(positionNumber)
|
|
|
{
|
|
|
PositionNumber = positionNumber,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送入库命令修改为红绿灯
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
// public Result<bool> SendInboundCommandsReq(byte positionNumber)
|
|
|
// {
|
|
|
// if (!Connected)
|
|
|
// {
|
|
|
// return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
// }
|
|
|
// InboundCommandsReq req = new InboundCommandsReq(positionNumber)
|
|
|
// {
|
|
|
// PositionNumber = positionNumber,
|
|
|
// };
|
|
|
// this.Channel.WriteAndFlushAsync(req);
|
|
|
// return Result<bool>.Success();
|
|
|
// }
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送终止命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendTerminationOrderReq( )
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
TerminationOrderReq req = new TerminationOrderReq();
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送故障复位命令
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendFaultResetReq()
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
FaultResetReq req = new FaultResetReq();
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送电池充电状态
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendWhetherChargedReq()
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
List<BinInfo> binInfos = _binInfoRepository.Query();
|
|
|
var configuration = new MapperConfiguration(cfg => cfg.CreateMap<BinInfo, BinInfoResp>());
|
|
|
var mapper = configuration.CreateMapper();
|
|
|
|
|
|
List<BinInfoResp> binInfoList = mapper.Map<List<BinInfoResp>>(binInfos);
|
|
|
byte[] granaries = new byte[8];
|
|
|
|
|
|
for (int i = 0; i < binInfoList.Count && i < granaries.Length; i++)
|
|
|
{
|
|
|
granaries[i] = (binInfoList[i].ChargeStatus == 0 || binInfoList[i].ChargeStatus.Value == 2 || binInfoList[i].ChargeStatus.Value == 4) ? (byte)0 : (byte)1;
|
|
|
}
|
|
|
WhetherChargedReq req=new WhetherChargedReq(granaries[0], granaries[1], granaries[2], granaries[3], granaries[4], granaries[5], granaries[6], granaries[7]);
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
|
|
|
///// <summary>
|
|
|
///// 发送电池充电状态
|
|
|
///// </summary>
|
|
|
///// <param name="sn">Plc编号</param>
|
|
|
///// <param name="msg">消息</param>
|
|
|
//public Result<bool> SendWhetherChargedResq()
|
|
|
//{
|
|
|
// if (!Connected)
|
|
|
// {
|
|
|
// return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
// }
|
|
|
// List<BinInfo> binInfos = _binInfoRepository.Query();
|
|
|
// var configuration = new MapperConfiguration(cfg => cfg.CreateMap<BinInfo, BinInfoResp>());
|
|
|
// var mapper = configuration.CreateMapper();
|
|
|
|
|
|
// List<BinInfoResp> binInfoList = mapper.Map<List<BinInfoResp>>(binInfos);
|
|
|
// byte[] granaries = new byte[8];
|
|
|
|
|
|
// for (int i = 0; i < binInfoList.Count && i < granaries.Length; i++)
|
|
|
// {
|
|
|
// granaries[i] = (binInfoList[i].ChargeStatus == 0 || binInfoList[i].ChargeStatus.Value == 2 || binInfoList[i].ChargeStatus.Value == 4) ? (byte)0 : (byte)1;
|
|
|
// }
|
|
|
// WhetherChargedResq req = new WhetherChargedResq(granaries[0], granaries[1], granaries[2], granaries[3], granaries[4], granaries[5], granaries[6], granaries[7]);
|
|
|
// this.Channel.WriteAndFlushAsync(req);
|
|
|
// return Result<bool>.Success();
|
|
|
//}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
///// <summary>
|
|
|
///// 发送参数设置
|
|
|
///// </summary>
|
|
|
///// <param name="sn">Plc编号</param>
|
|
|
///// <param name="msg">消息</param>
|
|
|
//public Result<bool> SendParameterSettingsReq(byte[] messageBodyAddress,byte parameterType,byte parameter)
|
|
|
//{
|
|
|
// if (!Connected)
|
|
|
// {
|
|
|
// return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
// }
|
|
|
// ParameterSettingsReq req = new ParameterSettingsReq( parameterType, parameter)
|
|
|
// {
|
|
|
// MessageBodyAddress = messageBodyAddress,
|
|
|
// ParameterType = parameterType,
|
|
|
// Parameter = parameter,
|
|
|
// };
|
|
|
// this.Channel.WriteAndFlushAsync(req);
|
|
|
// return Result<bool>.Success();
|
|
|
//}
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送参数设置
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendParameterSettingsReq( byte parameterType, byte parameter)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
ParameterSettingsReq req = new ParameterSettingsReq(parameterType, parameter)
|
|
|
{
|
|
|
ParameterType = parameterType,
|
|
|
Parameter = parameter,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
public EquipAlarmDefineRepository _equipAlarmDefineRepository = AppInfo.Container.Resolve<EquipAlarmDefineRepository>();
|
|
|
|
|
|
public List<EquipAlarmDefine> GetAlarmDeinneList()
|
|
|
{
|
|
|
return _equipAlarmDefineRepository.QueryByClauseToList(i => i.EquipCode == "plc");
|
|
|
}
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
/// 发送准备电池开启
|
|
|
/// </summary>
|
|
|
/// <param name="sn">Plc编号</param>
|
|
|
/// <param name="msg">消息</param>
|
|
|
public Result<bool> SendPrepareBatteryOnReq(byte readyBatterySign,byte takePositionNumber)
|
|
|
{
|
|
|
if (!Connected)
|
|
|
{
|
|
|
return Result<bool>.Fail($"Plc{Sn}未连接");
|
|
|
}
|
|
|
PrepareBatteryOnReq req = new PrepareBatteryOnReq(readyBatterySign, takePositionNumber)
|
|
|
{
|
|
|
ReadyBatterySign = readyBatterySign,
|
|
|
TakePositionNumber = takePositionNumber,
|
|
|
};
|
|
|
this.Channel.WriteAndFlushAsync(req);
|
|
|
return Result<bool>.Success();
|
|
|
}
|
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
|
|
|
|
public void Reset()
|
|
|
{
|
|
|
SwapDone = false;
|
|
|
DisassembleDone = false;
|
|
|
SwapStart = false;
|
|
|
ResetTaskNo();
|
|
|
}
|
|
|
|
|
|
public override ILog Logger()
|
|
|
{
|
|
|
return Log();
|
|
|
}
|
|
|
private ILog Log()
|
|
|
{
|
|
|
var name = "Plc" + this.Sn;
|
|
|
ILog logger = LogManager.GetLogger(name);
|
|
|
|
|
|
Console.WriteLine(name + "-" + logger.GetHashCode());
|
|
|
return logger;
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
///
|
|
|
/// </summary>
|
|
|
/// <returns></returns>
|
|
|
public bool Connect()
|
|
|
{
|
|
|
base.BaseConnect();
|
|
|
Log().Info($"charger {Sn} connect succeed");
|
|
|
return Connected;
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
///
|
|
|
/// </summary>
|
|
|
/// <param name="sn"></param>
|
|
|
/// <param name="destAddr"></param>
|
|
|
public void SessionAttr(string sn, string destAddr)
|
|
|
{
|
|
|
ChannelUtils.AddAttr(Channel, PlcConst.ChargerSn, sn);
|
|
|
ChannelUtils.AddAttr(Channel, PlcConst.EqmTypeNo, sn);
|
|
|
ChannelUtils.AddAttr(Channel, PlcConst.EqmCode, sn);
|
|
|
ChannelUtils.AddAttr(Channel, PlcConst.DestAddr, destAddr);
|
|
|
}
|
|
|
}
|