QDAirPortBackend0122/doc/work/飞机GIS链路稳定性优化审查报告_20260302.md

7.8 KiB
Raw Blame History

飞机GIS链路稳定性与前端显示优化审查报告

  • 审查日期: 2026-03-02
  • 审查方式: 静态代码审查(未启动服务、未运行测试)
  • 审查范围: GIS接收 -> 速度/角度计算 -> 平滑/防跳点 -> WebSocket下发

1. 审查结论(先说结论)

当前链路已经有“去抖 + 限跳 + 合并推送”的基础能力,但距离“专业级稳定显示”还有关键缺口。

最主要风险集中在3点

  1. 处理线程与采集线程并发写同一状态对象,存在旧数据回写覆盖新数据的可能,会导致前端回跳、抖动。
  2. 非飞机目标在“异常跳点重获”时采用“丢2次后直接接受原始点”的策略仍可能出现突然跳远。
  3. 速度/航向在不可计算时使用固定默认值40/25/20 km/h, heading=0会向前端输出伪物理状态。

2. 关键问题清单(按严重度)

P0-1 并发回写导致轨迹回跳(高风险)

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/DataProcessingService.java:122
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/DataProcessingService.java:201
    • qaup-collision/src/main/java/com/qaup/collision/common/config/SchedulerConfig.java:19
  • 现象: 先拍快照再计算,计算后再 put 回缓存;在多线程调度下,采集线程可能已经写入更新位置,随后被处理线程“旧快照对象”覆盖。
  • 直接后果: 前端位置回退、路径折返、局部抖动。

P0-2 非飞机对象“重获”策略仍可能瞬移(高风险)

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/websocket/broadcaster/WebSocketMessageBroadcaster.java:522
    • qaup-collision/src/main/java/com/qaup/collision/websocket/broadcaster/WebSocketMessageBroadcaster.java:533
    • qaup-collision/src/main/java/com/qaup/collision/websocket/broadcaster/WebSocketMessageBroadcaster.java:536
  • 现象: 非飞机跳点超限时前2次丢弃第3次直接接受原始坐标。
  • 直接后果: 仍可能“一下子跳出去很远”尤其在短时GPS漂移或上游坐标抖动时。

P0-3 输出伪速度/伪航向(高风险)

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/DataProcessingService.java:170
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/DataProcessingService.java:190
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/DataProcessingService.java:234
  • 现象: 速度/方向算不出来时直接下发默认速度和朝向40/25/20、0度
  • 直接后果: 前端若按速度做插值,会出现“方向突变”或“虚假运动”。

P1-1 飞机同批去重只按 flightNo时间戳并列时无稳定择优中高

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java:415
    • qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java:425
    • qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java:438
  • 现象: 同 flightNo 多点时只看 sourceTimestampMs,并列或空时间戳时选择不稳定。
  • 直接后果: 同一周期内点位可能来回切换,路径“绕一下”或折线异常。

P1-2 速度历史缓存缺少生命周期对齐(中高)

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/SpeedCalculationService.java:32
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/SpeedCalculationService.java:174
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/SpeedCalculationService.java:181
  • 现象: positionHistory 长驻;对象在活跃缓存被清理后,速度历史未同步清理。
  • 直接后果: 对象重现时可能引用过旧历史,造成首帧速度/方向不稳定。

P1-3 时间戳单位双轨(微秒/毫秒)增加前端误用风险(中)

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/websocket/event/PositionUpdateEvent.java:32
    • qaup-collision/src/main/java/com/qaup/collision/dataprocessing/service/DataProcessingService.java:260
    • qaup-collision/src/main/java/com/qaup/collision/websocket/message/UniversalMessage.java:28
  • 现象: 外层消息 timestamp 为微秒payload timestamp 为毫秒。
  • 直接后果: 前端若误用外层时间做动画插值,会出现时间比例错误和轨迹异常。

P2-1 非飞机滤波参数未配置化落地,依赖代码默认值(中)

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/websocket/broadcaster/WebSocketMessageBroadcaster.java:58
    • qaup-collision/src/main/java/com/qaup/collision/websocket/broadcaster/WebSocketMessageBroadcaster.java:130
    • qaup-admin/src/main/resources/application-dev.yml:80
    • qaup-admin/src/main/resources/application-prod.yml:58
  • 现象: 平滑参数大量由 @Value 默认值承载,环境缺少显式配置基线。
  • 直接后果: 不同机场/地图比例下难以精细调参,稳定性受限。

P2-2 x/y 与 lat/lon 语义依赖约定,缺少强校验(中)

  • 证据:
    • qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java:361
    • qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleStatusAggregationService.java:64
  • 现象: 某些来源使用 x/y代码按“x=lat,y=lon”解释若上游调整语义容易引入反转问题。
  • 直接后果: 轨迹漂移、跳点、方向异常。

3. 专业级优化方案(不改代码版建议)

P0 立即改(先止血)

  1. 统一“位置状态单写者”模型。
    • 采集线程只写原始缓存,处理线程只读不回写位置。
    • 速度/航向另设派生字段缓存,避免覆盖位置主状态。
  2. 调整非飞机重获策略。
    • 禁止“第3次直接接收原始点”改为“限步过渡”直到收敛。
    • 这样可消除大跳点。
  3. 去掉默认伪速度/伪航向下发。
    • 不可计算时下发 nullvalid=false 标记。
    • 前端接到无效值时保持上一帧方向,位置只按真实点更新。

P1 本周内改(提升稳定)

  1. 飞机去重引入稳定择优键。
    • 建议排序键: sourceTimestampMs -> trackNumber -> 与上一点距离最小。
  2. 速度历史增加TTL并与对象清理联动。
    • 对象清理时同步 clearHistory(objectId)
  3. 统一消息时间语义。
    • 约定只让前端使用 payload.timestamp(ms) 做运动插值。
    • 外层时间仅用于日志/排序。

P2 持续优化(工程化)

  1. websocket.position.filter.* 全量放入 application-*.yml,分环境调参。
  2. 增加坐标语义守卫。
    • 对 x/y 来源记录 schema 版本并做运行时一致性检测。
  3. 输出质量指标。
    • 每对象统计 drop_rate, outlier_count, max_step_meter, reacquire_count

4. 前端“专业级稳定显示”验收指标(建议)

  1. 单帧位移上限: 非飞机 <= 20m可按业务调飞机 <= 80m。
  2. 跳点率: outlier_drop / total_points < 1%
  3. 抖动率: 静止目标在30秒窗口内位移标准差 <= 1m。
  4. 轨迹连续性: 不允许出现“反向回跳再前进”锯齿(除非上游真实回退)。
  5. 时间一致性: 前端插值仅使用毫秒时间戳,严禁混用微秒。

5. 其它观察

  • 已抽查关键文件编码均为 UTF-8 无 BOM编码规范执行良好。
  • 发现调试日志以 error 级别输出的临时内容,建议后续清理,避免掩盖真实异常。

6. 结语

该项目已经具备基础防抖和限跳框架,但要达到你要求的“前端稳定、专业级显示”,核心是先解决并发回写与重获瞬移策略,再统一速度/时间语义。按本报告的 P0 -> P1 顺序推进,可以明显降低“跳出去很远、路径绕行、频繁抖动”问题。