Commit 0858f7995b8236d79c6e39a5974cb7a13bcb4e3e

Authored by 648540858
1 parent 3dfbc843

优化ssrc存储结构,避免因为大量ssrc存在MediaServer中导致redis读取超时

src/main/java/com/genersoft/iot/vmp/conf/redis/RedisConfig.java
@@ -9,12 +9,8 @@ import org.springframework.context.annotation.Bean; @@ -9,12 +9,8 @@ import org.springframework.context.annotation.Bean;
9 import org.springframework.context.annotation.Configuration; 9 import org.springframework.context.annotation.Configuration;
10 import org.springframework.core.annotation.Order; 10 import org.springframework.core.annotation.Order;
11 import org.springframework.data.redis.connection.RedisConnectionFactory; 11 import org.springframework.data.redis.connection.RedisConnectionFactory;
12 -import org.springframework.data.redis.core.RedisTemplate;  
13 import org.springframework.data.redis.listener.PatternTopic; 12 import org.springframework.data.redis.listener.PatternTopic;
14 import org.springframework.data.redis.listener.RedisMessageListenerContainer; 13 import org.springframework.data.redis.listener.RedisMessageListenerContainer;
15 -import org.springframework.data.redis.serializer.StringRedisSerializer;  
16 -  
17 -import com.genersoft.iot.vmp.utils.redis.FastJsonRedisSerializer;  
18 14
19 15
20 /** 16 /**
@@ -48,21 +44,7 @@ public class RedisConfig extends CachingConfigurerSupport { @@ -48,21 +44,7 @@ public class RedisConfig extends CachingConfigurerSupport {
48 @Autowired 44 @Autowired
49 private RedisPushStreamResponseListener redisPushStreamResponseListener; 45 private RedisPushStreamResponseListener redisPushStreamResponseListener;
50 46
51 - @Bean  
52 - public RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) {  
53 - RedisTemplate<Object, Object> redisTemplate = new RedisTemplate<>();  
54 - // 使用fastJson序列化  
55 - FastJsonRedisSerializer fastJsonRedisSerializer = new FastJsonRedisSerializer(Object.class);  
56 - // value值的序列化采用fastJsonRedisSerializer  
57 - redisTemplate.setValueSerializer(fastJsonRedisSerializer);  
58 - redisTemplate.setHashValueSerializer(fastJsonRedisSerializer);  
59 -  
60 - // key的序列化采用StringRedisSerializer  
61 - redisTemplate.setKeySerializer(new StringRedisSerializer());  
62 - redisTemplate.setHashKeySerializer(new StringRedisSerializer());  
63 - redisTemplate.setConnectionFactory(redisConnectionFactory);  
64 - return redisTemplate;  
65 - } 47 +
66 48
67 49
68 /** 50 /**
src/main/java/com/genersoft/iot/vmp/conf/redis/RedisTemplateConfig.java 0 → 100644
  1 +package com.genersoft.iot.vmp.conf.redis;
  2 +
  3 +import com.genersoft.iot.vmp.utils.redis.FastJsonRedisSerializer;
  4 +import org.springframework.context.annotation.Bean;
  5 +import org.springframework.context.annotation.Configuration;
  6 +import org.springframework.data.redis.connection.RedisConnectionFactory;
  7 +import org.springframework.data.redis.core.RedisTemplate;
  8 +import org.springframework.data.redis.serializer.StringRedisSerializer;
  9 +
  10 +@Configuration
  11 +public class RedisTemplateConfig {
  12 +
  13 + @Bean
  14 + public RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) {
  15 + RedisTemplate<Object, Object> redisTemplate = new RedisTemplate<>();
  16 + // 使用fastJson序列化
  17 + FastJsonRedisSerializer fastJsonRedisSerializer = new FastJsonRedisSerializer(Object.class);
  18 + // value值的序列化采用fastJsonRedisSerializer
  19 + redisTemplate.setValueSerializer(fastJsonRedisSerializer);
  20 + redisTemplate.setHashValueSerializer(fastJsonRedisSerializer);
  21 +
  22 + // key的序列化采用StringRedisSerializer
  23 + redisTemplate.setKeySerializer(new StringRedisSerializer());
  24 + redisTemplate.setHashKeySerializer(new StringRedisSerializer());
  25 + redisTemplate.setConnectionFactory(redisConnectionFactory);
  26 + return redisTemplate;
  27 + }
  28 +}
src/main/java/com/genersoft/iot/vmp/gb28181/session/SSRCFactory.java 0 → 100644
  1 +package com.genersoft.iot.vmp.gb28181.session;
  2 +
  3 +import com.genersoft.iot.vmp.conf.SipConfig;
  4 +import org.springframework.beans.factory.annotation.Autowired;
  5 +import org.springframework.data.redis.core.StringRedisTemplate;
  6 +import org.springframework.stereotype.Component;
  7 +
  8 +import java.util.ArrayList;
  9 +import java.util.List;
  10 +import java.util.Set;
  11 +
  12 +/**
  13 + * ssrc使用
  14 + */
  15 +@Component
  16 +public class SSRCFactory {
  17 +
  18 + /**
  19 + * 播流最大并发个数
  20 + */
  21 + private static final Integer MAX_STREAM_COUNT = 10000;
  22 +
  23 + /**
  24 + * 播流最大并发个数
  25 + */
  26 + private static final String SSRC_INFO_KEY = "VMP_SSRC_INFO_";
  27 +
  28 + @Autowired
  29 + private StringRedisTemplate redisTemplate;
  30 +
  31 + @Autowired
  32 + private SipConfig sipConfig;
  33 +
  34 +
  35 + public void initMediaServerSSRC(String mediaServerId, Set<String> usedSet) {
  36 + String ssrcPrefix = sipConfig.getDomain().substring(3, 8);
  37 + String redisKey = SSRC_INFO_KEY + mediaServerId;
  38 + List<String> ssrcList = new ArrayList<>();
  39 + for (int i = 1; i < MAX_STREAM_COUNT; i++) {
  40 + String ssrc = String.format("%s%04d", ssrcPrefix, i);
  41 +
  42 + if (null == usedSet || !usedSet.contains(ssrc)) {
  43 + ssrcList.add(ssrc);
  44 +
  45 + }
  46 + }
  47 + if (redisTemplate.opsForSet().size(redisKey) != null) {
  48 + redisTemplate.delete(redisKey);
  49 + }
  50 + redisTemplate.opsForSet().add(redisKey, ssrcList.toArray(new String[0]));
  51 + }
  52 +
  53 +
  54 + /**
  55 + * 获取视频预览的SSRC值,第一位固定为0
  56 + *
  57 + * @return ssrc
  58 + */
  59 + public String getPlaySsrc(String mediaServerId) {
  60 + return "0" + getSN(mediaServerId);
  61 + }
  62 +
  63 + /**
  64 + * 获取录像回放的SSRC值,第一位固定为1
  65 + */
  66 + public String getPlayBackSsrc(String mediaServerId) {
  67 + return "1" + getSN(mediaServerId);
  68 + }
  69 +
  70 + /**
  71 + * 释放ssrc,主要用完的ssrc一定要释放,否则会耗尽
  72 + *
  73 + * @param ssrc 需要重置的ssrc
  74 + */
  75 + public void releaseSsrc(String mediaServerId, String ssrc) {
  76 + if (ssrc == null) {
  77 + return;
  78 + }
  79 + String sn = ssrc.substring(1);
  80 + String redisKey = SSRC_INFO_KEY + mediaServerId;
  81 + redisTemplate.opsForSet().add(redisKey, sn);
  82 + }
  83 +
  84 + /**
  85 + * 获取后四位数SN,随机数
  86 + */
  87 + private String getSN(String mediaServerId) {
  88 + String sn = null;
  89 + String redisKey = SSRC_INFO_KEY + mediaServerId;
  90 + Long size = redisTemplate.opsForSet().size(redisKey);
  91 + if (size == null || size == 0) {
  92 + throw new RuntimeException("ssrc已经用完");
  93 + } else {
  94 + // 在集合中移除并返回一个随机成员。
  95 + sn = (String) redisTemplate.opsForSet().pop(redisKey);
  96 + redisTemplate.opsForSet().remove(redisKey, sn);
  97 + }
  98 + return sn;
  99 + }
  100 +
  101 + /**
  102 + * 重置一个流媒体服务的所有ssrc
  103 + *
  104 + * @param mediaServerId 流媒体服务ID
  105 + */
  106 + public void reset(String mediaServerId) {
  107 + this.initMediaServerSSRC(mediaServerId, null);
  108 + }
  109 +
  110 + /**
  111 + * 是否已经存在了某个MediaServer的SSRC信息
  112 + *
  113 + * @param mediaServerId 流媒体服务ID
  114 + */
  115 + public boolean hasMediaServerSSRC(String mediaServerId) {
  116 + String redisKey = SSRC_INFO_KEY + mediaServerId;
  117 + return redisTemplate.opsForSet().members(redisKey) != null;
  118 + }
  119 +
  120 + /**
  121 + * 查询ssrc是否可用
  122 + *
  123 + * @param mediaServerId
  124 + * @param ssrc
  125 + * @return
  126 + */
  127 + public boolean checkSsrc(String mediaServerId, String ssrc) {
  128 + String sn = ssrc.substring(1);
  129 + String redisKey = SSRC_INFO_KEY + mediaServerId;
  130 + return redisTemplate.opsForSet().isMember(redisKey, sn) != null;
  131 + }
  132 +}
