MQTT解析

Java

java 复制代码
package com.qqbot;

import java.io.*;
import java.nio.charset.StandardCharsets;

public class MqttEntityEncoder {

    public static byte[] encode(MqttEntity entity) throws IOException {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        DataOutputStream dos = new DataOutputStream(baos);

        // 1. mdcSn[20]
        writeFixedLengthString(dos, entity.getMdcSn(), 20);

        // 2. length = 54 + msgLen
        int length = 54 + (entity.getMsgBody() == null ? 0 : entity.getMsgBody().length);
        dos.writeInt(Integer.reverseBytes(length)); // 小端写入

        // 3. timeStamp (uint64_t)
        dos.writeLong(Long.reverseBytes(entity.getTimeStamp()));

        // 4. transId[36]
        writeFixedLengthString(dos, entity.getTransId(), 36);

        // 5. msgType (uint16_t)
        dos.writeShort(Short.reverseBytes(entity.getMsgType()));

        // 6. msgLen (uint32_t)
        int msgLen = entity.getMsgBody() == null ? 0 : entity.getMsgBody().length;
        dos.writeInt(Integer.reverseBytes(msgLen));

        // 7. protVer (uint32_t)
        dos.writeInt(Integer.reverseBytes(entity.getProtVer()));

        // 8. msgBody[msgLen]
        if (entity.getMsgBody() != null) {
            dos.write(entity.getMsgBody());
        }

        dos.flush();
        return baos.toByteArray();
    }

    private static void writeFixedLengthString(DataOutputStream dos, String value, int fixedLength) throws IOException {
        byte[] bytes = value != null ? value.getBytes(StandardCharsets.UTF_8) : new byte[0];
        if (bytes.length > fixedLength) {
            dos.write(bytes, 0, fixedLength); // 截断
        } else {
            dos.write(bytes);                 // 写入实际内容
            for (int i = 0; i < fixedLength - bytes.length; i++) {
                dos.writeByte(0);             // 补0
            }
        }
    }

    public static void main(String[] args) throws IOException {
        MqttEntity entity = new MqttEntity();
        entity.setMdcSn("ABC123EFGGGHDDD");
        entity.setTimeStamp(System.currentTimeMillis());
        entity.setTransId("123e4567-e89b-12d3-a456");
        entity.setMsgType((short) 1);
        entity.setProtVer(1);
        entity.setMsgBody("hello mqtt test ddd".getBytes(StandardCharsets.UTF_8));

        byte[] payload = MqttEntityEncoder.encode(entity);
// payload 可直接通过 MQTT 或 TCP 发送
        System.out.println(payload);

    }
}

C++

c 复制代码
#include <iostream>
#include <cstdint>
#include <cstring>

#pragma pack(push, 1)
struct MqttStruct {
    char mdcSn[20];
    uint32_t length;
    uint64_t timeStamp;
    char transId[36];
    uint16_t msgType;
    uint32_t msgLen;
    uint32_t protVer;
    // msgBody follows
};
#pragma pack(pop)

int main() {
    uint8_t data[] = {
        65, 66, 67, 49, 50, 51, 69, 70, 71, 71, 71, 72, 68, 68, 68, 0, 0, 0, 0, 0, // mdcSn
        73, 0, 0, 0,                                                             // length = 73
        33, 227, 216, 122, 152, 1, 0, 0,                                         // timeStamp (小端)
        49, 50, 51, 101, 52, 53, 54, 55, 45, 101, 56, 57, 98, 45, 49, 50, 
        100, 51, 45, 97, 52, 53, 54, 
        0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,                                   // transId 补齐到 36
        1, 0,                                                                    // msgType
        19, 0, 0, 0,                                                             // msgLen = 19
        1, 0, 0, 0,                                                              // protVer
        104, 101, 108, 108, 111, 32, 109, 113, 116, 116, 32, 116, 101, 115, 116, 32, 100, 100, 100
    };

    MqttStruct header{};
    std::memcpy(&header, data, sizeof(MqttStruct));

    std::cout << "mdcSn: " << std::string(header.mdcSn, 20) << std::endl;
    std::cout << "length: " << header.length << std::endl;
    std::cout << "timestamp: " << header.timeStamp << std::endl;
    std::cout << "transId: " << std::string(header.transId, 36) << std::endl;
    std::cout << "msgType: " << header.msgType << std::endl;
    std::cout << "msgLen: " << header.msgLen << std::endl;
    std::cout << "protVer: " << header.protVer << std::endl;

    const char* msgBody = reinterpret_cast<const char*>(data + sizeof(MqttStruct));
    std::cout << "msgBody: " << std::string(msgBody, header.msgLen) << std::endl;

    return 0;
}
相关推荐
大模型码小白2 分钟前
在 Windows 下 Codex 安装、配置与使用详细指南
java·人工智能·windows
Gauss松鼠会17 分钟前
【GaussDB】GaussDB锁阻塞源头查询
java·开发语言·前端·数据库·算法·gaussdb·经验总结
mingo_敏33 分钟前
DeepAgents : 后端(Backends)
java·开发语言
霸道流氓气质34 分钟前
SpringBoot中事务内同步处理 + 事务后异步调用外部系统的通用模式示例
java·spring boot·后端
霸道流氓气质1 小时前
Spring 事务传播机制与 REQUIRES_NEW
java·数据库·spring
BerryS3N1 小时前
Java 后端转型大模型:Demo 能跑不等于能上线
java·人工智能·python·java后端·spring ai·langchain4j·大模型转型
心机之蛙qee1 小时前
Docker Compose 多容器编排
java·docker·容器
秋田君1 小时前
QT_QColorDialog颜色对话框
java·数据库·qt
用户91366296220122 小时前
ViewModelScope 简介与使用
java
上海安当技术2 小时前
老系统零改造接入:旁路代理统一认证实战
java·servlet·架构·kubernetes·jenkins