Files
dc-tranlog-service/UDP_MULTICAST_SENDER.md
2026-01-26 18:08:01 +08:00

6.2 KiB
Raw Permalink Blame History

UDP多播发送功能说明

概述

本功能实现了UDP多播发送逻辑,对应C++代码TLogServer.cpp中的发送广播机制。作为独立功能,不依赖Spring框架,可以直接使用。

功能对应关系

C++代码对应关系

C++代码 Java实现 说明
m_SendCtrl.Start(m_iSendPort, m_IP.c_str()) MulticastSender.initialize() 启动UDP多播发送
m_SendCtrl.AddChannel(m_SendGrpIP.c_str(), m_iSendPort) MulticastSender构造函数配置 配置发送通道
m_SendCtrl.Send(item) MulticastSender.send(item) 发送COP_ITEM数据
item->GetMessage() COPMessageBuilder.buildMessage(item) 构建COP协议消息

核心组件

1. MulticastSender

UDP多播发送器,负责:

  • 创建并配置UDP多播Socket
  • 发送COP协议数据
  • 管理发送状态和监听器

位置: com.afe.dc.tranlog.service.multicast.MulticastSender

主要方法:

  • initialize(): 初始化发送器
  • send(COPItem item): 发送COPItem数据
  • sendRaw(byte[] data): 发送原始字节数据
  • close(): 关闭发送器
  • addListener(SendListener listener): 添加发送监听器

2. COPMessageBuilder

COP协议消息构建器,负责将COPItem对象转换为字节数组(COP协议格式)。

位置: com.afe.dc.tranlog.service.multicast.COPMessageBuilder

主要方法:

  • buildMessage(COPItem item): 构建COP协议消息

使用示例

基本使用

// 1. 创建发送配置
MulticastSender.Config config = new MulticastSender.Config(
    5001,              // 发送端口
    "225.6.7.9"       // 多播组IP
);
config.setLocalIp("0.0.0.0")      // 本地IP(可选)
     .setTtl(1)                    // TTL值(可选,默认1)
     .setLoopbackDisabled(true);   // 禁用回环(可选,默认true)

// 2. 创建发送器
MulticastSender sender = new MulticastSender(config);

// 3. 初始化
if (!sender.initialize()) {
    System.err.println("初始化失败");
    return;
}

try {
    // 4. 创建COPItem数据
    COPItem item = COPItem.builder()
            .itemNo(12345L)
            .msgType(COPItem.MsgType.MGT_UPDATE)
            .build();
    
    // 添加FID字段
    item.addField(COPItem.FID.FID_TRAN_LOG, "交易数据");
    item.addField(COPItem.FID.FID_ASK, 100.5f);
    item.addField(COPItem.FID.FID_BID, 100.3f);
    
    // 5. 发送数据
    boolean success = sender.send(item);
    
} finally {
    // 6. 关闭发送器
    sender.close();
}

使用发送监听器

// 添加发送监听器
sender.addListener(new MulticastSender.SendListener() {
    @Override
    public void onSendSuccess(COPItem item, int bytesSent) {
        System.out.println("发送成功 - itemNo: " + item.getItemNo() 
                + ", 大小: " + bytesSent + " 字节");
    }
    
    @Override
    public void onSendError(COPItem item, Exception error) {
        System.err.println("发送失败 - itemNo: " + item.getItemNo() 
                + ", 错误: " + error.getMessage());
    }
});

发送原始字节数据

byte[] rawData = new byte[]{0x01, 0x02, 0x03, 0x04};
sender.sendRaw(rawData);

配置说明

MulticastSender.Config

参数 类型 必填 默认值 说明
sendPort int 是 - 发送端口
groupIp String 是 - 多播组IP地址
localIp String 否 "0.0.0.0" 本地网络接口IP地址
ttl int 否 1 TTL值(Time To Live)
loopbackDisabled boolean 否 true 是否禁用回环

配置方法

MulticastSender.Config config = new MulticastSender.Config(5001, "225.6.7.9")
    .setLocalIp("192.168.1.100")    // 链式调用设置本地IP
    .setTtl(2)                       // 设置TTL
    .setLoopbackDisabled(false);     // 允许回环

COP协议格式

当前实现的COP协议格式:

消息头(16字节):
  - 消息类型(1字节)
  - ItemNo(4字节,小端序)
  - 其他头部信息(11字节,当前用0填充)

FID字段(每个字段):
  - FID编号(2字节)
  - 数据类型(1字节)
  - 数据长度(2字节)
  - 数据内容(变长)

支持的数据类型

数据类型 标识 Java类型 大小
CHAR 0x01 Byte, Character 1字节
SHORT 0x02 Short 2字节
INT 0x04 Integer 4字节
LONG 0x08 Long 8字节
FLOAT 0x10 Float 4字节
DOUBLE 0x20 Double 8字节
STRING 0x40 String 变长
BYTE_ARRAY 0x80 byte[] 变长

注意事项

  1. 独立功能: 本功能不依赖Spring框架,可以在任何Java应用中使用。

  2. 线程安全: MulticastSender不是线程安全的,如果需要在多线程环境中使用,需要外部同步。

  3. 资源管理: 使用完毕后务必调用close()方法释放资源。

  4. 网络权限: 在某些操作系统上,发送UDP多播数据可能需要特殊权限。

  5. 防火墙: 确保防火墙允许UDP数据包通过配置的端口。

  6. TTL值: TTL值决定了数据包可以经过的路由器数量,通常设置为1(本地网络)或更大的值(跨网络)。

  7. 回环: 如果loopbackDisabled为true,发送的数据不会回环到本地接收端,适合生产环境。

故障排查

初始化失败

  1. 检查多播组IP地址是否有效(必须是224.0.0.0到239.255.255.255之间)
  2. 检查端口是否被占用
  3. 检查网络接口是否正确
  4. 查看日志中的详细错误信息

发送失败

  1. 检查网络连接
  2. 检查防火墙设置
  3. 检查多播组地址和端口是否正确
  4. 查看日志中的详细错误信息

数据格式问题

  1. 检查COP协议格式是否与接收端一致
  2. 检查数据类型是否正确
  3. 查看COPMessageBuilder的构建逻辑

扩展

如果需要扩展功能,可以:

  1. 自定义协议格式: 修改COPMessageBuilder以支持不同的协议格式
  2. 批量发送: 添加批量发送方法
  3. 异步发送: 添加异步发送支持
  4. 发送统计: 添加发送统计和监控功能
  5. 重试机制: 添加发送失败重试机制

完整示例

参考 MulticastSenderExample.java 文件中的完整示例代码。