src/main/java/com/genersoft/iot/vmp/gb28181/session/SsrcConfig.java deleted 100644 → 0
1 -package com.genersoft.iot.vmp.gb28181.session;  
2 -  
3 -import com.genersoft.iot.vmp.utils.ConfigConst;  
4 -import io.swagger.v3.oas.annotations.media.Schema;  
5 -  
6 -import java.util.ArrayList;  
7 -import java.util.List;  
8 -import java.util.Random;  
9 -import java.util.Set;  
10 -  
11 -@Schema(description = "ssrc信息")  
12 -public class SsrcConfig {  
13 -  
14 - /**  
15 - * zlm流媒体服务器Id  
16 - */  
17 - @Schema(description = "流媒体服务器Id")  
18 - private String mediaServerId;  
19 -  
20 - @Schema(description = "SSRC前缀")  
21 - private String ssrcPrefix;  
22 -  
23 - /**  
24 - * zlm流媒体服务器已用会话句柄  
25 - */  
26 - @Schema(description = "zlm流媒体服务器已用会话句柄")  
27 - private List<String> isUsed;  
28 -  
29 - /**  
30 - * zlm流媒体服务器可用会话句柄  
31 - */  
32 - @Schema(description = "zlm流媒体服务器可用会话句柄")  
33 - private List<String> notUsed;  
34 -  
35 - public SsrcConfig() {  
36 - }  
37 -  
38 - public SsrcConfig(String mediaServerId, Set<String> usedSet, String sipDomain) {  
39 - this.mediaServerId = mediaServerId;  
40 - this.isUsed = new ArrayList<>();  
41 - this.ssrcPrefix = sipDomain.substring(3, 8);  
42 - this.notUsed = new ArrayList<>();  
43 - for (int i = 1; i < ConfigConst.MAX_STRTEAM_COUNT; i++) {  
44 - String ssrc;  
45 - if (i < 10) {  
46 - ssrc = "000" + i;  
47 - } else if (i < 100) {  
48 - ssrc = "00" + i;  
49 - } else if (i < 1000) {  
50 - ssrc = "0" + i;  
51 - } else {  
52 - ssrc = String.valueOf(i);  
53 - }  
54 - if (null == usedSet || !usedSet.contains(ssrc)) {  
55 - this.notUsed.add(ssrc);  
56 - } else {  
57 - this.isUsed.add(ssrc);  
58 - }  
59 - }  
60 - }  
61 -  
62 -  
63 - /**  
64 - * 获取视频预览的SSRC值,第一位固定为0  
65 - * @return ssrc  
66 - */  
67 - public String getPlaySsrc() {  
68 - return "0" + getSsrcPrefix() + getSN();  
69 - }  
70 -  
71 - /**  
72 - * 获取录像回放的SSRC值,第一位固定为1  
73 - *  
74 - */  
75 - public String getPlayBackSsrc() {  
76 - return "1" + getSsrcPrefix() + getSN();  
77 - }  
78 -  
79 - /**  
80 - * 释放ssrc,主要用完的ssrc一定要释放,否则会耗尽  
81 - * @param ssrc 需要重置的ssrc  
82 - */  
83 - public void releaseSsrc(String ssrc) {  
84 - if (ssrc == null) {  
85 - return;  
86 - }  
87 - String sn = ssrc.substring(6);  
88 - try {  
89 - isUsed.remove(sn);  
90 - notUsed.add(sn);  
91 - }catch (NullPointerException e){  
92 - }  
93 - }  
94 -  
95 - /**  
96 - * 获取后四位数SN,随机数  
97 - *  
98 - */  
99 - private String getSN() {  
100 - String sn = null;  
101 - int index = 0;  
102 - if (notUsed.size() == 0) {  
103 - throw new RuntimeException("ssrc已经用完");  
104 - } else if (notUsed.size() == 1) {  
105 - sn = notUsed.get(0);  
106 - } else {  
107 - index = new Random().nextInt(notUsed.size() - 1);  
108 - sn = notUsed.get(index);  
109 - }  
110 - notUsed.remove(index);  
111 - isUsed.add(sn);  
112 - return sn;  
113 - }  
114 -  
115 - public String getSsrcPrefix() {  
116 - return ssrcPrefix;  
117 - }  
118 -  
119 - public String getMediaServerId() {  
120 - return mediaServerId;  
121 - }  
122 -  
123 - public void setMediaServerId(String mediaServerId) {  
124 - this.mediaServerId = mediaServerId;  
125 - }  
126 -  
127 - public void setSsrcPrefix(String ssrcPrefix) {  
128 - this.ssrcPrefix = ssrcPrefix;  
129 - }  
130 -  
131 - public List<String> getIsUsed() {  
132 - return isUsed;  
133 - }  
134 -  
135 - public void setIsUsed(List<String> isUsed) {  
136 - this.isUsed = isUsed;  
137 - }  
138 -  
139 - public List<String> getNotUsed() {  
140 - return notUsed;  
141 - }  
142 -  
143 - public void setNotUsed(List<String> notUsed) {  
144 - this.notUsed = notUsed;  
145 - }  
146 -  
147 - public boolean checkSsrc(String ssrcInResponse) {  
148 - return !isUsed.contains(ssrcInResponse);  
149 - }  
150 -}  
src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/request/impl/InviteRequestProcessor.java
@@ -5,7 +5,7 @@ import com.genersoft.iot.vmp.conf.DynamicTask; @@ -5,7 +5,7 @@ import com.genersoft.iot.vmp.conf.DynamicTask;
5 import com.genersoft.iot.vmp.conf.UserSetting; 5 import com.genersoft.iot.vmp.conf.UserSetting;
6 import com.genersoft.iot.vmp.gb28181.bean.*; 6 import com.genersoft.iot.vmp.gb28181.bean.*;
7 import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; 7 import com.genersoft.iot.vmp.gb28181.event.SipSubscribe;
8 -import com.genersoft.iot.vmp.gb28181.session.SsrcConfig; 8 +import com.genersoft.iot.vmp.gb28181.session.SSRCFactory;
9 import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; 9 import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager;
10 import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver; 10 import com.genersoft.iot.vmp.gb28181.transmit.SIPProcessorObserver;
11 import com.genersoft.iot.vmp.gb28181.transmit.SIPSender; 11 import com.genersoft.iot.vmp.gb28181.transmit.SIPSender;
@@ -75,6 +75,9 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements @@ -75,6 +75,9 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements
75 private IRedisCatchStorage redisCatchStorage; 75 private IRedisCatchStorage redisCatchStorage;
76 76
77 @Autowired 77 @Autowired
  78 + private SSRCFactory ssrcFactory;
  79 +
  80 + @Autowired
