255 lines
9.4 KiB
C#
Raw Normal View History

using Abp;
using DotNetty.Buffers;
2024-11-26 13:45:28 +08:00
using DotNetty.Transport.Channels;
using MySqlX.XDevAPI;
using System;
using System.Collections;
2024-12-02 14:52:59 +08:00
using System.Collections.Concurrent;
2024-11-26 13:45:28 +08:00
using System.Collections.Generic;
2024-12-09 11:05:15 +08:00
using System.ComponentModel.Design;
2024-11-26 13:45:28 +08:00
using System.Diagnostics;
2024-10-18 18:41:02 +08:00
using System.Text;
using System.Threading.Tasks;
2024-11-26 13:45:28 +08:00
using Yunda.ISAS.DataMonitoringServer.DataAnalysis;
2024-12-06 16:32:13 +08:00
using Yunda.SOMS.DataMonitoringServer.FTPHandle;
2024-10-18 18:41:02 +08:00
namespace Yunda.SOMS.DataMonitoringServer.TcpSocket.Server
{
using static ConstValue;
public class DotNettyServerHandler : SimpleChannelInboundHandler<IByteBuffer>
{
2024-12-06 16:32:13 +08:00
2024-11-26 13:45:28 +08:00
private IChannelHandlerContext _context;
// 定义事件,事件处理程序包含消息和功能描述
2024-12-02 14:52:59 +08:00
private readonly ConcurrentDictionary<byte, IChannelHandlerContext> _connections;
2024-11-26 13:45:28 +08:00
private readonly Action<byte, byte[], byte> _onMessageReceived;
2024-12-02 14:52:59 +08:00
public DotNettyServerHandler(ConcurrentDictionary<byte, IChannelHandlerContext> connections,
2024-12-06 16:32:13 +08:00
Action<byte, byte[], byte> onMessageReceived)
2024-10-18 18:41:02 +08:00
{
2024-11-26 13:45:28 +08:00
_connections = connections;
_onMessageReceived = onMessageReceived;
}
2024-10-18 18:41:02 +08:00
public override void ChannelActive(IChannelHandlerContext context)
{
2024-11-26 13:45:28 +08:00
try
{
string clientIp = context.Channel.RemoteAddress.ToString();
MonitoringEventBus.LogHandler($"客户端连接:{clientIp}", "103客户端发送消息");
base.ChannelActive(context);
}
catch (Exception ex)
{
MonitoringEventBus.LogHandler($"{ex.StackTrace}", "103客户端错误信息");
}
2024-10-18 18:41:02 +08:00
}
2024-11-26 13:45:28 +08:00
public override void ChannelInactive(IChannelHandlerContext context)
2024-10-18 18:41:02 +08:00
{
2024-11-26 13:45:28 +08:00
try
2024-10-18 18:41:02 +08:00
{
2024-11-26 13:45:28 +08:00
string clientIp = context.Channel.RemoteAddress.ToString();
MonitoringEventBus.LogHandler($"客户端断开连接:{clientIp}", "103客户端发送消息");
base.ChannelInactive(context);
2024-10-18 18:41:02 +08:00
}
2024-11-26 13:45:28 +08:00
catch (Exception ex)
{
MonitoringEventBus.LogHandler($"{ex.StackTrace}", "103客户端错误信息");
}
}
protected override void ChannelRead0(IChannelHandlerContext ctx, IByteBuffer msg)
{
_context = ctx;
try
{
byte startByte = msg.ReadByte();
ushort length = msg.ReadUnsignedShort();
byte address = msg.ReadByte();
byte controlWord = msg.ReadByte();
byte functionType = msg.ReadByte();
2024-10-18 18:41:02 +08:00
2024-11-26 13:45:28 +08:00
// 计算数据长度
int dataLength = length - 6;
if (msg.ReadableBytes < dataLength)
{
// 数据不足,等待更多数据
return;
}
byte[] data = new byte[dataLength];
msg.ReadBytes(data);
2024-10-18 18:41:02 +08:00
2024-11-26 13:45:28 +08:00
string clientIp = ctx.Channel.RemoteAddress.ToString();
string description = FunctionCodeDescriptions.GetDescription(functionType);
2024-12-06 16:32:13 +08:00
//MonitoringEventBus.LogHandler($"装置地址 {address} 功能码:{functionType} 数据长度:{dataLength}", "103客户端消息");
2024-11-26 13:45:28 +08:00
Task.Run(() => _onMessageReceived?.Invoke(address, data, functionType));
HandleFunctionCodeAsync(functionType, address, controlWord, data, ctx);
}
catch (Exception ex)
{
MonitoringEventBus.LogHandler($"Error in ChannelRead0: {ex.StackTrace}", "103客户端发送消息");
}
}
2024-10-18 18:41:02 +08:00
2024-11-26 13:45:28 +08:00
private async Task HandleFunctionCodeAsync(byte functionType, byte address, byte controlWord, byte[] data, IChannelHandlerContext ctx)
2024-12-06 16:32:13 +08:00
{
2024-11-26 13:45:28 +08:00
switch (functionType)
{
case 0:
HandleConfirmationMessage(address, data, ctx);
break;
case 1:
MonitoringEventBus.LogHandler($"收到用户定值信息: {BitConverter.ToString(data)}", "103客户端信息");
break;
case 2:
// 厂家定值信息处理
break;
case 3:
MonitoringEventBus.LogHandler($"版本信息: {Encoding.ASCII.GetString(data)}", "103客户端信息");
break;
case 4:
// 自检信息处理
2024-10-18 18:41:02 +08:00
2024-11-26 13:45:28 +08:00
break;
case 5:
MonitoringEventBus.LogHandler($"开入开出信息: {Encoding.ASCII.GetString(data)}", "103客户端信息");
break;
case 6:
await UpdateDeviceCommunicationStateAsync(address, data, ctx);
break;
case 7:
// B码对时状态处理
Debug.WriteLine($"B码对时状态处理: {BitConverter.ToString(data)}");
break;
default:
MonitoringEventBus.LogHandler("未知的功能码", "103客户端信息");
break;
}
2024-10-18 18:41:02 +08:00
}
2024-11-26 13:45:28 +08:00
private void HandleConfirmationMessage(byte address, byte[] data, IChannelHandlerContext ctx)
2024-10-18 18:41:02 +08:00
{
2024-11-26 13:45:28 +08:00
Debug.WriteLine($"确认开入开出信息: {Encoding.ASCII.GetString(data)}");
// 可以添加发送确认报文的逻辑
2024-10-18 18:41:02 +08:00
}
2024-11-26 13:45:28 +08:00
private async Task UpdateDeviceCommunicationStateAsync(byte address, byte[] data, IChannelHandlerContext ctx)
2024-10-18 18:41:02 +08:00
{
2024-11-26 13:45:28 +08:00
await Task.Run(async () =>
2024-10-18 18:41:02 +08:00
{
2024-11-26 13:45:28 +08:00
try
2024-10-18 18:41:02 +08:00
{
2024-12-09 11:05:15 +08:00
if (DateTime.Now.Hour == 0&&DateTime.Now.Minute == 5&& DateTime.Now.Second<30)
{
await SendCustomMessageAsync(ctx, address, 0, 4, 0);//发送版本信息请求
}
2024-12-06 16:32:13 +08:00
UpdateConnectionContext(address, ctx);
await UpdateCommunicationStateCountAsync(address, ctx);
2024-11-26 13:45:28 +08:00
}
catch (Exception ex)
{
MonitoringEventBus.LogHandler($"Error: {ex.StackTrace}", "103客户端发送消息");
2024-10-18 18:41:02 +08:00
}
});
}
2024-12-06 16:32:13 +08:00
private void UpdateConnectionContext(byte address, IChannelHandlerContext ctx)
{
_connections[address] = ctx;
}
private async Task UpdateCommunicationStateCountAsync(byte address, IChannelHandlerContext ctx)
{
if (_connections.TryGetValue(address, out _))
{
//_communicationStateCounts[address]++;
//已经存在的装置地址
}
else
{
//新加入的装置的地址
await SendInitMsgToDeviceAsync(ctx, address);
}
}
private async Task SendInitMsgToDeviceAsync(IChannelHandlerContext ctx, byte address)
{
for (byte i = 1; i < 6; i++)
{
await SendCustomMessageAsync(ctx, address, 0, 5, i);
}
await SendCustomMessageAsync(ctx, address, 0, 1, 0);
await SendCustomMessageAsync(ctx, address, 0, 2, 0);
await SendCustomMessageAsync(ctx, address, 0, 3, 0);
await SendCustomMessageAsync(ctx, address, 0, 4, 0);
await SendCustomMessageAsync(ctx, address, 0, 7, 0);
}
2024-11-26 13:45:28 +08:00
public override async void ExceptionCaught(IChannelHandlerContext context, Exception ex)
{
try
{
MonitoringEventBus.LogHandler(ex.Message, "103客户端错误消息");
await context.CloseAsync();
}
catch (Exception ex1)
{
MonitoringEventBus.LogHandler($"Error: {ex1.StackTrace}", "关闭tcp客户端");
}
}
// 发送自定义消息
public async Task SendCustomMessageAsync(IChannelHandlerContext context, byte address, byte controlWord, byte functionType, byte data)
{
try
{
// 构建数据帧
byte[] buffer = new byte[7];
// 填入启动字符
buffer[0] = 0x16;
// 填入长度假设数据部分为50字节2字节长度字段+1字节地址+1字节标志位
byte dataLength = 7;
buffer[1] = 0; // 长度低字节
buffer[2] = dataLength; // 长度高字节
// 填入地址、应用控制字、功能类型
buffer[3] = address; // 示例地址
buffer[4] = controlWord; // 示例应用控制字
buffer[5] = functionType; // 示例功能类型
buffer[6] = data;
// 填入数据部分
IByteBuffer wrappedBuffer = Unpooled.WrappedBuffer(buffer);
// 发送数据
await context.WriteAndFlushAsync(wrappedBuffer);
string hexString = BitConverter.ToString(buffer).Replace("-", " ");
MonitoringEventBus.LogHandler($"地址:{address} 功能码:{functionType} 数据:{hexString}", "103客户端发送消息");
await Task.Delay(1000);
}
catch (Exception ex)
{
MonitoringEventBus.LogHandler($"Error: {ex.StackTrace}", "103客户端发送消息");
}
}
}
2024-10-18 18:41:02 +08:00
2024-11-26 13:45:28 +08:00
2024-10-18 18:41:02 +08:00
}