Commit 21506440d22a2f77d4bbeb4bb646a27b03bb9022
Committed by
GitHub
Merge branch 'wvp-28181-2.0' into wvp-28181-2.0
Showing
39 changed files
with
667 additions
and
292 deletions
Too many changes to show.
To preserve performance only 39 of 41 files are displayed.
sql/mysql.sql
| @@ -44,7 +44,7 @@ CREATE TABLE `device` ( | @@ -44,7 +44,7 @@ CREATE TABLE `device` ( | ||
| 44 | `charset` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, | 44 | `charset` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, |
| 45 | PRIMARY KEY (`id`), | 45 | PRIMARY KEY (`id`), |
| 46 | UNIQUE KEY `device_deviceId_uindex` (`deviceId`) | 46 | UNIQUE KEY `device_deviceId_uindex` (`deviceId`) |
| 47 | -) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; | 47 | +) ENGINE=InnoDB AUTO_INCREMENT=21 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; |
| 48 | /*!40101 SET character_set_client = @saved_cs_client */; | 48 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 49 | 49 | ||
| 50 | -- | 50 | -- |
| @@ -129,7 +129,7 @@ CREATE TABLE `device_channel` ( | @@ -129,7 +129,7 @@ CREATE TABLE `device_channel` ( | ||
| 129 | PRIMARY KEY (`id`), | 129 | PRIMARY KEY (`id`), |
| 130 | UNIQUE KEY `device_channel_id_uindex` (`id`), | 130 | UNIQUE KEY `device_channel_id_uindex` (`id`), |
| 131 | UNIQUE KEY `device_channel_pk` (`channelId`,`deviceId`) | 131 | UNIQUE KEY `device_channel_pk` (`channelId`,`deviceId`) |
| 132 | -) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; | 132 | +) ENGINE=InnoDB AUTO_INCREMENT=46 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; |
| 133 | /*!40101 SET character_set_client = @saved_cs_client */; | 133 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 134 | 134 | ||
| 135 | -- | 135 | -- |
| @@ -198,7 +198,7 @@ CREATE TABLE `gb_stream` ( | @@ -198,7 +198,7 @@ CREATE TABLE `gb_stream` ( | ||
| 198 | PRIMARY KEY (`gbStreamId`) USING BTREE, | 198 | PRIMARY KEY (`gbStreamId`) USING BTREE, |
| 199 | UNIQUE KEY `app` (`app`,`stream`) USING BTREE, | 199 | UNIQUE KEY `app` (`app`,`stream`) USING BTREE, |
| 200 | UNIQUE KEY `gbId` (`gbId`) USING BTREE | 200 | UNIQUE KEY `gbId` (`gbId`) USING BTREE |
| 201 | -) ENGINE=InnoDB AUTO_INCREMENT=375 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; | 201 | +) ENGINE=InnoDB AUTO_INCREMENT=300766 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; |
| 202 | /*!40101 SET character_set_client = @saved_cs_client */; | 202 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 203 | 203 | ||
| 204 | -- | 204 | -- |
| @@ -228,7 +228,7 @@ CREATE TABLE `log` ( | @@ -228,7 +228,7 @@ CREATE TABLE `log` ( | ||
| 228 | `username` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL, | 228 | `username` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL, |
| 229 | `createTime` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL, | 229 | `createTime` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL, |
| 230 | PRIMARY KEY (`id`) USING BTREE | 230 | PRIMARY KEY (`id`) USING BTREE |
| 231 | -) ENGINE=InnoDB AUTO_INCREMENT=313 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; | 231 | +) ENGINE=InnoDB AUTO_INCREMENT=962 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; |
| 232 | /*!40101 SET character_set_client = @saved_cs_client */; | 232 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 233 | 233 | ||
| 234 | -- | 234 | -- |
| @@ -317,7 +317,7 @@ CREATE TABLE `parent_platform` ( | @@ -317,7 +317,7 @@ CREATE TABLE `parent_platform` ( | ||
| 317 | PRIMARY KEY (`id`), | 317 | PRIMARY KEY (`id`), |
| 318 | UNIQUE KEY `parent_platform_id_uindex` (`id`), | 318 | UNIQUE KEY `parent_platform_id_uindex` (`id`), |
| 319 | UNIQUE KEY `parent_platform_pk` (`serverGBId`) | 319 | UNIQUE KEY `parent_platform_pk` (`serverGBId`) |
| 320 | -) ENGINE=InnoDB AUTO_INCREMENT=14 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; | 320 | +) ENGINE=InnoDB AUTO_INCREMENT=23 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; |
| 321 | /*!40101 SET character_set_client = @saved_cs_client */; | 321 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 322 | 322 | ||
| 323 | -- | 323 | -- |
| @@ -367,7 +367,7 @@ CREATE TABLE `platform_gb_channel` ( | @@ -367,7 +367,7 @@ CREATE TABLE `platform_gb_channel` ( | ||
| 367 | `catalogId` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, | 367 | `catalogId` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, |
| 368 | `deviceChannelId` int NOT NULL, | 368 | `deviceChannelId` int NOT NULL, |
| 369 | PRIMARY KEY (`id`) | 369 | PRIMARY KEY (`id`) |
| 370 | -) ENGINE=InnoDB AUTO_INCREMENT=8 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; | 370 | +) ENGINE=InnoDB AUTO_INCREMENT=47 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; |
| 371 | /*!40101 SET character_set_client = @saved_cs_client */; | 371 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 372 | 372 | ||
| 373 | -- | 373 | -- |
| @@ -393,7 +393,7 @@ CREATE TABLE `platform_gb_stream` ( | @@ -393,7 +393,7 @@ CREATE TABLE `platform_gb_stream` ( | ||
| 393 | `id` int NOT NULL AUTO_INCREMENT, | 393 | `id` int NOT NULL AUTO_INCREMENT, |
| 394 | PRIMARY KEY (`id`), | 394 | PRIMARY KEY (`id`), |
| 395 | UNIQUE KEY `platform_gb_stream_pk` (`platformId`,`catalogId`,`gbStreamId`) | 395 | UNIQUE KEY `platform_gb_stream_pk` (`platformId`,`catalogId`,`gbStreamId`) |
| 396 | -) ENGINE=InnoDB AUTO_INCREMENT=406 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; | 396 | +) ENGINE=InnoDB AUTO_INCREMENT=301207 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci ROW_FORMAT=DYNAMIC; |
| 397 | /*!40101 SET character_set_client = @saved_cs_client */; | 397 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 398 | 398 | ||
| 399 | -- | 399 | -- |
| @@ -415,7 +415,6 @@ DROP TABLE IF EXISTS `stream_proxy`; | @@ -415,7 +415,6 @@ DROP TABLE IF EXISTS `stream_proxy`; | ||
| 415 | CREATE TABLE `stream_proxy` ( | 415 | CREATE TABLE `stream_proxy` ( |
| 416 | `id` int NOT NULL AUTO_INCREMENT, | 416 | `id` int NOT NULL AUTO_INCREMENT, |
| 417 | `type` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, | 417 | `type` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, |
| 418 | - `name` varchar(255) COLLATE utf8mb4_general_ci NOT NULL, | ||
| 419 | `app` varchar(255) COLLATE utf8mb4_general_ci NOT NULL, | 418 | `app` varchar(255) COLLATE utf8mb4_general_ci NOT NULL, |
| 420 | `name` varchar(255) COLLATE utf8mb4_general_ci NOT NULL, | 419 | `name` varchar(255) COLLATE utf8mb4_general_ci NOT NULL, |
| 421 | `stream` varchar(255) COLLATE utf8mb4_general_ci NOT NULL, | 420 | `stream` varchar(255) COLLATE utf8mb4_general_ci NOT NULL, |
| @@ -432,9 +431,10 @@ CREATE TABLE `stream_proxy` ( | @@ -432,9 +431,10 @@ CREATE TABLE `stream_proxy` ( | ||
| 432 | `status` bit(1) NOT NULL, | 431 | `status` bit(1) NOT NULL, |
| 433 | `enable_remove_none_reader` bit(1) NOT NULL, | 432 | `enable_remove_none_reader` bit(1) NOT NULL, |
| 434 | `createTime` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, | 433 | `createTime` varchar(50) COLLATE utf8mb4_general_ci NOT NULL, |
| 434 | + `name` varchar(255) COLLATE utf8mb4_general_ci DEFAULT NULL, | ||
| 435 | PRIMARY KEY (`id`), | 435 | PRIMARY KEY (`id`), |
| 436 | UNIQUE KEY `stream_proxy_pk` (`app`,`stream`) | 436 | UNIQUE KEY `stream_proxy_pk` (`app`,`stream`) |
| 437 | -) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; | 437 | +) ENGINE=InnoDB AUTO_INCREMENT=8 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; |
| 438 | /*!40101 SET character_set_client = @saved_cs_client */; | 438 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 439 | 439 | ||
| 440 | -- | 440 | -- |
| @@ -465,7 +465,7 @@ CREATE TABLE `stream_push` ( | @@ -465,7 +465,7 @@ CREATE TABLE `stream_push` ( | ||
| 465 | `mediaServerId` varchar(50) COLLATE utf8mb4_general_ci DEFAULT NULL, | 465 | `mediaServerId` varchar(50) COLLATE utf8mb4_general_ci DEFAULT NULL, |
| 466 | PRIMARY KEY (`id`), | 466 | PRIMARY KEY (`id`), |
| 467 | UNIQUE KEY `stream_push_pk` (`app`,`stream`) | 467 | UNIQUE KEY `stream_push_pk` (`app`,`stream`) |
| 468 | -) ENGINE=InnoDB AUTO_INCREMENT=394 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; | 468 | +) ENGINE=InnoDB AUTO_INCREMENT=300799 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; |
| 469 | /*!40101 SET character_set_client = @saved_cs_client */; | 469 | /*!40101 SET character_set_client = @saved_cs_client */; |
| 470 | 470 | ||
| 471 | -- | 471 | -- |
| @@ -502,7 +502,7 @@ CREATE TABLE `user` ( | @@ -502,7 +502,7 @@ CREATE TABLE `user` ( | ||
| 502 | 502 | ||
| 503 | LOCK TABLES `user` WRITE; | 503 | LOCK TABLES `user` WRITE; |
| 504 | /*!40000 ALTER TABLE `user` DISABLE KEYS */; | 504 | /*!40000 ALTER TABLE `user` DISABLE KEYS */; |
| 505 | -INSERT INTO `user` VALUES (1,'admin','21232f297a57a5a743894a0e4a801fc3',1,'2021-04-13 14:14:57','2021-04-13 14:14:57'); | 505 | +INSERT INTO `user` VALUES (1,'admin','21232f297a57a5a743894a0e4a801fc3',1,'2021 - 04 - 13 14:14:57','2021 - 04 - 13 14:14:57'); |
| 506 | /*!40000 ALTER TABLE `user` ENABLE KEYS */; | 506 | /*!40000 ALTER TABLE `user` ENABLE KEYS */; |
| 507 | UNLOCK TABLES; | 507 | UNLOCK TABLES; |
| 508 | 508 | ||
| @@ -542,4 +542,4 @@ UNLOCK TABLES; | @@ -542,4 +542,4 @@ UNLOCK TABLES; | ||
| 542 | /*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; | 542 | /*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; |
| 543 | /*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */; | 543 | /*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */; |
| 544 | 544 | ||
| 545 | --- Dump completed on 2022-02-25 20:32:21 | 545 | +-- Dump completed on 2022-03-07 8:26:30 |
src/main/java/com/genersoft/iot/vmp/conf/DynamicTask.java
| @@ -5,6 +5,7 @@ import org.springframework.context.annotation.Bean; | @@ -5,6 +5,7 @@ import org.springframework.context.annotation.Bean; | ||
| 5 | import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler; | 5 | import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler; |
| 6 | import org.springframework.stereotype.Component; | 6 | import org.springframework.stereotype.Component; |
| 7 | 7 | ||
| 8 | +import java.util.Date; | ||
| 8 | import java.util.Map; | 9 | import java.util.Map; |
| 9 | import java.util.concurrent.ConcurrentHashMap; | 10 | import java.util.concurrent.ConcurrentHashMap; |
| 10 | import java.util.concurrent.ScheduledFuture; | 11 | import java.util.concurrent.ScheduledFuture; |
| @@ -25,15 +26,38 @@ public class DynamicTask { | @@ -25,15 +26,38 @@ public class DynamicTask { | ||
| 25 | return new ThreadPoolTaskScheduler(); | 26 | return new ThreadPoolTaskScheduler(); |
| 26 | } | 27 | } |
| 27 | 28 | ||
| 29 | + /** | ||
| 30 | + * 循环执行的任务 | ||
| 31 | + * @param key 任务ID | ||
| 32 | + * @param task 任务 | ||
| 33 | + * @param cycleForCatalog 间隔 | ||
| 34 | + * @return | ||
| 35 | + */ | ||
| 28 | public String startCron(String key, Runnable task, int cycleForCatalog) { | 36 | public String startCron(String key, Runnable task, int cycleForCatalog) { |
| 29 | - stopCron(key); | 37 | + stop(key); |
| 30 | // scheduleWithFixedDelay 必须等待上一个任务结束才开始计时period, cycleForCatalog表示执行的间隔 | 38 | // scheduleWithFixedDelay 必须等待上一个任务结束才开始计时period, cycleForCatalog表示执行的间隔 |
| 31 | ScheduledFuture future = threadPoolTaskScheduler.scheduleWithFixedDelay(task, cycleForCatalog * 1000L); | 39 | ScheduledFuture future = threadPoolTaskScheduler.scheduleWithFixedDelay(task, cycleForCatalog * 1000L); |
| 32 | futureMap.put(key, future); | 40 | futureMap.put(key, future); |
| 33 | return "startCron"; | 41 | return "startCron"; |
| 34 | } | 42 | } |
| 35 | 43 | ||
| 36 | - public void stopCron(String key) { | 44 | + /** |
| 45 | + * 延时任务 | ||
| 46 | + * @param key 任务ID | ||
| 47 | + * @param task 任务 | ||
| 48 | + * @param delay 延时 /秒 | ||
| 49 | + * @return | ||
| 50 | + */ | ||
| 51 | + public String startDelay(String key, Runnable task, int delay) { | ||
| 52 | + stop(key); | ||
| 53 | + Date starTime = new Date(System.currentTimeMillis() + delay * 1000); | ||
| 54 | + // scheduleWithFixedDelay 必须等待上一个任务结束才开始计时period, cycleForCatalog表示执行的间隔 | ||
| 55 | + ScheduledFuture future = threadPoolTaskScheduler.schedule(task, starTime); | ||
| 56 | + futureMap.put(key, future); | ||
| 57 | + return "startCron"; | ||
| 58 | + } | ||
| 59 | + | ||
| 60 | + public void stop(String key) { | ||
| 37 | if (futureMap.get(key) != null && !futureMap.get(key).isCancelled()) { | 61 | if (futureMap.get(key) != null && !futureMap.get(key).isCancelled()) { |
| 38 | futureMap.get(key).cancel(true); | 62 | futureMap.get(key).cancel(true); |
| 39 | } | 63 | } |
src/main/java/com/genersoft/iot/vmp/conf/SipPlatformRunner.java
| @@ -59,8 +59,11 @@ public class SipPlatformRunner implements CommandLineRunner { | @@ -59,8 +59,11 @@ public class SipPlatformRunner implements CommandLineRunner { | ||
| 59 | redisCatchStorage.updatePlatformCatchInfo(parentPlatformCatch); | 59 | redisCatchStorage.updatePlatformCatchInfo(parentPlatformCatch); |
| 60 | 60 | ||
| 61 | // 取消订阅 | 61 | // 取消订阅 |
| 62 | - sipCommanderForPlatform.unregister(parentPlatform, null, null); | ||
| 63 | - Thread.sleep(500); | 62 | + sipCommanderForPlatform.unregister(parentPlatform, null, (eventResult)->{ |
| 63 | + ParentPlatform platform = storager.queryParentPlatByServerGBId(parentPlatform.getServerGBId()); | ||
| 64 | + sipCommanderForPlatform.register(platform, null, null); | ||
| 65 | + }); | ||
| 66 | + | ||
| 64 | // 发送平台未注册消息 | 67 | // 发送平台未注册消息 |
| 65 | publisher.platformNotRegisterEventPublish(parentPlatform.getServerGBId()); | 68 | publisher.platformNotRegisterEventPublish(parentPlatform.getServerGBId()); |
| 66 | } | 69 | } |
src/main/java/com/genersoft/iot/vmp/conf/UserSetup.java
| @@ -19,8 +19,6 @@ public class UserSetup { | @@ -19,8 +19,6 @@ public class UserSetup { | ||
| 19 | 19 | ||
| 20 | private Long playTimeout = 18000L; | 20 | private Long playTimeout = 18000L; |
| 21 | 21 | ||
| 22 | - private Boolean waitTrack = Boolean.FALSE; | ||
| 23 | - | ||
| 24 | private Boolean interfaceAuthentication = Boolean.TRUE; | 22 | private Boolean interfaceAuthentication = Boolean.TRUE; |
| 25 | 23 | ||
| 26 | private Boolean recordPushLive = Boolean.TRUE; | 24 | private Boolean recordPushLive = Boolean.TRUE; |
| @@ -57,10 +55,6 @@ public class UserSetup { | @@ -57,10 +55,6 @@ public class UserSetup { | ||
| 57 | return playTimeout; | 55 | return playTimeout; |
| 58 | } | 56 | } |
| 59 | 57 | ||
| 60 | - public Boolean isWaitTrack() { | ||
| 61 | - return waitTrack; | ||
| 62 | - } | ||
| 63 | - | ||
| 64 | public Boolean isInterfaceAuthentication() { | 58 | public Boolean isInterfaceAuthentication() { |
| 65 | return interfaceAuthentication; | 59 | return interfaceAuthentication; |
| 66 | } | 60 | } |
| @@ -89,10 +83,6 @@ public class UserSetup { | @@ -89,10 +83,6 @@ public class UserSetup { | ||
| 89 | this.playTimeout = playTimeout; | 83 | this.playTimeout = playTimeout; |
| 90 | } | 84 | } |
| 91 | 85 | ||
| 92 | - public void setWaitTrack(Boolean waitTrack) { | ||
| 93 | - this.waitTrack = waitTrack; | ||
| 94 | - } | ||
| 95 | - | ||
| 96 | public void setInterfaceAuthentication(boolean interfaceAuthentication) { | 86 | public void setInterfaceAuthentication(boolean interfaceAuthentication) { |
| 97 | this.interfaceAuthentication = interfaceAuthentication; | 87 | this.interfaceAuthentication = interfaceAuthentication; |
| 98 | } | 88 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/auth/RegisterLogicHandler.java
| 1 | package com.genersoft.iot.vmp.gb28181.auth; | 1 | package com.genersoft.iot.vmp.gb28181.auth; |
| 2 | 2 | ||
| 3 | +import com.genersoft.iot.vmp.storager.impl.VideoManagerStoragerImpl; | ||
| 3 | import org.slf4j.Logger; | 4 | import org.slf4j.Logger; |
| 4 | import org.slf4j.LoggerFactory; | 5 | import org.slf4j.LoggerFactory; |
| 5 | import org.springframework.beans.factory.annotation.Autowired; | 6 | import org.springframework.beans.factory.annotation.Autowired; |
| @@ -20,13 +21,24 @@ public class RegisterLogicHandler { | @@ -20,13 +21,24 @@ public class RegisterLogicHandler { | ||
| 20 | 21 | ||
| 21 | @Autowired | 22 | @Autowired |
| 22 | private SIPCommander cmder; | 23 | private SIPCommander cmder; |
| 24 | + | ||
| 25 | + @Autowired | ||
| 26 | + private VideoManagerStoragerImpl storager; | ||
| 23 | 27 | ||
| 24 | public void onRegister(Device device) { | 28 | public void onRegister(Device device) { |
| 25 | // 只有第一次注册时调用查询设备信息,如需更新调用更新API接口 | 29 | // 只有第一次注册时调用查询设备信息,如需更新调用更新API接口 |
| 30 | + // TODO 此处错误无法获取到通道 | ||
| 31 | + Device device1 = storager.queryVideoDevice(device.getDeviceId()); | ||
| 26 | if (device.isFirsRegister()) { | 32 | if (device.isFirsRegister()) { |
| 27 | logger.info("[{}] 首次注册,查询设备信息以及通道信息", device.getDeviceId()); | 33 | logger.info("[{}] 首次注册,查询设备信息以及通道信息", device.getDeviceId()); |
| 28 | - cmder.deviceInfoQuery(device); | ||
| 29 | - cmder.catalogQuery(device, null); | 34 | + try { |
| 35 | + Thread.sleep(100); | ||
| 36 | + cmder.deviceInfoQuery(device); | ||
| 37 | + Thread.sleep(100); | ||
| 38 | + cmder.catalogQuery(device, null); | ||
| 39 | + } catch (InterruptedException e) { | ||
| 40 | + e.printStackTrace(); | ||
| 41 | + } | ||
| 30 | } | 42 | } |
| 31 | } | 43 | } |
| 32 | } | 44 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/bean/SendRtpItem.java
| @@ -81,6 +81,10 @@ public class SendRtpItem { | @@ -81,6 +81,10 @@ public class SendRtpItem { | ||
| 81 | */ | 81 | */ |
| 82 | private boolean isPlay; | 82 | private boolean isPlay; |
| 83 | 83 | ||
| 84 | + private byte[] transaction; | ||
| 85 | + | ||
| 86 | + private byte[] dialog; | ||
| 87 | + | ||
| 84 | public String getIp() { | 88 | public String getIp() { |
| 85 | return ip; | 89 | return ip; |
| 86 | } | 90 | } |
| @@ -200,4 +204,20 @@ public class SendRtpItem { | @@ -200,4 +204,20 @@ public class SendRtpItem { | ||
| 200 | public void setPlay(boolean play) { | 204 | public void setPlay(boolean play) { |
| 201 | isPlay = play; | 205 | isPlay = play; |
| 202 | } | 206 | } |
| 207 | + | ||
| 208 | + public byte[] getTransaction() { | ||
| 209 | + return transaction; | ||
| 210 | + } | ||
| 211 | + | ||
| 212 | + public void setTransaction(byte[] transaction) { | ||
| 213 | + this.transaction = transaction; | ||
| 214 | + } | ||
| 215 | + | ||
| 216 | + public byte[] getDialog() { | ||
| 217 | + return dialog; | ||
| 218 | + } | ||
| 219 | + | ||
| 220 | + public void setDialog(byte[] dialog) { | ||
| 221 | + this.dialog = dialog; | ||
| 222 | + } | ||
| 203 | } | 223 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/event/offline/KeepaliveTimeoutListenerForPlatform.java
| @@ -2,7 +2,10 @@ package com.genersoft.iot.vmp.gb28181.event.offline; | @@ -2,7 +2,10 @@ package com.genersoft.iot.vmp.gb28181.event.offline; | ||
| 2 | 2 | ||
| 3 | import com.genersoft.iot.vmp.conf.RedisKeyExpirationEventMessageListener; | 3 | import com.genersoft.iot.vmp.conf.RedisKeyExpirationEventMessageListener; |
| 4 | import com.genersoft.iot.vmp.conf.UserSetup; | 4 | import com.genersoft.iot.vmp.conf.UserSetup; |
| 5 | +import com.genersoft.iot.vmp.gb28181.bean.Device; | ||
| 6 | +import com.genersoft.iot.vmp.gb28181.bean.ParentPlatform; | ||
| 5 | import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; | 7 | import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; |
| 8 | +import com.genersoft.iot.vmp.storager.IVideoManagerStorager; | ||
| 6 | import org.slf4j.Logger; | 9 | import org.slf4j.Logger; |
| 7 | import org.slf4j.LoggerFactory; | 10 | import org.slf4j.LoggerFactory; |
| 8 | import org.springframework.beans.factory.InitializingBean; | 11 | import org.springframework.beans.factory.InitializingBean; |
| @@ -39,6 +42,9 @@ public class KeepaliveTimeoutListenerForPlatform extends RedisKeyExpirationEvent | @@ -39,6 +42,9 @@ public class KeepaliveTimeoutListenerForPlatform extends RedisKeyExpirationEvent | ||
| 39 | @Autowired | 42 | @Autowired |
| 40 | private SipSubscribe sipSubscribe; | 43 | private SipSubscribe sipSubscribe; |
| 41 | 44 | ||
| 45 | + @Autowired | ||
| 46 | + private IVideoManagerStorager storager; | ||
| 47 | + | ||
| 42 | public KeepaliveTimeoutListenerForPlatform(RedisMessageListenerContainer listenerContainer, UserSetup userSetup) { | 48 | public KeepaliveTimeoutListenerForPlatform(RedisMessageListenerContainer listenerContainer, UserSetup userSetup) { |
| 43 | super(listenerContainer, userSetup); | 49 | super(listenerContainer, userSetup); |
| 44 | } | 50 | } |
| @@ -61,15 +67,22 @@ public class KeepaliveTimeoutListenerForPlatform extends RedisKeyExpirationEvent | @@ -61,15 +67,22 @@ public class KeepaliveTimeoutListenerForPlatform extends RedisKeyExpirationEvent | ||
| 61 | String REGISTER_INFO_PREFIX = VideoManagerConstants.PLATFORM_REGISTER_INFO_PREFIX + userSetup.getServerId() + "_"; | 67 | String REGISTER_INFO_PREFIX = VideoManagerConstants.PLATFORM_REGISTER_INFO_PREFIX + userSetup.getServerId() + "_"; |
| 62 | if (expiredKey.startsWith(PLATFORM_KEEPLIVEKEY_PREFIX)) { | 68 | if (expiredKey.startsWith(PLATFORM_KEEPLIVEKEY_PREFIX)) { |
| 63 | String platformGBId = expiredKey.substring(PLATFORM_KEEPLIVEKEY_PREFIX.length(),expiredKey.length()); | 69 | String platformGBId = expiredKey.substring(PLATFORM_KEEPLIVEKEY_PREFIX.length(),expiredKey.length()); |
| 64 | - | ||
| 65 | - publisher.platformKeepaliveExpireEventPublish(platformGBId); | 70 | + ParentPlatform platform = storager.queryParentPlatByServerGBId(platformGBId); |
| 71 | + if (platform != null) { | ||
| 72 | + publisher.platformKeepaliveExpireEventPublish(platformGBId); | ||
| 73 | + } | ||
| 66 | }else if (expiredKey.startsWith(PLATFORM_REGISTER_PREFIX)) { | 74 | }else if (expiredKey.startsWith(PLATFORM_REGISTER_PREFIX)) { |
| 67 | String platformGBId = expiredKey.substring(PLATFORM_REGISTER_PREFIX.length(),expiredKey.length()); | 75 | String platformGBId = expiredKey.substring(PLATFORM_REGISTER_PREFIX.length(),expiredKey.length()); |
| 68 | - | ||
| 69 | - publisher.platformRegisterCycleEventPublish(platformGBId); | 76 | + ParentPlatform platform = storager.queryParentPlatByServerGBId(platformGBId); |
| 77 | + if (platform != null) { | ||
| 78 | + publisher.platformRegisterCycleEventPublish(platformGBId); | ||
| 79 | + } | ||
| 70 | }else if (expiredKey.startsWith(KEEPLIVEKEY_PREFIX)){ | 80 | }else if (expiredKey.startsWith(KEEPLIVEKEY_PREFIX)){ |
| 71 | String deviceId = expiredKey.substring(KEEPLIVEKEY_PREFIX.length(),expiredKey.length()); | 81 | String deviceId = expiredKey.substring(KEEPLIVEKEY_PREFIX.length(),expiredKey.length()); |
| 72 | - publisher.outlineEventPublish(deviceId, KEEPLIVEKEY_PREFIX); | 82 | + Device device = storager.queryVideoDevice(deviceId); |
| 83 | + if (device != null) { | ||
| 84 | + publisher.outlineEventPublish(deviceId, KEEPLIVEKEY_PREFIX); | ||
| 85 | + } | ||
| 73 | }else if (expiredKey.startsWith(REGISTER_INFO_PREFIX)) { | 86 | }else if (expiredKey.startsWith(REGISTER_INFO_PREFIX)) { |
| 74 | String callid = expiredKey.substring(REGISTER_INFO_PREFIX.length()); | 87 | String callid = expiredKey.substring(REGISTER_INFO_PREFIX.length()); |
| 75 | SipSubscribe.EventResult eventResult = new SipSubscribe.EventResult(); | 88 | SipSubscribe.EventResult eventResult = new SipSubscribe.EventResult(); |
src/main/java/com/genersoft/iot/vmp/gb28181/event/offline/OfflineEventListener.java
| @@ -2,8 +2,13 @@ package com.genersoft.iot.vmp.gb28181.event.offline; | @@ -2,8 +2,13 @@ package com.genersoft.iot.vmp.gb28181.event.offline; | ||
| 2 | 2 | ||
| 3 | import com.genersoft.iot.vmp.conf.UserSetup; | 3 | import com.genersoft.iot.vmp.conf.UserSetup; |
| 4 | import com.genersoft.iot.vmp.gb28181.bean.DeviceChannel; | 4 | import com.genersoft.iot.vmp.gb28181.bean.DeviceChannel; |
| 5 | +import com.genersoft.iot.vmp.gb28181.bean.SsrcTransaction; | ||
| 5 | import com.genersoft.iot.vmp.gb28181.event.EventPublisher; | 6 | import com.genersoft.iot.vmp.gb28181.event.EventPublisher; |
| 6 | import com.genersoft.iot.vmp.gb28181.event.subscribe.catalog.CatalogEvent; | 7 | import com.genersoft.iot.vmp.gb28181.event.subscribe.catalog.CatalogEvent; |
| 8 | +import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; | ||
| 9 | +import com.genersoft.iot.vmp.media.zlm.ZLMRTPServerFactory; | ||
| 10 | +import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; | ||
| 11 | +import com.genersoft.iot.vmp.service.IMediaServerService; | ||
| 7 | import org.slf4j.Logger; | 12 | import org.slf4j.Logger; |
| 8 | import org.slf4j.LoggerFactory; | 13 | import org.slf4j.LoggerFactory; |
| 9 | import org.springframework.beans.factory.annotation.Autowired; | 14 | import org.springframework.beans.factory.annotation.Autowired; |
| @@ -32,6 +37,9 @@ public class OfflineEventListener implements ApplicationListener<OfflineEvent> { | @@ -32,6 +37,9 @@ public class OfflineEventListener implements ApplicationListener<OfflineEvent> { | ||
| 32 | 37 | ||
| 33 | @Autowired | 38 | @Autowired |
| 34 | private IVideoManagerStorager storager; | 39 | private IVideoManagerStorager storager; |
| 40 | + | ||
| 41 | + @Autowired | ||
| 42 | + private VideoStreamSessionManager streamSession; | ||
| 35 | 43 | ||
| 36 | @Autowired | 44 | @Autowired |
| 37 | private RedisUtil redis; | 45 | private RedisUtil redis; |
| @@ -42,6 +50,14 @@ public class OfflineEventListener implements ApplicationListener<OfflineEvent> { | @@ -42,6 +50,14 @@ public class OfflineEventListener implements ApplicationListener<OfflineEvent> { | ||
| 42 | @Autowired | 50 | @Autowired |
| 43 | private EventPublisher eventPublisher; | 51 | private EventPublisher eventPublisher; |
| 44 | 52 | ||
| 53 | + | ||
| 54 | + @Autowired | ||
| 55 | + private IMediaServerService mediaServerService; | ||
| 56 | + | ||
| 57 | + | ||
| 58 | + @Autowired | ||
| 59 | + private ZLMRTPServerFactory zlmrtpServerFactory; | ||
| 60 | + | ||
| 45 | @Override | 61 | @Override |
| 46 | public void onApplicationEvent(OfflineEvent event) { | 62 | public void onApplicationEvent(OfflineEvent event) { |
| 47 | 63 | ||
| @@ -73,5 +89,15 @@ public class OfflineEventListener implements ApplicationListener<OfflineEvent> { | @@ -73,5 +89,15 @@ public class OfflineEventListener implements ApplicationListener<OfflineEvent> { | ||
| 73 | 89 | ||
| 74 | // TODO 离线取消订阅 | 90 | // TODO 离线取消订阅 |
| 75 | 91 | ||
| 92 | + // 离线释放所有ssrc | ||
| 93 | + List<SsrcTransaction> ssrcTransactions = streamSession.getSsrcTransactionForAll(event.getDeviceId(), null, null, null); | ||
| 94 | + if (ssrcTransactions.size() > 0) { | ||
| 95 | + for (SsrcTransaction ssrcTransaction : ssrcTransactions) { | ||
| 96 | + mediaServerService.releaseSsrc(ssrcTransaction.getMediaServerId(), ssrcTransaction.getSsrc()); | ||
| 97 | + mediaServerService.closeRTPServer(event.getDeviceId(), ssrcTransaction.getChannelId(), ssrcTransaction.getStream()); | ||
| 98 | + streamSession.remove(event.getDeviceId(), ssrcTransaction.getChannelId(), ssrcTransaction.getStream()); | ||
| 99 | + } | ||
| 100 | + } | ||
| 101 | + | ||
| 76 | } | 102 | } |
| 77 | } | 103 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/event/platformNotRegister/PlatformNotRegisterEventLister.java
| @@ -75,7 +75,7 @@ public class PlatformNotRegisterEventLister implements ApplicationListener<Platf | @@ -75,7 +75,7 @@ public class PlatformNotRegisterEventLister implements ApplicationListener<Platf | ||
| 75 | stream.append(","); | 75 | stream.append(","); |
| 76 | } | 76 | } |
| 77 | stream.append(sendRtpItem.getStreamId()); | 77 | stream.append(sendRtpItem.getStreamId()); |
| 78 | - redisCatchStorage.deleteSendRTPServer(event.getPlatformGbID(), sendRtpItem.getChannelId()); | 78 | + redisCatchStorage.deleteSendRTPServer(event.getPlatformGbID(), sendRtpItem.getChannelId(), null, null); |
| 79 | MediaServerItem mediaInfo = mediaServerService.getOne(sendRtpItem.getMediaServerId()); | 79 | MediaServerItem mediaInfo = mediaServerService.getOne(sendRtpItem.getMediaServerId()); |
| 80 | Map<String, Object> param = new HashMap<>(); | 80 | Map<String, Object> param = new HashMap<>(); |
| 81 | param.put("vhost", "__defaultVhost__"); | 81 | param.put("vhost", "__defaultVhost__"); |
| @@ -84,9 +84,7 @@ public class PlatformNotRegisterEventLister implements ApplicationListener<Platf | @@ -84,9 +84,7 @@ public class PlatformNotRegisterEventLister implements ApplicationListener<Platf | ||
| 84 | zlmrtpServerFactory.stopSendRtpStream(mediaInfo, param); | 84 | zlmrtpServerFactory.stopSendRtpStream(mediaInfo, param); |
| 85 | } | 85 | } |
| 86 | 86 | ||
| 87 | - | ||
| 88 | } | 87 | } |
| 89 | - | ||
| 90 | Timer timer = new Timer(); | 88 | Timer timer = new Timer(); |
| 91 | SipSubscribe.Event okEvent = (responseEvent)->{ | 89 | SipSubscribe.Event okEvent = (responseEvent)->{ |
| 92 | timer.cancel(); | 90 | timer.cancel(); |
src/main/java/com/genersoft/iot/vmp/gb28181/event/subscribe/SubscribeListenerForPlatform.java
| @@ -4,8 +4,6 @@ import com.genersoft.iot.vmp.common.VideoManagerConstants; | @@ -4,8 +4,6 @@ import com.genersoft.iot.vmp.common.VideoManagerConstants; | ||
| 4 | import com.genersoft.iot.vmp.conf.DynamicTask; | 4 | import com.genersoft.iot.vmp.conf.DynamicTask; |
| 5 | import com.genersoft.iot.vmp.conf.RedisKeyExpirationEventMessageListener; | 5 | import com.genersoft.iot.vmp.conf.RedisKeyExpirationEventMessageListener; |
| 6 | import com.genersoft.iot.vmp.conf.UserSetup; | 6 | import com.genersoft.iot.vmp.conf.UserSetup; |
| 7 | -import com.genersoft.iot.vmp.gb28181.event.EventPublisher; | ||
| 8 | -import org.checkerframework.checker.units.qual.A; | ||
| 9 | import org.slf4j.Logger; | 7 | import org.slf4j.Logger; |
| 10 | import org.slf4j.LoggerFactory; | 8 | import org.slf4j.LoggerFactory; |
| 11 | import org.springframework.beans.factory.annotation.Autowired; | 9 | import org.springframework.beans.factory.annotation.Autowired; |
| @@ -46,7 +44,7 @@ public class SubscribeListenerForPlatform extends RedisKeyExpirationEventMessage | @@ -46,7 +44,7 @@ public class SubscribeListenerForPlatform extends RedisKeyExpirationEventMessage | ||
| 46 | String PLATFORM_KEEPLIVEKEY_PREFIX = VideoManagerConstants.SIP_SUBSCRIBE_PREFIX + userSetup.getServerId() + "_"; | 44 | String PLATFORM_KEEPLIVEKEY_PREFIX = VideoManagerConstants.SIP_SUBSCRIBE_PREFIX + userSetup.getServerId() + "_"; |
| 47 | if (expiredKey.startsWith(PLATFORM_KEEPLIVEKEY_PREFIX)) { | 45 | if (expiredKey.startsWith(PLATFORM_KEEPLIVEKEY_PREFIX)) { |
| 48 | // 取消定时任务 | 46 | // 取消定时任务 |
| 49 | - dynamicTask.stopCron(expiredKey); | 47 | + dynamicTask.stop(expiredKey); |
| 50 | } | 48 | } |
| 51 | } | 49 | } |
| 52 | } | 50 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/session/VideoStreamSessionManager.java
| @@ -86,6 +86,15 @@ public class VideoStreamSessionManager { | @@ -86,6 +86,15 @@ public class VideoStreamSessionManager { | ||
| 86 | return dialog; | 86 | return dialog; |
| 87 | } | 87 | } |
| 88 | 88 | ||
| 89 | + public SIPDialog getDialogByCallId(String deviceId, String channelId, String callID){ | ||
| 90 | + SsrcTransaction ssrcTransaction = getSsrcTransaction(deviceId, channelId, callID, null); | ||
| 91 | + if (ssrcTransaction == null) return null; | ||
| 92 | + byte[] dialogByteArray = ssrcTransaction.getDialog(); | ||
| 93 | + if (dialogByteArray == null) return null; | ||
| 94 | + SIPDialog dialog = (SIPDialog)SerializeUtils.deSerialize(dialogByteArray); | ||
| 95 | + return dialog; | ||
| 96 | + } | ||
| 97 | + | ||
| 89 | public SsrcTransaction getSsrcTransaction(String deviceId, String channelId, String callId, String stream){ | 98 | public SsrcTransaction getSsrcTransaction(String deviceId, String channelId, String callId, String stream){ |
| 90 | if (StringUtils.isEmpty(callId)) callId ="*"; | 99 | if (StringUtils.isEmpty(callId)) callId ="*"; |
| 91 | if (StringUtils.isEmpty(stream)) stream ="*"; | 100 | if (StringUtils.isEmpty(stream)) stream ="*"; |
| @@ -95,6 +104,21 @@ public class VideoStreamSessionManager { | @@ -95,6 +104,21 @@ public class VideoStreamSessionManager { | ||
| 95 | return (SsrcTransaction)redisUtil.get((String) scanResult.get(0)); | 104 | return (SsrcTransaction)redisUtil.get((String) scanResult.get(0)); |
| 96 | } | 105 | } |
| 97 | 106 | ||
| 107 | + public List<SsrcTransaction> getSsrcTransactionForAll(String deviceId, String channelId, String callId, String stream){ | ||
| 108 | + if (StringUtils.isEmpty(deviceId)) deviceId ="*"; | ||
| 109 | + if (StringUtils.isEmpty(channelId)) channelId ="*"; | ||
| 110 | + if (StringUtils.isEmpty(callId)) callId ="*"; | ||
| 111 | + if (StringUtils.isEmpty(stream)) stream ="*"; | ||
| 112 | + String key = VideoManagerConstants.MEDIA_TRANSACTION_USED_PREFIX + userSetup.getServerId() + "_" + deviceId + "_" + channelId + "_" + callId+ "_" + stream; | ||
| 113 | + List<Object> scanResult = redisUtil.scan(key); | ||
| 114 | + if (scanResult.size() == 0) return null; | ||
| 115 | + List<SsrcTransaction> result = new ArrayList<>(); | ||
| 116 | + for (Object keyObj : scanResult) { | ||
| 117 | + result.add((SsrcTransaction)redisUtil.get((String) keyObj)); | ||
| 118 | + } | ||
| 119 | + return result; | ||
| 120 | + } | ||
| 121 | + | ||
| 98 | public String getMediaServerId(String deviceId, String channelId, String stream){ | 122 | public String getMediaServerId(String deviceId, String channelId, String stream){ |
| 99 | SsrcTransaction ssrcTransaction = getSsrcTransaction(deviceId, channelId, null, stream); | 123 | SsrcTransaction ssrcTransaction = getSsrcTransaction(deviceId, channelId, null, stream); |
| 100 | if (ssrcTransaction == null) return null; | 124 | if (ssrcTransaction == null) return null; |
src/main/java/com/genersoft/iot/vmp/gb28181/task/GPSSubscribeTask.java
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/cmd/ISIPCommanderForPlatform.java
| @@ -96,4 +96,11 @@ public interface ISIPCommanderForPlatform { | @@ -96,4 +96,11 @@ public interface ISIPCommanderForPlatform { | ||
| 96 | * @param recordInfo 录像信息 | 96 | * @param recordInfo 录像信息 |
| 97 | */ | 97 | */ |
| 98 | boolean recordInfo(DeviceChannel deviceChannel, ParentPlatform parentPlatform, String fromTag, RecordInfo recordInfo); | 98 | boolean recordInfo(DeviceChannel deviceChannel, ParentPlatform parentPlatform, String fromTag, RecordInfo recordInfo); |
| 99 | + | ||
| 100 | + /** | ||
| 101 | + * 向发起点播的上级回复bye | ||
| 102 | + * @param platform 平台信息 | ||
| 103 | + * @param callId callId | ||
| 104 | + */ | ||
| 105 | + void streamByeCmd(ParentPlatform platform, String callId); | ||
| 99 | } | 106 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/cmd/impl/SIPCommander.java
| @@ -2,6 +2,7 @@ package com.genersoft.iot.vmp.gb28181.transmit.cmd.impl; | @@ -2,6 +2,7 @@ package com.genersoft.iot.vmp.gb28181.transmit.cmd.impl; | ||
| 2 | 2 | ||
| 3 | import com.alibaba.fastjson.JSONObject; | 3 | import com.alibaba.fastjson.JSONObject; |
| 4 | import com.genersoft.iot.vmp.common.StreamInfo; | 4 | import com.genersoft.iot.vmp.common.StreamInfo; |
| 5 | +import com.genersoft.iot.vmp.conf.DynamicTask; | ||
| 5 | import com.genersoft.iot.vmp.conf.SipConfig; | 6 | import com.genersoft.iot.vmp.conf.SipConfig; |
| 6 | import com.genersoft.iot.vmp.conf.UserSetup; | 7 | import com.genersoft.iot.vmp.conf.UserSetup; |
| 7 | import com.genersoft.iot.vmp.gb28181.bean.Device; | 8 | import com.genersoft.iot.vmp.gb28181.bean.Device; |
| @@ -85,6 +86,9 @@ public class SIPCommander implements ISIPCommander { | @@ -85,6 +86,9 @@ public class SIPCommander implements ISIPCommander { | ||
| 85 | @Autowired | 86 | @Autowired |
| 86 | private IMediaServerService mediaServerService; | 87 | private IMediaServerService mediaServerService; |
| 87 | 88 | ||
| 89 | + @Autowired | ||
| 90 | + private DynamicTask dynamicTask; | ||
| 91 | + | ||
| 88 | 92 | ||
| 89 | /** | 93 | /** |
| 90 | * 云台方向放控制,使用配置文件中的默认镜头移动速度 | 94 | * 云台方向放控制,使用配置文件中的默认镜头移动速度 |
| @@ -330,7 +334,8 @@ public class SIPCommander implements ISIPCommander { | @@ -330,7 +334,8 @@ public class SIPCommander implements ISIPCommander { | ||
| 330 | * @param errorEvent sip错误订阅 | 334 | * @param errorEvent sip错误订阅 |
| 331 | */ | 335 | */ |
| 332 | @Override | 336 | @Override |
| 333 | - public void playStreamCmd(MediaServerItem mediaServerItem, SSRCInfo ssrcInfo, Device device, String channelId, ZLMHttpHookSubscribe.Event event, SipSubscribe.Event errorEvent) { | 337 | + public void playStreamCmd(MediaServerItem mediaServerItem, SSRCInfo ssrcInfo, Device device, String channelId, |
| 338 | + ZLMHttpHookSubscribe.Event event, SipSubscribe.Event errorEvent) { | ||
| 334 | String streamId = ssrcInfo.getStream(); | 339 | String streamId = ssrcInfo.getStream(); |
| 335 | try { | 340 | try { |
| 336 | if (device == null) return; | 341 | if (device == null) return; |
| @@ -342,15 +347,13 @@ public class SIPCommander implements ISIPCommander { | @@ -342,15 +347,13 @@ public class SIPCommander implements ISIPCommander { | ||
| 342 | subscribeKey.put("app", "rtp"); | 347 | subscribeKey.put("app", "rtp"); |
| 343 | subscribeKey.put("stream", streamId); | 348 | subscribeKey.put("stream", streamId); |
| 344 | subscribeKey.put("regist", true); | 349 | subscribeKey.put("regist", true); |
| 350 | + subscribeKey.put("schema", "rtmp"); | ||
| 345 | subscribeKey.put("mediaServerId", mediaServerItem.getId()); | 351 | subscribeKey.put("mediaServerId", mediaServerItem.getId()); |
| 346 | subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey, | 352 | subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey, |
| 347 | (MediaServerItem mediaServerItemInUse, JSONObject json)->{ | 353 | (MediaServerItem mediaServerItemInUse, JSONObject json)->{ |
| 348 | - if (userSetup.isWaitTrack() && json.getJSONArray("tracks") == null) return; | ||
| 349 | if (event != null) { | 354 | if (event != null) { |
| 350 | event.response(mediaServerItemInUse, json); | 355 | event.response(mediaServerItemInUse, json); |
| 351 | } | 356 | } |
| 352 | - | ||
| 353 | -// subscribe.removeSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey); | ||
| 354 | }); | 357 | }); |
| 355 | // | 358 | // |
| 356 | StringBuffer content = new StringBuffer(200); | 359 | StringBuffer content = new StringBuffer(200); |
| @@ -419,7 +422,7 @@ public class SIPCommander implements ISIPCommander { | @@ -419,7 +422,7 @@ public class SIPCommander implements ISIPCommander { | ||
| 419 | 422 | ||
| 420 | transmitRequest(device, request, (e -> { | 423 | transmitRequest(device, request, (e -> { |
| 421 | streamSession.remove(device.getDeviceId(), channelId, ssrcInfo.getStream()); | 424 | streamSession.remove(device.getDeviceId(), channelId, ssrcInfo.getStream()); |
| 422 | - mediaServerService.releaseSsrc(mediaServerItem, ssrcInfo.getSsrc()); | 425 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); |
| 423 | errorEvent.response(e); | 426 | errorEvent.response(e); |
| 424 | }), e ->{ | 427 | }), e ->{ |
| 425 | // 这里为例避免一个通道的点播只有一个callID这个参数使用一个固定值 | 428 | // 这里为例避免一个通道的点播只有一个callID这个参数使用一个固定值 |
| @@ -458,8 +461,6 @@ public class SIPCommander implements ISIPCommander { | @@ -458,8 +461,6 @@ public class SIPCommander implements ISIPCommander { | ||
| 458 | logger.debug("录像回放添加订阅,订阅内容:" + subscribeKey.toString()); | 461 | logger.debug("录像回放添加订阅,订阅内容:" + subscribeKey.toString()); |
| 459 | subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey, | 462 | subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey, |
| 460 | (MediaServerItem mediaServerItemInUse, JSONObject json)->{ | 463 | (MediaServerItem mediaServerItemInUse, JSONObject json)->{ |
| 461 | - System.out.println(344444); | ||
| 462 | - if (userSetup.isWaitTrack() && json.getJSONArray("tracks") == null) return; | ||
| 463 | if (event != null) { | 464 | if (event != null) { |
| 464 | event.response(mediaServerItemInUse, json); | 465 | event.response(mediaServerItemInUse, json); |
| 465 | } | 466 | } |
| @@ -565,7 +566,6 @@ public class SIPCommander implements ISIPCommander { | @@ -565,7 +566,6 @@ public class SIPCommander implements ISIPCommander { | ||
| 565 | logger.debug("录像回放添加订阅,订阅内容:" + subscribeKey.toString()); | 566 | logger.debug("录像回放添加订阅,订阅内容:" + subscribeKey.toString()); |
| 566 | subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey, | 567 | subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey, |
| 567 | (MediaServerItem mediaServerItemInUse, JSONObject json)->{ | 568 | (MediaServerItem mediaServerItemInUse, JSONObject json)->{ |
| 568 | - if (userSetup.isWaitTrack() && json.getJSONArray("tracks") == null) return; | ||
| 569 | event.response(mediaServerItemInUse, json); | 569 | event.response(mediaServerItemInUse, json); |
| 570 | subscribe.removeSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey); | 570 | subscribe.removeSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey); |
| 571 | }); | 571 | }); |
| @@ -662,6 +662,7 @@ public class SIPCommander implements ISIPCommander { | @@ -662,6 +662,7 @@ public class SIPCommander implements ISIPCommander { | ||
| 662 | @Override | 662 | @Override |
| 663 | public void streamByeCmd(String deviceId, String channelId, String stream, SipSubscribe.Event okEvent) { | 663 | public void streamByeCmd(String deviceId, String channelId, String stream, SipSubscribe.Event okEvent) { |
| 664 | try { | 664 | try { |
| 665 | + SsrcTransaction ssrcTransaction = streamSession.getSsrcTransaction(deviceId, channelId, null, stream); | ||
| 665 | ClientTransaction transaction = streamSession.getTransactionByStream(deviceId, channelId, stream); | 666 | ClientTransaction transaction = streamSession.getTransactionByStream(deviceId, channelId, stream); |
| 666 | if (transaction == null) { | 667 | if (transaction == null) { |
| 667 | logger.warn("[ {} -> {}]停止视频流的时候发现事务已丢失", deviceId, channelId); | 668 | logger.warn("[ {} -> {}]停止视频流的时候发现事务已丢失", deviceId, channelId); |
| @@ -715,10 +716,9 @@ public class SIPCommander implements ISIPCommander { | @@ -715,10 +716,9 @@ public class SIPCommander implements ISIPCommander { | ||
| 715 | 716 | ||
| 716 | dialog.sendRequest(clientTransaction); | 717 | dialog.sendRequest(clientTransaction); |
| 717 | 718 | ||
| 718 | - SsrcTransaction ssrcTransaction = streamSession.getSsrcTransaction(deviceId, channelId, callIdHeader.getCallId(), null); | ||
| 719 | if (ssrcTransaction != null) { | 719 | if (ssrcTransaction != null) { |
| 720 | MediaServerItem mediaServerItem = mediaServerService.getOne(ssrcTransaction.getMediaServerId()); | 720 | MediaServerItem mediaServerItem = mediaServerService.getOne(ssrcTransaction.getMediaServerId()); |
| 721 | - mediaServerService.releaseSsrc(mediaServerItem, ssrcTransaction.getSsrc()); | 721 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcTransaction.getSsrc()); |
| 722 | mediaServerService.closeRTPServer(deviceId, channelId, ssrcTransaction.getStream()); | 722 | mediaServerService.closeRTPServer(deviceId, channelId, ssrcTransaction.getStream()); |
| 723 | streamSession.remove(deviceId, channelId, ssrcTransaction.getStream()); | 723 | streamSession.remove(deviceId, channelId, ssrcTransaction.getStream()); |
| 724 | } | 724 | } |
| @@ -1169,8 +1169,6 @@ public class SIPCommander implements ISIPCommander { | @@ -1169,8 +1169,6 @@ public class SIPCommander implements ISIPCommander { | ||
| 1169 | */ | 1169 | */ |
| 1170 | @Override | 1170 | @Override |
| 1171 | public boolean catalogQuery(Device device, SipSubscribe.Event errorEvent) { | 1171 | public boolean catalogQuery(Device device, SipSubscribe.Event errorEvent) { |
| 1172 | - // 清空通道 | ||
| 1173 | -// storager.cleanChannelsForDevice(device.getDeviceId()); | ||
| 1174 | try { | 1172 | try { |
| 1175 | StringBuffer catalogXml = new StringBuffer(200); | 1173 | StringBuffer catalogXml = new StringBuffer(200); |
| 1176 | catalogXml.append("<?xml version=\"1.0\" encoding=\"GB2312\"?>\r\n"); | 1174 | catalogXml.append("<?xml version=\"1.0\" encoding=\"GB2312\"?>\r\n"); |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/cmd/impl/SIPCommanderFroPlatform.java
| @@ -5,8 +5,16 @@ import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; | @@ -5,8 +5,16 @@ import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; | ||
| 5 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.ISIPCommanderForPlatform; | 5 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.ISIPCommanderForPlatform; |
| 6 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.SIPRequestHeaderPlarformProvider; | 6 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.SIPRequestHeaderPlarformProvider; |
| 7 | import com.genersoft.iot.vmp.gb28181.utils.DateUtil; | 7 | import com.genersoft.iot.vmp.gb28181.utils.DateUtil; |
| 8 | +import com.genersoft.iot.vmp.media.zlm.ZLMRTPServerFactory; | ||
| 9 | +import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; | ||
| 10 | +import com.genersoft.iot.vmp.service.IMediaServerService; | ||
| 8 | import com.genersoft.iot.vmp.service.bean.GPSMsgInfo; | 11 | import com.genersoft.iot.vmp.service.bean.GPSMsgInfo; |
| 9 | import com.genersoft.iot.vmp.storager.IRedisCatchStorage; | 12 | import com.genersoft.iot.vmp.storager.IRedisCatchStorage; |
| 13 | +import com.genersoft.iot.vmp.utils.SerializeUtils; | ||
| 14 | +import gov.nist.javax.sip.SipProviderImpl; | ||
| 15 | +import gov.nist.javax.sip.SipStackImpl; | ||
| 16 | +import gov.nist.javax.sip.message.SIPRequest; | ||
| 17 | +import gov.nist.javax.sip.stack.SIPDialog; | ||
| 10 | import org.slf4j.Logger; | 18 | import org.slf4j.Logger; |
| 11 | import org.slf4j.LoggerFactory; | 19 | import org.slf4j.LoggerFactory; |
| 12 | import org.springframework.beans.factory.annotation.Autowired; | 20 | import org.springframework.beans.factory.annotation.Autowired; |
| @@ -18,10 +26,14 @@ import org.springframework.stereotype.Component; | @@ -18,10 +26,14 @@ import org.springframework.stereotype.Component; | ||
| 18 | import org.springframework.util.StringUtils; | 26 | import org.springframework.util.StringUtils; |
| 19 | 27 | ||
| 20 | import javax.sip.*; | 28 | import javax.sip.*; |
| 29 | +import javax.sip.address.SipURI; | ||
| 21 | import javax.sip.header.CallIdHeader; | 30 | import javax.sip.header.CallIdHeader; |
| 31 | +import javax.sip.header.ViaHeader; | ||
| 22 | import javax.sip.header.WWWAuthenticateHeader; | 32 | import javax.sip.header.WWWAuthenticateHeader; |
| 23 | import javax.sip.message.Request; | 33 | import javax.sip.message.Request; |
| 34 | +import java.lang.reflect.Field; | ||
| 24 | import java.text.ParseException; | 35 | import java.text.ParseException; |
| 36 | +import java.util.HashSet; | ||
| 25 | import java.util.List; | 37 | import java.util.List; |
| 26 | import java.util.UUID; | 38 | import java.util.UUID; |
| 27 | 39 | ||
| @@ -38,17 +50,23 @@ public class SIPCommanderFroPlatform implements ISIPCommanderForPlatform { | @@ -38,17 +50,23 @@ public class SIPCommanderFroPlatform implements ISIPCommanderForPlatform { | ||
| 38 | private IRedisCatchStorage redisCatchStorage; | 50 | private IRedisCatchStorage redisCatchStorage; |
| 39 | 51 | ||
| 40 | @Autowired | 52 | @Autowired |
| 53 | + private IMediaServerService mediaServerService; | ||
| 54 | + | ||
| 55 | + @Autowired | ||
| 41 | private SipSubscribe sipSubscribe; | 56 | private SipSubscribe sipSubscribe; |
| 42 | 57 | ||
| 58 | + @Autowired | ||
| 59 | + private ZLMRTPServerFactory zlmrtpServerFactory; | ||
| 60 | + | ||
| 43 | @Lazy | 61 | @Lazy |
| 44 | @Autowired | 62 | @Autowired |
| 45 | @Qualifier(value="tcpSipProvider") | 63 | @Qualifier(value="tcpSipProvider") |
| 46 | - private SipProvider tcpSipProvider; | 64 | + private SipProviderImpl tcpSipProvider; |
| 47 | 65 | ||
| 48 | @Lazy | 66 | @Lazy |
| 49 | @Autowired | 67 | @Autowired |
| 50 | @Qualifier(value="udpSipProvider") | 68 | @Qualifier(value="udpSipProvider") |
| 51 | - private SipProvider udpSipProvider; | 69 | + private SipProviderImpl udpSipProvider; |
| 52 | 70 | ||
| 53 | @Override | 71 | @Override |
| 54 | public boolean register(ParentPlatform parentPlatform, SipSubscribe.Event errorEvent , SipSubscribe.Event okEvent) { | 72 | public boolean register(ParentPlatform parentPlatform, SipSubscribe.Event errorEvent , SipSubscribe.Event okEvent) { |
| @@ -57,13 +75,12 @@ public class SIPCommanderFroPlatform implements ISIPCommanderForPlatform { | @@ -57,13 +75,12 @@ public class SIPCommanderFroPlatform implements ISIPCommanderForPlatform { | ||
| 57 | 75 | ||
| 58 | @Override | 76 | @Override |
| 59 | public boolean unregister(ParentPlatform parentPlatform, SipSubscribe.Event errorEvent , SipSubscribe.Event okEvent) { | 77 | public boolean unregister(ParentPlatform parentPlatform, SipSubscribe.Event errorEvent , SipSubscribe.Event okEvent) { |
| 60 | - parentPlatform.setExpires("0"); | ||
| 61 | ParentPlatformCatch parentPlatformCatch = redisCatchStorage.queryPlatformCatchInfo(parentPlatform.getServerGBId()); | 78 | ParentPlatformCatch parentPlatformCatch = redisCatchStorage.queryPlatformCatchInfo(parentPlatform.getServerGBId()); |
| 62 | if (parentPlatformCatch != null) { | 79 | if (parentPlatformCatch != null) { |
| 63 | parentPlatformCatch.setParentPlatform(parentPlatform); | 80 | parentPlatformCatch.setParentPlatform(parentPlatform); |
| 64 | redisCatchStorage.updatePlatformCatchInfo(parentPlatformCatch); | 81 | redisCatchStorage.updatePlatformCatchInfo(parentPlatformCatch); |
| 65 | } | 82 | } |
| 66 | - | 83 | + parentPlatform.setExpires("0"); |
| 67 | return register(parentPlatform, null, null, errorEvent, okEvent, false); | 84 | return register(parentPlatform, null, null, errorEvent, okEvent, false); |
| 68 | } | 85 | } |
| 69 | 86 | ||
| @@ -543,4 +560,59 @@ public class SIPCommanderFroPlatform implements ISIPCommanderForPlatform { | @@ -543,4 +560,59 @@ public class SIPCommanderFroPlatform implements ISIPCommanderForPlatform { | ||
| 543 | } | 560 | } |
| 544 | return true; | 561 | return true; |
| 545 | } | 562 | } |
| 563 | + | ||
| 564 | + @Override | ||
| 565 | + public void streamByeCmd(ParentPlatform platform, String callId) { | ||
| 566 | + SendRtpItem sendRtpItem = redisCatchStorage.querySendRTPServer(platform.getServerGBId(), null, null, callId); | ||
| 567 | + if (sendRtpItem != null) { | ||
| 568 | + String mediaServerId = sendRtpItem.getMediaServerId(); | ||
| 569 | + MediaServerItem mediaServerItem = mediaServerService.getOne(mediaServerId); | ||
| 570 | + if (mediaServerItem != null) { | ||
| 571 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), sendRtpItem.getSsrc()); | ||
| 572 | + zlmrtpServerFactory.closeRTPServer(mediaServerItem, sendRtpItem.getStreamId()); | ||
| 573 | + } | ||
| 574 | + byte[] dialogByteArray = sendRtpItem.getDialog(); | ||
| 575 | + if (dialogByteArray != null) { | ||
| 576 | + SIPDialog dialog = (SIPDialog) SerializeUtils.deSerialize(dialogByteArray); | ||
| 577 | + SipStack sipStack = udpSipProvider.getSipStack(); | ||
| 578 | + SIPDialog sipDialog = ((SipStackImpl) sipStack).putDialog(dialog); | ||
| 579 | + if (dialog != sipDialog) { | ||
| 580 | + dialog = sipDialog; | ||
| 581 | + } else { | ||
| 582 | + try { | ||
| 583 | + dialog.setSipProvider(udpSipProvider); | ||
| 584 | + Field sipStackField = SIPDialog.class.getDeclaredField("sipStack"); | ||
| 585 | + sipStackField.setAccessible(true); | ||
| 586 | + sipStackField.set(dialog, sipStack); | ||
| 587 | + Field eventListenersField = SIPDialog.class.getDeclaredField("eventListeners"); | ||
| 588 | + eventListenersField.setAccessible(true); | ||
| 589 | + eventListenersField.set(dialog, new HashSet<>()); | ||
| 590 | + | ||
| 591 | + byte[] transactionByteArray = sendRtpItem.getTransaction(); | ||
| 592 | + ClientTransaction clientTransaction = (ClientTransaction) SerializeUtils.deSerialize(transactionByteArray); | ||
| 593 | + Request byeRequest = dialog.createRequest(Request.BYE); | ||
| 594 | + SipURI byeURI = (SipURI) byeRequest.getRequestURI(); | ||
| 595 | + SIPRequest request = (SIPRequest) clientTransaction.getRequest(); | ||
| 596 | + byeURI.setHost(request.getRemoteAddress().getHostName()); | ||
| 597 | + byeURI.setPort(request.getRemotePort()); | ||
| 598 | + if ("TCP".equals(platform.getTransport())) { | ||
| 599 | + clientTransaction = tcpSipProvider.getNewClientTransaction(byeRequest); | ||
| 600 | + } else if ("UDP".equals(platform.getTransport())) { | ||
| 601 | + clientTransaction = udpSipProvider.getNewClientTransaction(byeRequest); | ||
| 602 | + } | ||
| 603 | + dialog.sendRequest(clientTransaction); | ||
| 604 | + } catch (SipException e) { | ||
| 605 | + e.printStackTrace(); | ||
| 606 | + } catch (ParseException e) { | ||
| 607 | + e.printStackTrace(); | ||
| 608 | + } catch (NoSuchFieldException e) { | ||
| 609 | + e.printStackTrace(); | ||
| 610 | + } catch (IllegalAccessException e) { | ||
| 611 | + e.printStackTrace(); | ||
| 612 | + } | ||
| 613 | + | ||
| 614 | + } | ||
| 615 | + } | ||
| 616 | + } | ||
| 617 | + } | ||
| 546 | } | 618 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/request/impl/AckRequestProcessor.java
| @@ -3,6 +3,7 @@ package com.genersoft.iot.vmp.gb28181.transmit.event.request.impl; | @@ -3,6 +3,7 @@ package com.genersoft.iot.vmp.gb28181.transmit.event.request.impl; | ||
| 3 | import com.alibaba.fastjson.JSON; | 3 | import com.alibaba.fastjson.JSON; |
| 4 | import com.alibaba.fastjson.JSONObject; | 4 | import com.alibaba.fastjson.JSONObject; |
| 5 | import com.genersoft.iot.vmp.common.StreamInfo; | 5 | import com.genersoft.iot.vmp.common.StreamInfo; |
| 6 | +import com.genersoft.iot.vmp.conf.DynamicTask; | ||
| 6 | import com.genersoft.iot.vmp.gb28181.bean.SendRtpItem; | 7 | import com.genersoft.iot.vmp.gb28181.bean.SendRtpItem; |
| 7 | import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver; | 8 | import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver; |
| 8 | import com.genersoft.iot.vmp.gb28181.transmit.event.request.ISIPRequestProcessor; | 9 | import com.genersoft.iot.vmp.gb28181.transmit.event.request.ISIPRequestProcessor; |
| @@ -22,6 +23,7 @@ import javax.sip.Dialog; | @@ -22,6 +23,7 @@ import javax.sip.Dialog; | ||
| 22 | import javax.sip.DialogState; | 23 | import javax.sip.DialogState; |
| 23 | import javax.sip.RequestEvent; | 24 | import javax.sip.RequestEvent; |
| 24 | import javax.sip.address.SipURI; | 25 | import javax.sip.address.SipURI; |
| 26 | +import javax.sip.header.CallIdHeader; | ||
| 25 | import javax.sip.header.FromHeader; | 27 | import javax.sip.header.FromHeader; |
| 26 | import javax.sip.header.HeaderAddress; | 28 | import javax.sip.header.HeaderAddress; |
| 27 | import javax.sip.header.ToHeader; | 29 | import javax.sip.header.ToHeader; |
| @@ -60,6 +62,9 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | @@ -60,6 +62,9 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | ||
| 60 | @Autowired | 62 | @Autowired |
| 61 | private ZLMHttpHookSubscribe subscribe; | 63 | private ZLMHttpHookSubscribe subscribe; |
| 62 | 64 | ||
| 65 | + @Autowired | ||
| 66 | + private DynamicTask dynamicTask; | ||
| 67 | + | ||
| 63 | 68 | ||
| 64 | /** | 69 | /** |
| 65 | * 处理 ACK请求 | 70 | * 处理 ACK请求 |
| @@ -68,13 +73,16 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | @@ -68,13 +73,16 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | ||
| 68 | */ | 73 | */ |
| 69 | @Override | 74 | @Override |
| 70 | public void process(RequestEvent evt) { | 75 | public void process(RequestEvent evt) { |
| 71 | - logger.info("ACK请求: {}", ((System.currentTimeMillis()))); | ||
| 72 | Dialog dialog = evt.getDialog(); | 76 | Dialog dialog = evt.getDialog(); |
| 77 | + CallIdHeader callIdHeader = (CallIdHeader)evt.getRequest().getHeader(CallIdHeader.NAME); | ||
| 73 | if (dialog == null) return; | 78 | if (dialog == null) return; |
| 74 | if (dialog.getState()== DialogState.CONFIRMED) { | 79 | if (dialog.getState()== DialogState.CONFIRMED) { |
| 75 | String platformGbId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(FromHeader.NAME)).getAddress().getURI()).getUser(); | 80 | String platformGbId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(FromHeader.NAME)).getAddress().getURI()).getUser(); |
| 81 | + logger.info("ACK请求: platformGbId->{}", platformGbId); | ||
| 82 | + // 取消设置的超时任务 | ||
| 83 | + dynamicTask.stop(callIdHeader.getCallId()); | ||
| 76 | String channelId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(ToHeader.NAME)).getAddress().getURI()).getUser(); | 84 | String channelId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(ToHeader.NAME)).getAddress().getURI()).getUser(); |
| 77 | - SendRtpItem sendRtpItem = redisCatchStorage.querySendRTPServer(platformGbId, channelId); | 85 | + SendRtpItem sendRtpItem = redisCatchStorage.querySendRTPServer(platformGbId, channelId, null, callIdHeader.getCallId()); |
| 78 | String is_Udp = sendRtpItem.isTcp() ? "0" : "1"; | 86 | String is_Udp = sendRtpItem.isTcp() ? "0" : "1"; |
| 79 | String deviceId = sendRtpItem.getDeviceId(); | 87 | String deviceId = sendRtpItem.getDeviceId(); |
| 80 | StreamInfo streamInfo = null; | 88 | StreamInfo streamInfo = null; |
| @@ -83,15 +91,12 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | @@ -83,15 +91,12 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | ||
| 83 | }else { | 91 | }else { |
| 84 | streamInfo = redisCatchStorage.queryPlaybackByDevice(deviceId, channelId); | 92 | streamInfo = redisCatchStorage.queryPlaybackByDevice(deviceId, channelId); |
| 85 | } | 93 | } |
| 86 | - System.out.println(JSON.toJSON(streamInfo)); | ||
| 87 | if (streamInfo == null) { | 94 | if (streamInfo == null) { |
| 88 | streamInfo = new StreamInfo(); | 95 | streamInfo = new StreamInfo(); |
| 89 | streamInfo.setApp(sendRtpItem.getApp()); | 96 | streamInfo.setApp(sendRtpItem.getApp()); |
| 90 | streamInfo.setStream(sendRtpItem.getStreamId()); | 97 | streamInfo.setStream(sendRtpItem.getStreamId()); |
| 91 | } | 98 | } |
| 92 | redisCatchStorage.updateSendRTPSever(sendRtpItem); | 99 | redisCatchStorage.updateSendRTPSever(sendRtpItem); |
| 93 | - logger.info(platformGbId); | ||
| 94 | - logger.info(channelId); | ||
| 95 | Map<String, Object> param = new HashMap<>(); | 100 | Map<String, Object> param = new HashMap<>(); |
| 96 | param.put("vhost","__defaultVhost__"); | 101 | param.put("vhost","__defaultVhost__"); |
| 97 | param.put("app",streamInfo.getApp()); | 102 | param.put("app",streamInfo.getApp()); |
| @@ -100,42 +105,23 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | @@ -100,42 +105,23 @@ public class AckRequestProcessor extends SIPRequestProcessorParent implements In | ||
| 100 | param.put("dst_url",sendRtpItem.getIp()); | 105 | param.put("dst_url",sendRtpItem.getIp()); |
| 101 | param.put("dst_port", sendRtpItem.getPort()); | 106 | param.put("dst_port", sendRtpItem.getPort()); |
| 102 | param.put("is_udp", is_Udp); | 107 | param.put("is_udp", is_Udp); |
| 103 | - // 设备推流查询,成功后才能转推 | ||
| 104 | MediaServerItem mediaInfo = mediaServerService.getOne(sendRtpItem.getMediaServerId()); | 108 | MediaServerItem mediaInfo = mediaServerService.getOne(sendRtpItem.getMediaServerId()); |
| 105 | - zlmrtpServerFactory.startSendRtpStream(mediaInfo, param); | ||
| 106 | -// if (zlmrtpServerFactory.isStreamReady(mediaInfo, streamInfo.getApp(), streamInfo.getStreamId())) { | ||
| 107 | -// logger.info("已获取设备推流[{}/{}],开始向上级推流[{}:{}]", | ||
| 108 | -// streamInfo.getApp() ,streamInfo.getStreamId(), sendRtpItem.getIp(), sendRtpItem.getPort()); | ||
| 109 | -// zlmrtpServerFactory.startSendRtpStream(mediaInfo, param); | ||
| 110 | -// } else { | ||
| 111 | -// // 对hook进行订阅 | ||
| 112 | -// logger.info("等待设备推流[{}/{}].......", | ||
| 113 | -// streamInfo.getApp(), streamInfo.getStreamId()); | ||
| 114 | -// Timer timer = new Timer(); | ||
| 115 | -// timer.schedule(new TimerTask() { | ||
| 116 | -// @Override | ||
| 117 | -// public void run() { | ||
| 118 | -// logger.info("设备推流[{}/{}]超时,终止向上级推流", | ||
| 119 | -// finalStreamInfo.getApp() , finalStreamInfo.getStreamId()); | ||
| 120 | -// | ||
| 121 | -// } | ||
| 122 | -// }, 30*1000L); | ||
| 123 | -// // 添加订阅 | ||
| 124 | -// JSONObject subscribeKey = new JSONObject(); | ||
| 125 | -// subscribeKey.put("app", "rtp"); | ||
| 126 | -// subscribeKey.put("stream", streamInfo.getStreamId()); | ||
| 127 | -// subscribeKey.put("mediaServerId", streamInfo.getMediaServerId()); | ||
| 128 | -// subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_publish, subscribeKey, | ||
| 129 | -// (MediaServerItem mediaServerItemInUse, JSONObject json) -> { | ||
| 130 | -// logger.info("已获取设备推流[{}/{}],开始向上级推流[{}:{}]", | ||
| 131 | -// finalStreamInfo.getApp(), finalStreamInfo.getStreamId(), sendRtpItem.getIp(), sendRtpItem.getPort()); | ||
| 132 | -// timer.cancel(); | ||
| 133 | -// zlmrtpServerFactory.startSendRtpStream(mediaInfo, param); | ||
| 134 | -// subscribe.removeSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey); | ||
| 135 | -// }); | ||
| 136 | -// } | ||
| 137 | - | ||
| 138 | - | 109 | + JSONObject jsonObject = zlmrtpServerFactory.startSendRtpStream(mediaInfo, param); |
| 110 | + if (jsonObject.getInteger("code") != 0) { | ||
| 111 | + logger.info("监听流以等待流上线{}/{}", streamInfo.getApp(), streamInfo.getStream()); | ||
| 112 | + // 监听流上线 | ||
| 113 | + // 添加订阅 | ||
| 114 | + JSONObject subscribeKey = new JSONObject(); | ||
| 115 | + subscribeKey.put("app", "rtp"); | ||
| 116 | + subscribeKey.put("stream", streamInfo.getStream()); | ||
| 117 | + subscribeKey.put("regist", true); | ||
| 118 | + subscribeKey.put("schema", "rtmp"); | ||
| 119 | + subscribeKey.put("mediaServerId", sendRtpItem.getMediaServerId()); | ||
| 120 | + subscribe.addSubscribe(ZLMHttpHookSubscribe.HookType.on_stream_changed, subscribeKey, | ||
| 121 | + (MediaServerItem mediaServerItemInUse, JSONObject json)->{ | ||
| 122 | + zlmrtpServerFactory.startSendRtpStream(mediaInfo, param); | ||
| 123 | + }); | ||
| 124 | + } | ||
| 139 | } | 125 | } |
| 140 | } | 126 | } |
| 141 | } | 127 | } |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/request/impl/ByeRequestProcessor.java
| @@ -4,6 +4,8 @@ import com.genersoft.iot.vmp.common.StreamInfo; | @@ -4,6 +4,8 @@ import com.genersoft.iot.vmp.common.StreamInfo; | ||
| 4 | import com.genersoft.iot.vmp.gb28181.bean.Device; | 4 | import com.genersoft.iot.vmp.gb28181.bean.Device; |
| 5 | import com.genersoft.iot.vmp.gb28181.bean.ParentPlatform; | 5 | import com.genersoft.iot.vmp.gb28181.bean.ParentPlatform; |
| 6 | import com.genersoft.iot.vmp.gb28181.bean.SendRtpItem; | 6 | import com.genersoft.iot.vmp.gb28181.bean.SendRtpItem; |
| 7 | +import com.genersoft.iot.vmp.gb28181.bean.SsrcTransaction; | ||
| 8 | +import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; | ||
| 7 | import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver; | 9 | import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver; |
| 8 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.ISIPCommander; | 10 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.ISIPCommander; |
| 9 | import com.genersoft.iot.vmp.gb28181.transmit.event.request.ISIPRequestProcessor; | 11 | import com.genersoft.iot.vmp.gb28181.transmit.event.request.ISIPRequestProcessor; |
| @@ -13,6 +15,8 @@ import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; | @@ -13,6 +15,8 @@ import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; | ||
| 13 | import com.genersoft.iot.vmp.service.IMediaServerService; | 15 | import com.genersoft.iot.vmp.service.IMediaServerService; |
| 14 | import com.genersoft.iot.vmp.storager.IRedisCatchStorage; | 16 | import com.genersoft.iot.vmp.storager.IRedisCatchStorage; |
| 15 | import com.genersoft.iot.vmp.storager.IVideoManagerStorager; | 17 | import com.genersoft.iot.vmp.storager.IVideoManagerStorager; |
| 18 | +import com.genersoft.iot.vmp.utils.SerializeUtils; | ||
| 19 | +import gov.nist.javax.sip.stack.SIPDialog; | ||
| 16 | import org.slf4j.Logger; | 20 | import org.slf4j.Logger; |
| 17 | import org.slf4j.LoggerFactory; | 21 | import org.slf4j.LoggerFactory; |
| 18 | import org.springframework.beans.factory.InitializingBean; | 22 | import org.springframework.beans.factory.InitializingBean; |
| @@ -21,6 +25,7 @@ import org.springframework.stereotype.Component; | @@ -21,6 +25,7 @@ import org.springframework.stereotype.Component; | ||
| 21 | 25 | ||
| 22 | import javax.sip.*; | 26 | import javax.sip.*; |
| 23 | import javax.sip.address.SipURI; | 27 | import javax.sip.address.SipURI; |
| 28 | +import javax.sip.header.CallIdHeader; | ||
| 24 | import javax.sip.header.FromHeader; | 29 | import javax.sip.header.FromHeader; |
| 25 | import javax.sip.header.HeaderAddress; | 30 | import javax.sip.header.HeaderAddress; |
| 26 | import javax.sip.header.ToHeader; | 31 | import javax.sip.header.ToHeader; |
| @@ -56,6 +61,9 @@ public class ByeRequestProcessor extends SIPRequestProcessorParent implements In | @@ -56,6 +61,9 @@ public class ByeRequestProcessor extends SIPRequestProcessorParent implements In | ||
| 56 | @Autowired | 61 | @Autowired |
| 57 | private SIPProcessorObserver sipProcessorObserver; | 62 | private SIPProcessorObserver sipProcessorObserver; |
| 58 | 63 | ||
| 64 | + @Autowired | ||
| 65 | + private VideoStreamSessionManager streamSession; | ||
| 66 | + | ||
| 59 | @Override | 67 | @Override |
| 60 | public void afterPropertiesSet() throws Exception { | 68 | public void afterPropertiesSet() throws Exception { |
| 61 | // 添加消息处理的订阅 | 69 | // 添加消息处理的订阅 |
| @@ -71,11 +79,12 @@ public class ByeRequestProcessor extends SIPRequestProcessorParent implements In | @@ -71,11 +79,12 @@ public class ByeRequestProcessor extends SIPRequestProcessorParent implements In | ||
| 71 | try { | 79 | try { |
| 72 | responseAck(evt, Response.OK); | 80 | responseAck(evt, Response.OK); |
| 73 | Dialog dialog = evt.getDialog(); | 81 | Dialog dialog = evt.getDialog(); |
| 82 | + CallIdHeader callIdHeader = (CallIdHeader)evt.getRequest().getHeader(CallIdHeader.NAME); | ||
| 74 | if (dialog == null) return; | 83 | if (dialog == null) return; |
| 75 | if (dialog.getState().equals(DialogState.TERMINATED)) { | 84 | if (dialog.getState().equals(DialogState.TERMINATED)) { |
| 76 | String platformGbId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(FromHeader.NAME)).getAddress().getURI()).getUser(); | 85 | String platformGbId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(FromHeader.NAME)).getAddress().getURI()).getUser(); |
| 77 | String channelId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(ToHeader.NAME)).getAddress().getURI()).getUser(); | 86 | String channelId = ((SipURI) ((HeaderAddress) evt.getRequest().getHeader(ToHeader.NAME)).getAddress().getURI()).getUser(); |
| 78 | - SendRtpItem sendRtpItem = redisCatchStorage.querySendRTPServer(platformGbId, channelId); | 87 | + SendRtpItem sendRtpItem = redisCatchStorage.querySendRTPServer(platformGbId, channelId, null, callIdHeader.getCallId()); |
| 79 | logger.info("收到bye, [{}/{}]", platformGbId, channelId); | 88 | logger.info("收到bye, [{}/{}]", platformGbId, channelId); |
| 80 | if (sendRtpItem != null){ | 89 | if (sendRtpItem != null){ |
| 81 | String streamId = sendRtpItem.getStreamId(); | 90 | String streamId = sendRtpItem.getStreamId(); |
| @@ -87,35 +96,44 @@ public class ByeRequestProcessor extends SIPRequestProcessorParent implements In | @@ -87,35 +96,44 @@ public class ByeRequestProcessor extends SIPRequestProcessorParent implements In | ||
| 87 | logger.info("停止向上级推流:" + streamId); | 96 | logger.info("停止向上级推流:" + streamId); |
| 88 | MediaServerItem mediaInfo = mediaServerService.getOne(sendRtpItem.getMediaServerId()); | 97 | MediaServerItem mediaInfo = mediaServerService.getOne(sendRtpItem.getMediaServerId()); |
| 89 | zlmrtpServerFactory.stopSendRtpStream(mediaInfo, param); | 98 | zlmrtpServerFactory.stopSendRtpStream(mediaInfo, param); |
| 90 | - redisCatchStorage.deleteSendRTPServer(platformGbId, channelId); | 99 | + redisCatchStorage.deleteSendRTPServer(platformGbId, channelId, callIdHeader.getCallId(), null); |
| 91 | int totalReaderCount = zlmrtpServerFactory.totalReaderCount(mediaInfo, sendRtpItem.getApp(), streamId); | 100 | int totalReaderCount = zlmrtpServerFactory.totalReaderCount(mediaInfo, sendRtpItem.getApp(), streamId); |
| 92 | - if (totalReaderCount == 0) { | 101 | + if (totalReaderCount <= 0) { |
| 93 | logger.info(streamId + "无其它观看者,通知设备停止推流"); | 102 | logger.info(streamId + "无其它观看者,通知设备停止推流"); |
| 94 | cmder.streamByeCmd(sendRtpItem.getDeviceId(), channelId, streamId); | 103 | cmder.streamByeCmd(sendRtpItem.getDeviceId(), channelId, streamId); |
| 95 | - }else if (totalReaderCount == -1){ | ||
| 96 | - logger.warn(streamId + " 查找其它观看者失败"); | ||
| 97 | } | 104 | } |
| 98 | } | 105 | } |
| 99 | // 可能是设备主动停止 | 106 | // 可能是设备主动停止 |
| 100 | Device device = storager.queryVideoDeviceByChannelId(platformGbId); | 107 | Device device = storager.queryVideoDeviceByChannelId(platformGbId); |
| 101 | if (device != null) { | 108 | if (device != null) { |
| 109 | + storager.stopPlay(device.getDeviceId(), channelId); | ||
| 102 | StreamInfo streamInfo = redisCatchStorage.queryPlayByDevice(device.getDeviceId(), channelId); | 110 | StreamInfo streamInfo = redisCatchStorage.queryPlayByDevice(device.getDeviceId(), channelId); |
| 103 | - if (sendRtpItem != null) { | ||
| 104 | - if (sendRtpItem.isPlay()) { | ||
| 105 | - if (streamInfo != null) { | ||
| 106 | - redisCatchStorage.stopPlay(streamInfo); | ||
| 107 | - } | ||
| 108 | - }else { | ||
| 109 | - if (streamInfo != null) { | ||
| 110 | - redisCatchStorage.stopPlayback(streamInfo); | 111 | + if (streamInfo != null) { |
| 112 | + redisCatchStorage.stopPlay(streamInfo); | ||
| 113 | + mediaServerService.closeRTPServer(device.getDeviceId(), channelId, streamInfo.getStream()); | ||
| 114 | + } | ||
| 115 | + SsrcTransaction ssrcTransactionForPlay = streamSession.getSsrcTransaction(device.getDeviceId(), channelId, "play", null); | ||
| 116 | + if (ssrcTransactionForPlay != null){ | ||
| 117 | + SIPDialog dialogForPlay = (SIPDialog) SerializeUtils.deSerialize(ssrcTransactionForPlay.getDialog()); | ||
| 118 | + if (dialogForPlay.getCallId().equals(callIdHeader.getCallId())){ | ||
| 119 | + // 释放ssrc | ||
| 120 | + MediaServerItem mediaServerItem = mediaServerService.getOne(ssrcTransactionForPlay.getMediaServerId()); | ||
| 121 | + if (mediaServerItem != null) { | ||
| 122 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcTransactionForPlay.getSsrc()); | ||
| 111 | } | 123 | } |
| 124 | + streamSession.remove(device.getDeviceId(), channelId, ssrcTransactionForPlay.getStream()); | ||
| 112 | } | 125 | } |
| 113 | - | ||
| 114 | - storager.stopPlay(device.getDeviceId(), channelId); | ||
| 115 | - mediaServerService.closeRTPServer(device.getDeviceId(), channelId, streamInfo.getStream()); | 126 | + } |
| 127 | + SsrcTransaction ssrcTransactionForPlayBack = streamSession.getSsrcTransaction(device.getDeviceId(), channelId, callIdHeader.getCallId(), null); | ||
| 128 | + if (ssrcTransactionForPlayBack != null) { | ||
| 129 | + // 释放ssrc | ||
| 130 | + MediaServerItem mediaServerItem = mediaServerService.getOne(ssrcTransactionForPlayBack.getMediaServerId()); | ||
| 131 | + if (mediaServerItem != null) { | ||
| 132 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcTransactionForPlayBack.getSsrc()); | ||
| 133 | + } | ||
| 134 | + streamSession.remove(device.getDeviceId(), channelId, ssrcTransactionForPlayBack.getStream()); | ||
| 116 | } | 135 | } |
| 117 | } | 136 | } |
| 118 | - | ||
| 119 | } | 137 | } |
| 120 | } catch (SipException e) { | 138 | } catch (SipException e) { |
| 121 | e.printStackTrace(); | 139 | e.printStackTrace(); |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/request/impl/InviteRequestProcessor.java
| @@ -3,6 +3,7 @@ package com.genersoft.iot.vmp.gb28181.transmit.event.request.impl; | @@ -3,6 +3,7 @@ package com.genersoft.iot.vmp.gb28181.transmit.event.request.impl; | ||
| 3 | import com.alibaba.fastjson.JSON; | 3 | import com.alibaba.fastjson.JSON; |
| 4 | import com.alibaba.fastjson.JSONObject; | 4 | import com.alibaba.fastjson.JSONObject; |
| 5 | import com.genersoft.iot.vmp.common.StreamInfo; | 5 | import com.genersoft.iot.vmp.common.StreamInfo; |
| 6 | +import com.genersoft.iot.vmp.conf.DynamicTask; | ||
| 6 | import com.genersoft.iot.vmp.gb28181.bean.*; | 7 | import com.genersoft.iot.vmp.gb28181.bean.*; |
| 7 | import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; | 8 | import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; |
| 8 | import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver; | 9 | import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver; |
| @@ -21,6 +22,7 @@ import com.genersoft.iot.vmp.service.IPlayService; | @@ -21,6 +22,7 @@ import com.genersoft.iot.vmp.service.IPlayService; | ||
| 21 | import com.genersoft.iot.vmp.service.bean.SSRCInfo; | 22 | import com.genersoft.iot.vmp.service.bean.SSRCInfo; |
| 22 | import com.genersoft.iot.vmp.storager.IRedisCatchStorage; | 23 | import com.genersoft.iot.vmp.storager.IRedisCatchStorage; |
| 23 | import com.genersoft.iot.vmp.storager.IVideoManagerStorager; | 24 | import com.genersoft.iot.vmp.storager.IVideoManagerStorager; |
| 25 | +import com.genersoft.iot.vmp.utils.SerializeUtils; | ||
| 24 | import com.genersoft.iot.vmp.vmanager.gb28181.play.bean.PlayResult; | 26 | import com.genersoft.iot.vmp.vmanager.gb28181.play.bean.PlayResult; |
| 25 | import gov.nist.javax.sdp.TimeDescriptionImpl; | 27 | import gov.nist.javax.sdp.TimeDescriptionImpl; |
| 26 | import gov.nist.javax.sdp.fields.TimeField; | 28 | import gov.nist.javax.sdp.fields.TimeField; |
| @@ -69,6 +71,9 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | @@ -69,6 +71,9 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | ||
| 69 | private IRedisCatchStorage redisCatchStorage; | 71 | private IRedisCatchStorage redisCatchStorage; |
| 70 | 72 | ||
| 71 | @Autowired | 73 | @Autowired |
| 74 | + private DynamicTask dynamicTask; | ||
| 75 | + | ||
| 76 | + @Autowired | ||
| 72 | private SIPCommander cmder; | 77 | private SIPCommander cmder; |
| 73 | 78 | ||
| 74 | @Autowired | 79 | @Autowired |
| @@ -257,11 +262,13 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | @@ -257,11 +262,13 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | ||
| 257 | } | 262 | } |
| 258 | sendRtpItem.setCallId(callIdHeader.getCallId()); | 263 | sendRtpItem.setCallId(callIdHeader.getCallId()); |
| 259 | sendRtpItem.setPlay("Play".equals(sessionName)); | 264 | sendRtpItem.setPlay("Play".equals(sessionName)); |
| 265 | + byte[] dialogByteArray = SerializeUtils.serialize(evt.getDialog()); | ||
| 266 | + sendRtpItem.setDialog(dialogByteArray); | ||
| 267 | + byte[] transactionByteArray = SerializeUtils.serialize(evt.getServerTransaction()); | ||
| 268 | + sendRtpItem.setTransaction(transactionByteArray); | ||
| 260 | // 写入redis, 超时时回复 | 269 | // 写入redis, 超时时回复 |
| 261 | redisCatchStorage.updateSendRTPSever(sendRtpItem); | 270 | redisCatchStorage.updateSendRTPSever(sendRtpItem); |
| 262 | 271 | ||
| 263 | - Device finalDevice = device; | ||
| 264 | - MediaServerItem finalMediaServerItem = mediaServerItem; | ||
| 265 | Long finalStartTime = startTime; | 272 | Long finalStartTime = startTime; |
| 266 | Long finalStopTime = stopTime; | 273 | Long finalStopTime = stopTime; |
| 267 | ZLMHttpHookSubscribe.Event hookEvent = (mediaServerItemInUSe, responseJSON)->{ | 274 | ZLMHttpHookSubscribe.Event hookEvent = (mediaServerItemInUSe, responseJSON)->{ |
| @@ -289,7 +296,15 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | @@ -289,7 +296,15 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | ||
| 289 | content.append("f=\r\n"); | 296 | content.append("f=\r\n"); |
| 290 | 297 | ||
| 291 | try { | 298 | try { |
| 299 | + // 超时未收到Ack应该回复bye,当前等待时间为10秒 | ||
| 300 | + dynamicTask.startDelay(callIdHeader.getCallId(), ()->{ | ||
| 301 | + logger.info("Ack 等待超时"); | ||
| 302 | + mediaServerService.releaseSsrc(mediaServerItemInUSe.getId(), ssrc); | ||
| 303 | + // 回复bye | ||
| 304 | + cmderFroPlatform.streamByeCmd(platform, callIdHeader.getCallId()); | ||
| 305 | + }, 60); | ||
| 292 | responseSdpAck(evt, content.toString(), platform); | 306 | responseSdpAck(evt, content.toString(), platform); |
| 307 | + | ||
| 293 | } catch (SipException e) { | 308 | } catch (SipException e) { |
| 294 | e.printStackTrace(); | 309 | e.printStackTrace(); |
| 295 | } catch (InvalidArgumentException e) { | 310 | } catch (InvalidArgumentException e) { |
| @@ -320,6 +335,7 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | @@ -320,6 +335,7 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | ||
| 320 | if (result.getEvent() != null) { | 335 | if (result.getEvent() != null) { |
| 321 | errorEvent.response(result.getEvent()); | 336 | errorEvent.response(result.getEvent()); |
| 322 | } | 337 | } |
| 338 | + redisCatchStorage.deleteSendRTPServer(platform.getServerGBId(), channelId, callIdHeader.getCallId(), null); | ||
| 323 | try { | 339 | try { |
| 324 | responseAck(evt, Response.REQUEST_TIMEOUT); | 340 | responseAck(evt, Response.REQUEST_TIMEOUT); |
| 325 | } catch (SipException e) { | 341 | } catch (SipException e) { |
| @@ -343,7 +359,9 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | @@ -343,7 +359,9 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | ||
| 343 | sendRtpItem.setStreamId(String.format("%s_%s", device.getDeviceId(), channelId)); | 359 | sendRtpItem.setStreamId(String.format("%s_%s", device.getDeviceId(), channelId)); |
| 344 | } | 360 | } |
| 345 | sendRtpItem.setPlay(false); | 361 | sendRtpItem.setPlay(false); |
| 346 | - playService.play(mediaServerItem,device.getDeviceId(), channelId, hookEvent,errorEvent); | 362 | + playService.play(mediaServerItem,device.getDeviceId(), channelId, hookEvent, errorEvent, ()->{ |
| 363 | + redisCatchStorage.deleteSendRTPServer(platform.getServerGBId(), channelId, callIdHeader.getCallId(), null); | ||
| 364 | + }); | ||
| 347 | }else { | 365 | }else { |
| 348 | sendRtpItem.setStreamId(streamInfo.getStream()); | 366 | sendRtpItem.setStreamId(streamInfo.getStream()); |
| 349 | hookEvent.response(mediaServerItem, null); | 367 | hookEvent.response(mediaServerItem, null); |
| @@ -365,6 +383,11 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | @@ -365,6 +383,11 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements | ||
| 365 | 383 | ||
| 366 | // 写入redis, 超时时回复 | 384 | // 写入redis, 超时时回复 |
| 367 | sendRtpItem.setStatus(1); | 385 | sendRtpItem.setStatus(1); |
| 386 | + sendRtpItem.setCallId(callIdHeader.getCallId()); | ||
| 387 | + byte[] dialogByteArray = SerializeUtils.serialize(evt.getDialog()); | ||
| 388 | + sendRtpItem.setDialog(dialogByteArray); | ||
| 389 | + byte[] transactionByteArray = SerializeUtils.serialize(evt.getServerTransaction()); | ||
| 390 | + sendRtpItem.setTransaction(transactionByteArray); | ||
| 368 | redisCatchStorage.updateSendRTPSever(sendRtpItem); | 391 | redisCatchStorage.updateSendRTPSever(sendRtpItem); |
| 369 | StringBuffer content = new StringBuffer(200); | 392 | StringBuffer content = new StringBuffer(200); |
| 370 | content.append("v=0\r\n"); | 393 | content.append("v=0\r\n"); |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/request/impl/RegisterRequestProcessor.java
| @@ -158,6 +158,10 @@ public class RegisterRequestProcessor extends SIPRequestProcessorParent implemen | @@ -158,6 +158,10 @@ public class RegisterRequestProcessor extends SIPRequestProcessorParent implemen | ||
| 158 | device.setCharset("gb2312"); | 158 | device.setCharset("gb2312"); |
| 159 | device.setDeviceId(deviceId); | 159 | device.setDeviceId(deviceId); |
| 160 | device.setFirsRegister(true); | 160 | device.setFirsRegister(true); |
| 161 | + }else { | ||
| 162 | + if (device.getOnline() == 0) { | ||
| 163 | + device.setFirsRegister(true); | ||
| 164 | + } | ||
| 161 | } | 165 | } |
| 162 | device.setIp(received); | 166 | device.setIp(received); |
| 163 | device.setPort(rPort); | 167 | device.setPort(rPort); |
| @@ -187,7 +191,6 @@ public class RegisterRequestProcessor extends SIPRequestProcessorParent implemen | @@ -187,7 +191,6 @@ public class RegisterRequestProcessor extends SIPRequestProcessorParent implemen | ||
| 187 | if (serverTransaction.getDialog() != null) serverTransaction.getDialog().delete(); | 191 | if (serverTransaction.getDialog() != null) serverTransaction.getDialog().delete(); |
| 188 | // 注册成功 | 192 | // 注册成功 |
| 189 | // 保存到redis | 193 | // 保存到redis |
| 190 | - // 下发catelog查询目录 | ||
| 191 | if (registerFlag == 1 ) { | 194 | if (registerFlag == 1 ) { |
| 192 | logger.info("[{}] 注册成功! deviceId:" + device.getDeviceId(), requestAddress); | 195 | logger.info("[{}] 注册成功! deviceId:" + device.getDeviceId(), requestAddress); |
| 193 | publisher.onlineEventPublish(device, VideoManagerConstants.EVENT_ONLINE_REGISTER); | 196 | publisher.onlineEventPublish(device, VideoManagerConstants.EVENT_ONLINE_REGISTER); |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/request/impl/SubscribeRequestProcessor.java
| @@ -27,9 +27,7 @@ import javax.sip.InvalidArgumentException; | @@ -27,9 +27,7 @@ import javax.sip.InvalidArgumentException; | ||
| 27 | import javax.sip.RequestEvent; | 27 | import javax.sip.RequestEvent; |
| 28 | import javax.sip.ServerTransaction; | 28 | import javax.sip.ServerTransaction; |
| 29 | import javax.sip.SipException; | 29 | import javax.sip.SipException; |
| 30 | -import javax.sip.header.CallIdHeader; | ||
| 31 | import javax.sip.header.ExpiresHeader; | 30 | import javax.sip.header.ExpiresHeader; |
| 32 | -import javax.sip.header.Header; | ||
| 33 | import javax.sip.header.ToHeader; | 31 | import javax.sip.header.ToHeader; |
| 34 | import javax.sip.message.Request; | 32 | import javax.sip.message.Request; |
| 35 | import javax.sip.message.Response; | 33 | import javax.sip.message.Response; |
| @@ -139,19 +137,17 @@ public class SubscribeRequestProcessor extends SIPRequestProcessorParent impleme | @@ -139,19 +137,17 @@ public class SubscribeRequestProcessor extends SIPRequestProcessorParent impleme | ||
| 139 | 137 | ||
| 140 | if (subscribeInfo.getExpires() > 0) { | 138 | if (subscribeInfo.getExpires() > 0) { |
| 141 | if (redisCatchStorage.getSubscribe(key) != null) { | 139 | if (redisCatchStorage.getSubscribe(key) != null) { |
| 142 | - dynamicTask.stopCron(key); | 140 | + dynamicTask.stop(key); |
| 143 | } | 141 | } |
| 144 | String interval = XmlUtil.getText(rootElement, "Interval"); // GPS上报时间间隔 | 142 | String interval = XmlUtil.getText(rootElement, "Interval"); // GPS上报时间间隔 |
| 145 | dynamicTask.startCron(key, new GPSSubscribeTask(redisCatchStorage, sipCommanderForPlatform, storager, platformId, sn, key), Integer.parseInt(interval)); | 143 | dynamicTask.startCron(key, new GPSSubscribeTask(redisCatchStorage, sipCommanderForPlatform, storager, platformId, sn, key), Integer.parseInt(interval)); |
| 146 | 144 | ||
| 147 | redisCatchStorage.updateSubscribe(key, subscribeInfo); | 145 | redisCatchStorage.updateSubscribe(key, subscribeInfo); |
| 148 | }else if (subscribeInfo.getExpires() == 0) { | 146 | }else if (subscribeInfo.getExpires() == 0) { |
| 149 | - dynamicTask.stopCron(key); | 147 | + dynamicTask.stop(key); |
| 150 | redisCatchStorage.delSubscribe(key); | 148 | redisCatchStorage.delSubscribe(key); |
| 151 | } | 149 | } |
| 152 | 150 | ||
| 153 | - | ||
| 154 | - | ||
| 155 | try { | 151 | try { |
| 156 | ParentPlatform parentPlatform = storager.queryParentPlatByServerGBId(platformId); | 152 | ParentPlatform parentPlatform = storager.queryParentPlatByServerGBId(platformId); |
| 157 | Response response = responseXmlAck(evt, resultXml.toString(), parentPlatform); | 153 | Response response = responseXmlAck(evt, resultXml.toString(), parentPlatform); |
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/response/impl/RegisterResponseProcessor.java
| @@ -85,19 +85,18 @@ public class RegisterResponseProcessor extends SIPResponseProcessorAbstract { | @@ -85,19 +85,18 @@ public class RegisterResponseProcessor extends SIPResponseProcessorAbstract { | ||
| 85 | redisCatchStorage.delPlatformRegisterInfo(callId); | 85 | redisCatchStorage.delPlatformRegisterInfo(callId); |
| 86 | parentPlatform.setStatus("注册".equals(action)); | 86 | parentPlatform.setStatus("注册".equals(action)); |
| 87 | // 取回Expires设置,避免注销过程中被置为0 | 87 | // 取回Expires设置,避免注销过程中被置为0 |
| 88 | - ParentPlatform parentPlatformTmp = storager.queryParentPlatByServerGBId(platformGBId); | ||
| 89 | - String expires = parentPlatformTmp.getExpires(); | ||
| 90 | - parentPlatform.setExpires(expires); | ||
| 91 | - parentPlatform.setId(parentPlatformTmp.getId()); | 88 | + if (!parentPlatformCatch.getParentPlatform().getExpires().equals("0")) { |
| 89 | + ParentPlatform parentPlatformTmp = storager.queryParentPlatByServerGBId(platformGBId); | ||
| 90 | + String expires = parentPlatformTmp.getExpires(); | ||
| 91 | + parentPlatform.setExpires(expires); | ||
| 92 | + parentPlatform.setId(parentPlatformTmp.getId()); | ||
| 93 | + redisCatchStorage.updatePlatformRegister(parentPlatform); | ||
| 94 | + redisCatchStorage.updatePlatformKeepalive(parentPlatform); | ||
| 95 | + parentPlatformCatch.setParentPlatform(parentPlatform); | ||
| 96 | + redisCatchStorage.updatePlatformCatchInfo(parentPlatformCatch); | ||
| 97 | + } | ||
| 92 | storager.updateParentPlatformStatus(platformGBId, "注册".equals(action)); | 98 | storager.updateParentPlatformStatus(platformGBId, "注册".equals(action)); |
| 93 | 99 | ||
| 94 | - redisCatchStorage.updatePlatformRegister(parentPlatform); | ||
| 95 | - | ||
| 96 | - redisCatchStorage.updatePlatformKeepalive(parentPlatform); | ||
| 97 | - | ||
| 98 | - parentPlatformCatch.setParentPlatform(parentPlatform); | ||
| 99 | - | ||
| 100 | - redisCatchStorage.updatePlatformCatchInfo(parentPlatformCatch); | ||
| 101 | } | 100 | } |
| 102 | } | 101 | } |
| 103 | 102 |
src/main/java/com/genersoft/iot/vmp/media/zlm/ZLMHttpHookListener.java
| @@ -504,7 +504,7 @@ public class ZLMHttpHookListener { | @@ -504,7 +504,7 @@ public class ZLMHttpHookListener { | ||
| 504 | } | 504 | } |
| 505 | String mediaServerId = json.getString("mediaServerId"); | 505 | String mediaServerId = json.getString("mediaServerId"); |
| 506 | MediaServerItem mediaInfo = mediaServerService.getOne(mediaServerId); | 506 | MediaServerItem mediaInfo = mediaServerService.getOne(mediaServerId); |
| 507 | - if (userSetup.isAutoApplyPlay() && mediaInfo != null) { | 507 | + if (userSetup.isAutoApplyPlay() && mediaInfo != null && mediaInfo.isRtpEnable()) { |
| 508 | String app = json.getString("app"); | 508 | String app = json.getString("app"); |
| 509 | String streamId = json.getString("stream"); | 509 | String streamId = json.getString("stream"); |
| 510 | if ("rtp".equals(app)) { | 510 | if ("rtp".equals(app)) { |
| @@ -514,28 +514,16 @@ public class ZLMHttpHookListener { | @@ -514,28 +514,16 @@ public class ZLMHttpHookListener { | ||
| 514 | String channelId = s[1]; | 514 | String channelId = s[1]; |
| 515 | Device device = redisCatchStorage.getDevice(deviceId); | 515 | Device device = redisCatchStorage.getDevice(deviceId); |
| 516 | if (device != null) { | 516 | if (device != null) { |
| 517 | - UUID uuid = UUID.randomUUID(); | ||
| 518 | - SSRCInfo ssrcInfo; | ||
| 519 | - String streamId2 = null; | ||
| 520 | - if (mediaInfo.isRtpEnable()) { | ||
| 521 | - streamId2 = String.format("%s_%s", device.getDeviceId(), channelId); | ||
| 522 | - } | ||
| 523 | - ssrcInfo = mediaServerService.openRTPServer(mediaInfo, streamId2); | ||
| 524 | - cmder.playStreamCmd(mediaInfo, ssrcInfo, device, channelId, (MediaServerItem mediaServerItemInuse, JSONObject response) -> { | ||
| 525 | - logger.info("收到订阅消息: " + response.toJSONString()); | ||
| 526 | - playService.onPublishHandlerForPlay(mediaServerItemInuse, response, deviceId, channelId, uuid.toString()); | ||
| 527 | - }, null); | 517 | + playService.play(mediaInfo,deviceId, channelId, null, null, null); |
| 528 | } | 518 | } |
| 529 | - | ||
| 530 | } | 519 | } |
| 531 | } | 520 | } |
| 532 | - | ||
| 533 | } | 521 | } |
| 534 | 522 | ||
| 535 | JSONObject ret = new JSONObject(); | 523 | JSONObject ret = new JSONObject(); |
| 536 | ret.put("code", 0); | 524 | ret.put("code", 0); |
| 537 | ret.put("msg", "success"); | 525 | ret.put("msg", "success"); |
| 538 | - return new ResponseEntity<String>(ret.toString(),HttpStatus.OK); | 526 | + return new ResponseEntity<>(ret.toString(),HttpStatus.OK); |
| 539 | } | 527 | } |
| 540 | 528 | ||
| 541 | /** | 529 | /** |
src/main/java/com/genersoft/iot/vmp/media/zlm/ZLMRTPServerFactory.java
| @@ -205,7 +205,7 @@ public class ZLMRTPServerFactory { | @@ -205,7 +205,7 @@ public class ZLMRTPServerFactory { | ||
| 205 | /** | 205 | /** |
| 206 | * 调用zlm RESTful API —— startSendRtp | 206 | * 调用zlm RESTful API —— startSendRtp |
| 207 | */ | 207 | */ |
| 208 | - public Boolean startSendRtpStream(MediaServerItem mediaServerItem, Map<String, Object>param) { | 208 | + public JSONObject startSendRtpStream(MediaServerItem mediaServerItem, Map<String, Object>param) { |
| 209 | Boolean result = false; | 209 | Boolean result = false; |
| 210 | JSONObject jsonObject = zlmresTfulUtils.startSendRtp(mediaServerItem, param); | 210 | JSONObject jsonObject = zlmresTfulUtils.startSendRtp(mediaServerItem, param); |
| 211 | if (jsonObject == null) { | 211 | if (jsonObject == null) { |
| @@ -216,7 +216,7 @@ public class ZLMRTPServerFactory { | @@ -216,7 +216,7 @@ public class ZLMRTPServerFactory { | ||
| 216 | } else { | 216 | } else { |
| 217 | logger.error("RTP推流失败: " + jsonObject.getString("msg")); | 217 | logger.error("RTP推流失败: " + jsonObject.getString("msg")); |
| 218 | } | 218 | } |
| 219 | - return result; | 219 | + return jsonObject; |
| 220 | } | 220 | } |
| 221 | 221 | ||
| 222 | /** | 222 | /** |
src/main/java/com/genersoft/iot/vmp/media/zlm/event/ZLMStatusEventListener.java
| 1 | package com.genersoft.iot.vmp.media.zlm.event; | 1 | package com.genersoft.iot.vmp.media.zlm.event; |
| 2 | 2 | ||
| 3 | import com.genersoft.iot.vmp.service.IMediaServerService; | 3 | import com.genersoft.iot.vmp.service.IMediaServerService; |
| 4 | +import com.genersoft.iot.vmp.service.IPlayService; | ||
| 4 | import com.genersoft.iot.vmp.service.IStreamProxyService; | 5 | import com.genersoft.iot.vmp.service.IStreamProxyService; |
| 5 | import com.genersoft.iot.vmp.service.IStreamPushService; | 6 | import com.genersoft.iot.vmp.service.IStreamPushService; |
| 6 | import org.slf4j.Logger; | 7 | import org.slf4j.Logger; |
| @@ -34,6 +35,9 @@ public class ZLMStatusEventListener { | @@ -34,6 +35,9 @@ public class ZLMStatusEventListener { | ||
| 34 | @Autowired | 35 | @Autowired |
| 35 | private IMediaServerService mediaServerService; | 36 | private IMediaServerService mediaServerService; |
| 36 | 37 | ||
| 38 | + @Autowired | ||
| 39 | + private IPlayService playService; | ||
| 40 | + | ||
| 37 | private SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); | 41 | private SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); |
| 38 | 42 | ||
| 39 | @Async | 43 | @Async |
| @@ -55,6 +59,6 @@ public class ZLMStatusEventListener { | @@ -55,6 +59,6 @@ public class ZLMStatusEventListener { | ||
| 55 | mediaServerService.zlmServerOffline(event.getMediaServerId()); | 59 | mediaServerService.zlmServerOffline(event.getMediaServerId()); |
| 56 | streamProxyService.zlmServerOffline(event.getMediaServerId()); | 60 | streamProxyService.zlmServerOffline(event.getMediaServerId()); |
| 57 | streamPushService.zlmServerOffline(event.getMediaServerId()); | 61 | streamPushService.zlmServerOffline(event.getMediaServerId()); |
| 58 | - // TODO 处理对国标的影响 | 62 | + playService.zlmServerOffline(event.getMediaServerId()); |
| 59 | } | 63 | } |
| 60 | } | 64 | } |
src/main/java/com/genersoft/iot/vmp/service/IMediaServerService.java
| @@ -58,7 +58,7 @@ public interface IMediaServerService { | @@ -58,7 +58,7 @@ public interface IMediaServerService { | ||
| 58 | 58 | ||
| 59 | void removeCount(String mediaServerId); | 59 | void removeCount(String mediaServerId); |
| 60 | 60 | ||
| 61 | - void releaseSsrc(MediaServerItem mediaServerItem, String ssrc); | 61 | + void releaseSsrc(String mediaServerItemId, String ssrc); |
| 62 | 62 | ||
| 63 | void clearMediaServerForOnline(); | 63 | void clearMediaServerForOnline(); |
| 64 | 64 |
src/main/java/com/genersoft/iot/vmp/service/IPlayService.java
| @@ -17,11 +17,13 @@ public interface IPlayService { | @@ -17,11 +17,13 @@ public interface IPlayService { | ||
| 17 | 17 | ||
| 18 | void onPublishHandlerForPlay(MediaServerItem mediaServerItem, JSONObject resonse, String deviceId, String channelId, String uuid); | 18 | void onPublishHandlerForPlay(MediaServerItem mediaServerItem, JSONObject resonse, String deviceId, String channelId, String uuid); |
| 19 | 19 | ||
| 20 | - PlayResult play(MediaServerItem mediaServerItem, String deviceId, String channelId, ZLMHttpHookSubscribe.Event event, SipSubscribe.Event errorEvent); | 20 | + PlayResult play(MediaServerItem mediaServerItem, String deviceId, String channelId, ZLMHttpHookSubscribe.Event event, SipSubscribe.Event errorEvent, Runnable timeoutCallback); |
| 21 | 21 | ||
| 22 | MediaServerItem getNewMediaServerItem(Device device); | 22 | MediaServerItem getNewMediaServerItem(Device device); |
| 23 | 23 | ||
| 24 | void onPublishHandlerForDownload(MediaServerItem mediaServerItem, JSONObject response, String deviceId, String channelId, String toString); | 24 | void onPublishHandlerForDownload(MediaServerItem mediaServerItem, JSONObject response, String deviceId, String channelId, String toString); |
| 25 | 25 | ||
| 26 | DeferredResult<ResponseEntity<String>> playBack(String deviceId, String channelId, String startTime, String endTime, PlayBackCallback errorCallBack); | 26 | DeferredResult<ResponseEntity<String>> playBack(String deviceId, String channelId, String startTime, String endTime, PlayBackCallback errorCallBack); |
| 27 | + | ||
| 28 | + void zlmServerOffline(String mediaServerId); | ||
| 27 | } | 29 | } |
src/main/java/com/genersoft/iot/vmp/service/impl/DeviceServiceImpl.java
| @@ -52,11 +52,9 @@ public class DeviceServiceImpl implements IDeviceService { | @@ -52,11 +52,9 @@ public class DeviceServiceImpl implements IDeviceService { | ||
| 52 | return false; | 52 | return false; |
| 53 | } | 53 | } |
| 54 | logger.info("移除目录订阅: {}", device.getDeviceId()); | 54 | logger.info("移除目录订阅: {}", device.getDeviceId()); |
| 55 | - dynamicTask.stopCron(device.getDeviceId()); | 55 | + dynamicTask.stop(device.getDeviceId()); |
| 56 | device.setSubscribeCycleForCatalog(0); | 56 | device.setSubscribeCycleForCatalog(0); |
| 57 | sipCommander.catalogSubscribe(device, null, null); | 57 | sipCommander.catalogSubscribe(device, null, null); |
| 58 | - // 清空cseq计数 | ||
| 59 | - | ||
| 60 | return true; | 58 | return true; |
| 61 | } | 59 | } |
| 62 | } | 60 | } |
src/main/java/com/genersoft/iot/vmp/service/impl/MediaServerServiceImpl.java
| @@ -167,13 +167,14 @@ public class MediaServerServiceImpl implements IMediaServerService { | @@ -167,13 +167,14 @@ public class MediaServerServiceImpl implements IMediaServerService { | ||
| 167 | if (mediaServerItem != null) { | 167 | if (mediaServerItem != null) { |
| 168 | String streamId = String.format("%s_%s", deviceId, channelId); | 168 | String streamId = String.format("%s_%s", deviceId, channelId); |
| 169 | zlmrtpServerFactory.closeRTPServer(mediaServerItem, streamId); | 169 | zlmrtpServerFactory.closeRTPServer(mediaServerItem, streamId); |
| 170 | - releaseSsrc(mediaServerItem, ssrc); | 170 | + releaseSsrc(mediaServerItem.getId(), ssrc); |
| 171 | } | 171 | } |
| 172 | streamSession.remove(deviceId, channelId, stream); | 172 | streamSession.remove(deviceId, channelId, stream); |
| 173 | } | 173 | } |
| 174 | 174 | ||
| 175 | @Override | 175 | @Override |
| 176 | - public void releaseSsrc(MediaServerItem mediaServerItem, String ssrc) { | 176 | + public void releaseSsrc(String mediaServerItemId, String ssrc) { |
| 177 | + MediaServerItem mediaServerItem = getOne(mediaServerItemId); | ||
| 177 | if (mediaServerItem == null || ssrc == null) { | 178 | if (mediaServerItem == null || ssrc == null) { |
| 178 | return; | 179 | return; |
| 179 | } | 180 | } |
src/main/java/com/genersoft/iot/vmp/service/impl/PlayServiceImpl.java
| @@ -5,13 +5,13 @@ import com.alibaba.fastjson.JSONArray; | @@ -5,13 +5,13 @@ import com.alibaba.fastjson.JSONArray; | ||
| 5 | import com.alibaba.fastjson.JSONObject; | 5 | import com.alibaba.fastjson.JSONObject; |
| 6 | import com.genersoft.iot.vmp.common.StreamInfo; | 6 | import com.genersoft.iot.vmp.common.StreamInfo; |
| 7 | import com.genersoft.iot.vmp.conf.UserSetup; | 7 | import com.genersoft.iot.vmp.conf.UserSetup; |
| 8 | -import com.genersoft.iot.vmp.gb28181.bean.Device; | ||
| 9 | -import com.genersoft.iot.vmp.gb28181.bean.DeviceChannel; | 8 | +import com.genersoft.iot.vmp.gb28181.bean.*; |
| 10 | import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; | 9 | import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; |
| 11 | import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; | 10 | import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; |
| 12 | import com.genersoft.iot.vmp.gb28181.transmit.callback.DeferredResultHolder; | 11 | import com.genersoft.iot.vmp.gb28181.transmit.callback.DeferredResultHolder; |
| 13 | import com.genersoft.iot.vmp.gb28181.transmit.callback.RequestMessage; | 12 | import com.genersoft.iot.vmp.gb28181.transmit.callback.RequestMessage; |
| 14 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.impl.SIPCommander; | 13 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.impl.SIPCommander; |
| 14 | +import com.genersoft.iot.vmp.gb28181.transmit.cmd.impl.SIPCommanderFroPlatform; | ||
| 15 | import com.genersoft.iot.vmp.media.zlm.ZLMHttpHookSubscribe; | 15 | import com.genersoft.iot.vmp.media.zlm.ZLMHttpHookSubscribe; |
| 16 | import com.genersoft.iot.vmp.media.zlm.ZLMRESTfulUtils; | 16 | import com.genersoft.iot.vmp.media.zlm.ZLMRESTfulUtils; |
| 17 | import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; | 17 | import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; |
| @@ -37,8 +37,7 @@ import org.springframework.util.ResourceUtils; | @@ -37,8 +37,7 @@ import org.springframework.util.ResourceUtils; | ||
| 37 | import org.springframework.web.context.request.async.DeferredResult; | 37 | import org.springframework.web.context.request.async.DeferredResult; |
| 38 | 38 | ||
| 39 | import java.io.FileNotFoundException; | 39 | import java.io.FileNotFoundException; |
| 40 | -import java.util.Objects; | ||
| 41 | -import java.util.UUID; | 40 | +import java.util.*; |
| 42 | 41 | ||
| 43 | @SuppressWarnings(value = {"rawtypes", "unchecked"}) | 42 | @SuppressWarnings(value = {"rawtypes", "unchecked"}) |
| 44 | @Service | 43 | @Service |
| @@ -53,6 +52,9 @@ public class PlayServiceImpl implements IPlayService { | @@ -53,6 +52,9 @@ public class PlayServiceImpl implements IPlayService { | ||
| 53 | private SIPCommander cmder; | 52 | private SIPCommander cmder; |
| 54 | 53 | ||
| 55 | @Autowired | 54 | @Autowired |
| 55 | + private SIPCommanderFroPlatform sipCommanderFroPlatform; | ||
| 56 | + | ||
| 57 | + @Autowired | ||
| 56 | private IRedisCatchStorage redisCatchStorage; | 58 | private IRedisCatchStorage redisCatchStorage; |
| 57 | 59 | ||
| 58 | @Autowired | 60 | @Autowired |
| @@ -78,7 +80,9 @@ public class PlayServiceImpl implements IPlayService { | @@ -78,7 +80,9 @@ public class PlayServiceImpl implements IPlayService { | ||
| 78 | 80 | ||
| 79 | 81 | ||
| 80 | @Override | 82 | @Override |
| 81 | - public PlayResult play(MediaServerItem mediaServerItem, String deviceId, String channelId, ZLMHttpHookSubscribe.Event hookEvent, SipSubscribe.Event errorEvent) { | 83 | + public PlayResult play(MediaServerItem mediaServerItem, String deviceId, String channelId, |
| 84 | + ZLMHttpHookSubscribe.Event hookEvent, SipSubscribe.Event errorEvent, | ||
| 85 | + Runnable timeoutCallback) { | ||
| 82 | PlayResult playResult = new PlayResult(); | 86 | PlayResult playResult = new PlayResult(); |
| 83 | RequestMessage msg = new RequestMessage(); | 87 | RequestMessage msg = new RequestMessage(); |
| 84 | String key = DeferredResultHolder.CALLBACK_CMD_PLAY + deviceId + channelId; | 88 | String key = DeferredResultHolder.CALLBACK_CMD_PLAY + deviceId + channelId; |
| @@ -101,29 +105,10 @@ public class PlayServiceImpl implements IPlayService { | @@ -101,29 +105,10 @@ public class PlayServiceImpl implements IPlayService { | ||
| 101 | Device device = redisCatchStorage.getDevice(deviceId); | 105 | Device device = redisCatchStorage.getDevice(deviceId); |
| 102 | StreamInfo streamInfo = redisCatchStorage.queryPlayByDevice(deviceId, channelId); | 106 | StreamInfo streamInfo = redisCatchStorage.queryPlayByDevice(deviceId, channelId); |
| 103 | playResult.setDevice(device); | 107 | playResult.setDevice(device); |
| 104 | - // 超时处理 | ||
| 105 | - result.onTimeout(()->{ | ||
| 106 | - logger.warn(String.format("设备点播超时,deviceId:%s ,channelId:%s", deviceId, channelId)); | ||
| 107 | - WVPResult wvpResult = new WVPResult(); | ||
| 108 | - wvpResult.setCode(-1); | ||
| 109 | - SIPDialog dialog = streamSession.getDialogByStream(deviceId, channelId, streamInfo.getStream()); | ||
| 110 | - if (dialog != null) { | ||
| 111 | - wvpResult.setMsg("收流超时,请稍候重试"); | ||
| 112 | - }else { | ||
| 113 | - wvpResult.setMsg("点播超时,请稍候重试"); | ||
| 114 | - } | ||
| 115 | 108 | ||
| 116 | - msg.setData(wvpResult); | ||
| 117 | - // 点播超时回复BYE | ||
| 118 | - cmder.streamByeCmd(device.getDeviceId(), channelId, streamInfo.getStream()); | ||
| 119 | - // 释放rtpserver | ||
| 120 | - mediaServerService.closeRTPServer(playResult.getDevice().getDeviceId(), channelId, streamInfo.getStream()); | ||
| 121 | - // 回复之前所有的点播请求 | ||
| 122 | - resultHolder.invokeAllResult(msg); | ||
| 123 | - // TODO 释放ssrc | ||
| 124 | - }); | ||
| 125 | result.onCompletion(()->{ | 109 | result.onCompletion(()->{ |
| 126 | // 点播结束时调用截图接口 | 110 | // 点播结束时调用截图接口 |
| 111 | + // TODO 应该在上流时调用更好,结束也可能是错误结束 | ||
| 127 | try { | 112 | try { |
| 128 | String classPath = ResourceUtils.getURL("classpath:").getPath(); | 113 | String classPath = ResourceUtils.getURL("classpath:").getPath(); |
| 129 | // 兼容打包为jar的class路径 | 114 | // 兼容打包为jar的class路径 |
| @@ -161,31 +146,60 @@ public class PlayServiceImpl implements IPlayService { | @@ -161,31 +146,60 @@ public class PlayServiceImpl implements IPlayService { | ||
| 161 | if (mediaServerItem.isRtpEnable()) { | 146 | if (mediaServerItem.isRtpEnable()) { |
| 162 | streamId = String.format("%s_%s", device.getDeviceId(), channelId); | 147 | streamId = String.format("%s_%s", device.getDeviceId(), channelId); |
| 163 | } | 148 | } |
| 164 | - | ||
| 165 | SSRCInfo ssrcInfo = mediaServerService.openRTPServer(mediaServerItem, streamId); | 149 | SSRCInfo ssrcInfo = mediaServerService.openRTPServer(mediaServerItem, streamId); |
| 150 | + // 超时处理 | ||
| 151 | + Timer timer = new Timer(); | ||
| 152 | + timer.schedule(new TimerTask() { | ||
| 153 | + @Override | ||
| 154 | + public void run() { | ||
| 155 | + logger.warn(String.format("设备点播超时,deviceId:%s ,channelId:%s", deviceId, channelId)); | ||
| 156 | + if (timeoutCallback != null) { | ||
| 157 | + timeoutCallback.run(); | ||
| 158 | + } | ||
| 159 | + WVPResult wvpResult = new WVPResult(); | ||
| 160 | + wvpResult.setCode(-1); | ||
| 161 | + SIPDialog dialog = streamSession.getDialogByStream(deviceId, channelId, ssrcInfo.getStream()); | ||
| 162 | + if (dialog != null) { | ||
| 163 | + wvpResult.setMsg("收流超时,请稍候重试"); | ||
| 164 | + // 点播超时回复BYE 同时释放ssrc以及此次点播的资源 | ||
| 165 | + cmder.streamByeCmd(device.getDeviceId(), channelId, ssrcInfo.getStream()); | ||
| 166 | + }else { | ||
| 167 | + wvpResult.setMsg("点播超时,请稍候重试"); | ||
| 168 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); | ||
| 169 | + mediaServerService.closeRTPServer(deviceId, channelId, ssrcInfo.getStream()); | ||
| 170 | + streamSession.remove(deviceId, channelId, ssrcInfo.getStream()); | ||
| 171 | + } | ||
| 172 | + | ||
| 173 | + msg.setData(wvpResult); | ||
| 174 | + | ||
| 175 | + // 回复之前所有的点播请求 | ||
| 176 | + resultHolder.invokeAllResult(msg); | ||
| 177 | + } | ||
| 178 | + }, userSetup.getPlayTimeout()); | ||
| 166 | // 发送点播消息 | 179 | // 发送点播消息 |
| 167 | cmder.playStreamCmd(mediaServerItem, ssrcInfo, device, channelId, (MediaServerItem mediaServerItemInUse, JSONObject response) -> { | 180 | cmder.playStreamCmd(mediaServerItem, ssrcInfo, device, channelId, (MediaServerItem mediaServerItemInUse, JSONObject response) -> { |
| 168 | logger.info("收到订阅消息: " + response.toJSONString()); | 181 | logger.info("收到订阅消息: " + response.toJSONString()); |
| 182 | + timer.cancel(); | ||
| 169 | onPublishHandlerForPlay(mediaServerItemInUse, response, deviceId, channelId, uuid); | 183 | onPublishHandlerForPlay(mediaServerItemInUse, response, deviceId, channelId, uuid); |
| 170 | if (hookEvent != null) { | 184 | if (hookEvent != null) { |
| 171 | hookEvent.response(mediaServerItem, response); | 185 | hookEvent.response(mediaServerItem, response); |
| 172 | } | 186 | } |
| 173 | }, (event) -> { | 187 | }, (event) -> { |
| 188 | + timer.cancel(); | ||
| 174 | WVPResult wvpResult = new WVPResult(); | 189 | WVPResult wvpResult = new WVPResult(); |
| 175 | wvpResult.setCode(-1); | 190 | wvpResult.setCode(-1); |
| 176 | // 点播返回sip错误 | 191 | // 点播返回sip错误 |
| 177 | mediaServerService.closeRTPServer(playResult.getDevice().getDeviceId(), channelId, ssrcInfo.getStream()); | 192 | mediaServerService.closeRTPServer(playResult.getDevice().getDeviceId(), channelId, ssrcInfo.getStream()); |
| 178 | // 释放ssrc | 193 | // 释放ssrc |
| 179 | - mediaServerService.releaseSsrc(mediaServerItem, ssrcInfo.getSsrc()); | 194 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); |
| 180 | streamSession.remove(deviceId, channelId, ssrcInfo.getStream()); | 195 | streamSession.remove(deviceId, channelId, ssrcInfo.getStream()); |
| 196 | + | ||
| 181 | wvpResult.setMsg(String.format("点播失败, 错误码: %s, %s", event.statusCode, event.msg)); | 197 | wvpResult.setMsg(String.format("点播失败, 错误码: %s, %s", event.statusCode, event.msg)); |
| 182 | msg.setData(wvpResult); | 198 | msg.setData(wvpResult); |
| 183 | resultHolder.invokeAllResult(msg); | 199 | resultHolder.invokeAllResult(msg); |
| 184 | if (errorEvent != null) { | 200 | if (errorEvent != null) { |
| 185 | errorEvent.response(event); | 201 | errorEvent.response(event); |
| 186 | } | 202 | } |
| 187 | - | ||
| 188 | - | ||
| 189 | }); | 203 | }); |
| 190 | } else { | 204 | } else { |
| 191 | String streamId = streamInfo.getStream(); | 205 | String streamId = streamInfo.getStream(); |
| @@ -222,13 +236,41 @@ public class PlayServiceImpl implements IPlayService { | @@ -222,13 +236,41 @@ public class PlayServiceImpl implements IPlayService { | ||
| 222 | streamId2 = String.format("%s_%s", device.getDeviceId(), channelId); | 236 | streamId2 = String.format("%s_%s", device.getDeviceId(), channelId); |
| 223 | } | 237 | } |
| 224 | SSRCInfo ssrcInfo = mediaServerService.openRTPServer(mediaServerItem, streamId2); | 238 | SSRCInfo ssrcInfo = mediaServerService.openRTPServer(mediaServerItem, streamId2); |
| 239 | + // 超时处理 | ||
| 240 | + Timer timer = new Timer(); | ||
| 241 | + timer.schedule(new TimerTask() { | ||
| 242 | + @Override | ||
| 243 | + public void run() { | ||
| 244 | + logger.warn(String.format("设备点播超时,deviceId:%s ,channelId:%s", deviceId, channelId)); | ||
| 245 | + if (timeoutCallback != null) { | ||
| 246 | + timeoutCallback.run(); | ||
| 247 | + } | ||
| 248 | + WVPResult wvpResult = new WVPResult(); | ||
| 249 | + wvpResult.setCode(-1); | ||
| 250 | + SIPDialog dialog = streamSession.getDialogByStream(deviceId, channelId, ssrcInfo.getStream()); | ||
| 251 | + if (dialog != null) { | ||
| 252 | + wvpResult.setMsg("收流超时,请稍候重试"); | ||
| 253 | + // 点播超时回复BYE 同时释放ssrc以及此次点播的资源 | ||
| 254 | + cmder.streamByeCmd(device.getDeviceId(), channelId, ssrcInfo.getStream()); | ||
| 255 | + }else { | ||
| 256 | + wvpResult.setMsg("点播超时,请稍候重试"); | ||
| 257 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); | ||
| 258 | + mediaServerService.closeRTPServer(deviceId, channelId, ssrcInfo.getStream()); | ||
| 259 | + streamSession.remove(deviceId, channelId, ssrcInfo.getStream()); | ||
| 260 | + } | ||
| 261 | + | ||
| 262 | + msg.setData(wvpResult); | ||
| 263 | + // 回复之前所有的点播请求 | ||
| 264 | + resultHolder.invokeAllResult(msg); | ||
| 265 | + } | ||
| 266 | + }, userSetup.getPlayTimeout()); | ||
| 225 | cmder.playStreamCmd(mediaServerItem, ssrcInfo, device, channelId, (MediaServerItem mediaServerItemInuse, JSONObject response) -> { | 267 | cmder.playStreamCmd(mediaServerItem, ssrcInfo, device, channelId, (MediaServerItem mediaServerItemInuse, JSONObject response) -> { |
| 226 | logger.info("收到订阅消息: " + response.toJSONString()); | 268 | logger.info("收到订阅消息: " + response.toJSONString()); |
| 227 | onPublishHandlerForPlay(mediaServerItemInuse, response, deviceId, channelId, uuid); | 269 | onPublishHandlerForPlay(mediaServerItemInuse, response, deviceId, channelId, uuid); |
| 228 | }, (event) -> { | 270 | }, (event) -> { |
| 229 | mediaServerService.closeRTPServer(playResult.getDevice().getDeviceId(), channelId, ssrcInfo.getStream()); | 271 | mediaServerService.closeRTPServer(playResult.getDevice().getDeviceId(), channelId, ssrcInfo.getStream()); |
| 230 | // 释放ssrc | 272 | // 释放ssrc |
| 231 | - mediaServerService.releaseSsrc(mediaServerItem, ssrcInfo.getSsrc()); | 273 | + mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); |
| 232 | streamSession.remove(deviceId, channelId, ssrcInfo.getStream()); | 274 | streamSession.remove(deviceId, channelId, ssrcInfo.getStream()); |
| 233 | WVPResult wvpResult = new WVPResult(); | 275 | WVPResult wvpResult = new WVPResult(); |
| 234 | wvpResult.setCode(-1); | 276 | wvpResult.setCode(-1); |
| @@ -306,14 +348,33 @@ public class PlayServiceImpl implements IPlayService { | @@ -306,14 +348,33 @@ public class PlayServiceImpl implements IPlayService { | ||
| 306 | msg.setId(uuid); | 348 | msg.setId(uuid); |
| 307 | msg.setKey(key); | 349 | msg.setKey(key); |
| 308 | PlayBackResult<RequestMessage> playBackResult = new PlayBackResult<>(); | 350 | PlayBackResult<RequestMessage> playBackResult = new PlayBackResult<>(); |
| 309 | - result.onTimeout(()->{ | ||
| 310 | - msg.setData("回放超时"); | ||
| 311 | - playBackResult.setCode(-1); | ||
| 312 | - playBackResult.setData(msg); | ||
| 313 | - callback.call(playBackResult); | ||
| 314 | - }); | 351 | + |
| 352 | + Timer timer = new Timer(); | ||
| 353 | + timer.schedule(new TimerTask() { | ||
| 354 | + @Override | ||
| 355 | + public void run() { | ||
| 356 | + logger.warn(String.format("设备回放超时,deviceId:%s ,channelId:%s", deviceId, channelId)); | ||
| 357 | + playBackResult.setCode(-1); | ||
| 358 | + playBackResult.setData(msg); | ||
| 359 | + callback.call(playBackResult); | ||
| 360 | + SIPDialog dialog = streamSession.getDialogByStream(deviceId, channelId, ssrcInfo.getStream()); | ||
| 361 | + // 点播超时回复BYE 同时释放ssrc以及此次点播的资源 | ||
| 362 | + if (dialog != null) { | ||
| 363 | + // 点播超时回复BYE 同时释放ssrc以及此次点播的资源 | ||
| 364 | + cmder.streamByeCmd(device.getDeviceId(), channelId, ssrcInfo.getStream()); | ||
| 365 | + }else { | ||
| 366 | + mediaServerService.releaseSsrc(newMediaServerItem.getId(), ssrcInfo.getSsrc()); | ||
| 367 | + mediaServerService.closeRTPServer(deviceId, channelId, ssrcInfo.getStream()); | ||
| 368 | + streamSession.remove(deviceId, channelId, ssrcInfo.getStream()); | ||
| 369 | + } | ||
| 370 | + cmder.streamByeCmd(device.getDeviceId(), channelId, ssrcInfo.getStream()); | ||
| 371 | + // 回复之前所有的点播请求 | ||
| 372 | + callback.call(playBackResult); | ||
| 373 | + } | ||
| 374 | + }, userSetup.getPlayTimeout()); | ||
| 315 | cmder.playbackStreamCmd(newMediaServerItem, ssrcInfo, device, channelId, startTime, endTime, (MediaServerItem mediaServerItem, JSONObject response) -> { | 375 | cmder.playbackStreamCmd(newMediaServerItem, ssrcInfo, device, channelId, startTime, endTime, (MediaServerItem mediaServerItem, JSONObject response) -> { |
| 316 | logger.info("收到订阅消息: " + response.toJSONString()); | 376 | logger.info("收到订阅消息: " + response.toJSONString()); |
| 377 | + timer.cancel(); | ||
| 317 | StreamInfo streamInfo = onPublishHandler(mediaServerItem, response, deviceId, channelId); | 378 | StreamInfo streamInfo = onPublishHandler(mediaServerItem, response, deviceId, channelId); |
| 318 | if (streamInfo == null) { | 379 | if (streamInfo == null) { |
| 319 | logger.warn("设备回放API调用失败!"); | 380 | logger.warn("设备回放API调用失败!"); |
| @@ -331,6 +392,7 @@ public class PlayServiceImpl implements IPlayService { | @@ -331,6 +392,7 @@ public class PlayServiceImpl implements IPlayService { | ||
| 331 | playBackResult.setResponse(response); | 392 | playBackResult.setResponse(response); |
| 332 | callback.call(playBackResult); | 393 | callback.call(playBackResult); |
| 333 | }, event -> { | 394 | }, event -> { |
| 395 | + timer.cancel(); | ||
| 334 | msg.setData(String.format("回放失败, 错误码: %s, %s", event.statusCode, event.msg)); | 396 | msg.setData(String.format("回放失败, 错误码: %s, %s", event.statusCode, event.msg)); |
| 335 | playBackResult.setCode(-1); | 397 | playBackResult.setCode(-1); |
| 336 | playBackResult.setData(msg); | 398 | playBackResult.setData(msg); |
| @@ -370,4 +432,26 @@ public class PlayServiceImpl implements IPlayService { | @@ -370,4 +432,26 @@ public class PlayServiceImpl implements IPlayService { | ||
| 370 | return streamInfo; | 432 | return streamInfo; |
| 371 | } | 433 | } |
| 372 | 434 | ||
| 435 | + @Override | ||
| 436 | + public void zlmServerOffline(String mediaServerId) { | ||
| 437 | + // 处理正在向上推流的上级平台 | ||
| 438 | + List<SendRtpItem> sendRtpItems = redisCatchStorage.querySendRTPServer(null); | ||
| 439 | + if (sendRtpItems.size() > 0) { | ||
| 440 | + for (SendRtpItem sendRtpItem : sendRtpItems) { | ||
| 441 | + if (sendRtpItem.getMediaServerId().equals(mediaServerId)) { | ||
| 442 | + ParentPlatform platform = storager.queryParentPlatByServerGBId(sendRtpItem.getPlatformId()); | ||
| 443 | + sipCommanderFroPlatform.streamByeCmd(platform, sendRtpItem.getCallId()); | ||
| 444 | + } | ||
| 445 | + } | ||
| 446 | + } | ||
| 447 | + // 处理正在观看的国标设备 | ||
| 448 | + List<SsrcTransaction> allSsrc = streamSession.getAllSsrc(); | ||
| 449 | + if (allSsrc.size() > 0) { | ||
| 450 | + for (SsrcTransaction ssrcTransaction : allSsrc) { | ||
| 451 | + if(ssrcTransaction.getMediaServerId().equals(mediaServerId)) { | ||
| 452 | + cmder.streamByeCmd(ssrcTransaction.getDeviceId(), ssrcTransaction.getChannelId(), ssrcTransaction.getStream()); | ||
| 453 | + } | ||
| 454 | + } | ||
| 455 | + } | ||
| 456 | + } | ||
| 373 | } | 457 | } |
src/main/java/com/genersoft/iot/vmp/storager/IRedisCatchStorage.java
| @@ -89,7 +89,7 @@ public interface IRedisCatchStorage { | @@ -89,7 +89,7 @@ public interface IRedisCatchStorage { | ||
| 89 | * @param channelId | 89 | * @param channelId |
| 90 | * @return sendRtpItem | 90 | * @return sendRtpItem |
| 91 | */ | 91 | */ |
| 92 | - SendRtpItem querySendRTPServer(String platformGbId, String channelId); | 92 | + SendRtpItem querySendRTPServer(String platformGbId, String channelId, String streamId, String callId); |
| 93 | 93 | ||
| 94 | List<SendRtpItem> querySendRTPServer(String platformGbId); | 94 | List<SendRtpItem> querySendRTPServer(String platformGbId); |
| 95 | 95 | ||
| @@ -98,7 +98,7 @@ public interface IRedisCatchStorage { | @@ -98,7 +98,7 @@ public interface IRedisCatchStorage { | ||
| 98 | * @param platformGbId | 98 | * @param platformGbId |
| 99 | * @param channelId | 99 | * @param channelId |
| 100 | */ | 100 | */ |
| 101 | - void deleteSendRTPServer(String platformGbId, String channelId); | 101 | + void deleteSendRTPServer(String platformGbId, String channelId, String callId, String streamId); |
| 102 | 102 | ||
| 103 | /** | 103 | /** |
| 104 | * 查询某个通道是否存在上级点播(RTP推送) | 104 | * 查询某个通道是否存在上级点播(RTP推送) |
src/main/java/com/genersoft/iot/vmp/storager/dao/DeviceChannelMapper.java
| @@ -135,6 +135,32 @@ public interface DeviceChannelMapper { | @@ -135,6 +135,32 @@ public interface DeviceChannelMapper { | ||
| 135 | "'${item.ipAddress}', ${item.port}, '${item.password}', ${item.PTZType}, ${item.status}, " + | 135 | "'${item.ipAddress}', ${item.port}, '${item.password}', ${item.PTZType}, ${item.status}, " + |
| 136 | "'${item.streamId}', ${item.longitude}, ${item.latitude},'${item.createTime}', '${item.updateTime}')" + | 136 | "'${item.streamId}', ${item.longitude}, ${item.latitude},'${item.createTime}', '${item.updateTime}')" + |
| 137 | "</foreach> " + | 137 | "</foreach> " + |
| 138 | + "ON DUPLICATE KEY UPDATE " + | ||
| 139 | + "updateTime=VALUES(updateTime), " + | ||
| 140 | + "name=VALUES(name), " + | ||
| 141 | + "manufacture=VALUES(manufacture), " + | ||
| 142 | + "model=VALUES(model), " + | ||
| 143 | + "owner=VALUES(owner), " + | ||
| 144 | + "civilCode=VALUES(civilCode), " + | ||
| 145 | + "block=VALUES(block), " + | ||
| 146 | + "subCount=VALUES(subCount), " + | ||
| 147 | + "address=VALUES(address), " + | ||
| 148 | + "parental=VALUES(parental), " + | ||
| 149 | + "parentId=VALUES(parentId), " + | ||
| 150 | + "safetyWay=VALUES(safetyWay), " + | ||
| 151 | + "registerWay=VALUES(registerWay), " + | ||
| 152 | + "certNum=VALUES(certNum), " + | ||
| 153 | + "certifiable=VALUES(certifiable), " + | ||
| 154 | + "errCode=VALUES(errCode), " + | ||
| 155 | + "secrecy=VALUES(secrecy), " + | ||
| 156 | + "ipAddress=VALUES(ipAddress), " + | ||
| 157 | + "port=VALUES(port), " + | ||
| 158 | + "password=VALUES(password), " + | ||
| 159 | + "PTZType=VALUES(PTZType), " + | ||
| 160 | + "status=VALUES(status), " + | ||
| 161 | + "streamId=VALUES(streamId), " + | ||
| 162 | + "longitude=VALUES(longitude), " + | ||
| 163 | + "latitude=VALUES(latitude)" + | ||
| 138 | "</script>") | 164 | "</script>") |
| 139 | int batchAdd(List<DeviceChannel> addChannels); | 165 | int batchAdd(List<DeviceChannel> addChannels); |
| 140 | 166 | ||
| @@ -211,4 +237,15 @@ public interface DeviceChannelMapper { | @@ -211,4 +237,15 @@ public interface DeviceChannelMapper { | ||
| 211 | " from device_channel\n" + | 237 | " from device_channel\n" + |
| 212 | " where deviceId = #{deviceId}") | 238 | " where deviceId = #{deviceId}") |
| 213 | List<DeviceChannelTree> tree(String deviceId); | 239 | List<DeviceChannelTree> tree(String deviceId); |
| 240 | + | ||
| 241 | + @Delete(value = {" <script>" + | ||
| 242 | + "DELETE " + | ||
| 243 | + "from " + | ||
| 244 | + "device_channel " + | ||
| 245 | + "WHERE " + | ||
| 246 | + "deviceId = #{deviceId} " + | ||
| 247 | + " AND channelId NOT IN " + | ||
| 248 | + "<foreach collection='channels' item='item' open='(' separator=',' close=')' > #{item.channelId}</foreach>" + | ||
| 249 | + " </script>"}) | ||
| 250 | + int cleanChannelsNotInList(String deviceId, List<DeviceChannel> channels); | ||
| 214 | } | 251 | } |
src/main/java/com/genersoft/iot/vmp/storager/impl/RedisCatchStorageImpl.java
| @@ -18,6 +18,7 @@ import com.genersoft.iot.vmp.utils.redis.RedisUtil; | @@ -18,6 +18,7 @@ import com.genersoft.iot.vmp.utils.redis.RedisUtil; | ||
| 18 | import org.slf4j.Logger; | 18 | import org.slf4j.Logger; |
| 19 | import org.slf4j.LoggerFactory; | 19 | import org.slf4j.LoggerFactory; |
| 20 | import org.springframework.beans.factory.annotation.Autowired; | 20 | import org.springframework.beans.factory.annotation.Autowired; |
| 21 | +import org.springframework.security.core.parameters.P; | ||
| 21 | import org.springframework.stereotype.Component; | 22 | import org.springframework.stereotype.Component; |
| 22 | import org.springframework.util.StringUtils; | 23 | import org.springframework.util.StringUtils; |
| 23 | 24 | ||
| @@ -276,19 +277,32 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { | @@ -276,19 +277,32 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { | ||
| 276 | 277 | ||
| 277 | @Override | 278 | @Override |
| 278 | public void updateSendRTPSever(SendRtpItem sendRtpItem) { | 279 | public void updateSendRTPSever(SendRtpItem sendRtpItem) { |
| 279 | - String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + sendRtpItem.getPlatformId() + "_" + sendRtpItem.getChannelId(); | 280 | + String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" |
| 281 | + + sendRtpItem.getPlatformId() + "_" + sendRtpItem.getChannelId() + "_" | ||
| 282 | + + sendRtpItem.getStreamId() + "_" + sendRtpItem.getCallId(); | ||
| 280 | redis.set(key, sendRtpItem); | 283 | redis.set(key, sendRtpItem); |
| 281 | } | 284 | } |
| 282 | 285 | ||
| 283 | @Override | 286 | @Override |
| 284 | - public SendRtpItem querySendRTPServer(String platformGbId, String channelId) { | ||
| 285 | - String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + platformGbId + "_" + channelId; | ||
| 286 | - return (SendRtpItem)redis.get(key); | 287 | + public SendRtpItem querySendRTPServer(String platformGbId, String channelId, String streamId, String callId) { |
| 288 | + if (platformGbId == null) platformGbId = "*"; | ||
| 289 | + if (channelId == null) channelId = "*"; | ||
| 290 | + if (streamId == null) streamId = "*"; | ||
| 291 | + if (callId == null) callId = "*"; | ||
| 292 | + String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + platformGbId | ||
| 293 | + + "_" + channelId + "_" + streamId + "_" + callId; | ||
| 294 | + List<Object> scan = redis.scan(key); | ||
| 295 | + if (scan.size() > 0) { | ||
| 296 | + return (SendRtpItem)redis.get((String)scan.get(0)); | ||
| 297 | + }else { | ||
| 298 | + return null; | ||
| 299 | + } | ||
| 287 | } | 300 | } |
| 288 | 301 | ||
| 289 | @Override | 302 | @Override |
| 290 | public List<SendRtpItem> querySendRTPServer(String platformGbId) { | 303 | public List<SendRtpItem> querySendRTPServer(String platformGbId) { |
| 291 | - String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + platformGbId + "_*"; | 304 | + if (platformGbId == null) platformGbId = "*"; |
| 305 | + String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + platformGbId + "_*" + "_*" + "_*"; | ||
| 292 | List<Object> queryResult = redis.scan(key); | 306 | List<Object> queryResult = redis.scan(key); |
| 293 | List<SendRtpItem> result= new ArrayList<>(); | 307 | List<SendRtpItem> result= new ArrayList<>(); |
| 294 | 308 | ||
| @@ -306,18 +320,28 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { | @@ -306,18 +320,28 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { | ||
| 306 | * @param channelId | 320 | * @param channelId |
| 307 | */ | 321 | */ |
| 308 | @Override | 322 | @Override |
| 309 | - public void deleteSendRTPServer(String platformGbId, String channelId) { | ||
| 310 | - String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + platformGbId + "_" + channelId; | ||
| 311 | - redis.del(key); | 323 | + public void deleteSendRTPServer(String platformGbId, String channelId, String callId, String streamId) { |
| 324 | + if (streamId == null) streamId = "*"; | ||
| 325 | + if (callId == null) callId = "*"; | ||
| 326 | + String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + platformGbId | ||
| 327 | + + "_" + channelId + "_" + streamId + "_" + callId; | ||
| 328 | + List<Object> scan = redis.scan(key); | ||
| 329 | + if (scan.size() > 0) { | ||
| 330 | + for (Object keyStr : scan) { | ||
| 331 | + redis.del((String)keyStr); | ||
| 332 | + } | ||
| 333 | + } | ||
| 312 | } | 334 | } |
| 313 | 335 | ||
| 336 | + | ||
| 337 | + | ||
| 314 | /** | 338 | /** |
| 315 | * 查询某个通道是否存在上级点播(RTP推送) | 339 | * 查询某个通道是否存在上级点播(RTP推送) |
| 316 | * @param channelId | 340 | * @param channelId |
| 317 | */ | 341 | */ |
| 318 | @Override | 342 | @Override |
| 319 | public boolean isChannelSendingRTP(String channelId) { | 343 | public boolean isChannelSendingRTP(String channelId) { |
| 320 | - String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + "*_" + channelId; | 344 | + String key = VideoManagerConstants.PLATFORM_SEND_RTP_INFO_PREFIX + userSetup.getServerId() + "_" + "*_" + channelId + "*_" + "*_"; |
| 321 | List<Object> RtpStreams = redis.scan(key); | 345 | List<Object> RtpStreams = redis.scan(key); |
| 322 | if (RtpStreams.size() > 0) { | 346 | if (RtpStreams.size() > 0) { |
| 323 | return true; | 347 | return true; |
src/main/java/com/genersoft/iot/vmp/storager/impl/VideoManagerStoragerImpl.java
| @@ -284,7 +284,8 @@ public class VideoManagerStoragerImpl implements IVideoManagerStorager { | @@ -284,7 +284,8 @@ public class VideoManagerStoragerImpl implements IVideoManagerStorager { | ||
| 284 | logger.debug("[目录查询]收到的数据存在重复: {}" , stringBuilder); | 284 | logger.debug("[目录查询]收到的数据存在重复: {}" , stringBuilder); |
| 285 | } | 285 | } |
| 286 | try { | 286 | try { |
| 287 | - int cleanChannelsResult = deviceChannelMapper.cleanChannelsByDeviceId(deviceId); | 287 | +// int cleanChannelsResult = deviceChannelMapper.cleanChannelsByDeviceId(deviceId); |
| 288 | + int cleanChannelsResult = deviceChannelMapper.cleanChannelsNotInList(deviceId, channels); | ||
| 288 | int limitCount = 300; | 289 | int limitCount = 300; |
| 289 | boolean result = cleanChannelsResult < 0; | 290 | boolean result = cleanChannelsResult < 0; |
| 290 | if (!result && channels.size() > 0) { | 291 | if (!result && channels.size() > 0) { |
src/main/java/com/genersoft/iot/vmp/vmanager/gb28181/device/DeviceQuery.java
| 1 | package com.genersoft.iot.vmp.vmanager.gb28181.device; | 1 | package com.genersoft.iot.vmp.vmanager.gb28181.device; |
| 2 | 2 | ||
| 3 | import com.alibaba.fastjson.JSONObject; | 3 | import com.alibaba.fastjson.JSONObject; |
| 4 | +import com.genersoft.iot.vmp.conf.DynamicTask; | ||
| 4 | import com.genersoft.iot.vmp.gb28181.bean.Device; | 5 | import com.genersoft.iot.vmp.gb28181.bean.Device; |
| 5 | import com.genersoft.iot.vmp.gb28181.bean.DeviceChannel; | 6 | import com.genersoft.iot.vmp.gb28181.bean.DeviceChannel; |
| 6 | import com.genersoft.iot.vmp.gb28181.event.DeviceOffLineDetector; | 7 | import com.genersoft.iot.vmp.gb28181.event.DeviceOffLineDetector; |
| @@ -13,7 +14,6 @@ import com.genersoft.iot.vmp.storager.IVideoManagerStorager; | @@ -13,7 +14,6 @@ import com.genersoft.iot.vmp.storager.IVideoManagerStorager; | ||
| 13 | import com.genersoft.iot.vmp.vmanager.bean.DeviceChannelTree; | 14 | import com.genersoft.iot.vmp.vmanager.bean.DeviceChannelTree; |
| 14 | import com.genersoft.iot.vmp.vmanager.bean.WVPResult; | 15 | import com.genersoft.iot.vmp.vmanager.bean.WVPResult; |
| 15 | import com.github.pagehelper.PageInfo; | 16 | import com.github.pagehelper.PageInfo; |
| 16 | -import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport; | ||
| 17 | import io.swagger.annotations.Api; | 17 | import io.swagger.annotations.Api; |
| 18 | import io.swagger.annotations.ApiImplicitParam; | 18 | import io.swagger.annotations.ApiImplicitParam; |
| 19 | import io.swagger.annotations.ApiImplicitParams; | 19 | import io.swagger.annotations.ApiImplicitParams; |
| @@ -57,6 +57,9 @@ public class DeviceQuery { | @@ -57,6 +57,9 @@ public class DeviceQuery { | ||
| 57 | @Autowired | 57 | @Autowired |
| 58 | private IDeviceService deviceService; | 58 | private IDeviceService deviceService; |
| 59 | 59 | ||
| 60 | + @Autowired | ||
| 61 | + private DynamicTask dynamicTask; | ||
| 62 | + | ||
| 60 | /** | 63 | /** |
| 61 | * 使用ID查询国标设备 | 64 | * 使用ID查询国标设备 |
| 62 | * @param deviceId 国标ID | 65 | * @param deviceId 国标ID |
| @@ -209,6 +212,8 @@ public class DeviceQuery { | @@ -209,6 +212,8 @@ public class DeviceQuery { | ||
| 209 | boolean isSuccess = storager.delete(deviceId); | 212 | boolean isSuccess = storager.delete(deviceId); |
| 210 | if (isSuccess) { | 213 | if (isSuccess) { |
| 211 | redisCatchStorage.clearCatchByDeviceId(deviceId); | 214 | redisCatchStorage.clearCatchByDeviceId(deviceId); |
| 215 | + // 停止此设备的订阅更新 | ||
| 216 | + dynamicTask.stop(deviceId); | ||
| 212 | JSONObject json = new JSONObject(); | 217 | JSONObject json = new JSONObject(); |
| 213 | json.put("deviceId", deviceId); | 218 | json.put("deviceId", deviceId); |
| 214 | return new ResponseEntity<>(json.toString(),HttpStatus.OK); | 219 | return new ResponseEntity<>(json.toString(),HttpStatus.OK); |
src/main/java/com/genersoft/iot/vmp/vmanager/gb28181/platform/PlatformController.java
| @@ -2,8 +2,9 @@ package com.genersoft.iot.vmp.vmanager.gb28181.platform; | @@ -2,8 +2,9 @@ package com.genersoft.iot.vmp.vmanager.gb28181.platform; | ||
| 2 | 2 | ||
| 3 | import com.alibaba.fastjson.JSON; | 3 | import com.alibaba.fastjson.JSON; |
| 4 | import com.alibaba.fastjson.JSONObject; | 4 | import com.alibaba.fastjson.JSONObject; |
| 5 | -import com.genersoft.iot.vmp.gb28181.bean.CatalogData; | ||
| 6 | -import com.genersoft.iot.vmp.gb28181.bean.DeviceChannel; | 5 | +import com.genersoft.iot.vmp.common.VideoManagerConstants; |
| 6 | +import com.genersoft.iot.vmp.conf.DynamicTask; | ||
| 7 | +import com.genersoft.iot.vmp.conf.UserSetup; | ||
| 7 | import com.genersoft.iot.vmp.gb28181.bean.ParentPlatform; | 8 | import com.genersoft.iot.vmp.gb28181.bean.ParentPlatform; |
| 8 | import com.genersoft.iot.vmp.gb28181.bean.PlatformCatalog; | 9 | import com.genersoft.iot.vmp.gb28181.bean.PlatformCatalog; |
| 9 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.ISIPCommanderForPlatform; | 10 | import com.genersoft.iot.vmp.gb28181.transmit.cmd.ISIPCommanderForPlatform; |
| @@ -40,6 +41,9 @@ public class PlatformController { | @@ -40,6 +41,9 @@ public class PlatformController { | ||
| 40 | private final static Logger logger = LoggerFactory.getLogger(PlatformController.class); | 41 | private final static Logger logger = LoggerFactory.getLogger(PlatformController.class); |
| 41 | 42 | ||
| 42 | @Autowired | 43 | @Autowired |
| 44 | + private UserSetup userSetup; | ||
| 45 | + | ||
| 46 | + @Autowired | ||
| 43 | private IVideoManagerStorager storager; | 47 | private IVideoManagerStorager storager; |
| 44 | 48 | ||
| 45 | @Autowired | 49 | @Autowired |
| @@ -48,11 +52,15 @@ public class PlatformController { | @@ -48,11 +52,15 @@ public class PlatformController { | ||
| 48 | @Autowired | 52 | @Autowired |
| 49 | private ISIPCommanderForPlatform commanderForPlatform; | 53 | private ISIPCommanderForPlatform commanderForPlatform; |
| 50 | 54 | ||
| 55 | + @Autowired | ||
| 56 | + private SipConfig sipConfig; | ||
| 57 | + | ||
| 51 | @Autowired | 58 | @Autowired |
| 52 | - private SipConfig sipConfig; | 59 | + private DynamicTask dynamicTask; |
| 53 | 60 | ||
| 54 | /** | 61 | /** |
| 55 | * 获取国标服务的配置 | 62 | * 获取国标服务的配置 |
| 63 | + * | ||
| 56 | * @return | 64 | * @return |
| 57 | */ | 65 | */ |
| 58 | @ApiOperation("获取国标服务的配置") | 66 | @ApiOperation("获取国标服务的配置") |
| @@ -65,8 +73,10 @@ public class PlatformController { | @@ -65,8 +73,10 @@ public class PlatformController { | ||
| 65 | result.put("password", sipConfig.getPassword()); | 73 | result.put("password", sipConfig.getPassword()); |
| 66 | return new ResponseEntity<>(result, HttpStatus.OK); | 74 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 67 | } | 75 | } |
| 76 | + | ||
| 68 | /** | 77 | /** |
| 69 | * 获取级联服务器信息 | 78 | * 获取级联服务器信息 |
| 79 | + * | ||
| 70 | * @return | 80 | * @return |
| 71 | */ | 81 | */ |
| 72 | @ApiOperation("获取国标服务的配置") | 82 | @ApiOperation("获取国标服务的配置") |
| @@ -78,7 +88,7 @@ public class PlatformController { | @@ -78,7 +88,7 @@ public class PlatformController { | ||
| 78 | wvpResult.setCode(0); | 88 | wvpResult.setCode(0); |
| 79 | wvpResult.setMsg("success"); | 89 | wvpResult.setMsg("success"); |
| 80 | wvpResult.setData(parentPlatform); | 90 | wvpResult.setData(parentPlatform); |
| 81 | - }else { | 91 | + } else { |
| 82 | wvpResult.setCode(-1); | 92 | wvpResult.setCode(-1); |
| 83 | wvpResult.setMsg("未查询到此平台"); | 93 | wvpResult.setMsg("未查询到此平台"); |
| 84 | } | 94 | } |
| @@ -87,7 +97,8 @@ public class PlatformController { | @@ -87,7 +97,8 @@ public class PlatformController { | ||
| 87 | 97 | ||
| 88 | /** | 98 | /** |
| 89 | * 分页查询级联平台 | 99 | * 分页查询级联平台 |
| 90 | - * @param page 当前页 | 100 | + * |
| 101 | + * @param page 当前页 | ||
| 91 | * @param count 每页条数 | 102 | * @param count 每页条数 |
| 92 | * @return | 103 | * @return |
| 93 | */ | 104 | */ |
| @@ -97,7 +108,7 @@ public class PlatformController { | @@ -97,7 +108,7 @@ public class PlatformController { | ||
| 97 | @ApiImplicitParam(name = "page", value = "当前页", dataTypeClass = Integer.class), | 108 | @ApiImplicitParam(name = "page", value = "当前页", dataTypeClass = Integer.class), |
| 98 | @ApiImplicitParam(name = "count", value = "每页条数", dataTypeClass = Integer.class), | 109 | @ApiImplicitParam(name = "count", value = "每页条数", dataTypeClass = Integer.class), |
| 99 | }) | 110 | }) |
| 100 | - public PageInfo<ParentPlatform> platforms(@PathVariable int page, @PathVariable int count){ | 111 | + public PageInfo<ParentPlatform> platforms(@PathVariable int page, @PathVariable int count) { |
| 101 | 112 | ||
| 102 | // if (logger.isDebugEnabled()) { | 113 | // if (logger.isDebugEnabled()) { |
| 103 | // logger.debug("查询所有上级设备API调用"); | 114 | // logger.debug("查询所有上级设备API调用"); |
| @@ -107,6 +118,7 @@ public class PlatformController { | @@ -107,6 +118,7 @@ public class PlatformController { | ||
| 107 | 118 | ||
| 108 | /** | 119 | /** |
| 109 | * 添加上级平台信息 | 120 | * 添加上级平台信息 |
| 121 | + * | ||
| 110 | * @param parentPlatform | 122 | * @param parentPlatform |
| 111 | * @return | 123 | * @return |
| 112 | */ | 124 | */ |
| @@ -116,28 +128,28 @@ public class PlatformController { | @@ -116,28 +128,28 @@ public class PlatformController { | ||
| 116 | }) | 128 | }) |
| 117 | @PostMapping("/add") | 129 | @PostMapping("/add") |
| 118 | @ResponseBody | 130 | @ResponseBody |
| 119 | - public ResponseEntity<WVPResult<String>> addPlatform(@RequestBody ParentPlatform parentPlatform){ | 131 | + public ResponseEntity<WVPResult<String>> addPlatform(@RequestBody ParentPlatform parentPlatform) { |
| 120 | 132 | ||
| 121 | if (logger.isDebugEnabled()) { | 133 | if (logger.isDebugEnabled()) { |
| 122 | logger.debug("保存上级平台信息API调用"); | 134 | logger.debug("保存上级平台信息API调用"); |
| 123 | } | 135 | } |
| 124 | WVPResult<String> wvpResult = new WVPResult<>(); | 136 | WVPResult<String> wvpResult = new WVPResult<>(); |
| 125 | if (StringUtils.isEmpty(parentPlatform.getName()) | 137 | if (StringUtils.isEmpty(parentPlatform.getName()) |
| 126 | - ||StringUtils.isEmpty(parentPlatform.getServerGBId()) | ||
| 127 | - ||StringUtils.isEmpty(parentPlatform.getServerGBDomain()) | ||
| 128 | - ||StringUtils.isEmpty(parentPlatform.getServerIP()) | ||
| 129 | - ||StringUtils.isEmpty(parentPlatform.getServerPort()) | ||
| 130 | - ||StringUtils.isEmpty(parentPlatform.getDeviceGBId()) | ||
| 131 | - ||StringUtils.isEmpty(parentPlatform.getExpires()) | ||
| 132 | - ||StringUtils.isEmpty(parentPlatform.getKeepTimeout()) | ||
| 133 | - ||StringUtils.isEmpty(parentPlatform.getTransport()) | ||
| 134 | - ||StringUtils.isEmpty(parentPlatform.getCharacterSet()) | ||
| 135 | - ){ | 138 | + || StringUtils.isEmpty(parentPlatform.getServerGBId()) |
| 139 | + || StringUtils.isEmpty(parentPlatform.getServerGBDomain()) | ||
| 140 | + || StringUtils.isEmpty(parentPlatform.getServerIP()) | ||
| 141 | + || StringUtils.isEmpty(parentPlatform.getServerPort()) | ||
| 142 | + || StringUtils.isEmpty(parentPlatform.getDeviceGBId()) | ||
| 143 | + || StringUtils.isEmpty(parentPlatform.getExpires()) | ||
| 144 | + || StringUtils.isEmpty(parentPlatform.getKeepTimeout()) | ||
| 145 | + || StringUtils.isEmpty(parentPlatform.getTransport()) | ||
| 146 | + || StringUtils.isEmpty(parentPlatform.getCharacterSet()) | ||
| 147 | + ) { | ||
| 136 | wvpResult.setCode(-1); | 148 | wvpResult.setCode(-1); |
| 137 | wvpResult.setMsg("missing parameters"); | 149 | wvpResult.setMsg("missing parameters"); |
| 138 | return new ResponseEntity<>(wvpResult, HttpStatus.BAD_REQUEST); | 150 | return new ResponseEntity<>(wvpResult, HttpStatus.BAD_REQUEST); |
| 139 | } | 151 | } |
| 140 | - if (parentPlatform.getServerPort()< 0 || parentPlatform.getServerPort() > 65535){ | 152 | + if (parentPlatform.getServerPort() < 0 || parentPlatform.getServerPort() > 65535) { |
| 141 | wvpResult.setCode(-1); | 153 | wvpResult.setCode(-1); |
| 142 | wvpResult.setMsg("error severPort"); | 154 | wvpResult.setMsg("error severPort"); |
| 143 | return new ResponseEntity<>(wvpResult, HttpStatus.BAD_REQUEST); | 155 | return new ResponseEntity<>(wvpResult, HttpStatus.BAD_REQUEST); |
| @@ -146,7 +158,7 @@ public class PlatformController { | @@ -146,7 +158,7 @@ public class PlatformController { | ||
| 146 | ParentPlatform parentPlatformOld = storager.queryParentPlatByServerGBId(parentPlatform.getServerGBId()); | 158 | ParentPlatform parentPlatformOld = storager.queryParentPlatByServerGBId(parentPlatform.getServerGBId()); |
| 147 | if (parentPlatformOld != null) { | 159 | if (parentPlatformOld != null) { |
| 148 | wvpResult.setCode(-1); | 160 | wvpResult.setCode(-1); |
| 149 | - wvpResult.setMsg("平台 "+parentPlatform.getServerGBId()+" 已存在"); | 161 | + wvpResult.setMsg("平台 " + parentPlatform.getServerGBId() + " 已存在"); |
| 150 | return new ResponseEntity<>(wvpResult, HttpStatus.OK); | 162 | return new ResponseEntity<>(wvpResult, HttpStatus.OK); |
| 151 | } | 163 | } |
| 152 | boolean updateResult = storager.updateParentPlatform(parentPlatform); | 164 | boolean updateResult = storager.updateParentPlatform(parentPlatform); |
| @@ -154,17 +166,17 @@ public class PlatformController { | @@ -154,17 +166,17 @@ public class PlatformController { | ||
| 154 | if (updateResult) { | 166 | if (updateResult) { |
| 155 | // 保存时启用就发送注册 | 167 | // 保存时启用就发送注册 |
| 156 | if (parentPlatform.isEnable()) { | 168 | if (parentPlatform.isEnable()) { |
| 157 | - if (parentPlatformOld.isStatus()) { | 169 | + if (parentPlatformOld != null && parentPlatformOld.isStatus()) { |
| 158 | commanderForPlatform.unregister(parentPlatformOld, null, eventResult -> { | 170 | commanderForPlatform.unregister(parentPlatformOld, null, eventResult -> { |
| 159 | // 只要保存就发送注册 | 171 | // 只要保存就发送注册 |
| 160 | commanderForPlatform.register(parentPlatform, null, null); | 172 | commanderForPlatform.register(parentPlatform, null, null); |
| 161 | }); | 173 | }); |
| 162 | - }else { | 174 | + } else { |
| 163 | // 只要保存就发送注册 | 175 | // 只要保存就发送注册 |
| 164 | commanderForPlatform.register(parentPlatform, null, null); | 176 | commanderForPlatform.register(parentPlatform, null, null); |
| 165 | } | 177 | } |
| 166 | 178 | ||
| 167 | - } else if (parentPlatformOld != null && parentPlatformOld.isEnable() && !parentPlatform.isEnable()){ // 关闭启用时注销 | 179 | + } else if (parentPlatformOld != null && parentPlatformOld.isEnable() && !parentPlatform.isEnable()) { // 关闭启用时注销 |
| 168 | commanderForPlatform.unregister(parentPlatform, null, null); | 180 | commanderForPlatform.unregister(parentPlatform, null, null); |
| 169 | } | 181 | } |
| 170 | wvpResult.setCode(0); | 182 | wvpResult.setCode(0); |
| @@ -179,6 +191,7 @@ public class PlatformController { | @@ -179,6 +191,7 @@ public class PlatformController { | ||
| 179 | 191 | ||
| 180 | /** | 192 | /** |
| 181 | * 保存上级平台信息 | 193 | * 保存上级平台信息 |
| 194 | + * | ||
| 182 | * @param parentPlatform | 195 | * @param parentPlatform |
| 183 | * @return | 196 | * @return |
| 184 | */ | 197 | */ |
| @@ -188,23 +201,23 @@ public class PlatformController { | @@ -188,23 +201,23 @@ public class PlatformController { | ||
| 188 | }) | 201 | }) |
| 189 | @PostMapping("/save") | 202 | @PostMapping("/save") |
| 190 | @ResponseBody | 203 | @ResponseBody |
| 191 | - public ResponseEntity<WVPResult<String>> savePlatform(@RequestBody ParentPlatform parentPlatform){ | 204 | + public ResponseEntity<WVPResult<String>> savePlatform(@RequestBody ParentPlatform parentPlatform) { |
| 192 | 205 | ||
| 193 | if (logger.isDebugEnabled()) { | 206 | if (logger.isDebugEnabled()) { |
| 194 | logger.debug("保存上级平台信息API调用"); | 207 | logger.debug("保存上级平台信息API调用"); |
| 195 | } | 208 | } |
| 196 | WVPResult<String> wvpResult = new WVPResult<>(); | 209 | WVPResult<String> wvpResult = new WVPResult<>(); |
| 197 | if (StringUtils.isEmpty(parentPlatform.getName()) | 210 | if (StringUtils.isEmpty(parentPlatform.getName()) |
| 198 | - ||StringUtils.isEmpty(parentPlatform.getServerGBId()) | ||
| 199 | - ||StringUtils.isEmpty(parentPlatform.getServerGBDomain()) | ||
| 200 | - ||StringUtils.isEmpty(parentPlatform.getServerIP()) | ||
| 201 | - ||StringUtils.isEmpty(parentPlatform.getServerPort()) | ||
| 202 | - ||StringUtils.isEmpty(parentPlatform.getDeviceGBId()) | ||
| 203 | - ||StringUtils.isEmpty(parentPlatform.getExpires()) | ||
| 204 | - ||StringUtils.isEmpty(parentPlatform.getKeepTimeout()) | ||
| 205 | - ||StringUtils.isEmpty(parentPlatform.getTransport()) | ||
| 206 | - ||StringUtils.isEmpty(parentPlatform.getCharacterSet()) | ||
| 207 | - ){ | 211 | + || StringUtils.isEmpty(parentPlatform.getServerGBId()) |
| 212 | + || StringUtils.isEmpty(parentPlatform.getServerGBDomain()) | ||
| 213 | + || StringUtils.isEmpty(parentPlatform.getServerIP()) | ||
| 214 | + || StringUtils.isEmpty(parentPlatform.getServerPort()) | ||
| 215 | + || StringUtils.isEmpty(parentPlatform.getDeviceGBId()) | ||
| 216 | + || StringUtils.isEmpty(parentPlatform.getExpires()) | ||
| 217 | + || StringUtils.isEmpty(parentPlatform.getKeepTimeout()) | ||
| 218 | + || StringUtils.isEmpty(parentPlatform.getTransport()) | ||
| 219 | + || StringUtils.isEmpty(parentPlatform.getCharacterSet()) | ||
| 220 | + ) { | ||
| 208 | wvpResult.setCode(-1); | 221 | wvpResult.setCode(-1); |
| 209 | wvpResult.setMsg("missing parameters"); | 222 | wvpResult.setMsg("missing parameters"); |
| 210 | return new ResponseEntity<>(wvpResult, HttpStatus.BAD_REQUEST); | 223 | return new ResponseEntity<>(wvpResult, HttpStatus.BAD_REQUEST); |
| @@ -216,7 +229,7 @@ public class PlatformController { | @@ -216,7 +229,7 @@ public class PlatformController { | ||
| 216 | if (updateResult) { | 229 | if (updateResult) { |
| 217 | // 保存时启用就发送注册 | 230 | // 保存时启用就发送注册 |
| 218 | if (parentPlatform.isEnable()) { | 231 | if (parentPlatform.isEnable()) { |
| 219 | - if (parentPlatformOld.isStatus()) { | 232 | + if (parentPlatformOld != null && parentPlatformOld.isStatus()) { |
| 220 | commanderForPlatform.unregister(parentPlatformOld, null, null); | 233 | commanderForPlatform.unregister(parentPlatformOld, null, null); |
| 221 | try { | 234 | try { |
| 222 | Thread.sleep(500); | 235 | Thread.sleep(500); |
| @@ -225,11 +238,11 @@ public class PlatformController { | @@ -225,11 +238,11 @@ public class PlatformController { | ||
| 225 | } | 238 | } |
| 226 | // 只要保存就发送注册 | 239 | // 只要保存就发送注册 |
| 227 | commanderForPlatform.register(parentPlatform, null, null); | 240 | commanderForPlatform.register(parentPlatform, null, null); |
| 228 | - }else { | 241 | + } else { |
| 229 | // 只要保存就发送注册 | 242 | // 只要保存就发送注册 |
| 230 | commanderForPlatform.register(parentPlatform, null, null); | 243 | commanderForPlatform.register(parentPlatform, null, null); |
| 231 | } | 244 | } |
| 232 | - } else if (parentPlatformOld != null && parentPlatformOld.isEnable() && !parentPlatform.isEnable()){ // 关闭启用时注销 | 245 | + } else if (parentPlatformOld != null && parentPlatformOld.isEnable() && !parentPlatform.isEnable()) { // 关闭启用时注销 |
| 233 | commanderForPlatform.unregister(parentPlatformOld, null, null); | 246 | commanderForPlatform.unregister(parentPlatformOld, null, null); |
| 234 | } | 247 | } |
| 235 | wvpResult.setCode(0); | 248 | wvpResult.setCode(0); |
| @@ -244,7 +257,8 @@ public class PlatformController { | @@ -244,7 +257,8 @@ public class PlatformController { | ||
| 244 | 257 | ||
| 245 | /** | 258 | /** |
| 246 | * 删除上级平台 | 259 | * 删除上级平台 |
| 247 | - * @param serverGBId 上级平台国标ID | 260 | + * |
| 261 | + * @param serverGBId 上级平台国标ID | ||
| 248 | * @return | 262 | * @return |
| 249 | */ | 263 | */ |
| 250 | @ApiOperation("删除上级平台") | 264 | @ApiOperation("删除上级平台") |
| @@ -253,13 +267,13 @@ public class PlatformController { | @@ -253,13 +267,13 @@ public class PlatformController { | ||
| 253 | }) | 267 | }) |
| 254 | @DeleteMapping("/delete/{serverGBId}") | 268 | @DeleteMapping("/delete/{serverGBId}") |
| 255 | @ResponseBody | 269 | @ResponseBody |
| 256 | - public ResponseEntity<String> deletePlatform(@PathVariable String serverGBId){ | 270 | + public ResponseEntity<String> deletePlatform(@PathVariable String serverGBId) { |
| 257 | 271 | ||
| 258 | if (logger.isDebugEnabled()) { | 272 | if (logger.isDebugEnabled()) { |
| 259 | logger.debug("删除上级平台API调用"); | 273 | logger.debug("删除上级平台API调用"); |
| 260 | } | 274 | } |
| 261 | if (StringUtils.isEmpty(serverGBId) | 275 | if (StringUtils.isEmpty(serverGBId) |
| 262 | - ){ | 276 | + ) { |
| 263 | return new ResponseEntity<>("missing parameters", HttpStatus.BAD_REQUEST); | 277 | return new ResponseEntity<>("missing parameters", HttpStatus.BAD_REQUEST); |
| 264 | } | 278 | } |
| 265 | ParentPlatform parentPlatform = storager.queryParentPlatByServerGBId(serverGBId); | 279 | ParentPlatform parentPlatform = storager.queryParentPlatByServerGBId(serverGBId); |
| @@ -280,17 +294,19 @@ public class PlatformController { | @@ -280,17 +294,19 @@ public class PlatformController { | ||
| 280 | boolean deleteResult = storager.deleteParentPlatform(parentPlatform); | 294 | boolean deleteResult = storager.deleteParentPlatform(parentPlatform); |
| 281 | storager.delCatalogByPlatformId(parentPlatform.getServerGBId()); | 295 | storager.delCatalogByPlatformId(parentPlatform.getServerGBId()); |
| 282 | storager.delRelationByPlatformId(parentPlatform.getServerGBId()); | 296 | storager.delRelationByPlatformId(parentPlatform.getServerGBId()); |
| 283 | - | ||
| 284 | - | 297 | + // 停止发送位置订阅定时任务 |
| 298 | + String key = VideoManagerConstants.SIP_SUBSCRIBE_PREFIX + userSetup.getServerId() + "_MobilePosition_" + parentPlatform.getServerGBId(); | ||
| 299 | + dynamicTask.stop(key); | ||
| 285 | if (deleteResult) { | 300 | if (deleteResult) { |
| 286 | return new ResponseEntity<>("success", HttpStatus.OK); | 301 | return new ResponseEntity<>("success", HttpStatus.OK); |
| 287 | - }else { | 302 | + } else { |
| 288 | return new ResponseEntity<>("fail", HttpStatus.OK); | 303 | return new ResponseEntity<>("fail", HttpStatus.OK); |
| 289 | } | 304 | } |
| 290 | } | 305 | } |
| 291 | 306 | ||
| 292 | /** | 307 | /** |
| 293 | * 查询上级平台是否存在 | 308 | * 查询上级平台是否存在 |
| 309 | + * | ||
| 294 | * @param serverGBId 上级平台国标ID | 310 | * @param serverGBId 上级平台国标ID |
| 295 | * @return | 311 | * @return |
| 296 | */ | 312 | */ |
| @@ -300,7 +316,7 @@ public class PlatformController { | @@ -300,7 +316,7 @@ public class PlatformController { | ||
| 300 | }) | 316 | }) |
| 301 | @GetMapping("/exit/{serverGBId}") | 317 | @GetMapping("/exit/{serverGBId}") |
| 302 | @ResponseBody | 318 | @ResponseBody |
| 303 | - public ResponseEntity<String> exitPlatform(@PathVariable String serverGBId){ | 319 | + public ResponseEntity<String> exitPlatform(@PathVariable String serverGBId) { |
| 304 | 320 | ||
| 305 | // if (logger.isDebugEnabled()) { | 321 | // if (logger.isDebugEnabled()) { |
| 306 | // logger.debug("查询上级平台是否存在API调用:" + serverGBId); | 322 | // logger.debug("查询上级平台是否存在API调用:" + serverGBId); |
| @@ -311,12 +327,13 @@ public class PlatformController { | @@ -311,12 +327,13 @@ public class PlatformController { | ||
| 311 | 327 | ||
| 312 | /** | 328 | /** |
| 313 | * 分页查询级联平台的所有所有通道 | 329 | * 分页查询级联平台的所有所有通道 |
| 314 | - * @param page 当前页 | ||
| 315 | - * @param count 每页条数 | ||
| 316 | - * @param platformId 上级平台ID | ||
| 317 | - * @param query 查询内容 | ||
| 318 | - * @param online 是否在线 | ||
| 319 | - * @param choosed 是否已选中 | 330 | + * |
| 331 | + * @param page 当前页 | ||
| 332 | + * @param count 每页条数 | ||
| 333 | + * @param platformId 上级平台ID | ||
| 334 | + * @param query 查询内容 | ||
| 335 | + * @param online 是否在线 | ||
| 336 | + * @param choosed 是否已选中 | ||
| 320 | * @param channelType 通道类型 | 337 | * @param channelType 通道类型 |
| 321 | * @return | 338 | * @return |
| 322 | */ | 339 | */ |
| @@ -333,22 +350,22 @@ public class PlatformController { | @@ -333,22 +350,22 @@ public class PlatformController { | ||
| 333 | @GetMapping("/channel_list") | 350 | @GetMapping("/channel_list") |
| 334 | @ResponseBody | 351 | @ResponseBody |
| 335 | public PageInfo<ChannelReduce> channelList(int page, int count, | 352 | public PageInfo<ChannelReduce> channelList(int page, int count, |
| 336 | - @RequestParam(required = false) String platformId, | ||
| 337 | - @RequestParam(required = false) String catalogId, | ||
| 338 | - @RequestParam(required = false) String query, | ||
| 339 | - @RequestParam(required = false) Boolean online, | ||
| 340 | - @RequestParam(required = false) Boolean channelType){ | 353 | + @RequestParam(required = false) String platformId, |
| 354 | + @RequestParam(required = false) String catalogId, | ||
| 355 | + @RequestParam(required = false) String query, | ||
| 356 | + @RequestParam(required = false) Boolean online, | ||
| 357 | + @RequestParam(required = false) Boolean channelType) { | ||
| 341 | 358 | ||
| 342 | // if (logger.isDebugEnabled()) { | 359 | // if (logger.isDebugEnabled()) { |
| 343 | // logger.debug("查询所有所有通道API调用"); | 360 | // logger.debug("查询所有所有通道API调用"); |
| 344 | // } | 361 | // } |
| 345 | - if(StringUtils.isEmpty(platformId)) { | 362 | + if (StringUtils.isEmpty(platformId)) { |
| 346 | platformId = null; | 363 | platformId = null; |
| 347 | } | 364 | } |
| 348 | - if(StringUtils.isEmpty(query)) { | 365 | + if (StringUtils.isEmpty(query)) { |
| 349 | query = null; | 366 | query = null; |
| 350 | } | 367 | } |
| 351 | - if(StringUtils.isEmpty(platformId) || StringUtils.isEmpty(catalogId)) { | 368 | + if (StringUtils.isEmpty(platformId) || StringUtils.isEmpty(catalogId)) { |
| 352 | catalogId = null; | 369 | catalogId = null; |
| 353 | } | 370 | } |
| 354 | PageInfo<ChannelReduce> channelReduces = storager.queryAllChannelList(page, count, query, online, channelType, platformId, catalogId); | 371 | PageInfo<ChannelReduce> channelReduces = storager.queryAllChannelList(page, count, query, online, channelType, platformId, catalogId); |
| @@ -358,6 +375,7 @@ public class PlatformController { | @@ -358,6 +375,7 @@ public class PlatformController { | ||
| 358 | 375 | ||
| 359 | /** | 376 | /** |
| 360 | * 向上级平台添加国标通道 | 377 | * 向上级平台添加国标通道 |
| 378 | + * | ||
| 361 | * @param param 通道关联参数 | 379 | * @param param 通道关联参数 |
| 362 | * @return | 380 | * @return |
| 363 | */ | 381 | */ |
| @@ -367,7 +385,7 @@ public class PlatformController { | @@ -367,7 +385,7 @@ public class PlatformController { | ||
| 367 | }) | 385 | }) |
| 368 | @PostMapping("/update_channel_for_gb") | 386 | @PostMapping("/update_channel_for_gb") |
| 369 | @ResponseBody | 387 | @ResponseBody |
| 370 | - public ResponseEntity<String> updateChannelForGB(@RequestBody UpdateChannelParam param){ | 388 | + public ResponseEntity<String> updateChannelForGB(@RequestBody UpdateChannelParam param) { |
| 371 | 389 | ||
| 372 | if (logger.isDebugEnabled()) { | 390 | if (logger.isDebugEnabled()) { |
| 373 | logger.debug("给上级平台添加国标通道API调用"); | 391 | logger.debug("给上级平台添加国标通道API调用"); |
| @@ -379,6 +397,7 @@ public class PlatformController { | @@ -379,6 +397,7 @@ public class PlatformController { | ||
| 379 | 397 | ||
| 380 | /** | 398 | /** |
| 381 | * 从上级平台移除国标通道 | 399 | * 从上级平台移除国标通道 |
| 400 | + * | ||
| 382 | * @param param 通道关联参数 | 401 | * @param param 通道关联参数 |
| 383 | * @return | 402 | * @return |
| 384 | */ | 403 | */ |
| @@ -388,7 +407,7 @@ public class PlatformController { | @@ -388,7 +407,7 @@ public class PlatformController { | ||
| 388 | }) | 407 | }) |
| 389 | @DeleteMapping("/del_channel_for_gb") | 408 | @DeleteMapping("/del_channel_for_gb") |
| 390 | @ResponseBody | 409 | @ResponseBody |
| 391 | - public ResponseEntity<String> delChannelForGB(@RequestBody UpdateChannelParam param){ | 410 | + public ResponseEntity<String> delChannelForGB(@RequestBody UpdateChannelParam param) { |
| 392 | 411 | ||
| 393 | if (logger.isDebugEnabled()) { | 412 | if (logger.isDebugEnabled()) { |
| 394 | logger.debug("给上级平台删除国标通道API调用"); | 413 | logger.debug("给上级平台删除国标通道API调用"); |
| @@ -400,8 +419,9 @@ public class PlatformController { | @@ -400,8 +419,9 @@ public class PlatformController { | ||
| 400 | 419 | ||
| 401 | /** | 420 | /** |
| 402 | * 获取目录 | 421 | * 获取目录 |
| 422 | + * | ||
| 403 | * @param platformId 平台ID | 423 | * @param platformId 平台ID |
| 404 | - * @param parentId 目录父ID | 424 | + * @param parentId 目录父ID |
| 405 | * @return | 425 | * @return |
| 406 | */ | 426 | */ |
| 407 | @ApiOperation("获取目录") | 427 | @ApiOperation("获取目录") |
| @@ -411,7 +431,7 @@ public class PlatformController { | @@ -411,7 +431,7 @@ public class PlatformController { | ||
| 411 | }) | 431 | }) |
| 412 | @GetMapping("/catalog") | 432 | @GetMapping("/catalog") |
| 413 | @ResponseBody | 433 | @ResponseBody |
| 414 | - public ResponseEntity<WVPResult<List<PlatformCatalog>>> getCatalogByPlatform(String platformId, String parentId){ | 434 | + public ResponseEntity<WVPResult<List<PlatformCatalog>>> getCatalogByPlatform(String platformId, String parentId) { |
| 415 | 435 | ||
| 416 | if (logger.isDebugEnabled()) { | 436 | if (logger.isDebugEnabled()) { |
| 417 | logger.debug("查询目录,platformId: {}, parentId: {}", platformId, parentId); | 437 | logger.debug("查询目录,platformId: {}, parentId: {}", platformId, parentId); |
| @@ -432,6 +452,7 @@ public class PlatformController { | @@ -432,6 +452,7 @@ public class PlatformController { | ||
| 432 | 452 | ||
| 433 | /** | 453 | /** |
| 434 | * 添加目录 | 454 | * 添加目录 |
| 455 | + * | ||
| 435 | * @param platformCatalog 目录 | 456 | * @param platformCatalog 目录 |
| 436 | * @return | 457 | * @return |
| 437 | */ | 458 | */ |
| @@ -441,7 +462,7 @@ public class PlatformController { | @@ -441,7 +462,7 @@ public class PlatformController { | ||
| 441 | }) | 462 | }) |
| 442 | @PostMapping("/catalog/add") | 463 | @PostMapping("/catalog/add") |
| 443 | @ResponseBody | 464 | @ResponseBody |
| 444 | - public ResponseEntity<WVPResult<List<PlatformCatalog>>> addCatalog(@RequestBody PlatformCatalog platformCatalog){ | 465 | + public ResponseEntity<WVPResult<List<PlatformCatalog>>> addCatalog(@RequestBody PlatformCatalog platformCatalog) { |
| 445 | 466 | ||
| 446 | if (logger.isDebugEnabled()) { | 467 | if (logger.isDebugEnabled()) { |
| 447 | logger.debug("添加目录,{}", JSON.toJSONString(platformCatalog)); | 468 | logger.debug("添加目录,{}", JSON.toJSONString(platformCatalog)); |
| @@ -452,7 +473,7 @@ public class PlatformController { | @@ -452,7 +473,7 @@ public class PlatformController { | ||
| 452 | 473 | ||
| 453 | if (platformCatalogInStore != null) { | 474 | if (platformCatalogInStore != null) { |
| 454 | result.setCode(-1); | 475 | result.setCode(-1); |
| 455 | - result.setMsg( platformCatalog.getId() + " already exists"); | 476 | + result.setMsg(platformCatalog.getId() + " already exists"); |
| 456 | return new ResponseEntity<>(result, HttpStatus.OK); | 477 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 457 | } | 478 | } |
| 458 | int addResult = storager.addCatalog(platformCatalog); | 479 | int addResult = storager.addCatalog(platformCatalog); |
| @@ -460,7 +481,7 @@ public class PlatformController { | @@ -460,7 +481,7 @@ public class PlatformController { | ||
| 460 | result.setCode(0); | 481 | result.setCode(0); |
| 461 | result.setMsg("success"); | 482 | result.setMsg("success"); |
| 462 | return new ResponseEntity<>(result, HttpStatus.OK); | 483 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 463 | - }else { | 484 | + } else { |
| 464 | result.setCode(-500); | 485 | result.setCode(-500); |
| 465 | result.setMsg("save error"); | 486 | result.setMsg("save error"); |
| 466 | return new ResponseEntity<>(result, HttpStatus.OK); | 487 | return new ResponseEntity<>(result, HttpStatus.OK); |
| @@ -469,6 +490,7 @@ public class PlatformController { | @@ -469,6 +490,7 @@ public class PlatformController { | ||
| 469 | 490 | ||
| 470 | /** | 491 | /** |
| 471 | * 编辑目录 | 492 | * 编辑目录 |
| 493 | + * | ||
| 472 | * @param platformCatalog 目录 | 494 | * @param platformCatalog 目录 |
| 473 | * @return | 495 | * @return |
| 474 | */ | 496 | */ |
| @@ -478,7 +500,7 @@ public class PlatformController { | @@ -478,7 +500,7 @@ public class PlatformController { | ||
| 478 | }) | 500 | }) |
| 479 | @PostMapping("/catalog/edit") | 501 | @PostMapping("/catalog/edit") |
| 480 | @ResponseBody | 502 | @ResponseBody |
| 481 | - public ResponseEntity<WVPResult<List<PlatformCatalog>>> editCatalog(@RequestBody PlatformCatalog platformCatalog){ | 503 | + public ResponseEntity<WVPResult<List<PlatformCatalog>>> editCatalog(@RequestBody PlatformCatalog platformCatalog) { |
| 482 | 504 | ||
| 483 | if (logger.isDebugEnabled()) { | 505 | if (logger.isDebugEnabled()) { |
| 484 | logger.debug("编辑目录,{}", JSON.toJSONString(platformCatalog)); | 506 | logger.debug("编辑目录,{}", JSON.toJSONString(platformCatalog)); |
| @@ -488,14 +510,14 @@ public class PlatformController { | @@ -488,14 +510,14 @@ public class PlatformController { | ||
| 488 | result.setCode(0); | 510 | result.setCode(0); |
| 489 | 511 | ||
| 490 | if (platformCatalogInStore == null) { | 512 | if (platformCatalogInStore == null) { |
| 491 | - result.setMsg( platformCatalog.getId() + " not exists"); | 513 | + result.setMsg(platformCatalog.getId() + " not exists"); |
| 492 | return new ResponseEntity<>(result, HttpStatus.OK); | 514 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 493 | } | 515 | } |
| 494 | int addResult = storager.updateCatalog(platformCatalog); | 516 | int addResult = storager.updateCatalog(platformCatalog); |
| 495 | if (addResult > 0) { | 517 | if (addResult > 0) { |
| 496 | result.setMsg("success"); | 518 | result.setMsg("success"); |
| 497 | return new ResponseEntity<>(result, HttpStatus.OK); | 519 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 498 | - }else { | 520 | + } else { |
| 499 | result.setMsg("save error"); | 521 | result.setMsg("save error"); |
| 500 | return new ResponseEntity<>(result, HttpStatus.OK); | 522 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 501 | } | 523 | } |
| @@ -503,6 +525,7 @@ public class PlatformController { | @@ -503,6 +525,7 @@ public class PlatformController { | ||
| 503 | 525 | ||
| 504 | /** | 526 | /** |
| 505 | * 删除目录 | 527 | * 删除目录 |
| 528 | + * | ||
| 506 | * @param id 目录Id | 529 | * @param id 目录Id |
| 507 | * @return | 530 | * @return |
| 508 | */ | 531 | */ |
| @@ -512,7 +535,7 @@ public class PlatformController { | @@ -512,7 +535,7 @@ public class PlatformController { | ||
| 512 | }) | 535 | }) |
| 513 | @DeleteMapping("/catalog/del") | 536 | @DeleteMapping("/catalog/del") |
| 514 | @ResponseBody | 537 | @ResponseBody |
| 515 | - public ResponseEntity<WVPResult<String>> delCatalog(String id, String platformId){ | 538 | + public ResponseEntity<WVPResult<String>> delCatalog(String id, String platformId) { |
| 516 | 539 | ||
| 517 | if (logger.isDebugEnabled()) { | 540 | if (logger.isDebugEnabled()) { |
| 518 | logger.debug("删除目录,{}", id); | 541 | logger.debug("删除目录,{}", id); |
| @@ -540,7 +563,7 @@ public class PlatformController { | @@ -540,7 +563,7 @@ public class PlatformController { | ||
| 540 | if (delResult > 0) { | 563 | if (delResult > 0) { |
| 541 | result.setMsg("success"); | 564 | result.setMsg("success"); |
| 542 | return new ResponseEntity<>(result, HttpStatus.OK); | 565 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 543 | - }else { | 566 | + } else { |
| 544 | result.setMsg("save error"); | 567 | result.setMsg("save error"); |
| 545 | return new ResponseEntity<>(result, HttpStatus.OK); | 568 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 546 | } | 569 | } |
| @@ -548,6 +571,7 @@ public class PlatformController { | @@ -548,6 +571,7 @@ public class PlatformController { | ||
| 548 | 571 | ||
| 549 | /** | 572 | /** |
| 550 | * 删除关联 | 573 | * 删除关联 |
| 574 | + * | ||
| 551 | * @param platformCatalog 关联的信息 | 575 | * @param platformCatalog 关联的信息 |
| 552 | * @return | 576 | * @return |
| 553 | */ | 577 | */ |
| @@ -557,7 +581,7 @@ public class PlatformController { | @@ -557,7 +581,7 @@ public class PlatformController { | ||
| 557 | }) | 581 | }) |
| 558 | @DeleteMapping("/catalog/relation/del") | 582 | @DeleteMapping("/catalog/relation/del") |
| 559 | @ResponseBody | 583 | @ResponseBody |
| 560 | - public ResponseEntity<WVPResult<List<PlatformCatalog>>> delRelation(@RequestBody PlatformCatalog platformCatalog){ | 584 | + public ResponseEntity<WVPResult<List<PlatformCatalog>>> delRelation(@RequestBody PlatformCatalog platformCatalog) { |
| 561 | 585 | ||
| 562 | if (logger.isDebugEnabled()) { | 586 | if (logger.isDebugEnabled()) { |
| 563 | logger.debug("删除关联,{}", JSON.toJSONString(platformCatalog)); | 587 | logger.debug("删除关联,{}", JSON.toJSONString(platformCatalog)); |
| @@ -569,7 +593,7 @@ public class PlatformController { | @@ -569,7 +593,7 @@ public class PlatformController { | ||
| 569 | if (delResult > 0) { | 593 | if (delResult > 0) { |
| 570 | result.setMsg("success"); | 594 | result.setMsg("success"); |
| 571 | return new ResponseEntity<>(result, HttpStatus.OK); | 595 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 572 | - }else { | 596 | + } else { |
| 573 | result.setMsg("save error"); | 597 | result.setMsg("save error"); |
| 574 | return new ResponseEntity<>(result, HttpStatus.OK); | 598 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 575 | } | 599 | } |
| @@ -578,8 +602,9 @@ public class PlatformController { | @@ -578,8 +602,9 @@ public class PlatformController { | ||
| 578 | 602 | ||
| 579 | /** | 603 | /** |
| 580 | * 修改默认目录 | 604 | * 修改默认目录 |
| 605 | + * | ||
| 581 | * @param platformId 平台Id | 606 | * @param platformId 平台Id |
| 582 | - * @param catalogId 目录Id | 607 | + * @param catalogId 目录Id |
| 583 | * @return | 608 | * @return |
| 584 | */ | 609 | */ |
| 585 | @ApiOperation("修改默认目录") | 610 | @ApiOperation("修改默认目录") |
| @@ -589,7 +614,7 @@ public class PlatformController { | @@ -589,7 +614,7 @@ public class PlatformController { | ||
| 589 | }) | 614 | }) |
| 590 | @PostMapping("/catalog/default/update") | 615 | @PostMapping("/catalog/default/update") |
| 591 | @ResponseBody | 616 | @ResponseBody |
| 592 | - public ResponseEntity<WVPResult<String>> setDefaultCatalog(String platformId, String catalogId){ | 617 | + public ResponseEntity<WVPResult<String>> setDefaultCatalog(String platformId, String catalogId) { |
| 593 | 618 | ||
| 594 | if (logger.isDebugEnabled()) { | 619 | if (logger.isDebugEnabled()) { |
| 595 | logger.debug("修改默认目录,{},{}", platformId, catalogId); | 620 | logger.debug("修改默认目录,{},{}", platformId, catalogId); |
| @@ -601,7 +626,7 @@ public class PlatformController { | @@ -601,7 +626,7 @@ public class PlatformController { | ||
| 601 | if (updateResult > 0) { | 626 | if (updateResult > 0) { |
| 602 | result.setMsg("success"); | 627 | result.setMsg("success"); |
| 603 | return new ResponseEntity<>(result, HttpStatus.OK); | 628 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 604 | - }else { | 629 | + } else { |
| 605 | result.setMsg("save error"); | 630 | result.setMsg("save error"); |
| 606 | return new ResponseEntity<>(result, HttpStatus.OK); | 631 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 607 | } | 632 | } |
src/main/java/com/genersoft/iot/vmp/vmanager/gb28181/play/PlayController.java
| @@ -88,7 +88,7 @@ public class PlayController { | @@ -88,7 +88,7 @@ public class PlayController { | ||
| 88 | // 获取可用的zlm | 88 | // 获取可用的zlm |
| 89 | Device device = storager.queryVideoDevice(deviceId); | 89 | Device device = storager.queryVideoDevice(deviceId); |
| 90 | MediaServerItem newMediaServerItem = playService.getNewMediaServerItem(device); | 90 | MediaServerItem newMediaServerItem = playService.getNewMediaServerItem(device); |
| 91 | - PlayResult playResult = playService.play(newMediaServerItem, deviceId, channelId, null, null); | 91 | + PlayResult playResult = playService.play(newMediaServerItem, deviceId, channelId, null, null, null); |
| 92 | 92 | ||
| 93 | return playResult.getResult(); | 93 | return playResult.getResult(); |
| 94 | } | 94 | } |
src/main/java/com/genersoft/iot/vmp/web/gb28181/ApiStreamController.java
| @@ -150,7 +150,7 @@ public class ApiStreamController { | @@ -150,7 +150,7 @@ public class ApiStreamController { | ||
| 150 | JSONObject result = new JSONObject(); | 150 | JSONObject result = new JSONObject(); |
| 151 | result.put("error", "channel[ " + code + " ] " + eventResult.msg); | 151 | result.put("error", "channel[ " + code + " ] " + eventResult.msg); |
| 152 | resultDeferredResult.setResult(result); | 152 | resultDeferredResult.setResult(result); |
| 153 | - }); | 153 | + }, null); |
| 154 | return resultDeferredResult; | 154 | return resultDeferredResult; |
| 155 | } | 155 | } |
| 156 | 156 |
src/main/resources/all-application.yml
| @@ -170,8 +170,6 @@ user-settings: | @@ -170,8 +170,6 @@ user-settings: | ||
| 170 | save-position-history: false | 170 | save-position-history: false |
| 171 | # 点播等待超时时间,单位:毫秒 | 171 | # 点播等待超时时间,单位:毫秒 |
| 172 | play-timeout: 3000 | 172 | play-timeout: 3000 |
| 173 | - # 等待音视频编码信息再返回, true: 可以根据编码选择合适的播放器,false: 可以更快点播 | ||
| 174 | - wait-track: false | ||
| 175 | # 是否开启接口鉴权 | 173 | # 是否开启接口鉴权 |
| 176 | interface-authentication: true | 174 | interface-authentication: true |
| 177 | # 自动配置redis 可以过期事件 | 175 | # 自动配置redis 可以过期事件 |
src/main/resources/application-dev.yml
| @@ -13,7 +13,7 @@ spring: | @@ -13,7 +13,7 @@ spring: | ||
| 13 | # [可选] 数据库 DB | 13 | # [可选] 数据库 DB |
| 14 | database: 6 | 14 | database: 6 |
| 15 | # [可选] 访问密码,若你的redis服务器没有设置密码,就不需要用密码去连接 | 15 | # [可选] 访问密码,若你的redis服务器没有设置密码,就不需要用密码去连接 |
| 16 | - password: | 16 | + password: face2020 |
| 17 | # [可选] 超时时间 | 17 | # [可选] 超时时间 |
| 18 | timeout: 10000 | 18 | timeout: 10000 |
| 19 | # [可选] jdbc数据库配置, 项目使用sqlite作为数据库,一般不需要配置 | 19 | # [可选] jdbc数据库配置, 项目使用sqlite作为数据库,一般不需要配置 |
| @@ -23,7 +23,7 @@ spring: | @@ -23,7 +23,7 @@ spring: | ||
| 23 | driver-class-name: com.mysql.cj.jdbc.Driver | 23 | driver-class-name: com.mysql.cj.jdbc.Driver |
| 24 | url: jdbc:mysql://127.0.0.1:3306/wvp?useUnicode=true&characterEncoding=UTF8&rewriteBatchedStatements=true&serverTimezone=PRC&useSSL=false | 24 | url: jdbc:mysql://127.0.0.1:3306/wvp?useUnicode=true&characterEncoding=UTF8&rewriteBatchedStatements=true&serverTimezone=PRC&useSSL=false |
| 25 | username: root | 25 | username: root |
| 26 | - password: root123 | 26 | + password: 123456 |
| 27 | druid: | 27 | druid: |
| 28 | initialSize: 10 # 连接池初始化连接数 | 28 | initialSize: 10 # 连接池初始化连接数 |
| 29 | maxActive: 200 # 连接池最大连接数 | 29 | maxActive: 200 # 连接池最大连接数 |
| @@ -50,7 +50,7 @@ server: | @@ -50,7 +50,7 @@ server: | ||
| 50 | # 作为28181服务器的配置 | 50 | # 作为28181服务器的配置 |
| 51 | sip: | 51 | sip: |
| 52 | # [必须修改] 本机的IP | 52 | # [必须修改] 本机的IP |
| 53 | - ip: 192.168.118.70 | 53 | + ip: 192.168.41.16 |
| 54 | # [可选] 28181服务监听的端口 | 54 | # [可选] 28181服务监听的端口 |
| 55 | port: 5060 | 55 | port: 5060 |
| 56 | # 根据国标6.1.2中规定,domain宜采用ID统一编码的前十位编码。国标附录D中定义前8位为中心编码(由省级、市级、区级、基层编号组成,参照GB/T 2260-2007) | 56 | # 根据国标6.1.2中规定,domain宜采用ID统一编码的前十位编码。国标附录D中定义前8位为中心编码(由省级、市级、区级、基层编号组成,参照GB/T 2260-2007) |
| @@ -67,9 +67,9 @@ sip: | @@ -67,9 +67,9 @@ sip: | ||
| 67 | media: | 67 | media: |
| 68 | id: FQ3TF8yT83wh5Wvz | 68 | id: FQ3TF8yT83wh5Wvz |
| 69 | # [必须修改] zlm服务器的内网IP | 69 | # [必须修改] zlm服务器的内网IP |
| 70 | - ip: 192.168.118.70 | 70 | + ip: 192.168.41.16 |
| 71 | # [必须修改] zlm服务器的http.port | 71 | # [必须修改] zlm服务器的http.port |
| 72 | - http-port: 80 | 72 | + http-port: 8091 |
| 73 | # [可选] zlm服务器的hook.admin_params=secret | 73 | # [可选] zlm服务器的hook.admin_params=secret |
| 74 | secret: 035c73f7-bb6b-4889-a715-d9eb2d1925cc | 74 | secret: 035c73f7-bb6b-4889-a715-d9eb2d1925cc |
| 75 | # 启用多端口模式, 多端口模式使用端口区分每路流,兼容性更好。 单端口使用流的ssrc区分, 点播超时建议使用多端口测试 | 75 | # 启用多端口模式, 多端口模式使用端口区分每路流,兼容性更好。 单端口使用流的ssrc区分, 点播超时建议使用多端口测试 |