feat(vd960DBN)+fix(DBNMQTTool): log_query 改 hex 原始字节上报 (2026-08-18)
背景: MQTT 快照流实测 MQTTSerialize_publish failed — JSON 化快照记录 ~810B/条 超 800B 发送缓冲
方案(用户拍板): 对齐 BLE 通道, 原始字节 hex 上报
固件 (V4.3):
- offlog.c/h: 新增 offlog_evt_to_hex() (32B→64 hex)
- snapshot.c/h: 新增 snap_rec_to_hex() (64B→128 hex); 删 SNAP_MAX_QUERY_JSON, 恢复 count=2
- tcp_json_srv.c / iot_mqtt_srv.c: log_query 改 {"seq":N,"hex":"..."}; SEND_BUF 保持 800
- 2 条快照 hex 响应 406B < 800B
文档: TCP JSON V1.03 / MQTT V1.07 §4.17 records 改 hex + 解析表引用 BLE §6.4/§7
工具: parse_offlog_hex/parse_snap_hex/offlog_payload_desc + hex 展示; 验证: gcc 9 断言 + 工具解析全过 + offscreen UI
This commit is contained in:
+31
-25
@@ -34,6 +34,7 @@ from dbn_mqtt_tool.protocol import (
|
||||
CMD_LOG_STAT, CMD_LOG_QUERY, CMD_LOG_CLEAR,
|
||||
STREAM_EVENT, STREAM_SNAPSHOT,
|
||||
ERROR_MSGS, FREQ_LEVELS, OUTPUT_MODES, EVENT_TYPES, LOG_EVENT_TYPE_DESC, SNAP_MISC_TYPE_DESC,
|
||||
OFFLOG_TYPE_NAMES, parse_offlog_hex, offlog_payload_desc, parse_snap_hex,
|
||||
data_ssc_net_set, data_iot_net_set, data_iot_topic_set,
|
||||
data_pwd_verify, data_pwd_set, data_report_config, data_log_query, data_log_clear,
|
||||
build_request, next_msg_id,
|
||||
@@ -1219,43 +1220,48 @@ class MainWindow(QMainWindow):
|
||||
def _apply_log_query_data(self, data: dict):
|
||||
records = data.get("records", [])
|
||||
start_seq = data.get("start_seq", 0)
|
||||
# 快照记录带 coil_count/channels 字段, 事件记录带 type 字段
|
||||
is_snap = bool(records) and ("coil_count" in records[0] or "channels" in records[0])
|
||||
# V1.07: 记录为 {"seq":N,"hex":"..."} 原始字节; hex 长度 128=快照(64B) / 64=事件(32B)
|
||||
is_snap = bool(records) and len(records[0].get("hex", "")) == 128
|
||||
stream_name = "传感快照" if is_snap else "事件日志"
|
||||
lines = [f"log_query[{stream_name}] start_seq={start_seq} → 返回 {len(records)} 条:"]
|
||||
for rec in records:
|
||||
ts_ms = rec.get("ts_ms", 0)
|
||||
hex_str = rec.get("hex", "")
|
||||
if is_snap:
|
||||
coil_count = rec.get("coil_count", 0)
|
||||
s = parse_snap_hex(hex_str)
|
||||
if "error" in s:
|
||||
lines.append(f" seq={rec.get('seq', 0)} 解析失败: {s['error']}")
|
||||
continue
|
||||
lines.append(
|
||||
f" seq={rec.get('seq', 0)} boot={rec.get('boot_seq', 0)} "
|
||||
f"boot+{ts_ms}ms ({coil_count}ch)"
|
||||
f" seq={s['seq']} boot={s['boot_seq']} "
|
||||
f"boot+{s['ts_ms']}ms ({s['coil_count']}ch)"
|
||||
)
|
||||
for ch in rec.get("channels", []):
|
||||
mt = ch.get("misc_type", "?")
|
||||
for ch in s["channels"]:
|
||||
mt = ch["misc_type"]
|
||||
misc_desc = SNAP_MISC_TYPE_DESC.get(mt, mt)
|
||||
lines.append(
|
||||
f" ch{ch.get('ch', 0)}: {ch.get('freq_level', '?')} "
|
||||
f"dir={ch.get('direction', 0)} ftype={ch.get('freq_type', 0)} "
|
||||
f"sens={ch.get('sensitivity', 0)} cond={ch.get('condition', 0)} "
|
||||
f"loop={'OK' if ch.get('loop_ok') else '断'} "
|
||||
f"car={'有' if ch.get('has_car') else '无'} "
|
||||
f"freq={ch.get('freq', 0)}Hz Δ={ch.get('variation', 0)} "
|
||||
f"[{misc_desc}] misc={ch.get('misc', 0)}"
|
||||
f" ch{ch['ch']}: {ch['freq_level']} "
|
||||
f"dir={ch['direction']} ftype={ch['freq_type']} "
|
||||
f"sens={ch['sensitivity']} cond={ch['condition']} "
|
||||
f"loop={'OK' if ch['loop_ok'] else '断'} "
|
||||
f"car={'有' if ch['has_car'] else '无'} "
|
||||
f"freq={ch['freq']}Hz Δ={ch['variation']} "
|
||||
f"[{misc_desc}] misc={ch['misc']}"
|
||||
)
|
||||
else:
|
||||
rtype = rec.get("type", "?")
|
||||
desc = LOG_EVENT_TYPE_DESC.get(rtype, rtype)
|
||||
unix_ts = rec.get("unix_ts", 0)
|
||||
if unix_ts:
|
||||
ts_str = datetime.fromtimestamp(unix_ts).strftime("%Y-%m-%d %H:%M:%S")
|
||||
e = parse_offlog_hex(hex_str)
|
||||
if "error" in e:
|
||||
lines.append(f" seq={rec.get('seq', 0)} 解析失败: {e['error']}")
|
||||
continue
|
||||
tname = OFFLOG_TYPE_NAMES.get(e["type"], f"0x{e['type']:02x}")
|
||||
desc = LOG_EVENT_TYPE_DESC.get(tname, tname)
|
||||
if e["unix_ts"]:
|
||||
ts_str = datetime.fromtimestamp(e["unix_ts"]).strftime("%Y-%m-%d %H:%M:%S")
|
||||
else:
|
||||
ts_str = f"boot+{ts_ms}ms (未同步)"
|
||||
rdata = rec.get("data")
|
||||
data_str = json.dumps(rdata, ensure_ascii=False) if rdata else ""
|
||||
ts_str = f"boot+{e['ts_ms']}ms (未同步)"
|
||||
pdesc = offlog_payload_desc(e["type"], e["payload"])
|
||||
lines.append(
|
||||
f" seq={rec.get('seq', 0)} boot={rec.get('boot_seq', 0)} "
|
||||
f"{ts_str} [{desc}] {data_str}"
|
||||
f" seq={e['seq']} boot={e['boot_seq']} "
|
||||
f"{ts_str} [{desc}] {pdesc}"
|
||||
)
|
||||
if not records:
|
||||
lines.append(" (无记录 / 起始序号越界, 可先用 log_stat 确认范围)")
|
||||
|
||||
Reference in New Issue
Block a user