| | |
| | | import com.genersoft.iot.vmp.gb28181.event.SipSubscribe; |
| | | import com.genersoft.iot.vmp.gb28181.transmit.cmd.ISIPCommanderForPlatform; |
| | | import com.genersoft.iot.vmp.gb28181.transmit.cmd.SIPRequestHeaderPlarformProvider; |
| | | import com.genersoft.iot.vmp.utils.DateUtil; |
| | | import com.genersoft.iot.vmp.media.zlm.ZLMRTPServerFactory; |
| | | import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; |
| | | import com.genersoft.iot.vmp.service.IMediaServerService; |
| | |
| | | import org.springframework.stereotype.Component; |
| | | import org.springframework.util.StringUtils; |
| | | |
| | | |
| | | import com.genersoft.iot.vmp.utils.DateUtil; |
| | | import javax.sip.*; |
| | | import javax.sip.address.SipURI; |
| | | import javax.sip.header.*; |
| | | import javax.sip.message.Request; |
| | | import java.lang.reflect.Field; |
| | | import java.net.InetAddress; |
| | | import java.text.ParseException; |
| | | import java.util.ArrayList; |
| | | import java.util.HashSet; |
| | |
| | | package com.genersoft.iot.vmp.gb28181.transmit.event.request.impl; |
| | | |
| | | import com.alibaba.fastjson.JSON; |
| | | import com.alibaba.fastjson.JSONObject; |
| | | import com.genersoft.iot.vmp.common.StreamInfo; |
| | | import com.genersoft.iot.vmp.conf.DynamicTask; |
| | | import com.genersoft.iot.vmp.gb28181.bean.*; |
| | | import com.genersoft.iot.vmp.gb28181.session.AudioBroadcastManager; |
| | |
| | | import gov.nist.javax.sip.message.SIPRequest; |
| | | import gov.nist.javax.sip.stack.SIPDialog; |
| | | import com.genersoft.iot.vmp.utils.SerializeUtils; |
| | | import org.ehcache.shadow.org.terracotta.offheapstore.storage.IntegerStorageEngine; |
| | | import org.slf4j.Logger; |
| | | import org.slf4j.LoggerFactory; |
| | | import org.springframework.beans.factory.InitializingBean; |
| | |
| | | import javax.sip.header.CallIdHeader; |
| | | import javax.sip.header.FromHeader; |
| | | import javax.sip.header.HeaderAddress; |
| | | import javax.sip.header.ToHeader; |
| | | import java.text.ParseException; |
| | | import java.util.*; |
| | | |
| | |
| | | sendRtpItem.getMediaServerId(), sendRtpItem.getApp(), sendRtpItem.getStreamId(), |
| | | sendRtpItem.getIp(), sendRtpItem.getPort(), sendRtpItem.getSsrc(), sendRtpItem.isTcp(), |
| | | sendRtpItem.getLocalPort(), sendRtpItem.getPt(), sendRtpItem.isUsePs(), sendRtpItem.isOnlyAudio()); |
| | | redisGbPlayMsgListener.sendMsgForStartSendRtpStream(sendRtpItem.getServerId(), requestPushStreamMsg, jsonObject->{ |
| | | startSendRtpStreamHand(evt, sendRtpItem, parentPlatform, jsonObject, param, callIdHeader); |
| | | redisGbPlayMsgListener.sendMsgForStartSendRtpStream(sendRtpItem.getServerId(), requestPushStreamMsg, json -> { |
| | | startSendRtpStreamHand(evt, sendRtpItem, parentPlatform, json, param, callIdHeader); |
| | | }); |
| | | }else { |
| | | JSONObject jsonObject = zlmrtpServerFactory.startSendRtpStream(mediaInfo, param); |
| | | startSendRtpStreamHand(evt, sendRtpItem, parentPlatform, jsonObject, param, callIdHeader); |
| | | JSONObject startSendRtpStreamResult = zlmrtpServerFactory.startSendRtpStream(mediaInfo, param); |
| | | startSendRtpStreamHand(evt, sendRtpItem, parentPlatform, startSendRtpStreamResult, param, callIdHeader); |
| | | } |
| | | |
| | | |
| | | } |
| | | } |
| | | } |
| | | private void startSendRtpStreamHand(RequestEvent evt, SendRtpItem sendRtpItem, ParentPlatform parentPlatform, |
| | | JSONObject jsonObject, Map<String, Object> param, CallIdHeader callIdHeader) { |
| | | if (jsonObject == null) { |
| | |
| | | import com.genersoft.iot.vmp.gb28181.transmit.event.request.ISIPRequestProcessor; |
| | | import com.genersoft.iot.vmp.gb28181.transmit.event.request.SIPRequestProcessorParent; |
| | | import com.genersoft.iot.vmp.gb28181.utils.SipUtils; |
| | | import com.genersoft.iot.vmp.gb28181.utils.XmlUtil; |
| | | import com.genersoft.iot.vmp.media.zlm.ZLMHttpHookSubscribe; |
| | | import com.genersoft.iot.vmp.media.zlm.ZLMMediaListManager; |
| | | import com.genersoft.iot.vmp.media.zlm.ZLMRESTfulUtils; |
| | | import com.genersoft.iot.vmp.media.zlm.ZLMRTPServerFactory; |
| | | import com.genersoft.iot.vmp.media.zlm.dto.MediaItem; |
| | | import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; |
| | | import com.genersoft.iot.vmp.media.zlm.dto.StreamPushItem; |
| | | import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItemLite; |
| | | import com.genersoft.iot.vmp.media.zlm.dto.StreamPushItem; |
| | | import com.genersoft.iot.vmp.service.IMediaServerService; |
| | | import com.genersoft.iot.vmp.service.IPlayService; |
| | | import com.genersoft.iot.vmp.service.IStreamPushService; |
| | |
| | | import javax.sip.message.Response; |
| | | import java.text.ParseException; |
| | | import java.time.Instant; |
| | | import java.util.Date; |
| | | import java.util.List; |
| | | import java.util.Vector; |
| | | |
| | | /** |
| | |
| | | |
| | | @Autowired |
| | | private ZLMRESTfulUtils zlmresTfulUtils; |
| | | |
| | | @Autowired |
| | | private IMediaServerService mediaServerService; |
| | | |
| | | @Autowired |
| | | private SIPProcessorObserver sipProcessorObserver; |
| | |
| | | // 查询请求是否来自上级平台\设备 |
| | | ParentPlatform platform = storager.queryParentPlatByServerGBId(requesterId); |
| | | if (platform == null) { |
| | | inviteFromDeviceHandle(evt, requesterId); |
| | | inviteFromDeviceHandle(evt, requesterId, channelId); |
| | | } else { |
| | | // 查询平台下是否有该通道 |
| | | DeviceChannel channel = storager.queryChannelInParentPlatform(requesterId, channelId); |
| | |
| | | } |
| | | } |
| | | |
| | | public void inviteFromDeviceHandle(RequestEvent evt, String requesterId) throws InvalidArgumentException, ParseException, SipException, SdpException { |
| | | public void inviteFromDeviceHandle(RequestEvent evt, String requesterId, String channelId1) throws InvalidArgumentException, ParseException, SipException, SdpException { |
| | | |
| | | // 非上级平台请求,查询是否设备请求(通常为接收语音广播的设备) |
| | | Device device = redisCatchStorage.getDevice(requesterId); |
| | | AudioBroadcastCatch audioBroadcastCatch = audioBroadcastManager.get(requesterId, channelId1); |
| | | if (audioBroadcastCatch == null) { |
| | | logger.warn("来自设备的Invite请求非语音广播,已忽略"); |
| | | responseAck(evt, Response.FORBIDDEN); |
| | | return; |
| | | } |
| | | Request request = evt.getRequest(); |
| | | if (device != null) { |
| | | logger.info("收到设备" + requesterId + "的语音广播Invite请求"); |
| | |
| | | int ssrcIndex = contentString.indexOf("y="); |
| | | if (ssrcIndex > 0) { |
| | | substring = contentString.substring(0, ssrcIndex); |
| | | ssrc = contentString.substring(ssrcIndex + 2, ssrcIndex + 12); |
| | | ssrc = contentString.substring(ssrcIndex + 2, ssrcIndex + 12).trim(); |
| | | } |
| | | ssrcIndex = substring.indexOf("f="); |
| | | if (ssrcIndex > 0) { |
| | |
| | | |
| | | // 获取支持的格式 |
| | | Vector mediaDescriptions = sdp.getMediaDescriptions(true); |
| | | |
| | | // 查看是否支持PS 负载96 |
| | | int port = -1; |
| | | //boolean recvonly = false; |
| | | boolean mediaTransmissionTCP = false; |
| | | Boolean tcpActive = null; |
| | | for (int i = 0; i < mediaDescriptions.size(); i++) { |
| | |
| | | responseAck(evt, Response.UNSUPPORTED_MEDIA_TYPE); // 不支持的格式,发415 |
| | | return; |
| | | } |
| | | String username = sdp.getOrigin().getUsername(); |
| | | String addressStr = sdp.getOrigin().getAddress(); |
| | | logger.info("设备{}请求语音流,地址:{}:{},ssrc:{}", username, addressStr, port, ssrc); |
| | | logger.info("设备{}请求语音流,地址:{}:{},ssrc:{}", requesterId, addressStr, port, ssrc); |
| | | |
| | | } else { |
| | | logger.warn("来自无效设备/平台的请求"); |
| | | responseAck(evt, Response.BAD_REQUEST); |
| | | MediaServerItem mediaServerItem = playService.getNewMediaServerItem(device); |
| | | if (mediaServerItem == null) { |
| | | logger.warn("未找到可用的zlm"); |
| | | responseAck(evt, Response.BUSY_HERE); |
| | | return; |
| | | } |
| | | SendRtpItem sendRtpItem = zlmrtpServerFactory.createSendRtpItem(mediaServerItem, addressStr, port, ssrc, requesterId, |
| | | device.getDeviceId(), audioBroadcastCatch.getChannelId(), |
| | | mediaTransmissionTCP); |
| | | if (sendRtpItem == null) { |
| | | logger.warn("服务器端口资源不足"); |
| | | responseAck(evt, Response.BUSY_HERE); |
| | | return; |
| | | } |
| | | sendRtpItem.setTcp(mediaTransmissionTCP); |
| | | if (tcpActive != null) { |
| | | sendRtpItem.setTcpActive(tcpActive); |
| | | } |
| | | String app = "broadcast"; |
| | | String stream = device.getDeviceId() + "_" + audioBroadcastCatch.getChannelId(); |
| | | |
| | | CallIdHeader callIdHeader = (CallIdHeader) request.getHeader(CallIdHeader.NAME); |
| | | sendRtpItem.setPlayType(InviteStreamType.PLAY); |
| | | sendRtpItem.setCallId(callIdHeader.getCallId()); |
| | |
| | | package com.genersoft.iot.vmp.service; |
| | | |
| | | import com.alibaba.fastjson.JSONObject; |
| | | import com.genersoft.iot.vmp.gb28181.bean.Device; |
| | | import com.genersoft.iot.vmp.media.zlm.ZLMServerConfig; |
| | | import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; |
| | | import com.genersoft.iot.vmp.service.bean.SSRCInfo; |
| | |
| | | import com.genersoft.iot.vmp.common.VideoManagerConstants; |
| | | import com.genersoft.iot.vmp.conf.SipConfig; |
| | | import com.genersoft.iot.vmp.conf.UserSetting; |
| | | import com.genersoft.iot.vmp.gb28181.bean.SsrcTransaction; |
| | | import com.genersoft.iot.vmp.gb28181.event.EventPublisher; |
| | | import com.genersoft.iot.vmp.gb28181.session.SsrcConfig; |
| | | import com.genersoft.iot.vmp.gb28181.session.VideoStreamSessionManager; |
| | |
| | | import org.springframework.transaction.TransactionStatus; |
| | | import org.springframework.util.StringUtils; |
| | | |
| | | import java.text.ParseException; |
| | | import java.text.SimpleDateFormat; |
| | | import java.time.LocalDateTime; |
| | | import java.util.*; |
| | | import java.util.stream.Collectors; |
| | | |
| | | /** |
| | | * 媒体服务器节点管理 |
| | |
| | | "postcss-url": "^7.2.1", |
| | | "rimraf": "^2.6.0", |
| | | "semver": "^5.3.0", |
| | | "shelljs": "^0.7.6", |
| | | "shelljs": "^0.8.5", |
| | | "uglifyjs-webpack-plugin": "^1.1.1", |
| | | "url-loader": "^0.5.8", |
| | | "vue-loader": "^13.3.0", |
| | |
| | | } |
| | | }, |
| | | "node_modules/shelljs": { |
| | | "version": "0.7.8", |
| | | "resolved": "https://registry.npm.taobao.org/shelljs/download/shelljs-0.7.8.tgz", |
| | | "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", |
| | | "version": "0.8.5", |
| | | "resolved": "https://registry.npmmirror.com/shelljs/-/shelljs-0.8.5.tgz", |
| | | "integrity": "sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==", |
| | | "dev": true, |
| | | "dependencies": { |
| | | "glob": "^7.0.0", |
| | |
| | | "shjs": "bin/shjs" |
| | | }, |
| | | "engines": { |
| | | "iojs": "*", |
| | | "node": ">=0.11.0" |
| | | "node": ">=4" |
| | | } |
| | | }, |
| | | "node_modules/shellwords": { |
| | |
| | | "dev": true |
| | | }, |
| | | "shelljs": { |
| | | "version": "0.7.8", |
| | | "resolved": "https://registry.npm.taobao.org/shelljs/download/shelljs-0.7.8.tgz", |
| | | "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", |
| | | "version": "0.8.5", |
| | | "resolved": "https://registry.npmmirror.com/shelljs/-/shelljs-0.8.5.tgz", |
| | | "integrity": "sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==", |
| | | "dev": true, |
| | | "requires": { |
| | | "glob": "^7.0.0", |