From 6f61b0c9bfb6dcdab80eaa4fd37e1bf8b54f37d8 Mon Sep 17 00:00:00 2001 From: 16337 <1633794139@qq.com> Date: Sun, 1 Mar 2026 19:58:56 +0800 Subject: [PATCH] =?UTF-8?q?fix(aiot):=20=E4=BF=AE=E5=A4=8D=E9=85=8D?= =?UTF-8?q?=E7=BD=AE=E6=8E=A8=E9=80=81=20rtsp=5Furl=20=E4=B8=BA=E7=A9=BA?= =?UTF-8?q?=E7=9A=84=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - selectByCameraCode 返回 null 时跳过该摄像头,不再推送空 rtsp_url - ZLM 回退 URL 改用 proxy 的 app/stream 构建,修复原先用 camera_code 格式导致的无效路径 - 行为与 buildPayloadFromFlat (HTTP推送) 保持一致 Co-Authored-By: Claude Opus 4.6 --- .../impl/AiRedisConfigServiceImpl.java | 68 +++++++++---------- 1 file changed, 34 insertions(+), 34 deletions(-) diff --git a/src/main/java/com/genersoft/iot/vmp/aiot/service/impl/AiRedisConfigServiceImpl.java b/src/main/java/com/genersoft/iot/vmp/aiot/service/impl/AiRedisConfigServiceImpl.java index 51d89b2d5..f6e82a602 100644 --- a/src/main/java/com/genersoft/iot/vmp/aiot/service/impl/AiRedisConfigServiceImpl.java +++ b/src/main/java/com/genersoft/iot/vmp/aiot/service/impl/AiRedisConfigServiceImpl.java @@ -492,15 +492,19 @@ public class AiRedisConfigServiceImpl implements IAiRedisConfigService { // 摄像头信息 Map cameraMap = new LinkedHashMap<>(); - // cameraId 现在是 camera_code 格式(从 ROI 表) - // 使用 camera_code 查询 StreamProxy 获取详细信息 + // 使用 camera_code 查询 StreamProxy 获取 RTSP 源地址 StreamProxy proxy = streamProxyMapper.selectByCameraCode(cameraId); - cameraMap.put("camera_code", cameraId); // 新字段名 - cameraMap.put("camera_id", cameraId); // 保持向后兼容 + if (proxy == null) { + log.warn("[AiRedis] 摄像头 {} 在 stream_proxy 表中未找到(camera_code 不匹配),跳过。" + + "请确认该摄像头的 camera_code 已正确写入 wvp_stream_proxy 表", cameraId); + continue; + } - // 获取 RTSP URL 和摄像头名称 - String rtspUrl = ""; + cameraMap.put("camera_code", cameraId); + cameraMap.put("camera_id", cameraId); + + // 获取摄像头名称 String cameraName = ""; List cameraRois = roiMapper.queryAllByCameraId(cameraId); @@ -518,48 +522,44 @@ public class AiRedisConfigServiceImpl implements IAiRedisConfigService { } } - // 优先使用 StreamProxy 中的源 URL - if (proxy != null && proxy.getSrcUrl() != null && !proxy.getSrcUrl().isEmpty()) { + // 获取 RTSP URL:优先使用 StreamProxy 的源 URL + String rtspUrl = ""; + if (proxy.getSrcUrl() != null && !proxy.getSrcUrl().isEmpty()) { rtspUrl = proxy.getSrcUrl(); log.debug("[AiRedis] 使用StreamProxy源URL: cameraCode={}, srcUrl={}", cameraId, rtspUrl); } else { - // 降级方案:构建 RTSP 代理地址(通过ZLM媒体服务器) - // cameraId格式为 {app}/{stream},ZLM的RTSP路径直接使用该格式 + // 降级方案:用 proxy 的 app/stream 通过 ZLM 媒体服务器构建代理地址 try { MediaServer mediaServer = mediaServerService.getDefaultMediaServer(); - if (mediaServer == null) { - log.warn("[AiRedis] 无法获取媒体服务器配置,请检查 ZLM 媒体服务器是否已配置"); - } else if (mediaServer.getRtspPort() != 0) { - rtspUrl = String.format("rtsp://%s:%s/%s", - mediaServer.getStreamIp() != null ? mediaServer.getStreamIp() : mediaServer.getIp(), - mediaServer.getRtspPort(), cameraId); - log.debug("[AiRedis] 使用媒体服务器构建RTSP: {}", rtspUrl); - } else if (mediaServer.getHttpPort() != 0) { - rtspUrl = String.format("http://%s:%s/%s.live.flv", - mediaServer.getStreamIp() != null ? mediaServer.getStreamIp() : mediaServer.getIp(), - mediaServer.getHttpPort(), cameraId); - log.debug("[AiRedis] 使用媒体服务器构建HTTP: {}", rtspUrl); - } else { - log.warn("[AiRedis] 媒体服务器 {} 未配置 RTSP/HTTP 端口", mediaServer.getIp()); + if (mediaServer != null && proxy.getApp() != null && proxy.getStream() != null) { + if (mediaServer.getRtspPort() != 0) { + rtspUrl = String.format("rtsp://%s:%s/%s/%s", + mediaServer.getStreamIp() != null ? mediaServer.getStreamIp() : mediaServer.getIp(), + mediaServer.getRtspPort(), proxy.getApp(), proxy.getStream()); + log.debug("[AiRedis] 使用ZLM代理构建RTSP: {}", rtspUrl); + } else if (mediaServer.getHttpPort() != 0) { + rtspUrl = String.format("http://%s:%s/%s/%s.live.flv", + mediaServer.getStreamIp() != null ? mediaServer.getStreamIp() : mediaServer.getIp(), + mediaServer.getHttpPort(), proxy.getApp(), proxy.getStream()); + log.debug("[AiRedis] 使用ZLM代理构建HTTP-FLV: {}", rtspUrl); + } } } catch (Exception e) { log.warn("[AiRedis] 获取媒体服务器信息失败: {}", e.getMessage()); } } + // 无有效 RTSP URL 则跳过,不推送空地址给 Edge + if (rtspUrl == null || rtspUrl.isEmpty()) { + log.warn("[AiRedis] 摄像头 {} 有 stream_proxy 记录但无有效 RTSP 地址(srcUrl 为空且 ZLM 不可用),跳过", cameraId); + continue; + } + cameraMap.put("camera_name", cameraName); cameraMap.put("enabled", true); cameraMap.put("location", ""); - - // 如果没有有效的 RTSP URL,记录警告但仍然添加摄像头(让 Edge 知道它的存在) - if (rtspUrl == null || rtspUrl.isEmpty()) { - log.warn("[AiRedis] 摄像头 {} 没有有效的 RTSP 地址(请检查 stream_proxy 表或媒体服务器配置)", cameraId); - cameraMap.put("rtsp_url", ""); - cameraMap.put("rtsp_url_valid", false); - } else { - cameraMap.put("rtsp_url", rtspUrl); - cameraMap.put("rtsp_url_valid", true); - } + cameraMap.put("rtsp_url", rtspUrl); + cameraMap.put("rtsp_url_valid", true); cameras.add(cameraMap); // 该摄像头下的 ROI 和绑定