78 private DynamicTask dynamicTask; 81 private DynamicTask dynamicTask;
79 82
80 @Autowired 83 @Autowired
@@ -491,12 +494,8 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements @@ -491,12 +494,8 @@ public class InviteRequestProcessor extends SIPRequestProcessorParent implements
491 } else if (gbStream != null) { 494 } else if (gbStream != null) {
492 if(ssrc.equals(ssrcDefault)) 495 if(ssrc.equals(ssrcDefault))
493 { 496 {
494 - SsrcConfig ssrcConfig = mediaServerItem.getSsrcConfig();  
495 - if(ssrcConfig != null)  
496 - {  
497 - ssrc = ssrcConfig.getPlaySsrc();  
498 - ssrcConfig.releaseSsrc(ssrc);  
499 - } 497 + ssrc = ssrcFactory.getPlaySsrc(mediaServerItem.getId());
  498 + ssrcFactory.releaseSsrc(mediaServerItem.getId(), ssrc);
500 } 499 }
501 if("push".equals(gbStream.getStreamType())) { 500 if("push".equals(gbStream.getStreamType())) {
502 if (streamPushItem != null && streamPushItem.isPushIng()) { 501 if (streamPushItem != null && streamPushItem.isPushIng()) {
src/main/java/com/genersoft/iot/vmp/media/zlm/dto/MediaServerItem.java
1 package com.genersoft.iot.vmp.media.zlm.dto; 1 package com.genersoft.iot.vmp.media.zlm.dto;
2 2
3 3
4 -import com.genersoft.iot.vmp.gb28181.session.SsrcConfig; 4 +import com.genersoft.iot.vmp.gb28181.session.SSRCFactory;
5 import com.genersoft.iot.vmp.media.zlm.ZLMServerConfig; 5 import com.genersoft.iot.vmp.media.zlm.ZLMServerConfig;
6 import io.swagger.v3.oas.annotations.media.Schema; 6 import io.swagger.v3.oas.annotations.media.Schema;
7 import org.springframework.util.ObjectUtils; 7 import org.springframework.util.ObjectUtils;
@@ -80,8 +80,8 @@ public class MediaServerItem{ @@ -80,8 +80,8 @@ public class MediaServerItem{
80 @Schema(description = "是否是默认ZLM") 80 @Schema(description = "是否是默认ZLM")
81 private boolean defaultServer; 81 private boolean defaultServer;
82 82
83 - @Schema(description = "SSRC信息")  
84 - private SsrcConfig ssrcConfig; 83 +// @Schema(description = "SSRC信息")
  84 +// private SsrcConfig ssrcConfig;
85 85
86 @Schema(description = "当前使用到的端口") 86 @Schema(description = "当前使用到的端口")
87 private int currentPort; 87 private int currentPort;
@@ -92,7 +92,7 @@ public class MediaServerItem{ @@ -92,7 +92,7 @@ public class MediaServerItem{
92 * 在ApplicationCheckRunner里对mediaServerSsrcMap进行初始化 92 * 在ApplicationCheckRunner里对mediaServerSsrcMap进行初始化
93 */ 93 */
94 @Schema(description = "ID") 94 @Schema(description = "ID")
95 - private HashMap<String, SsrcConfig> mediaServerSsrcMap; 95 + private HashMap<String, SSRCFactory> mediaServerSsrcMap;
96 96
97 public MediaServerItem() { 97 public MediaServerItem() {
98 } 98 }
@@ -279,22 +279,14 @@ public class MediaServerItem{ @@ -279,22 +279,14 @@ public class MediaServerItem{
279 this.updateTime = updateTime; 279 this.updateTime = updateTime;
280 } 280 }
281 281
282 - public HashMap<String, SsrcConfig> getMediaServerSsrcMap() { 282 + public HashMap<String, SSRCFactory> getMediaServerSsrcMap() {
283 return mediaServerSsrcMap; 283 return mediaServerSsrcMap;
284 } 284 }
285 285
286 - public void setMediaServerSsrcMap(HashMap<String, SsrcConfig> mediaServerSsrcMap) { 286 + public void setMediaServerSsrcMap(HashMap<String, SSRCFactory> mediaServerSsrcMap) {
287 this.mediaServerSsrcMap = mediaServerSsrcMap; 287 this.mediaServerSsrcMap = mediaServerSsrcMap;
288 } 288 }
289 289
290 - public SsrcConfig getSsrcConfig() {  
291 - return ssrcConfig;  
292 - }  
293 -  
294 - public void setSsrcConfig(SsrcConfig ssrcConfig) {  
295 - this.ssrcConfig = ssrcConfig;  
296 - }  
297 -  
298 public int getCurrentPort() { 290 public int getCurrentPort() {
299 return currentPort; 291 return currentPort;
300 } 292 }
src/main/java/com/genersoft/iot/vmp/service/impl/DeviceChannelServiceImpl.java
@@ -45,6 +45,8 @@ public class DeviceChannelServiceImpl implements IDeviceChannelService { @@ -45,6 +45,8 @@ public class DeviceChannelServiceImpl implements IDeviceChannelService {
45 device = deviceMapper.getDeviceByDeviceId(deviceChannel.getDeviceId()); 45 device = deviceMapper.getDeviceByDeviceId(deviceChannel.getDeviceId());
46 } 46 }
47 47
  48 +
  49 +
48 if ("WGS84".equals(device.getGeoCoordSys())) { 50 if ("WGS84".equals(device.getGeoCoordSys())) {
49 deviceChannel.setLongitudeWgs84(deviceChannel.getLongitude()); 51 deviceChannel.setLongitudeWgs84(deviceChannel.getLongitude());
50 deviceChannel.setLatitudeWgs84(deviceChannel.getLatitude()); 52 deviceChannel.setLatitudeWgs84(deviceChannel.getLatitude());
src/main/java/com/genersoft/iot/vmp/service/impl/MediaServerServiceImpl.java
@@ -9,7 +9,7 @@ import com.genersoft.iot.vmp.conf.SipConfig; @@ -9,7 +9,7 @@ import com.genersoft.iot.vmp.conf.SipConfig;
9 import com.genersoft.iot.vmp.conf.UserSetting; 9 import com.genersoft.iot.vmp.conf.UserSetting;
10 import com.genersoft.iot.vmp.conf.exception.ControllerException; 10 import com.genersoft.iot.vmp.conf.exception.ControllerException;
11 import com.genersoft.iot.vmp.gb28181.event.EventPublisher; 11 import com.genersoft.iot.vmp.gb28181.event.EventPublisher;
12 -import com.genersoft.iot.vmp.gb28181.session.SsrcConfig; 12 +import com.genersoft.iot.vmp.gb28181.session.SSRCFactory;
13 import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; 13 import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager;
14 import com.genersoft.iot.vmp.media.zlm.ZLMRESTfulUtils; 14 import com.genersoft.iot.vmp.media.zlm.ZLMRESTfulUtils;
15 import com.genersoft.iot.vmp.media.zlm.ZLMRTPServerFactory; 15 import com.genersoft.iot.vmp.media.zlm.ZLMRTPServerFactory;
@@ -54,6 +54,9 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -54,6 +54,9 @@ public class MediaServerServiceImpl implements IMediaServerService {
54 @Autowired 54 @Autowired
55 private SipConfig sipConfig; 55 private SipConfig sipConfig;
56 56
  57 + @Autowired
  58 + private SSRCFactory ssrcFactory;
  59 +
57 @Value("${server.ssl.enabled:false}") 60 @Value("${server.ssl.enabled:false}")
58 private boolean sslEnabled; 61 private boolean sslEnabled;
59 62
@@ -90,6 +93,7 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -90,6 +93,7 @@ public class MediaServerServiceImpl implements IMediaServerService {
90 @Autowired 93 @Autowired
91 private IRedisCatchStorage redisCatchStorage; 94 private IRedisCatchStorage redisCatchStorage;
92 95
  96 +
93 /** 97 /**
94 * 初始化 98 * 初始化
95 */ 99 */
@@ -101,9 +105,8 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -101,9 +105,8 @@ public class MediaServerServiceImpl implements IMediaServerService {
101 continue; 105 continue;
102 } 106 }
103 // 更新 107 // 更新
104 - if (mediaServerItem.getSsrcConfig() == null) {  
105 - SsrcConfig ssrcConfig = new SsrcConfig(mediaServerItem.getId(), null, sipConfig.getDomain());  
106 - mediaServerItem.setSsrcConfig(ssrcConfig); 108 + if (ssrcFactory.hasMediaServerSSRC(mediaServerItem.getId())) {
  109 + ssrcFactory.initMediaServerSSRC(mediaServerItem.getId(), null);
107 RedisUtil.set(VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItem.getId(), mediaServerItem); 110 RedisUtil.set(VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItem.getId(), mediaServerItem);
108 } 111 }
109 // 查询redis是否存在此mediaServer 112 // 查询redis是否存在此mediaServer
@@ -127,36 +130,27 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -127,36 +130,27 @@ public class MediaServerServiceImpl implements IMediaServerService {
127 return null; 130 return null;
128 } 131 }
129 // 获取mediaServer可用的ssrc 132 // 获取mediaServer可用的ssrc
130 - String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItem.getId();  
131 -  
132 - SsrcConfig ssrcConfig = mediaServerItem.getSsrcConfig();  
133 - if (ssrcConfig == null) {  
134 - logger.info("media server [ {} ] ssrcConfig is null", mediaServerItem.getId());  
135 - return null; 133 + String ssrc;
  134 + if (presetSsrc != null) {
  135 + ssrc = presetSsrc;
136 }else { 136 }else {
137 - String ssrc;  
138 - if (presetSsrc != null) {  
139 - ssrc = presetSsrc; 137 + if (isPlayback) {
  138 + ssrc = ssrcFactory.getPlayBackSsrc(mediaServerItem.getId());
140 }else { 139 }else {
141 - if (isPlayback) {  
142 - ssrc = ssrcConfig.getPlayBackSsrc();  
143 - }else {  
144 - ssrc = ssrcConfig.getPlaySsrc();  
145 - } 140 + ssrc = ssrcFactory.getPlaySsrc(mediaServerItem.getId());
146 } 141 }
  142 + }
147 143
148 - if (streamId == null) {  
149 - streamId = String.format("%08x", Integer.parseInt(ssrc)).toUpperCase();  
150 - }  
151 - int rtpServerPort;  
152 - if (mediaServerItem.isRtpEnable()) {  
153 - rtpServerPort = zlmrtpServerFactory.createRTPServer(mediaServerItem, streamId, ssrcCheck?Integer.parseInt(ssrc):0, port);  
154 - } else {  
155 - rtpServerPort = mediaServerItem.getRtpProxyPort();  
156 - }  
157 - RedisUtil.set(key, mediaServerItem);  
158 - return new SSRCInfo(rtpServerPort, ssrc, streamId); 144 + if (streamId == null) {
  145 + streamId = String.format("%08x", Integer.parseInt(ssrc)).toUpperCase();
  146 + }
  147 + int rtpServerPort;
  148 + if (mediaServerItem.isRtpEnable()) {
  149 + rtpServerPort = zlmrtpServerFactory.createRTPServer(mediaServerItem, streamId, ssrcCheck?Integer.parseInt(ssrc):0, port);
  150 + } else {
  151 + rtpServerPort = mediaServerItem.getRtpProxyPort();
159 } 152 }
  153 + return new SSRCInfo(rtpServerPort, ssrc, streamId);
160 } 154 }
161 155
162 @Override 156 @Override
@@ -184,11 +178,7 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -184,11 +178,7 @@ public class MediaServerServiceImpl implements IMediaServerService {
184 if (mediaServerItem == null || ssrc == null) { 178 if (mediaServerItem == null || ssrc == null) {
185 return; 179 return;
186 } 180 }
187 - SsrcConfig ssrcConfig = mediaServerItem.getSsrcConfig();  
188 - ssrcConfig.releaseSsrc(ssrc);  
189 - mediaServerItem.setSsrcConfig(ssrcConfig);  
190 - String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItem.getId();  
191 - RedisUtil.set(key, mediaServerItem); 181 + ssrcFactory.releaseSsrc(mediaServerItemId, ssrc);
192 } 182 }
193 183
194 /** 184 /**
@@ -196,8 +186,7 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -196,8 +186,7 @@ public class MediaServerServiceImpl implements IMediaServerService {
196 */ 186 */
197 @Override 187 @Override
198 public void clearRTPServer(MediaServerItem mediaServerItem) { 188 public void clearRTPServer(MediaServerItem mediaServerItem) {
199 - mediaServerItem.setSsrcConfig(new SsrcConfig(mediaServerItem.getId(), null, sipConfig.getDomain()));  
200 - RedisUtil.zAdd(VideoManagerConstants.MEDIA_SERVERS_ONLINE_PREFIX + userSetting.getServerId(), mediaServerItem.getId(), 0); 189 + ssrcFactory.reset(mediaServerItem.getId());
201 190
202 } 191 }
203 192
@@ -207,16 +196,8 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -207,16 +196,8 @@ public class MediaServerServiceImpl implements IMediaServerService {
207 mediaServerMapper.update(mediaSerItem); 196 mediaServerMapper.update(mediaSerItem);
208 MediaServerItem mediaServerItemInRedis = getOne(mediaSerItem.getId()); 197 MediaServerItem mediaServerItemInRedis = getOne(mediaSerItem.getId());
209 MediaServerItem mediaServerItemInDataBase = mediaServerMapper.queryOne(mediaSerItem.getId()); 198 MediaServerItem mediaServerItemInDataBase = mediaServerMapper.queryOne(mediaSerItem.getId());
210 - if (mediaServerItemInRedis != null && mediaServerItemInRedis.getSsrcConfig() != null) {  
211 - mediaServerItemInDataBase.setSsrcConfig(mediaServerItemInRedis.getSsrcConfig());  
212 - }else {  
213 - mediaServerItemInDataBase.setSsrcConfig(  
214 - new SsrcConfig(  
215 - mediaServerItemInDataBase.getId(),  
216 - null,  
217 - sipConfig.getDomain()  
218 - )  
219 - ); 199 + if (mediaServerItemInRedis == null || ssrcFactory.hasMediaServerSSRC(mediaSerItem.getId())) {
  200 + ssrcFactory.initMediaServerSSRC(mediaServerItemInDataBase.getId(),null);
220 } 201 }
221 String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItemInDataBase.getId(); 202 String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItemInDataBase.getId();
222 RedisUtil.set(key, mediaServerItemInDataBase); 203 RedisUtil.set(key, mediaServerItemInDataBase);
@@ -396,14 +377,8 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -396,14 +377,8 @@ public class MediaServerServiceImpl implements IMediaServerService {
396 } 377 }
397 mediaServerMapper.update(serverItem); 378 mediaServerMapper.update(serverItem);
398 String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + zlmServerConfig.getGeneralMediaServerId(); 379 String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + zlmServerConfig.getGeneralMediaServerId();
399 - if (RedisUtil.get(key) == null) {  
400 - SsrcConfig ssrcConfig = new SsrcConfig(zlmServerConfig.getGeneralMediaServerId(), null, sipConfig.getDomain());  
401 - serverItem.setSsrcConfig(ssrcConfig);  
402 - }else {  
403 - MediaServerItem mediaServerItemInRedis = JsonUtil.redisJsonToObject(key, MediaServerItem.class);  
404 - if (Objects.nonNull(mediaServerItemInRedis)) {  
405 - serverItem.setSsrcConfig(mediaServerItemInRedis.getSsrcConfig());  
406 - } 380 + if (ssrcFactory.hasMediaServerSSRC(serverItem.getId())) {
  381 + ssrcFactory.initMediaServerSSRC(zlmServerConfig.getGeneralMediaServerId(), null);
407 } 382 }
408 RedisUtil.set(key, serverItem); 383 RedisUtil.set(key, serverItem);
409 resetOnlineServerItem(serverItem); 384 resetOnlineServerItem(serverItem);
@@ -682,8 +657,7 @@ public class MediaServerServiceImpl implements IMediaServerService { @@ -682,8 +657,7 @@ public class MediaServerServiceImpl implements IMediaServerService {
682 } 657 }
683 // zlm连接重试 658 // zlm连接重试
684 logger.warn("[更新ZLM 保活信息]尝试链接zml id {}", mediaServerId); 659 logger.warn("[更新ZLM 保活信息]尝试链接zml id {}", mediaServerId);
685 - SsrcConfig ssrcConfig = new SsrcConfig(mediaServerItem.getId(), null, sipConfig.getDomain());  
686 - mediaServerItem.setSsrcConfig(ssrcConfig); 660 + ssrcFactory.initMediaServerSSRC(mediaServerItem.getId(), null);
687 String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItem.getId(); 661 String key = VideoManagerConstants.MEDIA_SERVER_PREFIX + userSetting.getServerId() + "_" + mediaServerItem.getId();
688 RedisUtil.set(key, mediaServerItem); 662 RedisUtil.set(key, mediaServerItem);
689 clearRTPServer(mediaServerItem); 663 clearRTPServer(mediaServerItem);
src/main/java/com/genersoft/iot/vmp/service/impl/PlayServiceImpl.java
@@ -11,6 +11,7 @@ import com.genersoft.iot.vmp.conf.exception.ServiceException; @@ -11,6 +11,7 @@ import com.genersoft.iot.vmp.conf.exception.ServiceException;
11 import com.genersoft.iot.vmp.conf.exception.SsrcTransactionNotFoundException; 11 import com.genersoft.iot.vmp.conf.exception.SsrcTransactionNotFoundException;
12 import com.genersoft.iot.vmp.gb28181.bean.*; 12 import com.genersoft.iot.vmp.gb28181.bean.*;
13 import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; 13 import com.genersoft.iot.vmp.gb28181.event.SipSubscribe;
  14 +import com.genersoft.iot.vmp.gb28181.session.SSRCFactory;
14 import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; 15 import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager;
15 import com.genersoft.iot.vmp.gb28181.transmit.callback.DeferredResultHolder; 16 import com.genersoft.iot.vmp.gb28181.transmit.callback.DeferredResultHolder;
16 import com.genersoft.iot.vmp.gb28181.transmit.callback.RequestMessage; 17 import com.genersoft.iot.vmp.gb28181.transmit.callback.RequestMessage;
@@ -100,6 +101,9 @@ public class PlayServiceImpl implements IPlayService { @@ -100,6 +101,9 @@ public class PlayServiceImpl implements IPlayService {
100 @Autowired 101 @Autowired
101 private ZlmHttpHookSubscribe subscribe; 102 private ZlmHttpHookSubscribe subscribe;
102 103
  104 + @Autowired
  105 + private SSRCFactory ssrcFactory;
  106 +
103 107
104 @Override 108 @Override
105 public void play(MediaServerItem mediaServerItem, String deviceId, String channelId, 109 public void play(MediaServerItem mediaServerItem, String deviceId, String channelId,
@@ -295,10 +299,10 @@ public class PlayServiceImpl implements IPlayService { @@ -295,10 +299,10 @@ public class PlayServiceImpl implements IPlayService {
295 if (!mediaServerItem.isRtpEnable() || device.isSsrcCheck()) { 299 if (!mediaServerItem.isRtpEnable() || device.isSsrcCheck()) {
296 logger.info("[点播消息] SSRC修正 {}->{}", ssrcInfo.getSsrc(), ssrcInResponse); 300 logger.info("[点播消息] SSRC修正 {}->{}", ssrcInfo.getSsrc(), ssrcInResponse);
297 301
298 - if (!mediaServerItem.getSsrcConfig().checkSsrc(ssrcInResponse)) { 302 + if (!ssrcFactory.checkSsrc(mediaServerItem.getId(),ssrcInResponse)) {
299 // ssrc 不可用 303 // ssrc 不可用
300 // 释放ssrc 304 // 释放ssrc
301 - mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); 305 + ssrcFactory.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc());
302 streamSession.remove(device.getDeviceId(), channelId, ssrcInfo.getStream()); 306 streamSession.remove(device.getDeviceId(), channelId, ssrcInfo.getStream());
303 event.msg = "下级自定义了ssrc,但是此ssrc不可用"; 307 event.msg = "下级自定义了ssrc,但是此ssrc不可用";
304 event.statusCode = 400; 308 event.statusCode = 400;
@@ -536,7 +540,7 @@ public class PlayServiceImpl implements IPlayService { @@ -536,7 +540,7 @@ public class PlayServiceImpl implements IPlayService {
536 if (!mediaServerItem.isRtpEnable() || device.isSsrcCheck()) { 540 if (!mediaServerItem.isRtpEnable() || device.isSsrcCheck()) {
537 logger.info("[回放消息] SSRC修正 {}->{}", ssrcInfo.getSsrc(), ssrcInResponse); 541 logger.info("[回放消息] SSRC修正 {}->{}", ssrcInfo.getSsrc(), ssrcInResponse);
538 542
539 - if (!mediaServerItem.getSsrcConfig().checkSsrc(ssrcInResponse)) { 543 + if (!ssrcFactory.checkSsrc(mediaServerItem.getId(),ssrcInResponse)) {
540 // ssrc 不可用 544 // ssrc 不可用
541 // 释放ssrc 545 // 释放ssrc
542 mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); 546 mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc());
@@ -675,7 +679,7 @@ public class PlayServiceImpl implements IPlayService { @@ -675,7 +679,7 @@ public class PlayServiceImpl implements IPlayService {
675 if (!mediaServerItem.isRtpEnable() || device.isSsrcCheck()) { 679 if (!mediaServerItem.isRtpEnable() || device.isSsrcCheck()) {
676 logger.info("[回放消息] SSRC修正 {}->{}", ssrcInfo.getSsrc(), ssrcInResponse); 680 logger.info("[回放消息] SSRC修正 {}->{}", ssrcInfo.getSsrc(), ssrcInResponse);
677 681
678 - if (!mediaServerItem.getSsrcConfig().checkSsrc(ssrcInResponse)) { 682 + if (!ssrcFactory.checkSsrc(mediaServerItem.getId(),ssrcInResponse)) {
679 // ssrc 不可用 683 // ssrc 不可用
680 // 释放ssrc 684 // 释放ssrc
681 mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc()); 685 mediaServerService.releaseSsrc(mediaServerItem.getId(), ssrcInfo.getSsrc());
src/main/java/com/genersoft/iot/vmp/utils/ConfigConst.java deleted 100644 → 0
1 -package com.genersoft.iot.vmp.utils;  
2 -  
3 -public class ConfigConst {  
4 - /**  
5 - * 播流最大并发个数  
6 - */  
7 - public static final Integer MAX_STRTEAM_COUNT = 10000;  
8 -}