Commit 85b24ea06b0579dd13551fbf92a0fe243adb9792

Authored by xp.Huang
2 parents 6b070a7f 0db46d8c

Merge branch 'master_dev_msa0311' into 'master_dev'

refactor: GBT28181结构调整

See merge request yunteng/thingskit!368
Showing 41 changed files with 1576 additions and 1651 deletions

Too many changes to show.

To preserve performance only 41 of 57 files are displayed.

... ... @@ -36,7 +36,6 @@ public class TkVideoControlController extends BaseController {
36 36
37 37 @GetMapping("/start/{deviceId}/{channelId}")
38 38 @ApiOperation(value = "视频点播/预览")
39   -// @PreAuthorize("@check.checkPermissions({'SYS_ADMIN','PLATFORM_ADMIN','TENANT_ADMIN','CUSTOMER_USER'},{'api:yt:video:control:play'})")
40 39 @PreAuthorize("hasAnyAuthority('SYS_ADMIN','PLATFORM_ADMIN','TENANT_ADMIN','CUSTOMER_USER')")
41 40 public DeferredResult<ResponseResult<StreamContentDTO>> startPlay(
42 41 @PathVariable("deviceId") String tbDeviceId, @PathVariable("channelId") String channelId)
... ...
... ... @@ -3,16 +3,17 @@ package org.thingsboard.server.controller.yunteng.media;
3 3 import com.fasterxml.jackson.databind.JsonNode;
4 4 import io.swagger.annotations.Api;
5 5 import io.swagger.annotations.ApiOperation;
  6 +import javax.servlet.http.HttpServletRequest;
6 7 import lombok.RequiredArgsConstructor;
7 8 import lombok.extern.slf4j.Slf4j;
  9 +import org.json.JSONObject;
8 10 import org.springframework.web.bind.annotation.*;
  11 +import org.springframework.web.context.request.async.DeferredResult;
9 12 import org.thingsboard.server.common.data.exception.ThingsboardException;
10 13 import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
11   -import org.thingsboard.server.common.data.yunteng.dto.DeviceDTO;
12 14 import org.thingsboard.server.common.data.yunteng.dto.sip.VideoChanelDTO;
13 15 import org.thingsboard.server.common.data.yunteng.dto.sip.hook.param.*;
14 16 import org.thingsboard.server.controller.BaseController;
15   -import org.thingsboard.server.dao.yunteng.service.TkDeviceService;
16 17 import org.thingsboard.server.dao.yunteng.service.media.TkMediaServerService;
17 18 import org.thingsboard.server.dao.yunteng.service.media.TkVideoChannelService;
18 19 import org.thingsboard.server.service.yunteng.media.TkVideoControlService;
... ... @@ -57,21 +58,140 @@ public class ZLMediaKitHookController extends BaseController {
57 58 @ResponseBody
58 59 @PostMapping(value = "/on_stream_none_reader", produces = "application/json;charset=UTF-8")
59 60 @ApiOperation(value = "流无人观看时事件,用户可以通过此事件选择是否关闭无人看的流")
60   - public JsonNode onStreamNoneReader(@RequestBody OnStreamNoneReaderHookParam param) throws ThingsboardException {
  61 + public JsonNode onStreamNoneReader(@RequestBody OnStreamNoneReaderHookParam param)
  62 + throws ThingsboardException {
61 63 JsonNode result = tkMediaServerService.zlmOnStreamNoneReader(param);
62   - if(result.has(FastIotConstants.ZLMediaBody.CHANNEL_ID) &&result.has(FastIotConstants.ZLMediaBody.CAMERA_CODE)){
  64 + if (result.has(FastIotConstants.ZLMediaBody.CHANNEL_ID)
  65 + && result.has(FastIotConstants.ZLMediaBody.CAMERA_CODE)) {
63 66 String channelId = result.get(FastIotConstants.ZLMediaBody.CHANNEL_ID).asText();
64 67 String cameraCode = result.get(FastIotConstants.ZLMediaBody.CAMERA_CODE).asText();
65   - VideoChanelDTO chanelDTO = tkVideoChannelService.findVideoChannelById(cameraCode,channelId, null);
66   - controlService.byeCmdInSsrcTransaction(chanelDTO.getTenantId(),
67   - false,
68   - chanelDTO.getDeviceId(),
69   - cameraCode,channelId,result.get(FastIotConstants.ZLMediaBody.SSRCINFO_STREAM).asText(),
70   - fromDeviceRpcResponse->{
71   -
72   - });
73   - tkVideoChannelService.updateVideoChannelStreamId(null, cameraCode, channelId);//storager.stopPlay(streamInfo.getDeviceID(), streamInfo.getChannelId());
  68 + VideoChanelDTO chanelDTO =
  69 + tkVideoChannelService.findVideoChannelById(cameraCode, channelId, null);
  70 + controlService.byeCmdInSsrcTransaction(
  71 + chanelDTO.getTenantId(),
  72 + false,
  73 + chanelDTO.getDeviceId(),
  74 + cameraCode,
  75 + channelId,
  76 + result.get(FastIotConstants.ZLMediaBody.SSRCINFO_STREAM).asText(),
  77 + fromDeviceRpcResponse -> {});
  78 + tkVideoChannelService.updateVideoChannelStreamId(
  79 + null,
  80 + cameraCode,
  81 + channelId); // storager.stopPlay(streamInfo.getDeviceID(), streamInfo.getChannelId());
74 82 }
75 83 return result;
76 84 }
  85 +
  86 + /** 流未找到事件,用户可以在此事件触发时,立即去拉流,这样可以实现按需拉流;此事件对回复不敏感。 */
  87 + @ResponseBody
  88 + @PostMapping(value = "/on_stream_not_found", produces = "application/json;charset=UTF-8")
  89 + public DeferredResult<HookResult> onStreamNotFound(@RequestBody OnStreamNotFoundHookParam param) {
  90 + // log.error("WEBHOOK流未找到【on_stream_not_found】,API参数【{}】",JSONObject.toJSONString(param));
  91 +
  92 + DeferredResult<HookResult> defaultResult = new DeferredResult<>();
  93 +
  94 + // MediaServerItem mediaInfo = mediaServerService.getOne(param.getMediaServerId());
  95 + // if (!userSetting.isAutoApplyPlay() || mediaInfo == null) {
  96 + // defaultResult.setResult(new HookResult(ErrorCode.ERROR404.getCode(),
  97 + // ErrorCode.ERROR404.getMsg()));
  98 + // return defaultResult;
  99 + // }
  100 + //
  101 + // if ("rtp".equals(param.getApp())) {
  102 + // String[] s = param.getStream().split("_");
  103 + // if (!mediaInfo.isRtpEnable() || s.length != 2) {
  104 + // defaultResult.setResult(HookResult.SUCCESS());
  105 + // return defaultResult;
  106 + // }
  107 + // String deviceId = s[0];
  108 + // String channelId = s[1];
  109 + // Device device = redisCatchStorage.getDevice(deviceId);
  110 + // if (device == null) {
  111 + // defaultResult.setResult(new HookResult(ErrorCode.ERROR404.getCode(),
  112 + // ErrorCode.ERROR404.getMsg()));
  113 + // return defaultResult;
  114 + // }
  115 + // DeviceChannel deviceChannel = storager.queryChannel(deviceId, channelId);
  116 + // if (deviceChannel == null) {
  117 + // defaultResult.setResult(new HookResult(ErrorCode.ERROR404.getCode(),
  118 + // ErrorCode.ERROR404.getMsg()));
  119 + // return defaultResult;
  120 + // }
  121 + // logger.info("[ZLM HOOK] 流未找到, 发起自动点播:{}->{}->{}/{}", param.getMediaServerId(),
  122 + // param.getSchema(), param.getApp(), param.getStream());
  123 + // RequestMessage msg = new RequestMessage();
  124 + // String key = DeferredResultHolder.CALLBACK_CMD_PLAY + deviceId + channelId;
  125 + // boolean exist = resultHolder.exist(key, null);
  126 + // msg.setKey(key);
  127 + // String uuid = UUID.randomUUID().toString();
  128 + // msg.setId(uuid);
  129 + // DeferredResult<HookResult> result = new
  130 + // DeferredResult<>(userSetting.getPlayTimeout().longValue());
  131 + // DeferredResultEx<HookResult> deferredResultEx = new DeferredResultEx<>(result);
  132 + //
  133 + // result.onTimeout(() -> {
  134 + // logger.info("点播接口等待超时");
  135 + // // 释放rtpserver
  136 + // msg.setData(new HookResult(ErrorCode.ERROR100.getCode(), "点播超时"));
  137 + // resultHolder.invokeResult(msg);
  138 + // });
  139 + // // TODO 在点播未成功的情况下在此调用接口点播会导致返回的流地址ip错误
  140 + // deferredResultEx.setFilter(result1 -> {
  141 + // WVPResult<StreamInfo> wvpResult1 = (WVPResult<StreamInfo>) result1;
  142 + // HookResult resultForEnd = new HookResult();
  143 + // resultForEnd.setCode(wvpResult1.getCode());
  144 + // resultForEnd.setMsg(wvpResult1.getMsg());
  145 + // return resultForEnd;
  146 + // });
  147 + //
  148 + // // 录像查询以channelId作为deviceId查询
  149 + // resultHolder.put(key, uuid, deferredResultEx);
  150 + //
  151 + // if (!exist) {
  152 + // playService.play(mediaInfo, deviceId, channelId, null, eventResult -> {
  153 + // msg.setData(new HookResult(eventResult.statusCode, eventResult.msg));
  154 + // resultHolder.invokeResult(msg);
  155 + // }, null);
  156 + // }
  157 + // return result;
  158 + // } else {
  159 + // // 拉流代理
  160 + // StreamProxyItem streamProxyByAppAndStream =
  161 + // streamProxyService.getStreamProxyByAppAndStream(param.getApp(), param.getStream());
  162 + // if (streamProxyByAppAndStream != null &&
  163 + // streamProxyByAppAndStream.isEnable_disable_none_reader()) {
  164 + // streamProxyService.start(param.getApp(), param.getStream());
  165 + // }
  166 + // DeferredResult<HookResult> result = new DeferredResult<>();
  167 + // result.setResult(HookResult.SUCCESS());
  168 + // return result;
  169 + // }
  170 + return defaultResult;
  171 + }
  172 +
  173 + /** 服务器启动事件,可以用于监听服务器崩溃重启;此事件对回复不敏感。 */
  174 + @ResponseBody
  175 + @PostMapping(value = "/on_server_started", produces = "application/json;charset=UTF-8")
  176 + public HookResult onServerStarted(
  177 + HttpServletRequest request, @RequestBody JSONObject jsonObject) {
  178 + //
  179 + // log.error("WEBHOOK服务器已启动【on_server_started】,请求对象【{}】,API参数【{}】",JSONObject.toJSONString(request),jsonObject);
  180 + // jsonObject.put("ip", request.getRemoteAddr());
  181 + // ZLMServerConfig zlmServerConfig = JSON.to(ZLMServerConfig.class, jsonObject);
  182 + // zlmServerConfig.setIp(request.getRemoteAddr());
  183 + // logger.info("[ZLM HOOK] zlm 启动 " + zlmServerConfig.getGeneralMediaServerId());
  184 + // taskExecutor.execute(() -> {
  185 + // List<ZlmHttpHookSubscribe.Event> subscribes =
  186 + // this.subscribe.getSubscribes(HookType.on_server_started);
  187 + // if (subscribes != null && subscribes.size() > 0) {
  188 + // for (ZlmHttpHookSubscribe.Event subscribe : subscribes) {
  189 + // subscribe.response(null, jsonObject);
  190 + // }
  191 + // }
  192 + // mediaServerService.zlmServerOnline(zlmServerConfig);
  193 + // });
  194 +
  195 + return HookResult.SUCCESS();
  196 + }
77 197 }
... ...
1 1 /**
2 2 * Copyright © 2016-2022 The Thingsboard Authors
3 3 *
4   - * Licensed under the Apache License, Version 2.0 (the "License");
5   - * you may not use this file except in compliance with the License.
6   - * You may obtain a copy of the License at
  4 + * <p>Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file
  5 + * except in compliance with the License. You may obtain a copy of the License at
7 6 *
8   - * http://www.apache.org/licenses/LICENSE-2.0
  7 + * <p>http://www.apache.org/licenses/LICENSE-2.0
9 8 *
10   - * Unless required by applicable law or agreed to in writing, software
11   - * distributed under the License is distributed on an "AS IS" BASIS,
12   - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   - * See the License for the specific language governing permissions and
  9 + * <p>Unless required by applicable law or agreed to in writing, software distributed under the
  10 + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
  11 + * express or implied. See the License for the specific language governing permissions and
14 12 * limitations under the License.
15 13 */
16 14 package org.thingsboard.server.service.transport;
... ... @@ -37,7 +35,6 @@ import java.util.concurrent.locks.ReentrantLock;
37 35 import java.util.stream.Collectors;
38 36 import lombok.RequiredArgsConstructor;
39 37 import lombok.extern.slf4j.Slf4j;
40   -import org.apache.zookeeper.Op;
41 38 import org.springframework.stereotype.Service;
42 39 import org.thingsboard.common.util.JacksonUtil;
43 40 import org.thingsboard.server.cache.ota.OtaPackageDataCache;
... ... @@ -74,13 +71,15 @@ import org.thingsboard.server.common.data.relation.EntityRelation;
74 71 import org.thingsboard.server.common.data.security.DeviceCredentials;
75 72 import org.thingsboard.server.common.data.security.DeviceCredentialsType;
76 73 import org.thingsboard.server.common.data.yunteng.common.media.VideoStreamSessionManager;
  74 +import org.thingsboard.server.common.data.yunteng.config.media.ZLMediaKitServerConfig;
77 75 import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
78 76 import org.thingsboard.server.common.data.yunteng.dto.DeviceDTO;
79 77 import org.thingsboard.server.common.data.yunteng.dto.TkDeviceScriptDTO;
  78 +import org.thingsboard.server.common.data.yunteng.dto.sip.MediaServerDTO;
80 79 import org.thingsboard.server.common.data.yunteng.dto.sip.SipDeviceDTO;
81   -import org.thingsboard.server.common.data.yunteng.dto.sip.SsrcTransactionDTO;
82 80 import org.thingsboard.server.common.data.yunteng.dto.sip.VideoChanelDTO;
83 81 import org.thingsboard.server.common.data.yunteng.enums.VideoCmdEnum;
  82 +import org.thingsboard.server.common.data.yunteng.utils.ZLMediaKitRestFulUtils;
84 83 import org.thingsboard.server.common.msg.EncryptionUtil;
85 84 import org.thingsboard.server.common.msg.TbMsg;
86 85 import org.thingsboard.server.common.msg.TbMsgDataType;
... ... @@ -99,6 +98,7 @@ import org.thingsboard.server.dao.yunteng.entities.TkVideoChannelEntity;
99 98 import org.thingsboard.server.dao.yunteng.service.TkDeviceScriptService;
100 99 import org.thingsboard.server.dao.yunteng.service.TkDeviceService;
101 100 import org.thingsboard.server.dao.yunteng.service.media.TkMediaServerNodeService;
  101 +import org.thingsboard.server.dao.yunteng.service.media.TkMediaServerService;
102 102 import org.thingsboard.server.dao.yunteng.service.media.TkVideoChannelService;
103 103 import org.thingsboard.server.gen.transport.TransportProtos;
104 104 import org.thingsboard.server.gen.transport.TransportProtos.DeviceInfoProto;
... ... @@ -126,650 +126,891 @@ import org.thingsboard.server.service.install.DefaultSystemDataLoaderService;
126 126 import org.thingsboard.server.service.profile.TbDeviceProfileCache;
127 127 import org.thingsboard.server.service.resource.TbResourceService;
128 128
129   -/**
130   - * Created by ashvayka on 05.10.18.
131   - */
  129 +/** Created by ashvayka on 05.10.18. */
132 130 @Slf4j
133 131 @Service
134 132 @TbCoreComponent
135 133 @RequiredArgsConstructor
136 134 public class DefaultTransportApiService implements TransportApiService {
137 135
138   - private static final ObjectMapper mapper = new ObjectMapper();
139   -
140   - private final TbDeviceProfileCache deviceProfileCache;
141   - private final TbTenantProfileCache tenantProfileCache;
142   - private final TbApiUsageStateService apiUsageStateService;
143   - private final DeviceService deviceService;
144   - private final TkDeviceService ytDeviceService;
145   - private final TkDeviceScriptService scriptService;
146   - private final TkVideoChannelService channelService;
147   - private final TkMediaServerNodeService mediaServerNodeService;
148   - private final VideoStreamSessionManager videoStreamSessionManager;
149   -
150   - private final RelationService relationService;
151   - private final DeviceCredentialsService deviceCredentialsService;
152   - private final DbCallbackExecutorService dbCallbackExecutorService;
153   - private final TbClusterService tbClusterService;
154   - private final DataDecodingEncodingService dataDecodingEncodingService;
155   - private final DeviceProvisionService deviceProvisionService;
156   - private final TbResourceService resourceService;
157   - private final OtaPackageService otaPackageService;
158   - private final OtaPackageDataCache otaPackageDataCache;
159   -
160   - private final ConcurrentMap<String, ReentrantLock> deviceCreationLocks = new ConcurrentHashMap<>();
161   -
162   - private static boolean checkIsMqttCredentials(DeviceCredentials credentials) {
163   - return credentials != null && DeviceCredentialsType.MQTT_BASIC.equals(credentials.getCredentialsType());
  136 + private static final ObjectMapper mapper = new ObjectMapper();
  137 +
  138 + private final TbDeviceProfileCache deviceProfileCache;
  139 + private final TbTenantProfileCache tenantProfileCache;
  140 + private final TbApiUsageStateService apiUsageStateService;
  141 + private final DeviceService deviceService;
  142 + private final TkDeviceService ytDeviceService;
  143 + private final TkDeviceScriptService scriptService;
  144 + private final TkVideoChannelService channelService;
  145 + private final TkMediaServerNodeService mediaServerNodeService;
  146 + private final VideoStreamSessionManager videoStreamSessionManager;
  147 + private final TkMediaServerService mediaServerService;
  148 + private final ZLMediaKitRestFulUtils zlMediaKitRestFulUtils;
  149 +
  150 + private final RelationService relationService;
  151 + private final DeviceCredentialsService deviceCredentialsService;
  152 + private final DbCallbackExecutorService dbCallbackExecutorService;
  153 + private final TbClusterService tbClusterService;
  154 + private final DataDecodingEncodingService dataDecodingEncodingService;
  155 + private final DeviceProvisionService deviceProvisionService;
  156 + private final TbResourceService resourceService;
  157 + private final OtaPackageService otaPackageService;
  158 + private final OtaPackageDataCache otaPackageDataCache;
  159 +
  160 + private final ConcurrentMap<String, ReentrantLock> deviceCreationLocks =
  161 + new ConcurrentHashMap<>();
  162 +
  163 + private static boolean checkIsMqttCredentials(DeviceCredentials credentials) {
  164 + return credentials != null
  165 + && DeviceCredentialsType.MQTT_BASIC.equals(credentials.getCredentialsType());
  166 + }
  167 +
  168 + @Override
  169 + public ListenableFuture<TbProtoQueueMsg<TransportApiResponseMsg>> handle(
  170 + TbProtoQueueMsg<TransportApiRequestMsg> tbProtoQueueMsg) {
  171 + TransportApiRequestMsg transportApiRequestMsg = tbProtoQueueMsg.getValue();
  172 + ListenableFuture<TransportApiResponseMsg> result = null;
  173 +
  174 + if (transportApiRequestMsg.hasValidateTokenRequestMsg()) {
  175 + ValidateDeviceTokenRequestMsg msg = transportApiRequestMsg.getValidateTokenRequestMsg();
  176 + result = validateCredentials(msg.getToken(), DeviceCredentialsType.ACCESS_TOKEN);
  177 + } else if (transportApiRequestMsg.hasValidateBasicMqttCredRequestMsg()) {
  178 + TransportProtos.ValidateBasicMqttCredRequestMsg msg =
  179 + transportApiRequestMsg.getValidateBasicMqttCredRequestMsg();
  180 + result = validateCredentials(msg);
  181 + } else if (transportApiRequestMsg.hasValidateX509CertRequestMsg()) {
  182 + ValidateDeviceX509CertRequestMsg msg = transportApiRequestMsg.getValidateX509CertRequestMsg();
  183 + result = validateCredentials(msg.getHash(), DeviceCredentialsType.X509_CERTIFICATE);
  184 + } else if (transportApiRequestMsg.hasGetOrCreateDeviceRequestMsg()) {
  185 + result = handle(transportApiRequestMsg.getGetOrCreateDeviceRequestMsg());
  186 + } else if (transportApiRequestMsg.hasEntityProfileRequestMsg()) {
  187 + result = handle(transportApiRequestMsg.getEntityProfileRequestMsg());
  188 + } else if (transportApiRequestMsg.hasLwM2MRequestMsg()) {
  189 + result = handle(transportApiRequestMsg.getLwM2MRequestMsg());
  190 + } else if (transportApiRequestMsg.hasValidateDeviceLwM2MCredentialsRequestMsg()) {
  191 + ValidateDeviceLwM2MCredentialsRequestMsg msg =
  192 + transportApiRequestMsg.getValidateDeviceLwM2MCredentialsRequestMsg();
  193 + result = validateCredentials(msg.getCredentialsId(), DeviceCredentialsType.LWM2M_CREDENTIALS);
  194 + } else if (transportApiRequestMsg.hasProvisionDeviceRequestMsg()) {
  195 + result = handle(transportApiRequestMsg.getProvisionDeviceRequestMsg());
  196 + } else if (transportApiRequestMsg.hasResourceRequestMsg()) {
  197 + result = handle(transportApiRequestMsg.getResourceRequestMsg());
  198 + } else if (transportApiRequestMsg.hasSnmpDevicesRequestMsg()) {
  199 + result = handle(transportApiRequestMsg.getSnmpDevicesRequestMsg());
  200 + } else if (transportApiRequestMsg.hasDeviceRequestMsg()) {
  201 + result = handle(transportApiRequestMsg.getDeviceRequestMsg());
  202 + } else if (transportApiRequestMsg.hasDeviceCredentialsRequestMsg()) {
  203 + result = handle(transportApiRequestMsg.getDeviceCredentialsRequestMsg());
  204 + } else if (transportApiRequestMsg.hasOtaPackageRequestMsg()) {
  205 + result = handle(transportApiRequestMsg.getOtaPackageRequestMsg());
164 206 }
165 207
166   - @Override
167   - public ListenableFuture<TbProtoQueueMsg<TransportApiResponseMsg>> handle(TbProtoQueueMsg<TransportApiRequestMsg> tbProtoQueueMsg) {
168   - TransportApiRequestMsg transportApiRequestMsg = tbProtoQueueMsg.getValue();
169   - ListenableFuture<TransportApiResponseMsg> result = null;
170   -
171   - if (transportApiRequestMsg.hasValidateTokenRequestMsg()) {
172   - ValidateDeviceTokenRequestMsg msg = transportApiRequestMsg.getValidateTokenRequestMsg();
173   - result = validateCredentials(msg.getToken(), DeviceCredentialsType.ACCESS_TOKEN);
174   - } else if (transportApiRequestMsg.hasValidateBasicMqttCredRequestMsg()) {
175   - TransportProtos.ValidateBasicMqttCredRequestMsg msg = transportApiRequestMsg.getValidateBasicMqttCredRequestMsg();
176   - result = validateCredentials(msg);
177   - } else if (transportApiRequestMsg.hasValidateX509CertRequestMsg()) {
178   - ValidateDeviceX509CertRequestMsg msg = transportApiRequestMsg.getValidateX509CertRequestMsg();
179   - result = validateCredentials(msg.getHash(), DeviceCredentialsType.X509_CERTIFICATE);
180   - } else if (transportApiRequestMsg.hasGetOrCreateDeviceRequestMsg()) {
181   - result = handle(transportApiRequestMsg.getGetOrCreateDeviceRequestMsg());
182   - } else if (transportApiRequestMsg.hasEntityProfileRequestMsg()) {
183   - result = handle(transportApiRequestMsg.getEntityProfileRequestMsg());
184   - } else if (transportApiRequestMsg.hasLwM2MRequestMsg()) {
185   - result = handle(transportApiRequestMsg.getLwM2MRequestMsg());
186   - } else if (transportApiRequestMsg.hasValidateDeviceLwM2MCredentialsRequestMsg()) {
187   - ValidateDeviceLwM2MCredentialsRequestMsg msg = transportApiRequestMsg.getValidateDeviceLwM2MCredentialsRequestMsg();
188   - result = validateCredentials(msg.getCredentialsId(), DeviceCredentialsType.LWM2M_CREDENTIALS);
189   - } else if (transportApiRequestMsg.hasProvisionDeviceRequestMsg()) {
190   - result = handle(transportApiRequestMsg.getProvisionDeviceRequestMsg());
191   - } else if (transportApiRequestMsg.hasResourceRequestMsg()) {
192   - result = handle(transportApiRequestMsg.getResourceRequestMsg());
193   - } else if (transportApiRequestMsg.hasSnmpDevicesRequestMsg()) {
194   - result = handle(transportApiRequestMsg.getSnmpDevicesRequestMsg());
195   - } else if (transportApiRequestMsg.hasDeviceRequestMsg()) {
196   - result = handle(transportApiRequestMsg.getDeviceRequestMsg());
197   - } else if (transportApiRequestMsg.hasDeviceCredentialsRequestMsg()) {
198   - result = handle(transportApiRequestMsg.getDeviceCredentialsRequestMsg());
199   - } else if (transportApiRequestMsg.hasOtaPackageRequestMsg()) {
200   - result = handle(transportApiRequestMsg.getOtaPackageRequestMsg());
201   - }
202   -
203   - //Thingskit function
204   - else if (transportApiRequestMsg.hasScript()) {
205   - result = handle(transportApiRequestMsg.getScript());
206   - }
207   - else if (transportApiRequestMsg.hasGbt28181RequestMsg()) {
208   - result = handleGbt(transportApiRequestMsg.getGbt28181RequestMsg());
209   - }
210   -
211   -
212   - return Futures.transform(Optional.ofNullable(result).orElseGet(this::getEmptyTransportApiResponseFuture),
213   - value -> new TbProtoQueueMsg<>(tbProtoQueueMsg.getKey(), value, tbProtoQueueMsg.getHeaders()),
214   - MoreExecutors.directExecutor());
  208 + // Thingskit function
  209 + else if (transportApiRequestMsg.hasScript()) {
  210 + result = handle(transportApiRequestMsg.getScript());
  211 + } else if (transportApiRequestMsg.hasGbt28181RequestMsg()) {
  212 + result = handleGbt(transportApiRequestMsg.getGbt28181RequestMsg());
  213 + } else if (transportApiRequestMsg.hasGbt28181MediaServerMsg()) {
  214 + result = handleGbtMedia(transportApiRequestMsg.getGbt28181MediaServerMsg());
215 215 }
216 216
217   - private ListenableFuture<TransportApiResponseMsg> validateCredentials(String credentialsId, DeviceCredentialsType credentialsType) {
218   - //TODO: Make async and enable caching
219   - DeviceCredentials credentials = deviceCredentialsService.findDeviceCredentialsByCredentialsId(credentialsId);
220   - if (credentials != null && credentials.getCredentialsType() == credentialsType) {
221   - return getDeviceInfo(credentials);
222   - } else {
223   - return getEmptyTransportApiResponseFuture();
224   - }
  217 + return Futures.transform(
  218 + Optional.ofNullable(result).orElseGet(this::getEmptyTransportApiResponseFuture),
  219 + value ->
  220 + new TbProtoQueueMsg<>(tbProtoQueueMsg.getKey(), value, tbProtoQueueMsg.getHeaders()),
  221 + MoreExecutors.directExecutor());
  222 + }
  223 +
  224 + private ListenableFuture<TransportApiResponseMsg> validateCredentials(
  225 + String credentialsId, DeviceCredentialsType credentialsType) {
  226 + // TODO: Make async and enable caching
  227 + DeviceCredentials credentials =
  228 + deviceCredentialsService.findDeviceCredentialsByCredentialsId(credentialsId);
  229 + if (credentials != null && credentials.getCredentialsType() == credentialsType) {
  230 + return getDeviceInfo(credentials);
  231 + } else {
  232 + return getEmptyTransportApiResponseFuture();
225 233 }
226   -
227   - private ListenableFuture<TransportApiResponseMsg> validateCredentials(TransportProtos.ValidateBasicMqttCredRequestMsg mqtt) {
228   - DeviceCredentials credentials;
229   - if (StringUtils.isEmpty(mqtt.getUserName())) {
230   - credentials = checkMqttCredentials(mqtt, EncryptionUtil.getSha3Hash(mqtt.getClientId()));
231   - if (credentials != null) {
232   - return getDeviceInfo(credentials);
233   - } else {
234   - return getEmptyTransportApiResponseFuture();
235   - }
  234 + }
  235 +
  236 + private ListenableFuture<TransportApiResponseMsg> validateCredentials(
  237 + TransportProtos.ValidateBasicMqttCredRequestMsg mqtt) {
  238 + DeviceCredentials credentials;
  239 + if (StringUtils.isEmpty(mqtt.getUserName())) {
  240 + credentials = checkMqttCredentials(mqtt, EncryptionUtil.getSha3Hash(mqtt.getClientId()));
  241 + if (credentials != null) {
  242 + return getDeviceInfo(credentials);
  243 + } else {
  244 + return getEmptyTransportApiResponseFuture();
  245 + }
  246 + } else {
  247 + credentials =
  248 + deviceCredentialsService.findDeviceCredentialsByCredentialsId(
  249 + EncryptionUtil.getSha3Hash("|", mqtt.getClientId(), mqtt.getUserName()));
  250 + if (checkIsMqttCredentials(credentials)) {
  251 + var validationResult = validateMqttCredentials(mqtt, credentials);
  252 + if (VALID.equals(validationResult)) {
  253 + return getDeviceInfo(credentials);
  254 + } else if (PASSWORD_MISMATCH.equals(validationResult)) {
  255 + return getEmptyTransportApiResponseFuture();
236 256 } else {
237   - credentials = deviceCredentialsService.findDeviceCredentialsByCredentialsId(
238   - EncryptionUtil.getSha3Hash("|", mqtt.getClientId(), mqtt.getUserName()));
239   - if (checkIsMqttCredentials(credentials)) {
240   - var validationResult = validateMqttCredentials(mqtt, credentials);
241   - if (VALID.equals(validationResult)) {
242   - return getDeviceInfo(credentials);
243   - } else if (PASSWORD_MISMATCH.equals(validationResult)) {
244   - return getEmptyTransportApiResponseFuture();
245   - } else {
246   - return validateUserNameCredentials(mqtt);
247   - }
248   - } else {
249   - return validateUserNameCredentials(mqtt);
250   - }
  257 + return validateUserNameCredentials(mqtt);
251 258 }
  259 + } else {
  260 + return validateUserNameCredentials(mqtt);
  261 + }
252 262 }
253   -
254   - private ListenableFuture<TransportApiResponseMsg> validateUserNameCredentials(TransportProtos.ValidateBasicMqttCredRequestMsg mqtt) {
255   - DeviceCredentials credentials = deviceCredentialsService.findDeviceCredentialsByCredentialsId(mqtt.getUserName());
256   - if (credentials != null) {
257   - switch (credentials.getCredentialsType()) {
258   - case ACCESS_TOKEN:
259   - return getDeviceInfo(credentials);
260   - case MQTT_BASIC:
261   - if (VALID.equals(validateMqttCredentials(mqtt, credentials))) {
262   - return getDeviceInfo(credentials);
263   - } else {
264   - return getEmptyTransportApiResponseFuture();
265   - }
266   - }
267   - }
268   - return getEmptyTransportApiResponseFuture();
  263 + }
  264 +
  265 + private ListenableFuture<TransportApiResponseMsg> validateUserNameCredentials(
  266 + TransportProtos.ValidateBasicMqttCredRequestMsg mqtt) {
  267 + DeviceCredentials credentials =
  268 + deviceCredentialsService.findDeviceCredentialsByCredentialsId(mqtt.getUserName());
  269 + if (credentials != null) {
  270 + switch (credentials.getCredentialsType()) {
  271 + case ACCESS_TOKEN:
  272 + return getDeviceInfo(credentials);
  273 + case MQTT_BASIC:
  274 + if (VALID.equals(validateMqttCredentials(mqtt, credentials))) {
  275 + return getDeviceInfo(credentials);
  276 + } else {
  277 + return getEmptyTransportApiResponseFuture();
  278 + }
  279 + }
269 280 }
270   -
271   - private DeviceCredentials checkMqttCredentials(TransportProtos.ValidateBasicMqttCredRequestMsg clientCred, String credId) {
272   - return checkMqttCredentials(clientCred, deviceCredentialsService.findDeviceCredentialsByCredentialsId(credId));
  281 + return getEmptyTransportApiResponseFuture();
  282 + }
  283 +
  284 + private DeviceCredentials checkMqttCredentials(
  285 + TransportProtos.ValidateBasicMqttCredRequestMsg clientCred, String credId) {
  286 + return checkMqttCredentials(
  287 + clientCred, deviceCredentialsService.findDeviceCredentialsByCredentialsId(credId));
  288 + }
  289 +
  290 + private DeviceCredentials checkMqttCredentials(
  291 + TransportProtos.ValidateBasicMqttCredRequestMsg clientCred,
  292 + DeviceCredentials deviceCredentials) {
  293 + if (deviceCredentials != null
  294 + && deviceCredentials.getCredentialsType() == DeviceCredentialsType.MQTT_BASIC) {
  295 + if (VALID.equals(validateMqttCredentials(clientCred, deviceCredentials))) {
  296 + return deviceCredentials;
  297 + }
273 298 }
274   -
275   - private DeviceCredentials checkMqttCredentials(TransportProtos.ValidateBasicMqttCredRequestMsg clientCred, DeviceCredentials deviceCredentials) {
276   - if (deviceCredentials != null && deviceCredentials.getCredentialsType() == DeviceCredentialsType.MQTT_BASIC) {
277   - if (VALID.equals(validateMqttCredentials(clientCred, deviceCredentials))) {
278   - return deviceCredentials;
279   - }
280   - }
281   - return null;
  299 + return null;
  300 + }
  301 +
  302 + private BasicCredentialsValidationResult validateMqttCredentials(
  303 + TransportProtos.ValidateBasicMqttCredRequestMsg clientCred,
  304 + DeviceCredentials deviceCredentials) {
  305 + BasicMqttCredentials dbCred =
  306 + JacksonUtil.fromString(deviceCredentials.getCredentialsValue(), BasicMqttCredentials.class);
  307 + if (!StringUtils.isEmpty(dbCred.getClientId())
  308 + && !dbCred.getClientId().equals(clientCred.getClientId())) {
  309 + return BasicCredentialsValidationResult.HASH_MISMATCH;
282 310 }
283   -
284   - private BasicCredentialsValidationResult validateMqttCredentials(TransportProtos.ValidateBasicMqttCredRequestMsg clientCred, DeviceCredentials deviceCredentials) {
285   - BasicMqttCredentials dbCred = JacksonUtil.fromString(deviceCredentials.getCredentialsValue(), BasicMqttCredentials.class);
286   - if (!StringUtils.isEmpty(dbCred.getClientId()) && !dbCred.getClientId().equals(clientCred.getClientId())) {
287   - return BasicCredentialsValidationResult.HASH_MISMATCH;
288   - }
289   - if (!StringUtils.isEmpty(dbCred.getUserName()) && !dbCred.getUserName().equals(clientCred.getUserName())) {
290   - return BasicCredentialsValidationResult.HASH_MISMATCH;
291   - }
292   - if (!StringUtils.isEmpty(dbCred.getPassword())) {
293   - if (StringUtils.isEmpty(clientCred.getPassword())) {
294   - return BasicCredentialsValidationResult.PASSWORD_MISMATCH;
295   - } else {
296   - return dbCred.getPassword().equals(clientCred.getPassword()) ? VALID : BasicCredentialsValidationResult.PASSWORD_MISMATCH;
297   - }
298   - }
299   - return VALID;
  311 + if (!StringUtils.isEmpty(dbCred.getUserName())
  312 + && !dbCred.getUserName().equals(clientCred.getUserName())) {
  313 + return BasicCredentialsValidationResult.HASH_MISMATCH;
300 314 }
301   -
302   - private ListenableFuture<TransportApiResponseMsg> handle(GetOrCreateDeviceFromGatewayRequestMsg requestMsg) {
303   - DeviceId gatewayId = new DeviceId(new UUID(requestMsg.getGatewayIdMSB(), requestMsg.getGatewayIdLSB()));
304   - ListenableFuture<Device> gatewayFuture = deviceService.findDeviceByIdAsync(TenantId.SYS_TENANT_ID, gatewayId);
305   - return Futures.transform(gatewayFuture, gateway -> {
306   - Lock deviceCreationLock = deviceCreationLocks.computeIfAbsent(requestMsg.getDeviceName(), id -> new ReentrantLock());
307   - deviceCreationLock.lock();
308   - try {
309   -
310   - //Thingskit function
311   - String slaveName = requestMsg.getDeviceName();
312   - if(gateway.getDeviceData().getTransportConfiguration().getType() == DeviceTransportType.TCP) {
313   - DeviceDTO iotDev = ytDeviceService.findSlaveDevice(gateway.getTenantId().getId().toString()
314   - , gateway.getId().getId().toString()
315   - ,slaveName);
316   - if(iotDev == null ){
317   - GetOrCreateDeviceFromGatewayResponseMsg.Builder builder = GetOrCreateDeviceFromGatewayResponseMsg.newBuilder();
318   - return TransportApiResponseMsg.newBuilder()
319   - .setGetOrCreateDeviceResponseMsg(builder.build())
320   - .build();
321   - }
322   - slaveName = iotDev.getName();
323   - }
324   -
325   - Device device = deviceService.findDeviceByTenantIdAndName(gateway.getTenantId(), slaveName);
326   -
327   - if (device == null) {
328   - TenantId tenantId = gateway.getTenantId();
329   - device = new Device();
330   - device.setTenantId(tenantId);
331   - device.setName(requestMsg.getDeviceName());
332   - device.setType(requestMsg.getDeviceType());
333   - device.setCustomerId(gateway.getCustomerId());
334   - DeviceProfile deviceProfile = deviceProfileCache.findOrCreateDeviceProfile(gateway.getTenantId(), DefaultSystemDataLoaderService.DEFAULT_DEVICE_TYPE);
335   - device.setDeviceProfileId(deviceProfile.getId());
336   - ObjectNode additionalInfo = JacksonUtil.newObjectNode();
337   - additionalInfo.put(DataConstants.LAST_CONNECTED_GATEWAY, gatewayId.toString());
338   - device.setAdditionalInfo(additionalInfo);
339   - Device savedDevice = deviceService.saveDevice(device);
340   -
341   -
342   - //Thingskit function
343   - ytDeviceService.saveSlaveDevice(savedDevice.getId().getId().toString(), savedDevice.getName(),deviceProfile.getId().getId().toString(), gateway.getId().getId().toString(),gateway.getCreatedTime());
344   -
345   -
346   - tbClusterService.onDeviceUpdated(savedDevice, null);
347   - device = savedDevice;
348   -
349   - relationService.saveRelationAsync(TenantId.SYS_TENANT_ID, new EntityRelation(gateway.getId(), device.getId(), "Created"));
350   -
351   - TbMsgMetaData metaData = new TbMsgMetaData();
352   - CustomerId customerId = gateway.getCustomerId();
353   - if (customerId != null && !customerId.isNullUid()) {
354   - metaData.putValue("customerId", customerId.toString());
355   - }
356   - metaData.putValue("gatewayId", gatewayId.toString());
357   -
358   - DeviceId deviceId = device.getId();
359   - ObjectNode entityNode = mapper.valueToTree(device);
360   - TbMsg tbMsg = TbMsg.newMsg(DataConstants.ENTITY_CREATED, deviceId, customerId, metaData, TbMsgDataType.JSON, mapper.writeValueAsString(entityNode));
361   - tbClusterService.pushMsgToRuleEngine(tenantId, deviceId, tbMsg, null);
362   - } else {
363   - JsonNode deviceAdditionalInfo = device.getAdditionalInfo();
364   - if (deviceAdditionalInfo == null) {
365   - deviceAdditionalInfo = JacksonUtil.newObjectNode();
366   - }
367   - if (deviceAdditionalInfo.isObject() &&
368   - (!deviceAdditionalInfo.has(DataConstants.LAST_CONNECTED_GATEWAY)
369   - || !gatewayId.toString().equals(deviceAdditionalInfo.get(DataConstants.LAST_CONNECTED_GATEWAY).asText()))) {
370   - ObjectNode newDeviceAdditionalInfo = (ObjectNode) deviceAdditionalInfo;
371   - newDeviceAdditionalInfo.put(DataConstants.LAST_CONNECTED_GATEWAY, gatewayId.toString());
372   - Device savedDevice = deviceService.saveDevice(device);
373   - tbClusterService.onDeviceUpdated(savedDevice, device);
374   - }
375   - }
376   - GetOrCreateDeviceFromGatewayResponseMsg.Builder builder = GetOrCreateDeviceFromGatewayResponseMsg.newBuilder()
377   - .setDeviceInfo(getDeviceInfoProto(device));
378   - DeviceProfile deviceProfile = deviceProfileCache.get(device.getTenantId(), device.getDeviceProfileId());
379   - if (deviceProfile != null) {
380   - builder.setProfileBody(ByteString.copyFrom(dataDecodingEncodingService.encode(deviceProfile)));
381   - } else {
382   - log.warn("[{}] Failed to find device profile [{}] for device. ", device.getId(), device.getDeviceProfileId());
383   - }
  315 + if (!StringUtils.isEmpty(dbCred.getPassword())) {
  316 + if (StringUtils.isEmpty(clientCred.getPassword())) {
  317 + return BasicCredentialsValidationResult.PASSWORD_MISMATCH;
  318 + } else {
  319 + return dbCred.getPassword().equals(clientCred.getPassword())
  320 + ? VALID
  321 + : BasicCredentialsValidationResult.PASSWORD_MISMATCH;
  322 + }
  323 + }
  324 + return VALID;
  325 + }
  326 +
  327 + private ListenableFuture<TransportApiResponseMsg> handle(
  328 + GetOrCreateDeviceFromGatewayRequestMsg requestMsg) {
  329 + DeviceId gatewayId =
  330 + new DeviceId(new UUID(requestMsg.getGatewayIdMSB(), requestMsg.getGatewayIdLSB()));
  331 + ListenableFuture<Device> gatewayFuture =
  332 + deviceService.findDeviceByIdAsync(TenantId.SYS_TENANT_ID, gatewayId);
  333 + return Futures.transform(
  334 + gatewayFuture,
  335 + gateway -> {
  336 + Lock deviceCreationLock =
  337 + deviceCreationLocks.computeIfAbsent(
  338 + requestMsg.getDeviceName(), id -> new ReentrantLock());
  339 + deviceCreationLock.lock();
  340 + try {
  341 +
  342 + // Thingskit function
  343 + String slaveName = requestMsg.getDeviceName();
  344 + if (gateway.getDeviceData().getTransportConfiguration().getType()
  345 + == DeviceTransportType.TCP) {
  346 + DeviceDTO iotDev =
  347 + ytDeviceService.findSlaveDevice(
  348 + gateway.getTenantId().getId().toString(),
  349 + gateway.getId().getId().toString(),
  350 + slaveName);
  351 + if (iotDev == null) {
  352 + GetOrCreateDeviceFromGatewayResponseMsg.Builder builder =
  353 + GetOrCreateDeviceFromGatewayResponseMsg.newBuilder();
384 354 return TransportApiResponseMsg.newBuilder()
385   - .setGetOrCreateDeviceResponseMsg(builder.build())
386   - .build();
387   - } catch (JsonProcessingException e) {
388   - log.warn("[{}] Failed to lookup device by gateway id and name: [{}]", gatewayId, requestMsg.getDeviceName(), e);
389   - throw new RuntimeException(e);
390   - } finally {
391   - deviceCreationLock.unlock();
  355 + .setGetOrCreateDeviceResponseMsg(builder.build())
  356 + .build();
  357 + }
  358 + slaveName = iotDev.getName();
392 359 }
393   - }, dbCallbackExecutorService);
394   - }
395 360
396   - private ListenableFuture<TransportApiResponseMsg> handle(ProvisionDeviceRequestMsg requestMsg) {
397   - ListenableFuture<ProvisionResponse> provisionResponseFuture = null;
398   - try {
399   - provisionResponseFuture = Futures.immediateFuture(deviceProvisionService.provisionDevice(
400   - new ProvisionRequest(
401   - requestMsg.getDeviceName(),
402   - requestMsg.getCredentialsType() != null ? DeviceCredentialsType.valueOf(requestMsg.getCredentialsType().name()) : null,
403   - new ProvisionDeviceCredentialsData(requestMsg.getCredentialsDataProto().getValidateDeviceTokenRequestMsg().getToken(),
404   - requestMsg.getCredentialsDataProto().getValidateBasicMqttCredRequestMsg().getClientId(),
405   - requestMsg.getCredentialsDataProto().getValidateBasicMqttCredRequestMsg().getUserName(),
406   - requestMsg.getCredentialsDataProto().getValidateBasicMqttCredRequestMsg().getPassword(),
407   - requestMsg.getCredentialsDataProto().getValidateDeviceX509CertRequestMsg().getHash()),
408   - new ProvisionDeviceProfileCredentials(
409   - requestMsg.getProvisionDeviceCredentialsMsg().getProvisionDeviceKey(),
410   - requestMsg.getProvisionDeviceCredentialsMsg().getProvisionDeviceSecret()))));
411   - } catch (ProvisionFailedException e) {
412   - return Futures.immediateFuture(getTransportApiResponseMsg(
413   - new DeviceCredentials(),
414   - TransportProtos.ResponseStatus.valueOf(e.getMessage())));
415   - }
416   - return Futures.transform(provisionResponseFuture, provisionResponse -> getTransportApiResponseMsg(provisionResponse.getDeviceCredentials(), TransportProtos.ResponseStatus.SUCCESS),
417   - dbCallbackExecutorService);
418   - }
  361 + Device device =
  362 + deviceService.findDeviceByTenantIdAndName(gateway.getTenantId(), slaveName);
419 363
420   - private TransportApiResponseMsg getTransportApiResponseMsg(DeviceCredentials
421   - deviceCredentials, TransportProtos.ResponseStatus status) {
422   - if (!status.equals(TransportProtos.ResponseStatus.SUCCESS)) {
423   - return TransportApiResponseMsg.newBuilder().setProvisionDeviceResponseMsg(TransportProtos.ProvisionDeviceResponseMsg.newBuilder().setStatus(status).build()).build();
424   - }
425   - TransportProtos.ProvisionDeviceResponseMsg.Builder provisionResponse = TransportProtos.ProvisionDeviceResponseMsg.newBuilder()
426   - .setCredentialsType(TransportProtos.CredentialsType.valueOf(deviceCredentials.getCredentialsType().name()))
427   - .setStatus(status);
428   - switch (deviceCredentials.getCredentialsType()) {
429   - case ACCESS_TOKEN:
430   - provisionResponse.setCredentialsValue(deviceCredentials.getCredentialsId());
431   - break;
432   - case MQTT_BASIC:
433   - case X509_CERTIFICATE:
434   - case LWM2M_CREDENTIALS:
435   - provisionResponse.setCredentialsValue(deviceCredentials.getCredentialsValue());
436   - break;
437   - }
438   -
439   - return TransportApiResponseMsg.newBuilder()
440   - .setProvisionDeviceResponseMsg(provisionResponse.build())
  364 + if (device == null) {
  365 + TenantId tenantId = gateway.getTenantId();
  366 + device = new Device();
  367 + device.setTenantId(tenantId);
  368 + device.setName(requestMsg.getDeviceName());
  369 + device.setType(requestMsg.getDeviceType());
  370 + device.setCustomerId(gateway.getCustomerId());
  371 + DeviceProfile deviceProfile =
  372 + deviceProfileCache.findOrCreateDeviceProfile(
  373 + gateway.getTenantId(), DefaultSystemDataLoaderService.DEFAULT_DEVICE_TYPE);
  374 + device.setDeviceProfileId(deviceProfile.getId());
  375 + ObjectNode additionalInfo = JacksonUtil.newObjectNode();
  376 + additionalInfo.put(DataConstants.LAST_CONNECTED_GATEWAY, gatewayId.toString());
  377 + device.setAdditionalInfo(additionalInfo);
  378 + Device savedDevice = deviceService.saveDevice(device);
  379 +
  380 + // Thingskit function
  381 + ytDeviceService.saveSlaveDevice(
  382 + savedDevice.getId().getId().toString(),
  383 + savedDevice.getName(),
  384 + deviceProfile.getId().getId().toString(),
  385 + gateway.getId().getId().toString(),
  386 + gateway.getCreatedTime());
  387 +
  388 + tbClusterService.onDeviceUpdated(savedDevice, null);
  389 + device = savedDevice;
  390 +
  391 + relationService.saveRelationAsync(
  392 + TenantId.SYS_TENANT_ID,
  393 + new EntityRelation(gateway.getId(), device.getId(), "Created"));
  394 +
  395 + TbMsgMetaData metaData = new TbMsgMetaData();
  396 + CustomerId customerId = gateway.getCustomerId();
  397 + if (customerId != null && !customerId.isNullUid()) {
  398 + metaData.putValue("customerId", customerId.toString());
  399 + }
  400 + metaData.putValue("gatewayId", gatewayId.toString());
  401 +
  402 + DeviceId deviceId = device.getId();
  403 + ObjectNode entityNode = mapper.valueToTree(device);
  404 + TbMsg tbMsg =
  405 + TbMsg.newMsg(
  406 + DataConstants.ENTITY_CREATED,
  407 + deviceId,
  408 + customerId,
  409 + metaData,
  410 + TbMsgDataType.JSON,
  411 + mapper.writeValueAsString(entityNode));
  412 + tbClusterService.pushMsgToRuleEngine(tenantId, deviceId, tbMsg, null);
  413 + } else {
  414 + JsonNode deviceAdditionalInfo = device.getAdditionalInfo();
  415 + if (deviceAdditionalInfo == null) {
  416 + deviceAdditionalInfo = JacksonUtil.newObjectNode();
  417 + }
  418 + if (deviceAdditionalInfo.isObject()
  419 + && (!deviceAdditionalInfo.has(DataConstants.LAST_CONNECTED_GATEWAY)
  420 + || !gatewayId
  421 + .toString()
  422 + .equals(
  423 + deviceAdditionalInfo
  424 + .get(DataConstants.LAST_CONNECTED_GATEWAY)
  425 + .asText()))) {
  426 + ObjectNode newDeviceAdditionalInfo = (ObjectNode) deviceAdditionalInfo;
  427 + newDeviceAdditionalInfo.put(
  428 + DataConstants.LAST_CONNECTED_GATEWAY, gatewayId.toString());
  429 + Device savedDevice = deviceService.saveDevice(device);
  430 + tbClusterService.onDeviceUpdated(savedDevice, device);
  431 + }
  432 + }
  433 + GetOrCreateDeviceFromGatewayResponseMsg.Builder builder =
  434 + GetOrCreateDeviceFromGatewayResponseMsg.newBuilder()
  435 + .setDeviceInfo(getDeviceInfoProto(device));
  436 + DeviceProfile deviceProfile =
  437 + deviceProfileCache.get(device.getTenantId(), device.getDeviceProfileId());
  438 + if (deviceProfile != null) {
  439 + builder.setProfileBody(
  440 + ByteString.copyFrom(dataDecodingEncodingService.encode(deviceProfile)));
  441 + } else {
  442 + log.warn(
  443 + "[{}] Failed to find device profile [{}] for device. ",
  444 + device.getId(),
  445 + device.getDeviceProfileId());
  446 + }
  447 + return TransportApiResponseMsg.newBuilder()
  448 + .setGetOrCreateDeviceResponseMsg(builder.build())
441 449 .build();
  450 + } catch (JsonProcessingException e) {
  451 + log.warn(
  452 + "[{}] Failed to lookup device by gateway id and name: [{}]",
  453 + gatewayId,
  454 + requestMsg.getDeviceName(),
  455 + e);
  456 + throw new RuntimeException(e);
  457 + } finally {
  458 + deviceCreationLock.unlock();
  459 + }
  460 + },
  461 + dbCallbackExecutorService);
  462 + }
  463 +
  464 + private ListenableFuture<TransportApiResponseMsg> handle(ProvisionDeviceRequestMsg requestMsg) {
  465 + ListenableFuture<ProvisionResponse> provisionResponseFuture = null;
  466 + try {
  467 + provisionResponseFuture =
  468 + Futures.immediateFuture(
  469 + deviceProvisionService.provisionDevice(
  470 + new ProvisionRequest(
  471 + requestMsg.getDeviceName(),
  472 + requestMsg.getCredentialsType() != null
  473 + ? DeviceCredentialsType.valueOf(requestMsg.getCredentialsType().name())
  474 + : null,
  475 + new ProvisionDeviceCredentialsData(
  476 + requestMsg
  477 + .getCredentialsDataProto()
  478 + .getValidateDeviceTokenRequestMsg()
  479 + .getToken(),
  480 + requestMsg
  481 + .getCredentialsDataProto()
  482 + .getValidateBasicMqttCredRequestMsg()
  483 + .getClientId(),
  484 + requestMsg
  485 + .getCredentialsDataProto()
  486 + .getValidateBasicMqttCredRequestMsg()
  487 + .getUserName(),
  488 + requestMsg
  489 + .getCredentialsDataProto()
  490 + .getValidateBasicMqttCredRequestMsg()
  491 + .getPassword(),
  492 + requestMsg
  493 + .getCredentialsDataProto()
  494 + .getValidateDeviceX509CertRequestMsg()
  495 + .getHash()),
  496 + new ProvisionDeviceProfileCredentials(
  497 + requestMsg.getProvisionDeviceCredentialsMsg().getProvisionDeviceKey(),
  498 + requestMsg
  499 + .getProvisionDeviceCredentialsMsg()
  500 + .getProvisionDeviceSecret()))));
  501 + } catch (ProvisionFailedException e) {
  502 + return Futures.immediateFuture(
  503 + getTransportApiResponseMsg(
  504 + new DeviceCredentials(), TransportProtos.ResponseStatus.valueOf(e.getMessage())));
442 505 }
443   -
444   - private ListenableFuture<TransportApiResponseMsg> handle(GetEntityProfileRequestMsg requestMsg) {
445   - EntityType entityType = EntityType.valueOf(requestMsg.getEntityType());
446   - UUID entityUuid = new UUID(requestMsg.getEntityIdMSB(), requestMsg.getEntityIdLSB());
447   - GetEntityProfileResponseMsg.Builder builder = GetEntityProfileResponseMsg.newBuilder();
448   - if (entityType.equals(EntityType.DEVICE_PROFILE)) {
449   - DeviceProfileId deviceProfileId = new DeviceProfileId(entityUuid);
450   - DeviceProfile deviceProfile = deviceProfileCache.find(deviceProfileId);
451   - builder.setData(ByteString.copyFrom(dataDecodingEncodingService.encode(deviceProfile)));
452   - } else if (entityType.equals(EntityType.TENANT)) {
453   - TenantId tenantId = TenantId.fromUUID(entityUuid);
454   - TenantProfile tenantProfile = tenantProfileCache.get(tenantId);
455   - ApiUsageState state = apiUsageStateService.getApiUsageState(tenantId);
456   - builder.setData(ByteString.copyFrom(dataDecodingEncodingService.encode(tenantProfile)));
457   - builder.setApiState(ByteString.copyFrom(dataDecodingEncodingService.encode(state)));
458   - } else {
459   - throw new RuntimeException("Invalid entity profile request: " + entityType);
460   - }
461   - return Futures.immediateFuture(TransportApiResponseMsg.newBuilder().setEntityProfileResponseMsg(builder).build());
  506 + return Futures.transform(
  507 + provisionResponseFuture,
  508 + provisionResponse ->
  509 + getTransportApiResponseMsg(
  510 + provisionResponse.getDeviceCredentials(), TransportProtos.ResponseStatus.SUCCESS),
  511 + dbCallbackExecutorService);
  512 + }
  513 +
  514 + private TransportApiResponseMsg getTransportApiResponseMsg(
  515 + DeviceCredentials deviceCredentials, TransportProtos.ResponseStatus status) {
  516 + if (!status.equals(TransportProtos.ResponseStatus.SUCCESS)) {
  517 + return TransportApiResponseMsg.newBuilder()
  518 + .setProvisionDeviceResponseMsg(
  519 + TransportProtos.ProvisionDeviceResponseMsg.newBuilder().setStatus(status).build())
  520 + .build();
462 521 }
463   -
464   - private ListenableFuture<TransportApiResponseMsg> handle(GetDeviceRequestMsg requestMsg) {
465   - DeviceId deviceId = new DeviceId(new UUID(requestMsg.getDeviceIdMSB(), requestMsg.getDeviceIdLSB()));
466   - Device device = deviceService.findDeviceById(TenantId.SYS_TENANT_ID, deviceId);
467   -
468   - TransportApiResponseMsg responseMsg;
469   - if (device != null) {
470   - UUID deviceProfileId = device.getDeviceProfileId().getId();
471   - responseMsg = TransportApiResponseMsg.newBuilder()
472   - .setDeviceResponseMsg(TransportProtos.GetDeviceResponseMsg.newBuilder()
473   - .setDeviceProfileIdMSB(deviceProfileId.getMostSignificantBits())
474   - .setDeviceProfileIdLSB(deviceProfileId.getLeastSignificantBits())
475   - .setDeviceTransportConfiguration(ByteString.copyFrom(
476   - dataDecodingEncodingService.encode(device.getDeviceData().getTransportConfiguration())
477   - )))
478   - .build();
479   - } else {
480   - responseMsg = TransportApiResponseMsg.getDefaultInstance();
481   - }
482   -
483   - return Futures.immediateFuture(responseMsg);
  522 + TransportProtos.ProvisionDeviceResponseMsg.Builder provisionResponse =
  523 + TransportProtos.ProvisionDeviceResponseMsg.newBuilder()
  524 + .setCredentialsType(
  525 + TransportProtos.CredentialsType.valueOf(
  526 + deviceCredentials.getCredentialsType().name()))
  527 + .setStatus(status);
  528 + switch (deviceCredentials.getCredentialsType()) {
  529 + case ACCESS_TOKEN:
  530 + provisionResponse.setCredentialsValue(deviceCredentials.getCredentialsId());
  531 + break;
  532 + case MQTT_BASIC:
  533 + case X509_CERTIFICATE:
  534 + case LWM2M_CREDENTIALS:
  535 + provisionResponse.setCredentialsValue(deviceCredentials.getCredentialsValue());
  536 + break;
484 537 }
485 538
486   - private ListenableFuture<TransportApiResponseMsg> handle(GetDeviceCredentialsRequestMsg requestMsg) {
487   - DeviceId deviceId = new DeviceId(new UUID(requestMsg.getDeviceIdMSB(), requestMsg.getDeviceIdLSB()));
488   - DeviceCredentials deviceCredentials = deviceCredentialsService.findDeviceCredentialsByDeviceId(TenantId.SYS_TENANT_ID, deviceId);
489   -
490   - return Futures.immediateFuture(TransportApiResponseMsg.newBuilder()
491   - .setDeviceCredentialsResponseMsg(TransportProtos.GetDeviceCredentialsResponseMsg.newBuilder()
492   - .setDeviceCredentialsData(ByteString.copyFrom(dataDecodingEncodingService.encode(deviceCredentials))))
493   - .build());
  539 + return TransportApiResponseMsg.newBuilder()
  540 + .setProvisionDeviceResponseMsg(provisionResponse.build())
  541 + .build();
  542 + }
  543 +
  544 + private ListenableFuture<TransportApiResponseMsg> handle(GetEntityProfileRequestMsg requestMsg) {
  545 + EntityType entityType = EntityType.valueOf(requestMsg.getEntityType());
  546 + UUID entityUuid = new UUID(requestMsg.getEntityIdMSB(), requestMsg.getEntityIdLSB());
  547 + GetEntityProfileResponseMsg.Builder builder = GetEntityProfileResponseMsg.newBuilder();
  548 + if (entityType.equals(EntityType.DEVICE_PROFILE)) {
  549 + DeviceProfileId deviceProfileId = new DeviceProfileId(entityUuid);
  550 + DeviceProfile deviceProfile = deviceProfileCache.find(deviceProfileId);
  551 + builder.setData(ByteString.copyFrom(dataDecodingEncodingService.encode(deviceProfile)));
  552 + } else if (entityType.equals(EntityType.TENANT)) {
  553 + TenantId tenantId = TenantId.fromUUID(entityUuid);
  554 + TenantProfile tenantProfile = tenantProfileCache.get(tenantId);
  555 + ApiUsageState state = apiUsageStateService.getApiUsageState(tenantId);
  556 + builder.setData(ByteString.copyFrom(dataDecodingEncodingService.encode(tenantProfile)));
  557 + builder.setApiState(ByteString.copyFrom(dataDecodingEncodingService.encode(state)));
  558 + } else {
  559 + throw new RuntimeException("Invalid entity profile request: " + entityType);
494 560 }
495   -
496   -
497   - private ListenableFuture<TransportApiResponseMsg> handle(GetResourceRequestMsg requestMsg) {
498   - TenantId tenantId = TenantId.fromUUID(new UUID(requestMsg.getTenantIdMSB(), requestMsg.getTenantIdLSB()));
499   - ResourceType resourceType = ResourceType.valueOf(requestMsg.getResourceType());
500   - String resourceKey = requestMsg.getResourceKey();
501   - TransportProtos.GetResourceResponseMsg.Builder builder = TransportProtos.GetResourceResponseMsg.newBuilder();
502   - TbResource resource = resourceService.getResource(tenantId, resourceType, resourceKey);
503   -
504   - if (resource == null && !tenantId.equals(TenantId.SYS_TENANT_ID)) {
505   - resource = resourceService.getResource(TenantId.SYS_TENANT_ID, resourceType, resourceKey);
506   - }
507   -
508   - if (resource != null) {
509   - builder.setResource(ByteString.copyFrom(dataDecodingEncodingService.encode(resource)));
510   - }
511   -
512   - return Futures.immediateFuture(TransportApiResponseMsg.newBuilder().setResourceResponseMsg(builder).build());
  561 + return Futures.immediateFuture(
  562 + TransportApiResponseMsg.newBuilder().setEntityProfileResponseMsg(builder).build());
  563 + }
  564 +
  565 + private ListenableFuture<TransportApiResponseMsg> handle(GetDeviceRequestMsg requestMsg) {
  566 + DeviceId deviceId =
  567 + new DeviceId(new UUID(requestMsg.getDeviceIdMSB(), requestMsg.getDeviceIdLSB()));
  568 + Device device = deviceService.findDeviceById(TenantId.SYS_TENANT_ID, deviceId);
  569 +
  570 + TransportApiResponseMsg responseMsg;
  571 + if (device != null) {
  572 + UUID deviceProfileId = device.getDeviceProfileId().getId();
  573 + responseMsg =
  574 + TransportApiResponseMsg.newBuilder()
  575 + .setDeviceResponseMsg(
  576 + TransportProtos.GetDeviceResponseMsg.newBuilder()
  577 + .setDeviceProfileIdMSB(deviceProfileId.getMostSignificantBits())
  578 + .setDeviceProfileIdLSB(deviceProfileId.getLeastSignificantBits())
  579 + .setDeviceTransportConfiguration(
  580 + ByteString.copyFrom(
  581 + dataDecodingEncodingService.encode(
  582 + device.getDeviceData().getTransportConfiguration()))))
  583 + .build();
  584 + } else {
  585 + responseMsg = TransportApiResponseMsg.getDefaultInstance();
513 586 }
514 587
515   - private ListenableFuture<TransportApiResponseMsg> handle(GetSnmpDevicesRequestMsg requestMsg) {
516   - PageLink pageLink = new PageLink(requestMsg.getPageSize(), requestMsg.getPage());
517   - PageData<UUID> result = deviceService.findDevicesIdsByDeviceProfileTransportType(DeviceTransportType.SNMP, pageLink);
518   -
519   - GetSnmpDevicesResponseMsg responseMsg = GetSnmpDevicesResponseMsg.newBuilder()
520   - .addAllIds(result.getData().stream()
521   - .map(UUID::toString)
522   - .collect(Collectors.toList()))
523   - .setHasNextPage(result.hasNext())
524   - .build();
  588 + return Futures.immediateFuture(responseMsg);
  589 + }
  590 +
  591 + private ListenableFuture<TransportApiResponseMsg> handle(
  592 + GetDeviceCredentialsRequestMsg requestMsg) {
  593 + DeviceId deviceId =
  594 + new DeviceId(new UUID(requestMsg.getDeviceIdMSB(), requestMsg.getDeviceIdLSB()));
  595 + DeviceCredentials deviceCredentials =
  596 + deviceCredentialsService.findDeviceCredentialsByDeviceId(TenantId.SYS_TENANT_ID, deviceId);
  597 +
  598 + return Futures.immediateFuture(
  599 + TransportApiResponseMsg.newBuilder()
  600 + .setDeviceCredentialsResponseMsg(
  601 + TransportProtos.GetDeviceCredentialsResponseMsg.newBuilder()
  602 + .setDeviceCredentialsData(
  603 + ByteString.copyFrom(dataDecodingEncodingService.encode(deviceCredentials))))
  604 + .build());
  605 + }
  606 +
  607 + private ListenableFuture<TransportApiResponseMsg> handle(GetResourceRequestMsg requestMsg) {
  608 + TenantId tenantId =
  609 + TenantId.fromUUID(new UUID(requestMsg.getTenantIdMSB(), requestMsg.getTenantIdLSB()));
  610 + ResourceType resourceType = ResourceType.valueOf(requestMsg.getResourceType());
  611 + String resourceKey = requestMsg.getResourceKey();
  612 + TransportProtos.GetResourceResponseMsg.Builder builder =
  613 + TransportProtos.GetResourceResponseMsg.newBuilder();
  614 + TbResource resource = resourceService.getResource(tenantId, resourceType, resourceKey);
  615 +
  616 + if (resource == null && !tenantId.equals(TenantId.SYS_TENANT_ID)) {
  617 + resource = resourceService.getResource(TenantId.SYS_TENANT_ID, resourceType, resourceKey);
  618 + }
525 619
526   - return Futures.immediateFuture(TransportApiResponseMsg.newBuilder()
527   - .setSnmpDevicesResponseMsg(responseMsg)
528   - .build());
  620 + if (resource != null) {
  621 + builder.setResource(ByteString.copyFrom(dataDecodingEncodingService.encode(resource)));
529 622 }
530 623
531   - private ListenableFuture<TransportApiResponseMsg> getDeviceInfo(DeviceCredentials credentials) {
532   - return Futures.transform(deviceService.findDeviceByIdAsync(TenantId.SYS_TENANT_ID, credentials.getDeviceId()), device -> {
533   - if (device == null) {
534   - log.trace("[{}] Failed to lookup device by id", credentials.getDeviceId());
535   - return getEmptyTransportApiResponse();
  624 + return Futures.immediateFuture(
  625 + TransportApiResponseMsg.newBuilder().setResourceResponseMsg(builder).build());
  626 + }
  627 +
  628 + private ListenableFuture<TransportApiResponseMsg> handle(GetSnmpDevicesRequestMsg requestMsg) {
  629 + PageLink pageLink = new PageLink(requestMsg.getPageSize(), requestMsg.getPage());
  630 + PageData<UUID> result =
  631 + deviceService.findDevicesIdsByDeviceProfileTransportType(
  632 + DeviceTransportType.SNMP, pageLink);
  633 +
  634 + GetSnmpDevicesResponseMsg responseMsg =
  635 + GetSnmpDevicesResponseMsg.newBuilder()
  636 + .addAllIds(result.getData().stream().map(UUID::toString).collect(Collectors.toList()))
  637 + .setHasNextPage(result.hasNext())
  638 + .build();
  639 +
  640 + return Futures.immediateFuture(
  641 + TransportApiResponseMsg.newBuilder().setSnmpDevicesResponseMsg(responseMsg).build());
  642 + }
  643 +
  644 + private ListenableFuture<TransportApiResponseMsg> getDeviceInfo(DeviceCredentials credentials) {
  645 + return Futures.transform(
  646 + deviceService.findDeviceByIdAsync(TenantId.SYS_TENANT_ID, credentials.getDeviceId()),
  647 + device -> {
  648 + if (device == null) {
  649 + log.trace("[{}] Failed to lookup device by id", credentials.getDeviceId());
  650 + return getEmptyTransportApiResponse();
  651 + }
  652 + try {
  653 + ValidateDeviceCredentialsResponseMsg.Builder builder =
  654 + ValidateDeviceCredentialsResponseMsg.newBuilder();
  655 + builder.setDeviceInfo(getDeviceInfoProto(device));
  656 + DeviceProfile deviceProfile =
  657 + deviceProfileCache.get(device.getTenantId(), device.getDeviceProfileId());
  658 + if (deviceProfile != null) {
  659 + builder.setProfileBody(
  660 + ByteString.copyFrom(dataDecodingEncodingService.encode(deviceProfile)));
  661 + } else {
  662 + log.warn(
  663 + "[{}] Failed to find device profile [{}] for device. ",
  664 + device.getId(),
  665 + device.getDeviceProfileId());
536 666 }
537   - try {
538   - ValidateDeviceCredentialsResponseMsg.Builder builder = ValidateDeviceCredentialsResponseMsg.newBuilder();
539   - builder.setDeviceInfo(getDeviceInfoProto(device));
540   - DeviceProfile deviceProfile = deviceProfileCache.get(device.getTenantId(), device.getDeviceProfileId());
541   - if (deviceProfile != null) {
542   - builder.setProfileBody(ByteString.copyFrom(dataDecodingEncodingService.encode(deviceProfile)));
543   - } else {
544   - log.warn("[{}] Failed to find device profile [{}] for device. ", device.getId(), device.getDeviceProfileId());
545   - }
546   - if (!StringUtils.isEmpty(credentials.getCredentialsValue())) {
547   - builder.setCredentialsBody(credentials.getCredentialsValue());
548   - }
549   - return TransportApiResponseMsg.newBuilder()
550   - .setValidateCredResponseMsg(builder.build()).build();
551   - } catch (JsonProcessingException e) {
552   - log.warn("[{}] Failed to lookup device by id", credentials.getDeviceId(), e);
553   - return getEmptyTransportApiResponse();
  667 + if (!StringUtils.isEmpty(credentials.getCredentialsValue())) {
  668 + builder.setCredentialsBody(credentials.getCredentialsValue());
554 669 }
555   - }, MoreExecutors.directExecutor());
  670 + return TransportApiResponseMsg.newBuilder()
  671 + .setValidateCredResponseMsg(builder.build())
  672 + .build();
  673 + } catch (JsonProcessingException e) {
  674 + log.warn("[{}] Failed to lookup device by id", credentials.getDeviceId(), e);
  675 + return getEmptyTransportApiResponse();
  676 + }
  677 + },
  678 + MoreExecutors.directExecutor());
  679 + }
  680 +
  681 + private DeviceInfoProto getDeviceInfoProto(Device device) throws JsonProcessingException {
  682 + DeviceInfoProto.Builder builder =
  683 + DeviceInfoProto.newBuilder()
  684 + .setTenantIdMSB(device.getTenantId().getId().getMostSignificantBits())
  685 + .setTenantIdLSB(device.getTenantId().getId().getLeastSignificantBits())
  686 + .setCustomerIdMSB(
  687 + Optional.ofNullable(device.getCustomerId())
  688 + .map(customerId -> customerId.getId().getMostSignificantBits())
  689 + .orElse(0L))
  690 + .setCustomerIdLSB(
  691 + Optional.ofNullable(device.getCustomerId())
  692 + .map(customerId -> customerId.getId().getLeastSignificantBits())
  693 + .orElse(0L))
  694 + .setDeviceIdMSB(device.getId().getId().getMostSignificantBits())
  695 + .setDeviceIdLSB(device.getId().getId().getLeastSignificantBits())
  696 + .setDeviceName(device.getName())
  697 + .setDeviceType(device.getType())
  698 + .setDeviceProfileIdMSB(device.getDeviceProfileId().getId().getMostSignificantBits())
  699 + .setDeviceProfileIdLSB(device.getDeviceProfileId().getId().getLeastSignificantBits())
  700 + .setAdditionalInfo(mapper.writeValueAsString(device.getAdditionalInfo()));
  701 +
  702 + PowerSavingConfiguration psmConfiguration = null;
  703 + switch (device.getDeviceData().getTransportConfiguration().getType()) {
  704 + case LWM2M:
  705 + psmConfiguration =
  706 + (Lwm2mDeviceTransportConfiguration) device.getDeviceData().getTransportConfiguration();
  707 + break;
  708 + case COAP:
  709 + psmConfiguration =
  710 + (CoapDeviceTransportConfiguration) device.getDeviceData().getTransportConfiguration();
  711 + break;
556 712 }
557 713
558   - private DeviceInfoProto getDeviceInfoProto(Device device) throws JsonProcessingException {
559   - DeviceInfoProto.Builder builder = DeviceInfoProto.newBuilder()
560   - .setTenantIdMSB(device.getTenantId().getId().getMostSignificantBits())
561   - .setTenantIdLSB(device.getTenantId().getId().getLeastSignificantBits())
562   - .setCustomerIdMSB(Optional.ofNullable(device.getCustomerId()).map(customerId -> customerId.getId().getMostSignificantBits()).orElse(0L))
563   - .setCustomerIdLSB(Optional.ofNullable(device.getCustomerId()).map(customerId -> customerId.getId().getLeastSignificantBits()).orElse(0L))
564   - .setDeviceIdMSB(device.getId().getId().getMostSignificantBits())
565   - .setDeviceIdLSB(device.getId().getId().getLeastSignificantBits())
566   - .setDeviceName(device.getName())
567   - .setDeviceType(device.getType())
568   - .setDeviceProfileIdMSB(device.getDeviceProfileId().getId().getMostSignificantBits())
569   - .setDeviceProfileIdLSB(device.getDeviceProfileId().getId().getLeastSignificantBits())
570   - .setAdditionalInfo(mapper.writeValueAsString(device.getAdditionalInfo()));
571   -
572   - PowerSavingConfiguration psmConfiguration = null;
573   - switch (device.getDeviceData().getTransportConfiguration().getType()) {
574   - case LWM2M:
575   - psmConfiguration = (Lwm2mDeviceTransportConfiguration) device.getDeviceData().getTransportConfiguration();
576   - break;
577   - case COAP:
578   - psmConfiguration = (CoapDeviceTransportConfiguration) device.getDeviceData().getTransportConfiguration();
579   - break;
580   - }
581   -
582   - if (psmConfiguration != null) {
583   - PowerMode powerMode = psmConfiguration.getPowerMode();
584   - if (powerMode != null) {
585   - builder.setPowerMode(powerMode.name());
586   - if (powerMode.equals(PowerMode.PSM)) {
587   - builder.setPsmActivityTimer(checkLong(psmConfiguration.getPsmActivityTimer()));
588   - } else if (powerMode.equals(PowerMode.E_DRX)) {
589   - builder.setEdrxCycle(checkLong(psmConfiguration.getEdrxCycle()));
590   - builder.setPagingTransmissionWindow(checkLong(psmConfiguration.getPagingTransmissionWindow()));
591   - }
592   - }
  714 + if (psmConfiguration != null) {
  715 + PowerMode powerMode = psmConfiguration.getPowerMode();
  716 + if (powerMode != null) {
  717 + builder.setPowerMode(powerMode.name());
  718 + if (powerMode.equals(PowerMode.PSM)) {
  719 + builder.setPsmActivityTimer(checkLong(psmConfiguration.getPsmActivityTimer()));
  720 + } else if (powerMode.equals(PowerMode.E_DRX)) {
  721 + builder.setEdrxCycle(checkLong(psmConfiguration.getEdrxCycle()));
  722 + builder.setPagingTransmissionWindow(
  723 + checkLong(psmConfiguration.getPagingTransmissionWindow()));
593 724 }
594   - return builder.build();
  725 + }
595 726 }
596   -
597   - private ListenableFuture<TransportApiResponseMsg> getEmptyTransportApiResponseFuture() {
598   - return Futures.immediateFuture(getEmptyTransportApiResponse());
  727 + return builder.build();
  728 + }
  729 +
  730 + private ListenableFuture<TransportApiResponseMsg> getEmptyTransportApiResponseFuture() {
  731 + return Futures.immediateFuture(getEmptyTransportApiResponse());
  732 + }
  733 +
  734 + private TransportApiResponseMsg getEmptyTransportApiResponse() {
  735 + return TransportApiResponseMsg.newBuilder()
  736 + .setValidateCredResponseMsg(ValidateDeviceCredentialsResponseMsg.getDefaultInstance())
  737 + .build();
  738 + }
  739 +
  740 + private ListenableFuture<TransportApiResponseMsg> handle(
  741 + TransportProtos.LwM2MRequestMsg requestMsg) {
  742 + if (requestMsg.hasRegistrationMsg()) {
  743 + return handleRegistration(requestMsg.getRegistrationMsg());
  744 + } else {
  745 + return Futures.immediateFailedFuture(new RuntimeException("Not supported!"));
599 746 }
600   -
601   - private TransportApiResponseMsg getEmptyTransportApiResponse() {
602   - return TransportApiResponseMsg.newBuilder()
603   - .setValidateCredResponseMsg(ValidateDeviceCredentialsResponseMsg.getDefaultInstance()).build();
  747 + }
  748 +
  749 + private ListenableFuture<TransportApiResponseMsg> handle(
  750 + TransportProtos.GetOtaPackageRequestMsg requestMsg) {
  751 + TenantId tenantId =
  752 + TenantId.fromUUID(new UUID(requestMsg.getTenantIdMSB(), requestMsg.getTenantIdLSB()));
  753 + DeviceId deviceId =
  754 + new DeviceId(new UUID(requestMsg.getDeviceIdMSB(), requestMsg.getDeviceIdLSB()));
  755 + OtaPackageType otaPackageType = OtaPackageType.valueOf(requestMsg.getType());
  756 + Device device = deviceService.findDeviceById(tenantId, deviceId);
  757 +
  758 + if (device == null) {
  759 + return getEmptyTransportApiResponseFuture();
604 760 }
605 761
606   - private ListenableFuture<TransportApiResponseMsg> handle(TransportProtos.LwM2MRequestMsg requestMsg) {
607   - if (requestMsg.hasRegistrationMsg()) {
608   - return handleRegistration(requestMsg.getRegistrationMsg());
609   - } else {
610   - return Futures.immediateFailedFuture(new RuntimeException("Not supported!"));
611   - }
612   - }
613   -
614   - private ListenableFuture<TransportApiResponseMsg> handle(TransportProtos.GetOtaPackageRequestMsg requestMsg) {
615   - TenantId tenantId = TenantId.fromUUID(new UUID(requestMsg.getTenantIdMSB(), requestMsg.getTenantIdLSB()));
616   - DeviceId deviceId = new DeviceId(new UUID(requestMsg.getDeviceIdMSB(), requestMsg.getDeviceIdLSB()));
617   - OtaPackageType otaPackageType = OtaPackageType.valueOf(requestMsg.getType());
618   - Device device = deviceService.findDeviceById(tenantId, deviceId);
619   -
620   - if (device == null) {
621   - return getEmptyTransportApiResponseFuture();
622   - }
623   -
624   - OtaPackageId otaPackageId = OtaPackageUtil.getOtaPackageId(device, otaPackageType);
625   - if (otaPackageId == null) {
626   - DeviceProfile deviceProfile = deviceProfileCache.find(device.getDeviceProfileId());
627   - otaPackageId = OtaPackageUtil.getOtaPackageId(deviceProfile, otaPackageType);
628   - }
629   -
630   - TransportProtos.GetOtaPackageResponseMsg.Builder builder = TransportProtos.GetOtaPackageResponseMsg.newBuilder();
631   -
632   - if (otaPackageId == null) {
633   - builder.setResponseStatus(TransportProtos.ResponseStatus.NOT_FOUND);
634   - } else {
635   - OtaPackageInfo otaPackageInfo = otaPackageService.findOtaPackageInfoById(tenantId, otaPackageId);
636   -
637   - if (otaPackageInfo == null) {
638   - builder.setResponseStatus(TransportProtos.ResponseStatus.NOT_FOUND);
639   - } else if (otaPackageInfo.hasUrl()) {
640   - builder.setResponseStatus(TransportProtos.ResponseStatus.FAILURE);
641   - log.trace("[{}] Can`t send OtaPackage with URL data!", otaPackageInfo.getId());
642   - } else {
643   - builder.setResponseStatus(TransportProtos.ResponseStatus.SUCCESS);
644   - builder.setOtaPackageIdMSB(otaPackageId.getId().getMostSignificantBits());
645   - builder.setOtaPackageIdLSB(otaPackageId.getId().getLeastSignificantBits());
646   - builder.setType(otaPackageInfo.getType().name());
647   - builder.setTitle(otaPackageInfo.getTitle());
648   - builder.setVersion(otaPackageInfo.getVersion());
649   - builder.setFileName(otaPackageInfo.getFileName());
650   - builder.setContentType(otaPackageInfo.getContentType());
651   - if (!otaPackageDataCache.has(otaPackageId.toString())) {
652   - OtaPackage otaPackage = otaPackageService.findOtaPackageById(tenantId, otaPackageId);
653   - otaPackageDataCache.put(otaPackageId.toString(), otaPackage.getData().array());
654   - }
655   - }
656   - }
657   -
658   - return Futures.immediateFuture(
659   - TransportApiResponseMsg.newBuilder()
660   - .setOtaPackageResponseMsg(builder.build())
661   - .build());
  762 + OtaPackageId otaPackageId = OtaPackageUtil.getOtaPackageId(device, otaPackageType);
  763 + if (otaPackageId == null) {
  764 + DeviceProfile deviceProfile = deviceProfileCache.find(device.getDeviceProfileId());
  765 + otaPackageId = OtaPackageUtil.getOtaPackageId(deviceProfile, otaPackageType);
662 766 }
663 767
664   - private ListenableFuture<TransportApiResponseMsg> handleRegistration
665   - (TransportProtos.LwM2MRegistrationRequestMsg msg) {
666   - TenantId tenantId = TenantId.fromUUID(UUID.fromString(msg.getTenantId()));
667   - String deviceName = msg.getEndpoint();
668   - Lock deviceCreationLock = deviceCreationLocks.computeIfAbsent(deviceName, id -> new ReentrantLock());
669   - deviceCreationLock.lock();
670   - try {
671   - Device device = deviceService.findDeviceByTenantIdAndName(tenantId, deviceName);
672   - if (device == null) {
673   - device = new Device();
674   - device.setTenantId(tenantId);
675   - device.setName(deviceName);
676   - device.setType("LwM2M");
677   - device = deviceService.saveDevice(device);
678   - tbClusterService.onDeviceUpdated(device, null);
679   - }
680   - TransportProtos.LwM2MRegistrationResponseMsg registrationResponseMsg =
681   - TransportProtos.LwM2MRegistrationResponseMsg.newBuilder()
682   - .setDeviceInfo(getDeviceInfoProto(device)).build();
683   - TransportProtos.LwM2MResponseMsg responseMsg = TransportProtos.LwM2MResponseMsg.newBuilder().setRegistrationMsg(registrationResponseMsg).build();
684   - return Futures.immediateFuture(TransportApiResponseMsg.newBuilder().setLwM2MResponseMsg(responseMsg).build());
685   - } catch (JsonProcessingException e) {
686   - log.warn("[{}][{}] Failed to lookup device by gateway id and name", tenantId, deviceName, e);
687   - throw new RuntimeException(e);
688   - } finally {
689   - deviceCreationLock.unlock();
  768 + TransportProtos.GetOtaPackageResponseMsg.Builder builder =
  769 + TransportProtos.GetOtaPackageResponseMsg.newBuilder();
  770 +
  771 + if (otaPackageId == null) {
  772 + builder.setResponseStatus(TransportProtos.ResponseStatus.NOT_FOUND);
  773 + } else {
  774 + OtaPackageInfo otaPackageInfo =
  775 + otaPackageService.findOtaPackageInfoById(tenantId, otaPackageId);
  776 +
  777 + if (otaPackageInfo == null) {
  778 + builder.setResponseStatus(TransportProtos.ResponseStatus.NOT_FOUND);
  779 + } else if (otaPackageInfo.hasUrl()) {
  780 + builder.setResponseStatus(TransportProtos.ResponseStatus.FAILURE);
  781 + log.trace("[{}] Can`t send OtaPackage with URL data!", otaPackageInfo.getId());
  782 + } else {
  783 + builder.setResponseStatus(TransportProtos.ResponseStatus.SUCCESS);
  784 + builder.setOtaPackageIdMSB(otaPackageId.getId().getMostSignificantBits());
  785 + builder.setOtaPackageIdLSB(otaPackageId.getId().getLeastSignificantBits());
  786 + builder.setType(otaPackageInfo.getType().name());
  787 + builder.setTitle(otaPackageInfo.getTitle());
  788 + builder.setVersion(otaPackageInfo.getVersion());
  789 + builder.setFileName(otaPackageInfo.getFileName());
  790 + builder.setContentType(otaPackageInfo.getContentType());
  791 + if (!otaPackageDataCache.has(otaPackageId.toString())) {
  792 + OtaPackage otaPackage = otaPackageService.findOtaPackageById(tenantId, otaPackageId);
  793 + otaPackageDataCache.put(otaPackageId.toString(), otaPackage.getData().array());
690 794 }
  795 + }
691 796 }
692 797
693   - private Long checkLong(Long l) {
694   - return l != null ? l : 0;
  798 + return Futures.immediateFuture(
  799 + TransportApiResponseMsg.newBuilder().setOtaPackageResponseMsg(builder.build()).build());
  800 + }
  801 +
  802 + private ListenableFuture<TransportApiResponseMsg> handleRegistration(
  803 + TransportProtos.LwM2MRegistrationRequestMsg msg) {
  804 + TenantId tenantId = TenantId.fromUUID(UUID.fromString(msg.getTenantId()));
  805 + String deviceName = msg.getEndpoint();
  806 + Lock deviceCreationLock =
  807 + deviceCreationLocks.computeIfAbsent(deviceName, id -> new ReentrantLock());
  808 + deviceCreationLock.lock();
  809 + try {
  810 + Device device = deviceService.findDeviceByTenantIdAndName(tenantId, deviceName);
  811 + if (device == null) {
  812 + device = new Device();
  813 + device.setTenantId(tenantId);
  814 + device.setName(deviceName);
  815 + device.setType("LwM2M");
  816 + device = deviceService.saveDevice(device);
  817 + tbClusterService.onDeviceUpdated(device, null);
  818 + }
  819 + TransportProtos.LwM2MRegistrationResponseMsg registrationResponseMsg =
  820 + TransportProtos.LwM2MRegistrationResponseMsg.newBuilder()
  821 + .setDeviceInfo(getDeviceInfoProto(device))
  822 + .build();
  823 + TransportProtos.LwM2MResponseMsg responseMsg =
  824 + TransportProtos.LwM2MResponseMsg.newBuilder()
  825 + .setRegistrationMsg(registrationResponseMsg)
  826 + .build();
  827 + return Futures.immediateFuture(
  828 + TransportApiResponseMsg.newBuilder().setLwM2MResponseMsg(responseMsg).build());
  829 + } catch (JsonProcessingException e) {
  830 + log.warn("[{}][{}] Failed to lookup device by gateway id and name", tenantId, deviceName, e);
  831 + throw new RuntimeException(e);
  832 + } finally {
  833 + deviceCreationLock.unlock();
695 834 }
696   -
697   -
698   -
699   - //Thingskit function
700   - private ListenableFuture<TransportApiResponseMsg> handle(TransportProtos.ScriptProto requestMsg) {
701   - List<TkDeviceScriptDTO> allScriptes = scriptService.getScriptes();
702   - TransportApiResponseMsg.Builder responseBuilder = TransportApiResponseMsg.newBuilder();
703   - allScriptes.forEach(
704   - item -> {
705   - UUID tenantId = UUID.fromString(item.getTenantId());
706   - UUID id = UUID.fromString(item.getId());
707   - responseBuilder.addScriptsResponseMsg(
708   - TransportProtos.ScriptProto.newBuilder()
709   - .setConvertJs(item.getConvertJs())
710   - .setTenantIdLSB(tenantId.getLeastSignificantBits())
711   - .setTenantIdMSB(tenantId.getMostSignificantBits())
712   - .setScriptIdLSB(id.getLeastSignificantBits())
713   - .setScriptIdMSB(id.getMostSignificantBits())
714   - .setFunctionType(item.getScriptType().name())
715   - .setStatus(item.getStatus()));
716   - });
717   - return Futures.immediateFuture(responseBuilder.build());
718   - }
719   - private ListenableFuture<TransportApiResponseMsg> handleGbt(TransportProtos.Gbt28181RequestMsg requestMsg) {
720   - TransportProtos.Gbt28181ResponseMsg.Builder responseMsgBuilder =TransportProtos.Gbt28181ResponseMsg.newBuilder();
721   - String tenantId = new UUID(requestMsg.getTenantIdMSB(), requestMsg.getTenantIdLSB()).toString();
722   - String tbDeviceId = new UUID(requestMsg.getEntityIdMSB(), requestMsg.getEntityIdLSB()).toString();
723   - String type = requestMsg.getContextType();
724   - switch (VideoCmdEnum.valueOf(type)){
725   - case DeviceInfo:
726   - Optional<SipDeviceDTO> camera = dataDecodingEncodingService.decode(requestMsg.getContext().toByteArray());
727   - camera.ifPresent(sip ->{
728   - ytDeviceService.updateDeviceInfo(tenantId,tbDeviceId, FastIotConstants.DeviceAdditional.SIP,JacksonUtil.valueToTree(sip));
729   - });
730   -
731   - break;
732   - case Catalog:
733   - Optional<List<VideoChanelDTO>> allChannel = dataDecodingEncodingService.decode(requestMsg.getContext().toByteArray());
734   - allChannel.ifPresent(d->{
735   - channelService.clearDeviceChannel(d.get(0).getCameraCode());
736   - List<TkVideoChannelEntity> chanel= d.stream().map(item -> item.getEntity(TkVideoChannelEntity.class)).collect(Collectors.toList());
737   - channelService.insertBatch(chanel,chanel.size());
738   - });
739   - break;
740   - default:
741   - release(tenantId,tbDeviceId);
742   -
743   - }
744   -// byte[] channaelMsgBytes = dataDecodingEncodingService.encode(channelDTO);
745   -// responseMsgBuilder.setContext(ByteString.copyFrom(channaelMsgBytes));
746   - return Futures.immediateFuture(TransportApiResponseMsg.newBuilder().setGbt28181ResponseMsg(responseMsgBuilder.build()).build());
  835 + }
  836 +
  837 + private Long checkLong(Long l) {
  838 + return l != null ? l : 0;
  839 + }
  840 +
  841 + // Thingskit function
  842 + private ListenableFuture<TransportApiResponseMsg> handle(TransportProtos.ScriptProto requestMsg) {
  843 + List<TkDeviceScriptDTO> allScriptes = scriptService.getScriptes();
  844 + TransportApiResponseMsg.Builder responseBuilder = TransportApiResponseMsg.newBuilder();
  845 + allScriptes.forEach(
  846 + item -> {
  847 + UUID tenantId = UUID.fromString(item.getTenantId());
  848 + UUID id = UUID.fromString(item.getId());
  849 + responseBuilder.addScriptsResponseMsg(
  850 + TransportProtos.ScriptProto.newBuilder()
  851 + .setConvertJs(item.getConvertJs())
  852 + .setTenantIdLSB(tenantId.getLeastSignificantBits())
  853 + .setTenantIdMSB(tenantId.getMostSignificantBits())
  854 + .setScriptIdLSB(id.getLeastSignificantBits())
  855 + .setScriptIdMSB(id.getMostSignificantBits())
  856 + .setFunctionType(item.getScriptType().name())
  857 + .setStatus(item.getStatus()));
  858 + });
  859 + return Futures.immediateFuture(responseBuilder.build());
  860 + }
  861 +
  862 + private ListenableFuture<TransportApiResponseMsg> handleGbt(
  863 + TransportProtos.Gbt28181RequestMsg requestMsg) {
  864 + TransportProtos.Gbt28181ResponseMsg.Builder responseMsgBuilder =
  865 + TransportProtos.Gbt28181ResponseMsg.newBuilder();
  866 + String tenantId = new UUID(requestMsg.getTenantIdMSB(), requestMsg.getTenantIdLSB()).toString();
  867 + String tbDeviceId =
  868 + new UUID(requestMsg.getEntityIdMSB(), requestMsg.getEntityIdLSB()).toString();
  869 + String type = requestMsg.getContextType();
  870 + switch (VideoCmdEnum.valueOf(type)) {
  871 + case DeviceInfo:
  872 + Optional<SipDeviceDTO> camera =
  873 + dataDecodingEncodingService.decode(requestMsg.getContext().toByteArray());
  874 + camera.ifPresent(
  875 + sip -> {
  876 + ytDeviceService.updateDeviceInfo(
  877 + tenantId,
  878 + tbDeviceId,
  879 + FastIotConstants.DeviceAdditional.SIP,
  880 + JacksonUtil.valueToTree(sip));
  881 + });
  882 +
  883 + break;
  884 + case Catalog:
  885 + Optional<List<VideoChanelDTO>> allChannel =
  886 + dataDecodingEncodingService.decode(requestMsg.getContext().toByteArray());
  887 + allChannel.ifPresent(
  888 + d -> {
  889 + channelService.clearDeviceChannel(d.get(0).getCameraCode());
  890 + List<TkVideoChannelEntity> chanel =
  891 + d.stream()
  892 + .map(item -> item.getEntity(TkVideoChannelEntity.class))
  893 + .collect(Collectors.toList());
  894 + channelService.insertBatch(chanel, chanel.size());
  895 + });
  896 + break;
  897 + default:
  898 + release(tenantId, tbDeviceId);
747 899 }
748   - private void release(String tenantId,String tbDeviceId){
749   - DeviceDTO device = ytDeviceService.findDeviceInfoByTbDeviceId(tenantId,tbDeviceId);
750   - Optional.ofNullable(device).ifPresent(dev->{
751   - JsonNode sip = dev.getDeviceInfo().get(FastIotConstants.DeviceAdditional.SIP);
752   - if(!sip.isEmpty() && sip.has(FastIotConstants.ZLMediaBody.CAMERA_CODE)){
  900 + // byte[] channaelMsgBytes = dataDecodingEncodingService.encode(channelDTO);
  901 + // responseMsgBuilder.setContext(ByteString.copyFrom(channaelMsgBytes));
  902 + return Futures.immediateFuture(
  903 + TransportApiResponseMsg.newBuilder()
  904 + .setGbt28181ResponseMsg(responseMsgBuilder.build())
  905 + .build());
  906 + }
  907 +
  908 + private void release(String tenantId, String tbDeviceId) {
  909 + DeviceDTO device = ytDeviceService.findDeviceInfoByTbDeviceId(tenantId, tbDeviceId);
  910 + Optional.ofNullable(device)
  911 + .ifPresent(
  912 + dev -> {
  913 + JsonNode sip = dev.getDeviceInfo().get(FastIotConstants.DeviceAdditional.SIP);
  914 + if (!sip.isEmpty() && sip.has(FastIotConstants.ZLMediaBody.CAMERA_CODE)) {
753 915 String cameraCode = sip.get(FastIotConstants.ZLMediaBody.CAMERA_CODE).asText();
754 916 Optional<Set<String>> ssrcKeys =
755   - videoStreamSessionManager.getSsrcTransactionCamaraKey(cameraCode);
756   - ssrcKeys.ifPresent(all ->{
757   - all.forEach(fullKey->{
758   - videoStreamSessionManager.getSsrcTransaction(fullKey).ifPresent(ssrcTransaction -> {
759   - mediaServerNodeService.releaseSsrc(
760   - ssrcTransaction.getMediaServerId(), ssrcTransaction.getSsrc());
761   - mediaServerNodeService.closeRTPServer(
762   - ssrcTransaction.getMediaServerId(), ssrcTransaction.getStream());
763   - videoStreamSessionManager.remove(
764   - cameraCode, ssrcTransaction.getChannelId(),
765   - ssrcTransaction.getStream());
766   - });
767   -
  917 + videoStreamSessionManager.getSsrcTransactionCamaraKey(cameraCode);
  918 + ssrcKeys.ifPresent(
  919 + all -> {
  920 + all.forEach(
  921 + fullKey -> {
  922 + videoStreamSessionManager
  923 + .getSsrcTransaction(fullKey)
  924 + .ifPresent(
  925 + ssrcTransaction -> {
  926 + mediaServerNodeService.releaseSsrc(
  927 + ssrcTransaction.getMediaServerId(),
  928 + ssrcTransaction.getSsrc());
  929 + mediaServerNodeService.closeRTPServer(
  930 + ssrcTransaction.getMediaServerId(),
  931 + ssrcTransaction.getStream());
  932 + videoStreamSessionManager.remove(
  933 + cameraCode,
  934 + ssrcTransaction.getChannelId(),
  935 + ssrcTransaction.getStream());
  936 + });
  937 + });
768 938 });
769   - });
770   - }
  939 + }
  940 + });
  941 + }
  942 +
  943 + private ListenableFuture<TransportApiResponseMsg> handleGbtMedia(
  944 + TransportProtos.Gbt28181MediaServerMsg requestMsg) {
  945 + Optional<JsonNode> newMediaOpt =
  946 + dataDecodingEncodingService.decode(requestMsg.getProfile().toByteArray());
  947 + newMediaOpt.ifPresent(
  948 + json -> {
  949 + MediaServerDTO entity = JacksonUtil.treeToValue(json, MediaServerDTO.class);
  950 + MediaServerDTO queryEntity =
  951 + mediaServerService.findMediaServerInfoById(null, entity.getMediaServerId());
  952 + if (null == queryEntity) {
  953 + mediaServerService.saveMediaServer(entity);
  954 + } else {
  955 + entity.setId(queryEntity.getId());
  956 + mediaServerService.updateMediaServer(entity);
  957 + }
771 958 });
772 959
773   -
  960 + List<MediaServerDTO> allMediaKit = mediaServerService.getAllMediaKit();
  961 + Optional.ofNullable(allMediaKit)
  962 + .ifPresent(
  963 + all -> {
  964 + all.forEach(
  965 + dto -> {
  966 + String key = dto.getMediaServerId();
  967 + ZLMediaKitServerConfig zlMediaKitServerConfig = connectZlmServer(dto);
  968 + if (null != zlMediaKitServerConfig) {
  969 + zlMediaKitServerConfig.setIp(dto.getIp());
  970 + zlMediaKitServerConfig.setHttpPort(dto.getHttpPort());
  971 + zlMediaKitServerConfig.setTenantId(dto.getTenantId());
  972 + // 进行上线操作
  973 + mediaServerNodeService.zlmServerOnline(zlMediaKitServerConfig);
  974 + } else {
  975 + mediaServerNodeService.zlmServerOffline(key);
  976 + }
  977 + });
  978 + });
  979 + TransportApiResponseMsg.Builder responseBuilder = TransportApiResponseMsg.newBuilder();
  980 + responseBuilder.addGbt28181MediaServerMsg(TransportProtos.Gbt28181MediaServerMsg.newBuilder());
  981 + return Futures.immediateFuture(responseBuilder.build());
  982 + }
  983 +
  984 + /**
  985 + * 调用流媒体API接口获取流媒体配置
  986 + *
  987 + * @param mediaServerItem
  988 + * @return
  989 + */
  990 + private ZLMediaKitServerConfig connectZlmServer(MediaServerDTO mediaServerItem) {
  991 + log.info("启动流媒体【ZLMedia】验证,流媒体编号【{}】", mediaServerItem.getMediaServerId());
  992 + JsonNode responseJson = zlMediaKitRestFulUtils.getMediaServerConfig(mediaServerItem);
  993 + if (responseJson == null) {
  994 + log.error(
  995 + "流媒体【{}】服务地址【{}:{}】无法访问",
  996 + mediaServerItem.getMediaServerId(),
  997 + mediaServerItem.getIp(),
  998 + mediaServerItem.getHttpPort());
  999 + return null;
  1000 + }
  1001 + JsonNode data = responseJson.get(FastIotConstants.ZLMediaBody.DATA);
  1002 + if (data != null && !data.isEmpty()) {
  1003 + log.info(
  1004 + "流媒体【{}:{}】调用成功,响应内容【{}】", mediaServerItem.getIp(), mediaServerItem.getHttpPort(), data);
  1005 + return org.thingsboard.server.common.data.yunteng.utils.JacksonUtil.convertValue(
  1006 + data.get(0), ZLMediaKitServerConfig.class);
  1007 + } else {
  1008 + log.error(
  1009 + "流媒体【{}:{}】调用失败,失败原因【{}】",
  1010 + mediaServerItem.getIp(),
  1011 + mediaServerItem.getHttpPort(),
  1012 + responseJson.get(FastIotConstants.ZLMediaBody.MSG));
774 1013 }
  1014 + return null;
  1015 + }
775 1016 }
... ...
1   -package org.thingsboard.server.service.yunteng.media;
2   -
3   -import com.fasterxml.jackson.databind.JsonNode;
4   -import lombok.Getter;
5   -import lombok.extern.slf4j.Slf4j;
6   -import org.springframework.beans.factory.annotation.Value;
7   -import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
8   -import org.springframework.stereotype.Component;
9   -import org.thingsboard.server.common.data.id.EntityId;
10   -import org.thingsboard.server.common.data.yunteng.config.media.ZLMediaKitServerConfig;
11   -import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
12   -import org.thingsboard.server.common.data.yunteng.dto.sip.MediaServerDTO;
13   -import org.thingsboard.server.common.data.yunteng.utils.JacksonUtil;
14   -import org.thingsboard.server.common.data.yunteng.utils.ZLMediaKitRestFulUtils;
15   -import org.thingsboard.server.dao.util.yunteng.ZLMediaKitTaskUtils;
16   -import org.thingsboard.server.dao.yunteng.service.media.TkMediaServerNodeService;
17   -import org.thingsboard.server.dao.yunteng.service.media.TkMediaServerService;
18   -import org.thingsboard.server.common.data.yunteng.config.media.MediaConfig;
19   -import org.thingsboard.server.queue.util.TbCoreComponent;
20   -
21   -import javax.annotation.PostConstruct;
22   -import java.util.List;
23   -import java.util.Map;
24   -import java.util.Optional;
25   -
26   -@Component("ZLMediaKitState")
27   -@TbCoreComponent
28   -@ConditionalOnExpression(
29   - "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
30   -@Slf4j
31   -public class ZLMediaKitStateRunner {
32   - private final ZLMediaKitRestFulUtils zlMediaKitRestFulUtils;
33   - private final TkMediaServerNodeService tkMediaServerNodeService;
34   - private final TkMediaServerService tkMediaServerService;
35   - private final MediaConfig mediaConfig;
36   - private final ZLMediaKitTaskUtils zlMediaKitTaskUtils;
37   - private final Map<String, Boolean> startGetMedia;
38   -
39   - @Value("${media.defaultStateCheckIntervalInSec}")
40   - @Getter
41   - private int defaultStateCheckIntervalInSec;
42   -
43   - public ZLMediaKitStateRunner(
44   - ZLMediaKitRestFulUtils zlMediaKitRestFulUtils,
45   - TkMediaServerNodeService tkMediaServerNodeService,
46   - TkMediaServerService tkMediaServerService,
47   - MediaConfig mediaConfig,
48   - ZLMediaKitTaskUtils zlMediaKitTaskUtils,
49   - Map<String, Boolean> startGetMedia) {
50   - this.zlMediaKitRestFulUtils = zlMediaKitRestFulUtils;
51   - this.tkMediaServerNodeService = tkMediaServerNodeService;
52   - this.tkMediaServerService = tkMediaServerService;
53   - this.mediaConfig = mediaConfig;
54   - this.zlMediaKitTaskUtils = zlMediaKitTaskUtils;
55   - this.startGetMedia = startGetMedia;
56   - }
57   -
58   - @PostConstruct
59   - public void init() {
60   - updateDefaultMediaServer();
61   - // 从数据库获取所有的流媒体信息
62   - List<MediaServerDTO> dtoList = tkMediaServerService.getAllMediaKit();
63   -
64   - Optional.ofNullable(dtoList).ifPresent( all ->{
65   - all.forEach(dto ->{
66   - String key = dto.getMediaServerId();
67   - startGetMedia.put(key, true);
68   - zlMediaKitTaskUtils.startCronTask(
69   - key,
70   - () -> {
71   - ZLMediaKitServerConfig zlMediaKitServerConfig = getMediaServerConfig(dto);
72   - if (null != zlMediaKitServerConfig) {
73   - startGetMedia.remove(dto.getMediaServerId());
74   - zlMediaKitTaskUtils.stop(key);
75   - zlMediaKitServerConfig.setIp(dto.getIp());
76   - zlMediaKitServerConfig.setHttpPort(dto.getHttpPort());
77   - zlMediaKitServerConfig.setTenantId(dto.getTenantId());
78   - // 进行上线操作
79   - tkMediaServerNodeService.zlmServerOnline(zlMediaKitServerConfig);
80   - }
81   - },
82   - defaultStateCheckIntervalInSec);
83   - });
84   - });
85   - }
86   -
87   - private void updateDefaultMediaServer() {
88   - // 默认流媒体服务器
89   - MediaServerDTO oldMediaServer = tkMediaServerService.findDefaultMediaServer();
90   - MediaServerDTO defaultConfig = mediaConfig.getMediaSerItem();
91   - if (oldMediaServer == null) {
92   - defaultConfig.setTenantId(EntityId.NULL_UUID.toString());
93   - }else{
94   - defaultConfig.setId(oldMediaServer.getId());
95   - defaultConfig.setTenantId(oldMediaServer.getTenantId());
96   - }
97   - tkMediaServerService.saveOrUpdateMediaServer(defaultConfig);
98   - }
99   -
100   - /**
101   - * 调用流媒体API接口获取流媒体配置
102   - * @param mediaServerItem
103   - * @return
104   - */
105   - private ZLMediaKitServerConfig getMediaServerConfig(MediaServerDTO mediaServerItem) {
106   - log.error("启动流媒体【ZLMedia】验证,流媒体编号【{}】",mediaServerItem.getMediaServerId());
107   - if (startGetMedia == null) {
108   - return null;
109   - }
110   - if (!mediaServerItem.isDefaultServer()
111   - && tkMediaServerNodeService.getOne(mediaServerItem.getMediaServerId()).isEmpty()) {
112   - return null;
113   - }
114   - if (startGetMedia.get(mediaServerItem.getMediaServerId()) == null
115   - || !startGetMedia.get(mediaServerItem.getMediaServerId())) {
116   - return null;
117   - }
118   - JsonNode responseJson = zlMediaKitRestFulUtils.getMediaServerConfig(mediaServerItem);
119   - if(responseJson == null){
120   - log.error("流媒体【{}】服务地址【{}:{}】无法访问",mediaServerItem.getMediaServerId(),mediaServerItem.getIp(),mediaServerItem.getHttpPort());
121   - return null;
122   - }
123   - JsonNode data = responseJson.get(FastIotConstants.ZLMediaBody.DATA);
124   - if (data != null && !data.isEmpty()) {
125   - log.error("流媒体【{}:{}】调用成功,响应内容【{}】",mediaServerItem.getIp(),mediaServerItem.getHttpPort(),data);
126   - return JacksonUtil.convertValue(data.get(0), ZLMediaKitServerConfig.class);
127   - }
128   - log.error("流媒体【{}:{}】调用失败,失败原因【{}】",mediaServerItem.getIp(),mediaServerItem.getHttpPort(),responseJson.get(FastIotConstants.ZLMediaBody.MSG));
129   - return null;
130   - }
131   -}
... ... @@ -721,6 +721,45 @@ transport:
721 721 gbt28181:
722 722 # Enable/disable gbt28181 transport protocol.
723 723 enabled: "${GBT28181_ENABLED:false}"
  724 + sip:
  725 + # [必须修改] 本机的IP,对应你的网卡,监听什么ip就是使用什么网卡,
  726 + # 如果要监听多张网卡,可以使用逗号分隔多个IP, 例如: 192.168.1.4,10.0.0.4
  727 + # 如果不明白,就使用0.0.0.0,大部分情况都是可以的
  728 + # 请不要使用127.0.0.1,任何包括localhost在内的域名都是不可以的。
  729 + ip: ${GBT28181_SIP_IP:127.0.0.1}
  730 + # [可选] 28181服务监听的端口
  731 + port: ${GBT28181_SIP_PORT:5060}
  732 + #[可选]
  733 + id: ${GBT28181_SIP_ID:51010700599000000001}
  734 + # 根据国标6.1.2中规定,domain宜采用ID统一编码的前十位编码。国标附录D中定义前8位为中心编码(由省级、市级、区级、基层编号组成,参照GB/T 2260-2007)
  735 + # 后两位为行业编码,定义参照附录D.3
  736 + # 3701020049标识山东济南历下区 信息行业接入
  737 + # [可选]
  738 + domain: ${GBT28181_SIP_DOMAIN:5101070059}
  739 + #[可选]
  740 + password: ${GBT28181_SIP_PASSWORD:61332286}
  741 + #zlm 默认服务器配置
  742 + media:
  743 + id: ${GBT28181_MEDIA_GENERAL_ID:D2okJWKKaQ5bX7Va}
  744 + # [必须修改] zlm服务器的内网IP
  745 + ip: ${GBT28181_MEDIA_IP:127.0.0.1}
  746 + # [必须修改] zlm服务器的http.port
  747 + http-port: ${GBT28181_MEDIA_HTTP_PORT:28080}
  748 + hook-ip: ${GBT28181_MEDIA_HOOK_IP:}
  749 + stream-ip: ${GBT28181_MEDIA_STREAM_IP:}
  750 + # [可选] zlm服务器的hook.admin_params=secret
  751 + secret: ${GBT28181_MEDIA_API_SECRET:QhrTN7k6HcDnt0YyeolwHwiVYDgIHPMZ}
  752 + # 启用多端口模式, 多端口模式使用端口区分每路流,兼容性更好。 单端口使用流的ssrc区分, 点播超时建议使用多端口测试
  753 + rtp:
  754 + # [可选] 是否启用多端口模式, 开启后会在portRange范围内选择端口用于媒体流传输
  755 + enable: true
  756 + # [可选] 在此范围内选择端口用于媒体流传输, 必须提前在zlm上配置该属性,不然自动配置此属性可能不成功
  757 + port-range: ${GBT28181_MEDIA_RTP_PORT_RANGE:30000,30500} # 端口范围
  758 + # [可选] 国标级联在此范围内选择端口发送媒体流,
  759 + send-port-range: ${GBT28181_MEDIA_RTP_PORT_RANGE:30000,30500} # 端口范围
  760 + # 录像辅助服务, 部署此服务可以实现zlm录像的管理与下载, 0 表示不使用
  761 + record-assist-port: 0
  762 + defaultStateCheckIntervalInSec: "${DEFAULT_STATE_CHECK_INTERVAL:10}"
724 763 tcp:
725 764 # Enable/disable tcp transport protocol.
726 765 enabled: "${TCP_ENABLED:true}"
... ... @@ -1227,43 +1266,6 @@ logging:
1227 1266 frp:
1228 1267 server:
1229 1268 address: ${FRP_SERVER_ADDRESS:http://127.0.0.1}
1230   -sip:
1231   - # [必须修改] 本机的IP,对应你的网卡,监听什么ip就是使用什么网卡,
1232   - # 如果要监听多张网卡,可以使用逗号分隔多个IP, 例如: 192.168.1.4,10.0.0.4
1233   - # 如果不明白,就使用0.0.0.0,大部分情况都是可以的
1234   - # 请不要使用127.0.0.1,任何包括localhost在内的域名都是不可以的。
1235   - ip: ${GBT28181_SIP_IP:127.0.0.1}
1236   - # [可选] 28181服务监听的端口
1237   - port: ${GBT28181_SIP_PORT:5060}
1238   - #[可选]
1239   - id: ${GBT28181_SIP_ID:51010700599000000001}
1240   - # 根据国标6.1.2中规定,domain宜采用ID统一编码的前十位编码。国标附录D中定义前8位为中心编码(由省级、市级、区级、基层编号组成,参照GB/T 2260-2007)
1241   - # 后两位为行业编码,定义参照附录D.3
1242   - # 标识四川成都武侯下区 信息行业接入
1243   - # [可选]
1244   - domain: ${GBT28181_SIP_DOMAIN:5101070059}
1245   - #[可选]
1246   - password: ${GBT28181_SIP_PASSWORD:61332286}
1247   -#zlm 默认服务器配置
1248   -media:
1249   - id: ${GBT28181_MEDIA_GENERAL_ID:D2okJWKKaQ5bX7Va}
1250   - # [必须修改] zlm服务器的内网IP
1251   - ip: ${GBT28181_MEDIA_IP:127.0.0.1}
1252   - # [必须修改] zlm服务器的http.port
1253   - http-port: ${GBT28181_MEDIA_HTTP_PORT:28080}
1254   - # [可选] zlm服务器的hook.admin_params=secret
1255   - secret: ${GBT28181_MEDIA_API_SECRET:QhrTN7k6HcDnt0YyeolwHwiVYDgIHPMZ}
1256   - # 启用多端口模式, 多端口模式使用端口区分每路流,兼容性更好。 单端口使用流的ssrc区分, 点播超时建议使用多端口测试
1257   - rtp:
1258   - # [可选] 是否启用多端口模式, 开启后会在portRange范围内选择端口用于媒体流传输
1259   - enable: true
1260   - # [可选] 在此范围内选择端口用于媒体流传输, 必须提前在zlm上配置该属性,不然自动配置此属性可能不成功
1261   - port-range: ${GBT28181_MEDIA_RTP_PORT_RANGE:30000,30500} # 端口范围
1262   - # [可选] 国标级联在此范围内选择端口发送媒体流,
1263   - send-port-range: ${GBT28181_MEDIA_RTP_PORT_RANGE:30000,30500} # 端口范围
1264   - # 录像辅助服务, 部署此服务可以实现zlm录像的管理与下载, 0 表示不使用
1265   - record-assist-port: 0
1266   - defaultStateCheckIntervalInSec: "${DEFAULT_STATE_CHECK_INTERVAL:10}"
1267 1269
1268 1270 thingskit:
1269 1271 release:
... ...
... ... @@ -680,6 +680,7 @@ message TransportApiRequestMsg {
680 680 //Thingskit function
681 681 ScriptProto script = 14;
682 682 Gbt28181RequestMsg gbt28181RequestMsg = 15;
  683 + Gbt28181MediaServerMsg gbt28181MediaServerMsg = 16;
683 684 }
684 685
685 686 /* Response from ThingsBoard Core Service to Transport Service */
... ... @@ -698,6 +699,7 @@ message TransportApiResponseMsg {
698 699 //Thingskit function
699 700 repeated ScriptProto scriptsResponseMsg = 11;
700 701 Gbt28181ResponseMsg gbt28181ResponseMsg = 12;
  702 + repeated Gbt28181MediaServerMsg gbt28181MediaServerMsg = 13;
701 703 }
702 704
703 705 /* Messages that are handled by ThingsBoard Core Service */
... ... @@ -826,5 +828,11 @@ message Gbt28181ResponseMsg{
826 828 int64 entityIdMSB = 11;
827 829 int64 entityIdLSB = 12;
828 830 }
  831 +message Gbt28181MediaServerMsg{
  832 + bytes profile = 1;
  833 +}
  834 +message Gbt28181MediaResponseMsg{
  835 + repeated Gbt28181MediaServerMsg profiles = 1;
  836 +}
829 837
830 838
... ...
... ... @@ -3,7 +3,6 @@ package org.thingsboard.server.common.data.yunteng.common.media;
3 3 import java.util.*;
4 4 import lombok.extern.slf4j.Slf4j;
5 5 import org.springframework.beans.factory.annotation.Autowired;
6   -import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
7 6 import org.springframework.stereotype.Component;
8 7 import org.thingsboard.server.common.data.yunteng.config.media.UserSetting;
9 8 import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
... ... @@ -88,12 +87,14 @@ public class VideoStreamSessionManager {
88 87 public Optional<SsrcTransactionDTO> getSsrcTransaction(String fullKey) {
89 88 return cacheUtils.get(cacheName, fullKey);
90 89 }
91   - public Optional<SsrcTransactionDTO> getSsrcTransaction(String cameraCode, String channelId, String stream) {
92   - Optional<Set<String>> keys =getSsrcTransactionChannelKey(cameraCode, channelId,stream);
93 90
94   - if(keys.isPresent()){
95   - Optional<String> fullKey =keys.get().stream().findFirst();
96   - if(fullKey.isPresent()){
  91 + public Optional<SsrcTransactionDTO> getSsrcTransaction(
  92 + String cameraCode, String channelId, String stream) {
  93 + Optional<Set<String>> keys = getSsrcTransactionChannelKey(cameraCode, channelId, stream);
  94 +
  95 + if (keys.isPresent()) {
  96 + Optional<String> fullKey = keys.get().stream().findFirst();
  97 + if (fullKey.isPresent()) {
97 98 return getSsrcTransaction(fullKey.get());
98 99 }
99 100 }
... ...
1   -package org.thingsboard.server.common.data.yunteng.config.media;
2   -
3   -import lombok.Data;
4   -import lombok.extern.slf4j.Slf4j;
5   -import org.springframework.beans.factory.annotation.Value;
6   -import org.springframework.boot.context.properties.ConfigurationProperties;
7   -import org.springframework.stereotype.Component;
8   -import org.springframework.util.ObjectUtils;
9   -import org.thingsboard.server.common.data.yunteng.dto.sip.MediaServerDTO;
10   -
11   -import java.net.InetAddress;
12   -import java.net.UnknownHostException;
13   -import java.util.Objects;
14   -import java.util.regex.Pattern;
15   -
16   -/**
17   - * 配置文件里面的流媒体配置信息
18   - */
19   -@ConfigurationProperties(prefix = "media")
20   -@Component
21   -@Data
22   -@Slf4j
23   -public class MediaConfig {
24   - @Value("${media.id}")
25   - private String mediaServerId;
26   -
27   - @Value("${media.ip}")
28   - private String ip;
29   -
30   - @Value("${media.hook-ip:}")
31   - private String hookIp;
32   -
33   - @Value("${sip.ip}")
34   - private String sipIp;
35   -
36   - @Value("${sip.domain}")
37   - private String sipDomain;
38   -
39   - @Value("${media.sdp-ip:${media.ip}}")
40   - private String sdpIp;
41   -
42   - @Value("${media.stream-ip:${media.ip}}")
43   - private String streamIp;
44   -
45   - @Value("${media.http-port}")
46   - private Integer httpPort;
47   -
48   - @Value("${media.http-ssl-port:0}")
49   - private Integer httpSslPort = 0;
50   -
51   - @Value("${media.rtmp-port:0}")
52   - private Integer rtmpPort = 0;
53   -
54   - @Value("${media.rtmp-ssl-port:0}")
55   - private Integer rtmpSslPort = 0;
56   -
57   - @Value("${media.rtp-proxy-port:0}")
58   - private Integer rtpProxyPort = 0;
59   -
60   - @Value("${media.rtsp-port:0}")
61   - private Integer rtspPort = 0;
62   -
63   - @Value("${media.rtsp-ssl-port:0}")
64   - private Integer rtspSslPort = 0;
65   -
66   - @Value("${media.auto-config:true}")
67   - private boolean autoConfig = true;
68   -
69   - @Value("${media.secret}")
70   - private String secret;
71   -
72   - @Value("${media.rtp.enable}")
73   - private boolean rtpEnable;
74   -
75   - @Value("${media.rtp.port-range}")
76   - private String rtpPortRange;
77   -
78   - @Value("${media.rtp.send-port-range}")
79   - private String rtpSendPortRange;
80   -
81   - @Value("${media.record-assist-port:0}")
82   - private Integer recordAssistPort = 0;
83   - private boolean status;
84   -
85   - public MediaServerDTO getMediaSerItem() {
86   - MediaServerDTO mediaServerItem = new MediaServerDTO();
87   - mediaServerItem.setMediaServerId(mediaServerId);
88   - mediaServerItem.setIp(ip);
89   - mediaServerItem.setDefaultServer(true);
90   - mediaServerItem.setHookIp(getHookIp());
91   - mediaServerItem.setSdpIp(getSdpIp());
92   - mediaServerItem.setStreamIp(getStreamIp());
93   - mediaServerItem.setHttpPort(httpPort);
94   - mediaServerItem.setHttpSslPort(httpSslPort);
95   - mediaServerItem.setRtmpPort(rtmpPort);
96   - mediaServerItem.setRtmpSslPort(rtmpSslPort);
97   - mediaServerItem.setRtpProxyPort(getRtpProxyPort());
98   - mediaServerItem.setRtspPort(rtspPort);
99   - mediaServerItem.setRtspSslPort(rtspSslPort);
100   - mediaServerItem.setAutoConfig(autoConfig);
101   - mediaServerItem.setSecret(secret);
102   - mediaServerItem.setRtpEnable(rtpEnable);
103   - mediaServerItem.setRtpPortRange(rtpPortRange);
104   - mediaServerItem.setSendRtpPortRange(rtpSendPortRange);
105   - mediaServerItem.setRecordAssistPort(recordAssistPort);
106   - mediaServerItem.setHookAliveInterval(30.00f);
107   - mediaServerItem.setStatus(status);
108   - return mediaServerItem;
109   - }
110   -
111   - public String getHookIp() {
112   - if (ObjectUtils.isEmpty(hookIp)) {
113   - return sipIp.split(",")[0];
114   - } else {
115   - return hookIp;
116   - }
117   - }
118   -
119   - public String getSipIp() {
120   - if (sipIp == null) {
121   - return this.ip;
122   - } else {
123   - return sipIp;
124   - }
125   - }
126   -
127   - public int getRtpProxyPort() {
128   - return Objects.requireNonNullElse(rtpProxyPort, 0);
129   - }
130   -
131   - public String getSdpIp() {
132   - if (ObjectUtils.isEmpty(sdpIp)) {
133   - return ip;
134   - } else {
135   - if (isValidIPAddress(sdpIp)) {
136   - return sdpIp;
137   - } else {
138   - // 按照域名解析
139   - String hostAddress = null;
140   - try {
141   - hostAddress = InetAddress.getByName(sdpIp).getHostAddress();
142   - } catch (UnknownHostException e) {
143   - log.error("[获取SDP IP]: 域名解析失败");
144   - }
145   - return hostAddress;
146   - }
147   - }
148   - }
149   -
150   - public String getStreamIp() {
151   - if (ObjectUtils.isEmpty(streamIp)) {
152   - return ip;
153   - } else {
154   - return streamIp;
155   - }
156   - }
157   -
158   - private boolean isValidIPAddress(String ipAddress) {
159   - if ((ipAddress != null) && (!ipAddress.isEmpty())) {
160   - return Pattern.matches(
161   - "^([1-9]|[1-9]\\d|1\\d{2}|2[0-4]\\d|25[0-5])(\\.(\\d|[1-9]\\d|1\\d{2}|2[0-4]\\d|25[0-5])){3}$",
162   - ipAddress);
163   - }
164   - return false;
165   - }
166   -}
1 1 package org.thingsboard.server.common.data.yunteng.config.media;
2 2
3 3 import lombok.Data;
4   -import org.springframework.boot.context.properties.ConfigurationProperties;
5 4 import org.springframework.stereotype.Component;
6 5
7   -@ConfigurationProperties(prefix = "user-settings")
8 6 @Component
9 7 @Data
10 8 public class UserSetting {
11   - private String serverId = "000000";
12   - private Boolean seniorSdp = Boolean.FALSE;
13   - private Boolean pushAuthority = Boolean.TRUE;
14   - private Boolean recordSip = Boolean.TRUE;
15   - private Boolean recordPushLive = Boolean.TRUE;
16   - private String recordPath = null;
17   - private Boolean streamOnDemand = Boolean.TRUE;
18   - private Boolean sipUseSourceIpAsRemoteAddress = Boolean.FALSE;
19   - private Integer playTimeout = 30000;
  9 + private String serverId = "000000";
  10 + private Boolean seniorSdp = Boolean.FALSE;
  11 + private Boolean pushAuthority = Boolean.TRUE;
  12 + private Boolean recordSip = Boolean.TRUE;
  13 + private Boolean recordPushLive = Boolean.TRUE;
  14 + private String recordPath = null;
  15 + private Boolean streamOnDemand = Boolean.TRUE;
  16 + private Boolean sipUseSourceIpAsRemoteAddress = Boolean.FALSE;
  17 + private Integer playTimeout = 30000;
20 18 }
... ...
... ... @@ -3,8 +3,6 @@ package org.thingsboard.server.common.data.yunteng.dto.sip;
3 3 import io.swagger.annotations.ApiModelProperty;
4 4 import lombok.Data;
5 5 import lombok.EqualsAndHashCode;
6   -import org.springframework.util.ObjectUtils;
7   -import org.thingsboard.server.common.data.yunteng.config.media.ZLMediaKitServerConfig;
8 6 import org.thingsboard.server.common.data.yunteng.dto.TenantDTO;
9 7
10 8 @EqualsAndHashCode(callSuper = true)
... ... @@ -63,11 +61,11 @@ public class MediaServerDTO extends TenantDTO {
63 61 @ApiModelProperty(value = "流媒体服务器的状态")
64 62 private boolean status;
65 63
66   - @ApiModelProperty(value = "多端口RTP收流端口范围")
  64 + @ApiModelProperty(value = "RTP收流端口范围")
67 65 private String rtpPortRange;
68 66
69   - @ApiModelProperty(value = "RTP发流端口范围")
70   - private String sendRtpPortRange;
  67 + @ApiModelProperty(value = "RTP推流端口范围")
  68 + private String rtpSendPortRange;
71 69
72 70 @ApiModelProperty(value = "assist服务端口")
73 71 private Integer recordAssistPort;
... ... @@ -81,33 +79,7 @@ public class MediaServerDTO extends TenantDTO {
81 79 @ApiModelProperty(value = "当前使用到的端口")
82 80 private Integer currentPort;
83 81
84   - public MediaServerDTO(){
85   -
86   - }
87   - public MediaServerDTO(ZLMediaKitServerConfig zlmServerConfig, String sipIp) {
88   - setId(zlmServerConfig.getGeneralMediaServerId());
89   - ip = zlmServerConfig.getIp();
90   - hookIp = ObjectUtils.isEmpty(zlmServerConfig.getHookIp()) ? sipIp : zlmServerConfig.getHookIp();
91   - sdpIp =
92   - ObjectUtils.isEmpty(zlmServerConfig.getSdpIp())
93   - ? zlmServerConfig.getIp()
94   - : zlmServerConfig.getSdpIp();
95   - streamIp =
96   - ObjectUtils.isEmpty(zlmServerConfig.getStreamIp())
97   - ? zlmServerConfig.getIp()
98   - : zlmServerConfig.getStreamIp();
99   - httpPort = zlmServerConfig.getHttpPort();
100   - httpSslPort = zlmServerConfig.getHttpSslPort();
101   - rtmpPort = zlmServerConfig.getRtmpPort();
102   - rtmpSslPort = zlmServerConfig.getRtmpSslPort();
103   - rtpProxyPort = zlmServerConfig.getRtpProxyPort();
104   - rtspPort = zlmServerConfig.getRtspPort();
105   - rtspSslPort = zlmServerConfig.getRtspSslPort();
106   - autoConfig = true; // 默认值true;
107   - secret = zlmServerConfig.getApiSecret();
108   - hookAliveInterval = zlmServerConfig.getHookAliveInterval();
109   - rtpEnable = false; // 默认使用单端口;直到用户自己设置开启多端口
110   - rtpPortRange = zlmServerConfig.getPortRange().replace("_", ","); // 默认使用30000,30500作为级联时发送流的端口号
111   - recordAssistPort = 0; // 默认关闭
112   - }
  82 + private String hookEnable;
  83 +
  84 + public MediaServerDTO() {}
113 85 }
... ...
1 1 package org.thingsboard.server.common.data.yunteng.dto.sip;
2 2
3 3 import io.swagger.annotations.ApiModelProperty;
  4 +import java.io.Serializable;
4 5 import lombok.Data;
5 6 import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
6 7
7   -import java.io.Serializable;
8   -
9 8 @Data
10 9 public class SipDeviceDTO implements Serializable {
11 10 @ApiModelProperty(value = "设备国标编号")
... ... @@ -37,6 +36,7 @@ public class SipDeviceDTO implements Serializable {
37 36
38 37 @ApiModelProperty(value = "是否开启ssrc校验,默认关闭,开启可以防止串流")
39 38 private boolean ssrcCheck = true;
  39 +
40 40 @ApiModelProperty(value = "生产厂商")
41 41 private String manufacturer;
42 42
... ... @@ -48,12 +48,13 @@ public class SipDeviceDTO implements Serializable {
48 48
49 49 @ApiModelProperty(value = "固件版本")
50 50 private String firmware;
  51 +
51 52 public Integer getStreamModeForParam() {
52 53 if (FastIotConstants.StreamMode.UDP.equalsIgnoreCase(streamMode)) {
53 54 return 0;
54   - }else if (FastIotConstants.StreamMode.TCP_PASSIVE.equalsIgnoreCase(streamMode)) {
  55 + } else if (FastIotConstants.StreamMode.TCP_PASSIVE.equalsIgnoreCase(streamMode)) {
55 56 return 1;
56   - }else if (FastIotConstants.StreamMode.TCP_ACTIVE.equalsIgnoreCase(streamMode)) {
  57 + } else if (FastIotConstants.StreamMode.TCP_ACTIVE.equalsIgnoreCase(streamMode)) {
57 58 return 2;
58 59 }
59 60 return 0;
... ...
... ... @@ -2,6 +2,8 @@ package org.thingsboard.server.common.data.yunteng.utils;
2 2
3 3 import lombok.extern.slf4j.Slf4j;
4 4
  5 +import java.util.regex.Pattern;
  6 +
5 7 /**
6 8 * 数值格式相关工具类
7 9 */
... ... @@ -35,4 +37,18 @@ public class DataUtils {
35 37 return false;
36 38 }
37 39 }
  40 +
  41 + /**
  42 + * 是否有效的IP地址
  43 + * @param ipAddress IP地址字符串
  44 + * @return
  45 + */
  46 + public static boolean isIPAddress(String ipAddress) {
  47 + if ((ipAddress != null) && (!ipAddress.isEmpty())) {
  48 + return Pattern.matches(
  49 + "^([1-9]|[1-9]\\d|1\\d{2}|2[0-4]\\d|25[0-5])(\\.(\\d|[1-9]\\d|1\\d{2}|2[0-4]\\d|25[0-5])){3}$",
  50 + ipAddress);
  51 + }
  52 + return false;
  53 + }
38 54 }
... ...
1   -/**
2   - * Copyright © 2016-2022 The Thingsboard Authors
3   - * <p>
4   - * Licensed under the Apache License, Version 2.0 (the "License");
5   - * you may not use this file except in compliance with the License.
6   - * You may obtain a copy of the License at
7   - * <p>
8   - * http://www.apache.org/licenses/LICENSE-2.0
9   - * <p>
10   - * Unless required by applicable law or agreed to in writing, software
11   - * distributed under the License is distributed on an "AS IS" BASIS,
12   - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   - * See the License for the specific language governing permissions and
14   - * limitations under the License.
15   - */
16   -package org.thingsboard.server.transport.adaptors;
17   -
18   -import io.netty.buffer.ByteBuf;
19   -import io.netty.handler.codec.mqtt.MqttPublishMessage;
20   -import java.nio.charset.Charset;
21   -import java.nio.charset.StandardCharsets;
22   -import java.util.Optional;
23   -import java.util.concurrent.ExecutionException;
24   -import org.thingsboard.server.common.data.ota.OtaPackageType;
25   -import org.thingsboard.server.common.transport.adaptor.AdaptorException;
26   -import org.thingsboard.server.gen.transport.TransportProtos.*;
27   -import org.thingsboard.server.transport.session.GbtDeviceSessionCtx;
28   -
29   -/**
30   - * 将收到的数据流转换为接口需要的数据格式
31   - * 1、基于解析脚本将ByteBuf转JSON对象。
32   - * 2、将JSON对象转PROTOBUF对象。
33   - */
34   -public interface GbtTransportAdaptor {
35   - static char[] HEX_VOCABLE = {'0', '1', '2', '3', '4', '5', '6', '7',
36   - '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};
37   - static final Charset UTF8 = StandardCharsets.UTF_8;
38   -
39   -
40   - /**
41   - * 设备数据转遥测数据
42   - *
43   - * @param ctx
44   - * @param inbound 设备上报的数据字符串
45   - * @return 平台需要的遥测数据
46   - * @throws AdaptorException
47   - */
48   - PostTelemetryMsg convertToPostTelemetry(GbtDeviceSessionCtx ctx, String inbound) throws AdaptorException;
49   -
50   -
51   - PostAttributeMsg convertToPostAttributes(GbtDeviceSessionCtx ctx, String inbound) throws AdaptorException;
52   -
53   - GetAttributeRequestMsg convertToGetAttributes(GbtDeviceSessionCtx ctx, MqttPublishMessage inbound, String topicBase) throws AdaptorException;
54   -
55   - ToDeviceRpcResponseMsg convertToDeviceRpcResponse(GbtDeviceSessionCtx ctx, String inbound) throws AdaptorException;
56   -
57   - ToServerRpcRequestMsg convertToServerRpcRequest(GbtDeviceSessionCtx ctx, MqttPublishMessage mqttMsg, String topicBase) throws AdaptorException;
58   -
59   -
60   -
61   - Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, GetAttributeResponseMsg responseMsg, String topicBase) throws AdaptorException;
62   -
63   -
64   - Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, AttributeUpdateNotificationMsg notificationMsg, String topic) throws AdaptorException;
65   -
66   -
67   - Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, ToDeviceRpcRequestMsg rpcRequest) throws ExecutionException, InterruptedException;
68   -
69   - Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, ToServerRpcResponseMsg rpcResponse, String topicBase) throws AdaptorException;
70   -
71   - ProvisionDeviceRequestMsg convertToProvisionRequestMsg(GbtDeviceSessionCtx ctx, MqttPublishMessage inbound) throws AdaptorException;
72   -
73   - Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, ProvisionDeviceResponseMsg provisionResponse) throws AdaptorException;
74   -
75   - Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, byte[] firmwareChunk, String requestId, int chunk, OtaPackageType firmwareType) throws AdaptorException;
76   -
77   - public static byte[] toBytes(ByteBuf inbound) {
78   - byte[] bytes = new byte[inbound.readableBytes()];
79   - int readerIndex = inbound.readerIndex();
80   - inbound.getBytes(readerIndex, bytes);
81   - return bytes;
82   - }
83   -
84   - public static String bytesToHex(byte[] bs) {
85   - StringBuilder sb = new StringBuilder();
86   - for (byte b : bs) {
87   - int high = (b >> 4) & 0x0f;
88   - int low = b & 0x0f;
89   - sb.append(HEX_VOCABLE[high]);
90   - sb.append(HEX_VOCABLE[low]);
91   - }
92   - return sb.toString();
93   - }
94   -}
1   -/**
2   - * Copyright © 2016-2022 The Thingsboard Authors
3   - * <p>
4   - * Licensed under the Apache License, Version 2.0 (the "License");
5   - * you may not use this file except in compliance with the License.
6   - * You may obtain a copy of the License at
7   - * <p>
8   - * http://www.apache.org/licenses/LICENSE-2.0
9   - * <p>
10   - * Unless required by applicable law or agreed to in writing, software
11   - * distributed under the License is distributed on an "AS IS" BASIS,
12   - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   - * See the License for the specific language governing permissions and
14   - * limitations under the License.
15   - */
16   -package org.thingsboard.server.transport.adaptors;
17   -
18   -import com.google.gson.JsonElement;
19   -import com.google.gson.JsonObject;
20   -import com.google.gson.JsonParser;
21   -import com.google.gson.JsonSyntaxException;
22   -import io.netty.buffer.ByteBuf;
23   -import io.netty.handler.codec.mqtt.MqttPublishMessage;
24   -import java.nio.charset.Charset;
25   -import java.nio.charset.StandardCharsets;
26   -import java.util.*;
27   -import java.util.concurrent.ExecutionException;
28   -import lombok.extern.slf4j.Slf4j;
29   -import org.springframework.stereotype.Component;
30   -import org.springframework.util.StringUtils;
31   -import org.thingsboard.server.common.data.ota.OtaPackageType;
32   -import org.thingsboard.server.common.transport.adaptor.AdaptorException;
33   -import org.thingsboard.server.common.transport.adaptor.JsonConverter;
34   -import org.thingsboard.server.gen.transport.TransportProtos;
35   -import org.thingsboard.server.transport.session.GbtDeviceSessionCtx;
36   -
37   -/**
38   - * @author Andrew Shvayka
39   - */
40   -@Component
41   -@Slf4j
42   -public class JsonGbtAdaptor implements GbtTransportAdaptor {
43   -
44   - protected static final Charset UTF8 = StandardCharsets.UTF_8;
45   - private static final JsonParser parser = new JsonParser();
46   -
47   -
48   - @Override
49   - public TransportProtos.PostTelemetryMsg convertToPostTelemetry(GbtDeviceSessionCtx ctx, String payload) throws AdaptorException {
50   - try {
51   - return JsonConverter.convertToTelemetryProto(new JsonParser().parse(payload));
52   - } catch (IllegalStateException | JsonSyntaxException ex) {
53   - log.debug("Failed to decode post telemetry request", ex);
54   - throw new AdaptorException(ex);
55   - }
56   - }
57   -
58   -
59   - @Override
60   - public TransportProtos.PostAttributeMsg convertToPostAttributes(GbtDeviceSessionCtx ctx, String payload) throws AdaptorException {
61   - try {
62   - return JsonConverter.convertToAttributesProto(new JsonParser().parse(payload));
63   - } catch (IllegalStateException | JsonSyntaxException ex) {
64   - log.debug("Failed to decode post attributes request", ex);
65   - throw new AdaptorException(ex);
66   - }
67   - }
68   -
69   -
70   - @Override
71   - public TransportProtos.ProvisionDeviceRequestMsg convertToProvisionRequestMsg(GbtDeviceSessionCtx ctx, MqttPublishMessage inbound) throws AdaptorException {
72   - String payload = validatePayload(ctx.getSessionId(), inbound.payload(), false);
73   - try {
74   - return JsonConverter.convertToProvisionRequestMsg(payload);
75   - } catch (IllegalStateException | JsonSyntaxException ex) {
76   - throw new AdaptorException(ex);
77   - }
78   - }
79   -
80   - @Override
81   - public TransportProtos.GetAttributeRequestMsg convertToGetAttributes(GbtDeviceSessionCtx ctx, MqttPublishMessage inbound, String topicBase) throws AdaptorException {
82   - return processGetAttributeRequestMsg(inbound, topicBase);
83   - }
84   -
85   - @Override
86   - public TransportProtos.ToDeviceRpcResponseMsg convertToDeviceRpcResponse(GbtDeviceSessionCtx ctx, String inbound) throws AdaptorException {
87   - try {
88   -// Integer requestId = ctx.getRpcRequesting(inbound.getIdentifier());
89   -// if(requestId != null){
90   -// String payload = JacksonUtil.toString(inbound.getDatas());
91   -// return TransportProtos.ToDeviceRpcResponseMsg.newBuilder().setRequestId(requestId).setPayload(payload).build();
92   -// }
93   - return null;
94   - } catch (RuntimeException e) {
95   - log.debug("Failed to decode rpc response", e);
96   - throw new AdaptorException(e);
97   - }
98   - }
99   -
100   - @Override
101   - public TransportProtos.ToServerRpcRequestMsg convertToServerRpcRequest(GbtDeviceSessionCtx ctx, MqttPublishMessage inbound, String topicBase) throws AdaptorException {
102   - return processToServerRpcRequestMsg(ctx, inbound, topicBase);
103   - }
104   -
105   - @Override
106   - public Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, TransportProtos.GetAttributeResponseMsg responseMsg, String topicBase) throws AdaptorException {
107   - return processConvertFromAttributeResponseMsg(ctx, responseMsg, topicBase);
108   - }
109   -
110   -
111   - @Override
112   - public Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, TransportProtos.AttributeUpdateNotificationMsg notificationMsg, String topic) {
113   - return Optional.of(createTcpMessage(ctx, JsonConverter.toJson(notificationMsg)));
114   - }
115   -
116   -
117   - @Override
118   - public Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, TransportProtos.ToDeviceRpcRequestMsg rpcRequest) throws ExecutionException, InterruptedException {
119   - String payload = rpcRequest.getParams();//methodThingskit
120   -
121   -// TcpDownEntry data = new TcpDownEntry();
122   -// data.setDatas(payload);
123   -// data.setIdentifier(payload);
124   - return Optional.of("data");
125   - }
126   -
127   -
128   -
129   - @Override
130   - public Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, TransportProtos.ToServerRpcResponseMsg rpcResponse, String topicBase) {
131   - return Optional.of(createTcpMessage(ctx, JsonConverter.toJson(rpcResponse)));
132   - }
133   -
134   - @Override
135   - public Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, TransportProtos.ProvisionDeviceResponseMsg provisionResponse) {
136   - return Optional.of(createTcpMessage(ctx, JsonConverter.toJson(provisionResponse)));
137   - }
138   -
139   - @Override
140   - public Optional<String> convertToPublish(GbtDeviceSessionCtx ctx, byte[] firmwareChunk, String requestId, int chunk, OtaPackageType firmwareType) {
141   - return Optional.of(null);
142   - }
143   -
144   - public static JsonElement validateJsonPayload(UUID sessionId, ByteBuf payloadData) throws AdaptorException {
145   - String payload = validatePayload(sessionId, payloadData, false);
146   - try {
147   - return new JsonParser().parse(payload);
148   - } catch (JsonSyntaxException ex) {
149   - log.debug("Payload is in incorrect format: {}", payload);
150   - throw new AdaptorException(ex);
151   - }
152   - }
153   -
154   - private TransportProtos.GetAttributeRequestMsg processGetAttributeRequestMsg(MqttPublishMessage inbound, String topicBase) throws AdaptorException {
155   - String topicName = inbound.variableHeader().topicName();
156   - try {
157   - TransportProtos.GetAttributeRequestMsg.Builder result = TransportProtos.GetAttributeRequestMsg.newBuilder();
158   - result.setRequestId(getRequestId(topicName, topicBase));
159   - String payload = inbound.payload().toString(UTF8);
160   - JsonElement requestBody = new JsonParser().parse(payload);
161   - Set<String> clientKeys = toStringSet(requestBody, "clientKeys");
162   - Set<String> sharedKeys = toStringSet(requestBody, "sharedKeys");
163   - if (clientKeys != null) {
164   - result.addAllClientAttributeNames(clientKeys);
165   - }
166   - if (sharedKeys != null) {
167   - result.addAllSharedAttributeNames(sharedKeys);
168   - }
169   - return result.build();
170   - } catch (RuntimeException e) {
171   - log.debug("Failed to decode get attributes request", e);
172   - throw new AdaptorException(e);
173   - }
174   - }
175   -
176   -
177   - private TransportProtos.ToServerRpcRequestMsg processToServerRpcRequestMsg(GbtDeviceSessionCtx ctx, MqttPublishMessage inbound, String topicBase) throws AdaptorException {
178   - String topicName = inbound.variableHeader().topicName();
179   - String payload = validatePayload(ctx.getSessionId(), inbound.payload(), false);
180   - try {
181   - int requestId = getRequestId(topicName, topicBase);
182   - return JsonConverter.convertToServerRpcRequest(new JsonParser().parse(payload), requestId);
183   - } catch (IllegalStateException | JsonSyntaxException ex) {
184   - log.debug("Failed to decode to server rpc request", ex);
185   - throw new AdaptorException(ex);
186   - }
187   - }
188   -
189   - private Optional<String> processConvertFromAttributeResponseMsg(GbtDeviceSessionCtx ctx, TransportProtos.GetAttributeResponseMsg responseMsg, String topicBase) throws AdaptorException {
190   - if (!StringUtils.isEmpty(responseMsg.getError())) {
191   - throw new AdaptorException(responseMsg.getError());
192   - } else {
193   - int requestId = responseMsg.getRequestId();
194   - if (requestId >= 0) {
195   - return Optional.of(createTcpMessage(ctx,
196   - JsonConverter.toJson(responseMsg)));
197   - }
198   - return Optional.empty();
199   - }
200   - }
201   -
202   - private Optional<String> processConvertFromGatewayAttributeResponseMsg(GbtDeviceSessionCtx ctx, String deviceName, TransportProtos.GetAttributeResponseMsg responseMsg) throws AdaptorException {
203   - if (!StringUtils.isEmpty(responseMsg.getError())) {
204   - throw new AdaptorException(responseMsg.getError());
205   - } else {
206   - JsonObject result = JsonConverter.getJsonObjectForGateway(deviceName, responseMsg);
207   - return Optional.of(createTcpMessage(ctx, result));
208   - }
209   - }
210   -
211   -
212   - private Set<String> toStringSet(JsonElement requestBody, String name) {
213   - JsonElement element = requestBody.getAsJsonObject().get(name);
214   - if (element != null) {
215   - return new HashSet<>(Arrays.asList(element.getAsString().split(",")));
216   - } else {
217   - return null;
218   - }
219   - }
220   -
221   - private static String validatePayload(UUID sessionId, ByteBuf payloadData, boolean isEmptyPayloadAllowed) throws AdaptorException {
222   - String payload = payloadData.toString(UTF8);
223   - if (payload == null) {
224   - log.debug("[{}] Payload is empty!", sessionId);
225   - if (!isEmptyPayloadAllowed) {
226   - throw new AdaptorException(new IllegalArgumentException("Payload is empty!"));
227   - }
228   - }
229   - return payload;
230   - }
231   -
232   -
233   - private int getRequestId(String topicName, String topic) {
234   - return Integer.parseInt(topicName.substring(topic.length()));
235   - }
236   -
237   -
238   - protected String createTcpMessage(GbtDeviceSessionCtx ctx, JsonElement json) {
239   -// TCPMessage msg = new TCPMessage(MqttMessageType.PUBLISH,);
240   -//// new MqttFixedHeader(MqttMessageType.PUBLISH, false, ctx.getQoSForTopic(topic), false, 0);
241   -// MqttPublishVariableHeader header = new MqttPublishVariableHeader(topic, ctx.nextMsgId());
242   -// ByteBuf payload = ALLOCATOR.buffer();
243   -// payload.writeBytes(json.toString().getBytes(UTF8));
244   -// return new MqttPublishMessage(mqttFixedHeader, header, payload);
245   - return null;
246   - }
247   -
248   -
249   -}
... ... @@ -10,13 +10,11 @@ import javax.sip.address.AddressFactory;
10 10 import javax.sip.address.SipURI;
11 11 import javax.sip.header.*;
12 12 import org.springframework.beans.factory.annotation.Autowired;
13   -import org.springframework.stereotype.Component;
14   -import org.thingsboard.server.common.data.yunteng.config.media.SipConfig;
15   -import org.thingsboard.server.common.data.yunteng.config.media.ThingsKitVersionConfig;
16   -import org.thingsboard.server.transport.gbt28181.SipLayer;
  13 +import org.thingsboard.server.transport.config.SipConfig;
  14 +import org.thingsboard.server.transport.config.ThingsKitVersionConfig;
  15 +import org.thingsboard.server.transport.gbt28181.sip.SipTransportService;
17 16
18   -@Component
19   -public class AbstractSIPRequestProcess {
  17 +public abstract class AbstractSIPRequestProcess {
20 18 @Autowired private SipConfig sipConfig;
21 19 @Autowired protected ThingsKitVersionConfig thingsKitVersionConfig;
22 20
... ... @@ -41,7 +39,7 @@ public class AbstractSIPRequestProcess {
41 39 ViaHeader viaHeader =
42 40 sipFactory
43 41 .createHeaderFactory()
44   - .createViaHeader(SipLayer.getLocalIp(localIp), sipConfig.getPort(), transport, viaTag);
  42 + .createViaHeader(SipTransportService.getLocalIp(localIp), sipConfig.getPort(), transport, viaTag);
45 43 viaHeader.setRPort();
46 44 viaHeaders.add(viaHeader);
47 45 return viaHeaders;
... ... @@ -78,7 +76,7 @@ public class AbstractSIPRequestProcess {
78 76 throws PeerUnavailableException, ParseException {
79 77 SipURI sipUri =
80 78 buildRequestLineSipUri(
81   - sipConfig.getId(), SipLayer.getLocalIp(localIp) + ":" + sipConfig.getPort());
  79 + sipConfig.getId(), SipTransportService.getLocalIp(localIp) + ":" + sipConfig.getPort());
82 80 Address concatAddress = sipFactory.createAddressFactory().createAddress(sipUri);
83 81 return sipFactory.createHeaderFactory().createContactHeader(concatAddress);
84 82 }
... ...
... ... @@ -15,12 +15,16 @@ import javax.sip.address.SipURI;
15 15 import javax.sip.header.*;
16 16 import javax.sip.message.Request;
17 17 import javax.sip.message.Response;
  18 +
  19 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
18 20 import org.springframework.stereotype.Component;
19 21 import org.thingsboard.server.common.data.yunteng.dto.sip.SipMessageHeaderDTO;
20 22 import org.thingsboard.server.transport.session.GbtDeviceSessionCtx;
21 23 import org.thingsboard.server.transport.util.TKSipUtils;
22 24
23 25 @Component
  26 +@ConditionalOnExpression(
  27 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
24 28 public class SIPRequestHeaderProcess extends AbstractSIPRequestProcess {
25 29 public Request createMessageRequest(
26 30 GbtDeviceSessionCtx sessionCtx,
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/cmd/SIPSender.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/SIPSender.java
1   -package org.thingsboard.server.transport;
  1 +package org.thingsboard.server.transport.cmd;
2 2
3 3 import gov.nist.javax.sip.SipProviderImpl;
4 4 import java.text.ParseException;
... ... @@ -11,15 +11,18 @@ import javax.sip.message.Request;
11 11 import javax.sip.message.Response;
12 12 import lombok.extern.slf4j.Slf4j;
13 13 import org.springframework.beans.factory.annotation.Autowired;
  14 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
14 15 import org.springframework.stereotype.Component;
15 16 import org.springframework.util.ObjectUtils;
16   -import org.thingsboard.server.common.data.yunteng.config.media.ThingsKitVersionConfig;
17   -import org.thingsboard.server.transport.gbt28181.SipLayer;
  17 +import org.thingsboard.server.transport.config.ThingsKitVersionConfig;
  18 +import org.thingsboard.server.transport.gbt28181.sip.SipTransportService;
18 19 import org.thingsboard.server.transport.gbt28181.SipSubscribe;
19 20 import org.thingsboard.server.transport.util.TKSipUtils;
20 21
21 22 /** 发送SIP信息 */
22 23 @Component
  24 +@ConditionalOnExpression(
  25 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
23 26 @Slf4j
24 27 public class SIPSender {
25 28
... ... @@ -80,7 +83,7 @@ public class SIPSender {
80 83 }
81 84
82 85 SipProviderImpl sipProvider =
83   - TCP.equals(transport) ? SipLayer.getTcpSipProvider(ip) : SipLayer.getUdpSipProvider(ip);
  86 + TCP.equals(transport) ? SipTransportService.getTcpSipProvider(ip) : SipTransportService.getUdpSipProvider(ip);
84 87 if (sipProvider == null) {
85 88 log.error("[发送信息失败] 未找到{}://{}的监听信息", transport, ip);
86 89 return;
... ... @@ -94,23 +97,23 @@ public class SIPSender {
94 97
95 98 public CallIdHeader getNewCallIdHeader(String ip, String transport) {
96 99 if (ObjectUtils.isEmpty(transport)) {
97   - return SipLayer.getUdpSipProvider().getNewCallId();
  100 + return SipTransportService.getUdpSipProvider().getNewCallId();
98 101 }
99 102 SipProviderImpl sipProvider;
100 103 if (ObjectUtils.isEmpty(ip)) {
101 104 sipProvider =
102 105 transport.equalsIgnoreCase(TCP)
103   - ? SipLayer.getTcpSipProvider()
104   - : SipLayer.getUdpSipProvider();
  106 + ? SipTransportService.getTcpSipProvider()
  107 + : SipTransportService.getUdpSipProvider();
105 108 } else {
106 109 sipProvider =
107 110 transport.equalsIgnoreCase(TCP)
108   - ? SipLayer.getTcpSipProvider(ip)
109   - : SipLayer.getUdpSipProvider(ip);
  111 + ? SipTransportService.getTcpSipProvider(ip)
  112 + : SipTransportService.getUdpSipProvider(ip);
110 113 }
111 114
112 115 if (sipProvider == null) {
113   - sipProvider = SipLayer.getUdpSipProvider();
  116 + sipProvider = SipTransportService.getUdpSipProvider();
114 117 }
115 118
116 119 if (sipProvider != null) {
... ...
... ... @@ -13,8 +13,7 @@ import org.thingsboard.server.common.data.yunteng.config.media.UserSetting;
13 13 import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
14 14 import org.thingsboard.server.common.data.yunteng.dto.sip.*;
15 15 import org.thingsboard.server.common.data.yunteng.enums.VideoCmdEnum;
16   -import org.thingsboard.server.transport.SIPSender;
17   -import org.thingsboard.server.transport.gbt28181.SipLayer;
  16 +import org.thingsboard.server.transport.gbt28181.sip.SipTransportService;
18 17 import org.thingsboard.server.transport.gbt28181.SipSubscribe;
19 18 import org.thingsboard.server.transport.session.GbtDeviceSessionCtx;
20 19 import org.thingsboard.server.transport.util.TKSipUtils;
... ... @@ -41,11 +40,11 @@ public class TKSipCommanderServiceImpl implements TKSipCommanderService {
41 40 sessionCtx.getCameraCode());
42 41 CallIdHeader callIdHeader =
43 42 sipSender.getNewCallIdHeader(
44   - SipLayer.getLocalIp(sessionCtx.getLocalIp()), sessionCtx.getTransport());
  43 + SipTransportService.getLocalIp(sessionCtx.getLocalIp()), sessionCtx.getTransport());
45 44 Request request =
46 45 headerProvider.createMessageRequest(
47 46 sessionCtx, sipMessageHeaderDTO, xmlContent, callIdHeader);
48   - sipSender.transmitRequest(SipLayer.getLocalIp(sessionCtx.getLocalIp()), request);
  47 + sipSender.transmitRequest(SipTransportService.getLocalIp(sessionCtx.getLocalIp()), request);
49 48 }
50 49
51 50 @Override
... ... @@ -63,13 +62,13 @@ public class TKSipCommanderServiceImpl implements TKSipCommanderService {
63 62 deviceSessionCtx.getCameraCode());
64 63 CallIdHeader callIdHeader =
65 64 sipSender.getNewCallIdHeader(
66   - SipLayer.getLocalIp(deviceSessionCtx.getLocalIp()), deviceSessionCtx.getTransport());
  65 + SipTransportService.getLocalIp(deviceSessionCtx.getLocalIp()), deviceSessionCtx.getTransport());
67 66 Request request =
68 67 headerProvider.createMessageRequest(
69 68 deviceSessionCtx, sipMessageHeaderDTO, xmlContent, callIdHeader);
70 69
71 70 sipSender.transmitRequest(
72   - SipLayer.getLocalIp(deviceSessionCtx.getLocalIp()), request, errorEvent);
  71 + SipTransportService.getLocalIp(deviceSessionCtx.getLocalIp()), request, errorEvent);
73 72 }
74 73
75 74 @Override
... ... @@ -86,12 +85,12 @@ public class TKSipCommanderServiceImpl implements TKSipCommanderService {
86 85 ptzCmd);
87 86 CallIdHeader callIdHeader =
88 87 sipSender.getNewCallIdHeader(
89   - SipLayer.getLocalIp(deviceSessionCtx.getLocalIp()), deviceSessionCtx.getTransport());
  88 + SipTransportService.getLocalIp(deviceSessionCtx.getLocalIp()), deviceSessionCtx.getTransport());
90 89 Request request =
91 90 headerProvider.createMessageRequest(
92 91 deviceSessionCtx, sipMessageHeaderDTO, xmlContent, callIdHeader);
93 92
94   - sipSender.transmitRequest(SipLayer.getLocalIp(deviceSessionCtx.getLocalIp()), request);
  93 + sipSender.transmitRequest(SipTransportService.getLocalIp(deviceSessionCtx.getLocalIp()), request);
95 94 }
96 95
97 96 @Override
... ... @@ -110,13 +109,13 @@ public class TKSipCommanderServiceImpl implements TKSipCommanderService {
110 109
111 110 CallIdHeader callIdHeader =
112 111 sipSender.getNewCallIdHeader(
113   - SipLayer.getLocalIp(devSession.getLocalIp()), devSession.getTransport());
  112 + SipTransportService.getLocalIp(devSession.getLocalIp()), devSession.getTransport());
114 113 Request request =
115 114 headerProvider.createInviteRequest(
116 115 devSession, sipMessageHeaderDTO, channelId, content, callIdHeader, ssrc);
117 116
118 117 sipSender.transmitRequest(
119   - SipLayer.getLocalIp(devSession.getLocalIp()), request, errorEvent, okEvent);
  118 + SipTransportService.getLocalIp(devSession.getLocalIp()), request, errorEvent, okEvent);
120 119 }
121 120
122 121 @Override
... ... @@ -144,7 +143,7 @@ public class TKSipCommanderServiceImpl implements TKSipCommanderService {
144 143 headerDTO.getViaTag(),
145 144 headerDTO.getFromTag(),
146 145 headerDTO.getToTag());
147   - sipSender.transmitRequest(SipLayer.getLocalIp(device.getLocalIp()), byteRequest, null, okEvent);
  146 + sipSender.transmitRequest(SipTransportService.getLocalIp(device.getLocalIp()), byteRequest, null, okEvent);
148 147 }
149 148
150 149 private String buildMessageBodyQueryXml(
... ...
  1 +package org.thingsboard.server.transport.config;
  2 +
  3 +import java.io.Serializable;
  4 +import lombok.Data;
  5 +import lombok.extern.slf4j.Slf4j;
  6 +import org.springframework.beans.factory.annotation.Value;
  7 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
  8 +import org.springframework.boot.context.properties.ConfigurationProperties;
  9 +import org.springframework.stereotype.Component;
  10 +
  11 +/** 配置文件里面的流媒体配置信息 */
  12 +@ConfigurationProperties(prefix = "transport.gbt28181.media")
  13 +@Component
  14 +@ConditionalOnExpression(
  15 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
  16 +@Data
  17 +@Slf4j
  18 +public class MediaConfig implements Serializable {
  19 + @Value("${transport.gbt28181.media.id}")
  20 + private String mediaServerId;
  21 +
  22 + @Value("${transport.gbt28181.media.ip}")
  23 + private String ip;
  24 +
  25 + @Value("${transport.gbt28181.media.hook-ip:}")
  26 + private String hookIp;
  27 +
  28 + @Value("${transport.gbt28181.media.sdp-ip:${transport.gbt28181.media.ip}}")
  29 + private String sdpIp;
  30 +
  31 + @Value("${transport.gbt28181.media.stream-ip:${transport.gbt28181.media.ip}}")
  32 + private String streamIp;
  33 +
  34 + @Value("${transport.gbt28181.media.http-port}")
  35 + private Integer httpPort;
  36 +
  37 + @Value("${transport.gbt28181.media.http-ssl-port:0}")
  38 + private Integer httpSslPort = 0;
  39 +
  40 + @Value("${transport.gbt28181.media.rtmp-port:0}")
  41 + private Integer rtmpPort = 0;
  42 +
  43 + @Value("${transport.gbt28181.media.rtmp-ssl-port:0}")
  44 + private Integer rtmpSslPort = 0;
  45 +
  46 + @Value("${transport.gbt28181.media.rtp-proxy-port:0}")
  47 + private Integer rtpProxyPort = 0;
  48 +
  49 + @Value("${transport.gbt28181.media.rtsp-port:0}")
  50 + private Integer rtspPort = 0;
  51 +
  52 + @Value("${transport.gbt28181.media.rtsp-ssl-port:0}")
  53 + private Integer rtspSslPort = 0;
  54 +
  55 + @Value("${transport.gbt28181.media.auto-config:true}")
  56 + private boolean autoConfig = true;
  57 +
  58 + @Value("${transport.gbt28181.media.secret}")
  59 + private String secret;
  60 +
  61 + @Value("${transport.gbt28181.media.rtp.enable}")
  62 + private boolean rtpEnable;
  63 +
  64 + @Value("${transport.gbt28181.media.rtp.port-range}")
  65 + private String rtpPortRange;
  66 +
  67 + @Value("${transport.gbt28181.media.rtp.send-port-range}")
  68 + private String rtpSendPortRange;
  69 +
  70 + @Value("${transport.gbt28181.media.record-assist-port:0}")
  71 + private Integer recordAssistPort = 0;
  72 +
  73 + private boolean status;
  74 +}
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/config/SipConfig.java renamed from common/data/src/main/java/org/thingsboard/server/common/data/yunteng/config/media/SipConfig.java
1   -package org.thingsboard.server.common.data.yunteng.config.media;
  1 +package org.thingsboard.server.transport.config;
2 2
3 3 import lombok.Data;
  4 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
4 5 import org.springframework.boot.context.properties.ConfigurationProperties;
5 6 import org.springframework.stereotype.Component;
6 7
7   -@ConfigurationProperties(prefix = "sip")
  8 +@ConfigurationProperties(prefix = "transport.gbt28181.sip")
8 9 @Component
  10 +@ConditionalOnExpression(
  11 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
9 12 @Data
10 13 public class SipConfig {
11   - private String ip;
12   - private String showIp;
13   - private Integer port;
14   - private String id;
15   - private String domain;
16   - private String password;
17   - Integer ptzSpeed = 50;
18   - Integer registerTimeInterval = 120;
19   - private boolean alarm;
  14 + private String ip;
  15 + private String showIp;
  16 + private Integer port;
  17 + private String id;
  18 + private String domain;
  19 + private String password;
  20 + Integer ptzSpeed = 50;
  21 + Integer registerTimeInterval = 120;
  22 + private boolean alarm;
20 23
21   - public String getShowIp() {
22   - if (this.showIp == null) {
23   - return this.ip;
24   - }
25   - return showIp;
  24 + public String getShowIp() {
  25 + if (this.showIp == null) {
  26 + return this.ip;
26 27 }
  28 + return showIp;
  29 + }
27 30 }
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/config/ThingsKitVersionConfig.java renamed from common/data/src/main/java/org/thingsboard/server/common/data/yunteng/config/media/ThingsKitVersionConfig.java
1   -package org.thingsboard.server.common.data.yunteng.config.media;
  1 +package org.thingsboard.server.transport.config;
2 2
3 3 import lombok.Data;
4 4 import org.springframework.beans.factory.annotation.Value;
  5 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
5 6 import org.springframework.stereotype.Component;
6 7
7 8 @Component
  9 +@ConditionalOnExpression(
  10 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
8 11 @Data
9 12 public class ThingsKitVersionConfig {
10 13 @Value("${thingskit.release.version}")
... ...
... ... @@ -13,12 +13,15 @@ import javax.sip.header.CallIdHeader;
13 13 import javax.sip.message.Response;
14 14 import org.slf4j.Logger;
15 15 import org.slf4j.LoggerFactory;
  16 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
16 17 import org.springframework.scheduling.annotation.Scheduled;
17 18 import org.springframework.stereotype.Component;
18   -import org.thingsboard.server.transport.gbt28181.event.DeviceNotFoundEvent;
  19 +import org.thingsboard.server.transport.gbt28181.sip.event.DeviceNotFoundEvent;
19 20
20 21 /** SIP订阅信息 */
21 22 @Component
  23 +@ConditionalOnExpression(
  24 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
22 25 public class SipSubscribe {
23 26
24 27 private final Logger logger = LoggerFactory.getLogger(SipSubscribe.class);
... ...
... ... @@ -36,8 +36,6 @@ import javax.sip.header.HeaderFactory;
36 36 import javax.sip.header.WWWAuthenticateHeader;
37 37 import javax.sip.message.Request;
38 38 import javax.sip.message.Response;
39   -import org.slf4j.Logger;
40   -import org.slf4j.LoggerFactory;
41 39
42 40 /** Implements the HTTP digest authentication method server side functionality. */
43 41 public class DigestServerAuthenticationHelper {
... ... @@ -99,6 +97,7 @@ public class DigestServerAuthenticationHelper {
99 97 }
100 98 return response;
101 99 }
  100 +
102 101 /**
103 102 * Authenticate the inbound request.
104 103 *
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/auth/RemoteAddressInfo.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/info/RemoteAddressInfo.java
1   -package org.thingsboard.server.transport.info;
  1 +package org.thingsboard.server.transport.gbt28181.auth;
2 2
  3 +import lombok.Data;
  4 +
  5 +@Data
3 6 public class RemoteAddressInfo {
4 7 private String ip;
5 8 private int port;
... ... @@ -8,20 +11,4 @@ public class RemoteAddressInfo {
8 11 this.ip = ip;
9 12 this.port = port;
10 13 }
11   -
12   - public String getIp() {
13   - return ip;
14   - }
15   -
16   - public void setIp(String ip) {
17   - this.ip = ip;
18   - }
19   -
20   - public int getPort() {
21   - return port;
22   - }
23   -
24   - public void setPort(int port) {
25   - this.port = port;
26   - }
27 14 }
... ...
... ... @@ -7,6 +7,7 @@ import java.util.*;
7 7 import java.util.concurrent.ConcurrentHashMap;
8 8 import java.util.concurrent.TimeUnit;
9 9
  10 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
10 11 import org.springframework.scheduling.annotation.Scheduled;
11 12 import org.springframework.stereotype.Component;
12 13 import org.thingsboard.server.common.data.yunteng.dto.sip.CatalogDataDTO;
... ... @@ -16,6 +17,8 @@ import org.thingsboard.server.common.data.yunteng.dto.sip.VideoChanelDTO;
16 17 import org.thingsboard.server.common.data.yunteng.enums.CatalogDataStatusEnum;
17 18
18 19 @Component
  20 +@ConditionalOnExpression(
  21 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
19 22 public class CatalogDataCatch {
20 23
21 24 public static Map<String, CatalogDataDTO> data = new ConcurrentHashMap<>();
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/session/GbtTransportContext.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/GbtTransportContext.java
1   -package org.thingsboard.server.transport;
  1 +package org.thingsboard.server.transport.gbt28181.session;
2 2
3   -import gov.nist.core.HostPort;
4 3 import io.netty.handler.ssl.SslHandler;
5   -import java.net.InetSocketAddress;
6 4 import java.util.concurrent.Executors;
7 5 import java.util.concurrent.ScheduledExecutorService;
8 6 import java.util.concurrent.atomic.AtomicInteger;
... ... @@ -10,13 +8,11 @@ import javax.annotation.PostConstruct;
10 8 import lombok.Getter;
11 9 import lombok.Setter;
12 10 import lombok.extern.slf4j.Slf4j;
13   -import org.springframework.beans.factory.annotation.Autowired;
14 11 import org.springframework.beans.factory.annotation.Value;
15 12 import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
16 13 import org.springframework.stereotype.Component;
17 14 import org.thingsboard.common.util.ThingsBoardThreadFactory;
18 15 import org.thingsboard.server.common.transport.TransportContext;
19   -import org.thingsboard.server.transport.adaptors.GbtTransportAdaptor;
20 16
21 17 @Slf4j
22 18 @Component
... ... @@ -24,8 +20,6 @@ import org.thingsboard.server.transport.adaptors.GbtTransportAdaptor;
24 20 "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
25 21 public class GbtTransportContext extends TransportContext {
26 22
27   - /** 注入多种数据协议处理器,例如:modbus等 */
28   - @Getter @Autowired private GbtTransportAdaptor jsonAdaptor;
29 23
30 24 @Getter
31 25 @Value("${transport.tcp.netty.max_payload_size}")
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/DefaultProperties.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/DefaultProperties.java
1   -package org.thingsboard.server.transport.gbt28181;
  1 +package org.thingsboard.server.transport.gbt28181.sip;
2 2
3 3 import lombok.extern.log4j.Log4j;
4 4
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/ISIPRequestProcessor.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/ISIPRequestProcessor.java
1   -package org.thingsboard.server.transport.gbt28181;
  1 +package org.thingsboard.server.transport.gbt28181.sip;
2 2
3 3 import javax.sip.RequestEvent;
4 4
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/ISIPResponseProcessor.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/ISIPResponseProcessor.java
1   -package org.thingsboard.server.transport.gbt28181;
  1 +package org.thingsboard.server.transport.gbt28181.sip;
2 2
3 3 import javax.sip.ResponseEvent;
4 4
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/SipTransportService.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/SipLayer.java
... ... @@ -11,7 +11,7 @@
11 11 * express or implied. See the License for the specific language governing permissions and
12 12 * limitations under the License.
13 13 */
14   -package org.thingsboard.server.transport.gbt28181;
  14 +package org.thingsboard.server.transport.gbt28181.sip;
15 15
16 16 import gov.nist.javax.sip.SipProviderImpl;
17 17 import gov.nist.javax.sip.SipStackImpl;
... ... @@ -26,20 +26,20 @@ import org.springframework.stereotype.Service;
26 26 import org.springframework.util.ObjectUtils;
27 27 import org.thingsboard.server.common.data.DataConstants;
28 28 import org.thingsboard.server.common.data.TbTransportService;
29   -import org.thingsboard.server.common.data.yunteng.config.media.SipConfig;
30   -import org.thingsboard.server.transport.SIPProvider;
  29 +import org.thingsboard.server.transport.gbt28181.sip.processor.SIPProvider;
  30 +import org.thingsboard.server.transport.config.SipConfig;
31 31
32 32 /**
33 33 * @author Andrew Shvayka
34 34 */
35   -@Service("GBT28181TransportService")
36   -@ConditionalOnExpression("'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
  35 +@Service()
  36 +@ConditionalOnExpression(
  37 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
37 38 @Slf4j
38   -public class SipLayer implements TbTransportService {
  39 +public class SipTransportService implements TbTransportService {
39 40 private static final Map<String, SipProviderImpl> tcpSipProviderMap = new ConcurrentHashMap<>();
40 41 private static final Map<String, SipProviderImpl> udpSipProviderMap = new ConcurrentHashMap<>();
41   - @Autowired
42   - private SIPProvider sipProvider;
  42 + @Autowired private SIPProvider sipProvider;
43 43
44 44 @Autowired private SipConfig sipConfig;
45 45
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/event/DeviceNotFoundEvent.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/event/DeviceNotFoundEvent.java
1   -package org.thingsboard.server.transport.gbt28181.event;
  1 +package org.thingsboard.server.transport.gbt28181.sip.event;
2 2
3 3 import java.util.EventObject;
4 4 import javax.sip.Dialog;
  5 +import lombok.Getter;
  6 +import lombok.Setter;
5 7
  8 +@Getter
  9 +@Setter
6 10 public class DeviceNotFoundEvent extends EventObject {
7 11
8 12 private String callId;
... ... @@ -16,12 +20,4 @@ public class DeviceNotFoundEvent extends EventObject {
16 20 public DeviceNotFoundEvent(Dialog dialog) {
17 21 super(dialog);
18 22 }
19   -
20   - public String getCallId() {
21   - return callId;
22   - }
23   -
24   - public void setCallId(String callId) {
25   - this.callId = callId;
26   - }
27 23 }
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/processor/ITimeoutProcessor.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/ITimeoutProcessor.java
1   -package org.thingsboard.server.transport.gbt28181;
  1 +package org.thingsboard.server.transport.gbt28181.sip.processor;
2 2
3 3 import javax.sip.TimeoutEvent;
4 4
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/processor/SIPProcessorObserver.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/SIPProcessorObserver.java
1   -package org.thingsboard.server.transport;
  1 +package org.thingsboard.server.transport.gbt28181.sip.processor;
2 2
3 3 import static org.thingsboard.server.common.transport.service.DefaultTransportService.SESSION_EVENT_MSG_CLOSED;
4 4 import static org.thingsboard.server.common.transport.service.DefaultTransportService.SESSION_EVENT_MSG_OPEN;
... ... @@ -40,8 +40,6 @@ import org.thingsboard.server.common.data.DeviceTransportType;
40 40 import org.thingsboard.server.common.data.StringUtils;
41 41 import org.thingsboard.server.common.data.id.DeviceId;
42 42 import org.thingsboard.server.common.data.rpc.RpcStatus;
43   -import org.thingsboard.server.common.data.yunteng.common.media.VideoStreamSessionManager;
44   -import org.thingsboard.server.common.data.yunteng.config.media.SipConfig;
45 43 import org.thingsboard.server.common.data.yunteng.config.media.UserSetting;
46 44 import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
47 45 import org.thingsboard.server.common.data.yunteng.dto.sip.PTZCmdDTO;
... ... @@ -58,11 +56,16 @@ import org.thingsboard.server.common.transport.auth.SessionInfoCreator;
58 56 import org.thingsboard.server.common.transport.auth.ValidateDeviceCredentialsResponse;
59 57 import org.thingsboard.server.common.transport.util.DataDecodingEncodingService;
60 58 import org.thingsboard.server.gen.transport.TransportProtos;
  59 +import org.thingsboard.server.transport.gbt28181.session.GbtTransportContext;
61 60 import org.thingsboard.server.transport.cmd.SIPRequestHeaderProcess;
62 61 import org.thingsboard.server.transport.cmd.TKSipCommanderService;
  62 +import org.thingsboard.server.transport.config.MediaConfig;
  63 +import org.thingsboard.server.transport.config.SipConfig;
63 64 import org.thingsboard.server.transport.gbt28181.*;
64 65 import org.thingsboard.server.transport.gbt28181.auth.DigestServerAuthenticationHelper;
65   -import org.thingsboard.server.transport.info.RemoteAddressInfo;
  66 +import org.thingsboard.server.transport.gbt28181.sip.ISIPRequestProcessor;
  67 +import org.thingsboard.server.transport.gbt28181.sip.ISIPResponseProcessor;
  68 +import org.thingsboard.server.transport.gbt28181.auth.RemoteAddressInfo;
66 69 import org.thingsboard.server.transport.session.GbtDeviceSessionCtx;
67 70 import org.thingsboard.server.transport.util.TKSipUtils;
68 71 import org.thingsboard.server.transport.util.TKXmlUtil;
... ... @@ -81,6 +84,7 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
81 84
82 85 private final SIPRequestHeaderProcess headerProvider;
83 86 private final SipConfig sipConfig;
  87 + private final MediaConfig mediaConfig;
84 88 private final UserSetting userSetting;
85 89 private final TKSipCommanderService commanderService;
86 90 private final DataDecodingEncodingService encodingService;
... ... @@ -93,7 +97,9 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
93 97
94 98 @Getter
95 99 private final ConcurrentHashMap<DeviceId, String> onlineDevice = new ConcurrentHashMap<>();
96   - private final ConcurrentHashMap<String, List<VideoChanelDTO>> deviceNewChanel = new ConcurrentHashMap<>();
  100 +
  101 + private final ConcurrentHashMap<String, List<VideoChanelDTO>> deviceNewChanel =
  102 + new ConcurrentHashMap<>();
97 103 private static final Map<String, ISIPRequestProcessor> requestProcessorMap =
98 104 new ConcurrentHashMap<>();
99 105 private static final Map<String, ISIPResponseProcessor> responseProcessorMap =
... ... @@ -101,6 +107,7 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
101 107 private static ITimeoutProcessor timeoutProcessor;
102 108
103 109 private final SipSubscribe sipSubscribe;
  110 +
104 111 /**
105 112 * 添加 request订阅
106 113 *
... ... @@ -159,7 +166,7 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
159 166 CSeqHeader cseqHeader = (CSeqHeader) responseEvent.getResponse().getHeader(CSeqHeader.NAME);
160 167 String methodName = cseqHeader.getMethod();
161 168 SIPResponse request = (SIPResponse) responseEvent.getResponse();
162   - log.debug(
  169 + log.info(
163 170 "收到ResponseEvent,方法类型【{}】,状态码【{}】,事件内容【{}】",
164 171 methodName,
165 172 status,
... ... @@ -178,8 +185,11 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
178 185 default:
179 186 log.debug("不支持的响应类型【{}】", method);
180 187 }
181   - if (status != Response.UNAUTHORIZED && responseEvent.getResponse() != null && sipSubscribe.getOkSubscribesSize() > 0 ) {
182   - CallIdHeader callIdHeader = (CallIdHeader)responseEvent.getResponse().getHeader(CallIdHeader.NAME);
  188 + if (status != Response.UNAUTHORIZED
  189 + && responseEvent.getResponse() != null
  190 + && sipSubscribe.getOkSubscribesSize() > 0) {
  191 + CallIdHeader callIdHeader =
  192 + (CallIdHeader) responseEvent.getResponse().getHeader(CallIdHeader.NAME);
183 193 if (callIdHeader != null) {
184 194 SipSubscribe.Event subscribe = sipSubscribe.getOkSubscribe(callIdHeader.getCallId());
185 195 if (subscribe != null) {
... ... @@ -192,20 +202,26 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
192 202 } else if ((status >= Response.TRYING) && (status < Response.OK)) {
193 203 // 增加其它无需回复的响应,如101、180等
194 204 } else {
195   - log.error("收到ResponseEvent,设备【{}】,状态码【{}】,失败原因【{}】,ResponseEvent内容【{}】",response.getHeader(FromHeader.NAME),status, response.getReasonPhrase(),response.getRawContent() == null ? null : new String(response.getRawContent()));
196   - if (responseEvent.getResponse() != null && sipSubscribe.getErrorSubscribesSize() > 0 ) {
197   - CallIdHeader callIdHeader = (CallIdHeader)responseEvent.getResponse().getHeader(CallIdHeader.NAME);
198   - if (callIdHeader != null) {
199   - SipSubscribe.Event subscribe = sipSubscribe.getErrorSubscribe(callIdHeader.getCallId());
200   - if (subscribe != null) {
201   - SipSubscribe.EventResult eventResult = new SipSubscribe.EventResult(responseEvent);
202   - subscribe.response(eventResult);
203   - sipSubscribe.removeErrorSubscribe(callIdHeader.getCallId());
204   - }
  205 + log.error(
  206 + "收到ResponseEvent,设备【{}】,状态码【{}】,失败原因【{}】,ResponseEvent内容【{}】",
  207 + response.getHeader(FromHeader.NAME),
  208 + status,
  209 + response.getReasonPhrase(),
  210 + response.getRawContent() == null ? null : new String(response.getRawContent()));
  211 + if (responseEvent.getResponse() != null && sipSubscribe.getErrorSubscribesSize() > 0) {
  212 + CallIdHeader callIdHeader =
  213 + (CallIdHeader) responseEvent.getResponse().getHeader(CallIdHeader.NAME);
  214 + if (callIdHeader != null) {
  215 + SipSubscribe.Event subscribe = sipSubscribe.getErrorSubscribe(callIdHeader.getCallId());
  216 + if (subscribe != null) {
  217 + SipSubscribe.EventResult eventResult = new SipSubscribe.EventResult(responseEvent);
  218 + subscribe.response(eventResult);
  219 + sipSubscribe.removeErrorSubscribe(callIdHeader.getCallId());
205 220 }
  221 + }
206 222 }
207 223 if (responseEvent.getDialog() != null) {
208   - responseEvent.getDialog().delete();
  224 + responseEvent.getDialog().delete();
209 225 }
210 226 }
211 227 }
... ... @@ -219,7 +235,7 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
219 235 public void processRequest(RequestEvent requestEvent) {
220 236 String methodName = requestEvent.getRequest().getMethod();
221 237 SIPRequest request = (SIPRequest) requestEvent.getRequest();
222   - log.debug(
  238 + log.info(
223 239 "收到RequestEvent,方法类型【{}】,事件内容【{}】",
224 240 methodName,
225 241 request.getRawContent() == null ? null : new String(request.getRawContent()));
... ... @@ -307,14 +323,15 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
307 323 */
308 324 void processResponseMessage(GbtDeviceSessionCtx ctx, ResponseEvent msg) {}
309 325
310   - private String cameraAddress(SIPRequest request){
  326 + private String cameraAddress(SIPRequest request) {
311 327 RemoteAddressInfo remoteAddressInfo =
312   - TKSipUtils.getRemoteAddressFromRequest(
313   - request, userSetting.getSipUseSourceIpAsRemoteAddress());
  328 + TKSipUtils.getRemoteAddressFromRequest(
  329 + request, userSetting.getSipUseSourceIpAsRemoteAddress());
314 330 String hostAddress = remoteAddressInfo.getIp();
315 331 int remotePort = remoteAddressInfo.getPort();
316 332 return hostAddress + ":" + remotePort;
317 333 }
  334 +
318 335 /**
319 336 * 处理请求事件的MESSAGE消息,根据XML数据的根节点名称进行分发
320 337 *
... ... @@ -342,7 +359,8 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
342 359 }
343 360 if (ctx != null) {
344 361 if (!ctx.getHostAddress().equals(cameraAddress(request))) {
345   - log.trace("摄像头【{}/{}】IP或端口已过期,断开连接", ctx.getDeviceInfo().getDeviceName(),ctx.getCameraCode());
  362 + log.trace(
  363 + "摄像头【{}/{}】IP或端口已过期,断开连接", ctx.getDeviceInfo().getDeviceName(), ctx.getCameraCode());
346 364 deviceSessions.remove(ctx.getCameraCode());
347 365 responseAck(request, Response.OK);
348 366 return;
... ... @@ -454,7 +472,7 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
454 472 transportService.deregisterSession(ds.getSessionInfo());
455 473 transportService.process(ds.getSessionInfo(), SESSION_EVENT_MSG_CLOSED, null);
456 474 try {
457   - cameraResponseRequest(ds, request, null,null);
  475 + cameraResponseRequest(ds, request, null, null);
458 476 } catch (InvalidArgumentException | ParseException | SipException e) {
459 477 throw new RuntimeException(e);
460 478 }
... ... @@ -515,24 +533,25 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
515 533 case DeviceInfo:
516 534 SipDeviceDTO cameraInfoDTO = TKXmlUtil.cameraInfoBuilder(rootElement);
517 535 cameraInfoDTO.setHostAddress(request.getViaHost() + ":" + request.getViaPort());
  536 + cameraInfoDTO.setMediaServerId(mediaConfig.getMediaServerId());
518 537 byte[] cameraMsgBytes = encodingService.encode(cameraInfoDTO);
519 538 msgBuilder.setContext(ByteString.copyFrom(cameraMsgBytes));
520 539 break;
521 540 case Catalog:
522 541 List<VideoChanelDTO> channelDTO = TKXmlUtil.channelInfoBuilder(devSession, rootElement);
523 542 String cameraCode = devSession.getCameraCode();
524   - int channelNum =1;
525   - if(!channelDTO.isEmpty()){
526   - channelNum = channelDTO.get(0).getSumNum();
527   - List<VideoChanelDTO> itemChanel = new ArrayList<>();
528   - if(deviceNewChanel.containsKey(cameraCode)){
529   - itemChanel =deviceNewChanel.get(cameraCode);
530   - }else{
531   - deviceNewChanel.put(cameraCode,itemChanel);
532   - }
533   - itemChanel.addAll(channelDTO);
534   - }
535   - if(channelNum == deviceNewChanel.get(cameraCode).size()){
  543 + int channelNum = 1;
  544 + if (!channelDTO.isEmpty()) {
  545 + channelNum = channelDTO.get(0).getSumNum();
  546 + List<VideoChanelDTO> itemChanel = new ArrayList<>();
  547 + if (deviceNewChanel.containsKey(cameraCode)) {
  548 + itemChanel = deviceNewChanel.get(cameraCode);
  549 + } else {
  550 + deviceNewChanel.put(cameraCode, itemChanel);
  551 + }
  552 + itemChanel.addAll(channelDTO);
  553 + }
  554 + if (channelNum == deviceNewChanel.get(cameraCode).size()) {
536 555 byte[] channaelMsgBytes = encodingService.encode(deviceNewChanel.get(cameraCode));
537 556 msgBuilder.setContext(ByteString.copyFrom(channaelMsgBytes));
538 557 deviceNewChanel.remove(cameraCode);
... ... @@ -644,7 +663,7 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
644 663 return;
645 664 }
646 665 DeviceProfile profile = msg.getDeviceProfile();
647   - if(profile.getTransportType() != DeviceTransportType.GBT28181){
  666 + if (profile.getTransportType() != DeviceTransportType.GBT28181) {
648 667 return;
649 668 }
650 669 GbtDeviceSessionCtx deviceSessionCtx =
... ... @@ -698,12 +717,12 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
698 717 .build();
699 718 commanderService.queryDeviceInfo(deviceSessionCtx, deviceInfoHeader);
700 719 int sn = (int) ((Math.random() * 9 + 1) * 100000);
701   - rpcCameraChannel(deviceSessionCtx,sn);
  720 + rpcCameraChannel(deviceSessionCtx, sn);
702 721 } catch (InvalidArgumentException | SipException | ParseException e) {
703 722 throw new RuntimeException(e);
704 723 }
705 724
706   - // transportService.getCallbackExecutor().execute(() ->
  725 + // transportService.getCallbackExecutor().execute(() ->
707 726 // processQueueMessage(ctx)); //this callback will execute in Producer worker thread and
708 727 // hard or blocking work have to be submitted to the separate thread.
709 728 }
... ... @@ -735,9 +754,6 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
735 754 // sipSender.transmitRequest(hostAddress, finalResponse);
736 755 }
737 756
738   -
739   -
740   -
741 757 /**
742 758 * 向超时订阅发送消息
743 759 *
... ... @@ -792,10 +808,12 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
792 808
793 809 String channelId = rpcParamVal(rpcBody, FastIotConstants.ZLMediaBody.CHANNEL_ID);
794 810
795   - switch (VideoMethodEnum.valueOf(methodType)){
  811 + switch (VideoMethodEnum.valueOf(methodType)) {
796 812 case BYE:
797   - SipMessageHeaderDTO messageHeaderDTO = JacksonUtil.convertValue(rpcBody.get(FastIotConstants.ZLMediaBody.MSG_HEADER),SipMessageHeaderDTO.class);
798   - commanderService.streamByeCmd(devSession,messageHeaderDTO,channelId);
  813 + SipMessageHeaderDTO messageHeaderDTO =
  814 + JacksonUtil.convertValue(
  815 + rpcBody.get(FastIotConstants.ZLMediaBody.MSG_HEADER), SipMessageHeaderDTO.class);
  816 + commanderService.streamByeCmd(devSession, messageHeaderDTO, channelId);
799 817 break;
800 818 case INVITE:
801 819 JsonNode mediaInform = rpcBody.get(FastIotConstants.ZLMediaBody.MEDIA);
... ... @@ -807,64 +825,81 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
807 825 String stream = rpcParamVal(rpcBody, FastIotConstants.ZLMediaBody.SSRCINFO_STREAM);
808 826
809 827 ObjectNode responseJson = JacksonUtil.newObjectNode();
810   - responseJson.put(FastIotConstants.ZLMediaBody.SSRCINFO_STREAM,stream);
811   - responseJson.put(FastIotConstants.ZLMediaBody.SSRCINFO_PORT,ssrcPort);
812   - responseJson.put(FastIotConstants.ZLMediaBody.SSRCINFO_SSRC,ssrc);
813   - responseJson.set(FastIotConstants.ZLMediaBody.MEDIA,mediaInform);
814   - responseJson.put(FastIotConstants.ZLMediaBody.CAMERA_CODE,cameraCode);
815   -
  828 + responseJson.put(FastIotConstants.ZLMediaBody.SSRCINFO_STREAM, stream);
  829 + responseJson.put(FastIotConstants.ZLMediaBody.SSRCINFO_PORT, ssrcPort);
  830 + responseJson.put(FastIotConstants.ZLMediaBody.SSRCINFO_SSRC, ssrc);
  831 + responseJson.set(FastIotConstants.ZLMediaBody.MEDIA, mediaInform);
  832 + responseJson.put(FastIotConstants.ZLMediaBody.CAMERA_CODE, cameraCode);
816 833
817 834 SipMessageHeaderDTO sipMessageHeaderDTO =
818   - SipMessageHeaderDTO.builder()
819   - .viaTag(TKSipUtils.getNewViaTag())
820   - .fromTag(TKSipUtils.getNewViaTag())
821   - .toTag(null)
822   - .build();
  835 + SipMessageHeaderDTO.builder()
  836 + .viaTag(TKSipUtils.getNewViaTag())
  837 + .fromTag(TKSipUtils.getNewViaTag())
  838 + .toTag(null)
  839 + .build();
823 840
824 841 commanderService.previewStreamCmd(
825   - devSession, sipMessageHeaderDTO, sdpIp, ssrc, ssrcPort, channelId,
826   - e -> {
827   - // TODO: 2023/10/13 命令下发失败,需要流媒体处理的业务逻辑
828   -
829   -// responseJson.set(FastIotConstants.ZLMediaBody.MSG_HEADER, JacksonUtil.valueToTree(e));
830   - String contentString = JacksonUtil.toString(responseJson);
831   - log.warn("命令下发【失败】,响应给流媒体的数据【{}】",contentString);
832   - transportService.process(devSession.getSessionInfo(),
833   - TransportProtos.ToDeviceRpcResponseMsg.newBuilder()
834   - .setRequestId(rpcRequest.getRequestId()).setError(e.msg).build(), TransportServiceCallback.EMPTY);
835   - },
836   - e -> {
837   - // TODO: 2023/10/13 命令下发成功,需要流媒体处理的业务逻辑
838   - transportService.process(devSession.getSessionInfo(), rpcRequest, RpcStatus.SENT, TransportServiceCallback.EMPTY);
839   -
840   -
841   - responseJson.put(FastIotConstants.ZLMediaBody.CALL_ID,e.callId);
842   - ResponseEvent responseEvent = (ResponseEvent) e.event;
843   - SIPResponse response = (SIPResponse) responseEvent.getResponse();
844   - SipMessageHeaderDTO sipMessage =
845   - SipMessageHeaderDTO.builder()
846   - .callId(response.getCallIdHeader().getCallId())
847   - .fromTag(response.getFromTag())
848   - .toTag(response.getToTag())
849   - .viaBranch(response.getTopmostViaHeader().getBranch())
850   - .build();
851   - responseJson.set(FastIotConstants.ZLMediaBody.MSG_HEADER, JacksonUtil.valueToTree(sipMessage));
852   - String contentString = new String(responseEvent.getResponse().getRawContent());
853   - responseJson.put(FastIotConstants.ZLMediaBody.MSG_CONTEXT, contentString);
854   - responseJson.put(FastIotConstants.ZLMediaBody.SESSION_TYPE,SessionTypeEnum.PLAY.name());
855   - responseJson.put(FastIotConstants.ZLMediaBody.CHANNEL_ID,channelId);
856   - responseJson.put(FastIotConstants.ZLMediaBody.SSRC_CHECK,devSession.isSsrcCheck());
857   - String responseStr = JacksonUtil.toString(responseJson);
858   - log.warn("命令下发【成功】,CallId是否一致【{}】,响应给流媒体的数据【{}】",e.callId.equals(response.getCallIdHeader().getCallId()),responseStr);
859   - TransportProtos.ToDeviceRpcResponseMsg.Builder builder = TransportProtos.ToDeviceRpcResponseMsg.newBuilder();
860   - builder.setRequestId(rpcRequest.getRequestId()).setPayload(responseStr);
861   - transportService.process(devSession.getSessionInfo(),
862   - builder.build(), TransportServiceCallback.EMPTY);
863   -
864   - });
  842 + devSession,
  843 + sipMessageHeaderDTO,
  844 + sdpIp,
  845 + ssrc,
  846 + ssrcPort,
  847 + channelId,
  848 + e -> {
  849 + // TODO: 2023/10/13 命令下发失败,需要流媒体处理的业务逻辑
  850 +
  851 + // responseJson.set(FastIotConstants.ZLMediaBody.MSG_HEADER,
  852 + // JacksonUtil.valueToTree(e));
  853 + String contentString = JacksonUtil.toString(responseJson);
  854 + log.warn("命令下发【失败】,响应给流媒体的数据【{}】", contentString);
  855 + transportService.process(
  856 + devSession.getSessionInfo(),
  857 + TransportProtos.ToDeviceRpcResponseMsg.newBuilder()
  858 + .setRequestId(rpcRequest.getRequestId())
  859 + .setError(e.msg)
  860 + .build(),
  861 + TransportServiceCallback.EMPTY);
  862 + },
  863 + e -> {
  864 + // TODO: 2023/10/13 命令下发成功,需要流媒体处理的业务逻辑
  865 + transportService.process(
  866 + devSession.getSessionInfo(),
  867 + rpcRequest,
  868 + RpcStatus.SENT,
  869 + TransportServiceCallback.EMPTY);
  870 +
  871 + responseJson.put(FastIotConstants.ZLMediaBody.CALL_ID, e.callId);
  872 + ResponseEvent responseEvent = (ResponseEvent) e.event;
  873 + SIPResponse response = (SIPResponse) responseEvent.getResponse();
  874 + SipMessageHeaderDTO sipMessage =
  875 + SipMessageHeaderDTO.builder()
  876 + .callId(response.getCallIdHeader().getCallId())
  877 + .fromTag(response.getFromTag())
  878 + .toTag(response.getToTag())
  879 + .viaBranch(response.getTopmostViaHeader().getBranch())
  880 + .build();
  881 + responseJson.set(
  882 + FastIotConstants.ZLMediaBody.MSG_HEADER, JacksonUtil.valueToTree(sipMessage));
  883 + String contentString = new String(responseEvent.getResponse().getRawContent());
  884 + responseJson.put(FastIotConstants.ZLMediaBody.MSG_CONTEXT, contentString);
  885 + responseJson.put(
  886 + FastIotConstants.ZLMediaBody.SESSION_TYPE, SessionTypeEnum.PLAY.name());
  887 + responseJson.put(FastIotConstants.ZLMediaBody.CHANNEL_ID, channelId);
  888 + responseJson.put(FastIotConstants.ZLMediaBody.SSRC_CHECK, devSession.isSsrcCheck());
  889 + String responseStr = JacksonUtil.toString(responseJson);
  890 + log.warn(
  891 + "命令下发【成功】,CallId是否一致【{}】,响应给流媒体的数据【{}】",
  892 + e.callId.equals(response.getCallIdHeader().getCallId()),
  893 + responseStr);
  894 + TransportProtos.ToDeviceRpcResponseMsg.Builder builder =
  895 + TransportProtos.ToDeviceRpcResponseMsg.newBuilder();
  896 + builder.setRequestId(rpcRequest.getRequestId()).setPayload(responseStr);
  897 + transportService.process(
  898 + devSession.getSessionInfo(), builder.build(), TransportServiceCallback.EMPTY);
  899 + });
865 900 break;
866 901 case MESSAGE:
867   - toDeviceRpcMessage(devSession,channelId,rpcBody);
  902 + toDeviceRpcMessage(devSession, channelId, rpcBody);
868 903 break;
869 904 }
870 905 } catch (InvalidArgumentException | SipException | ParseException e) {
... ... @@ -873,47 +908,54 @@ public class SIPProcessorObserver extends SIPRequestProcessorParent
873 908 }
874 909 }
875 910
876   - private void toDeviceRpcMessage(GbtDeviceSessionCtx devSession,String channelId,JsonNode rpcBody) throws InvalidArgumentException, ParseException, SipException {
  911 + private void toDeviceRpcMessage(
  912 + GbtDeviceSessionCtx devSession, String channelId, JsonNode rpcBody)
  913 + throws InvalidArgumentException, ParseException, SipException {
877 914 SipMessageHeaderDTO controlHeaderDTO =
878   - SipMessageHeaderDTO.builder()
879   - .viaTag(TKSipUtils.getNewViaTag())
880   - .fromTag(TKSipUtils.getNewViaTag())
881   - .toTag(null)
882   - .build();
  915 + SipMessageHeaderDTO.builder()
  916 + .viaTag(TKSipUtils.getNewViaTag())
  917 + .fromTag(TKSipUtils.getNewViaTag())
  918 + .toTag(null)
  919 + .build();
883 920 String msgType = rpcBody.get(FastIotConstants.ZLMediaBody.MSG_TYPE).asText();
884   - switch (VideoXmlEnum.valueOf(msgType)){
  921 + switch (VideoXmlEnum.valueOf(msgType)) {
885 922 case Control:
886   - PTZCmdDTO ptzCmdDTO = JacksonUtil.convertValue(rpcBody.get(FastIotConstants.ZLMediaBody.MSG_CONTEXT),PTZCmdDTO.class);
887   - commanderService.controlPtzCmd(channelId,devSession,controlHeaderDTO,ptzCmdDTO);
  923 + PTZCmdDTO ptzCmdDTO =
  924 + JacksonUtil.convertValue(
  925 + rpcBody.get(FastIotConstants.ZLMediaBody.MSG_CONTEXT), PTZCmdDTO.class);
  926 + commanderService.controlPtzCmd(channelId, devSession, controlHeaderDTO, ptzCmdDTO);
888 927 break;
889 928 case Query:
890 929 int sn = rpcBody.get(FastIotConstants.ZLMediaBody.MSG_CONTEXT).intValue();
891   - rpcCameraChannel(devSession,sn);
  930 + rpcCameraChannel(devSession, sn);
892 931 }
893 932 }
894 933
895 934 /**
896 935 * 查询设备通道信息
  936 + *
897 937 * @throws InvalidArgumentException
898 938 * @throws SipException
899 939 * @throws ParseException
900 940 */
901   - private void rpcCameraChannel(GbtDeviceSessionCtx deviceSessionCtx,int sn) throws InvalidArgumentException, SipException, ParseException {
  941 + private void rpcCameraChannel(GbtDeviceSessionCtx deviceSessionCtx, int sn)
  942 + throws InvalidArgumentException, SipException, ParseException {
902 943 SipMessageHeaderDTO catalogHeader =
903   - SipMessageHeaderDTO.builder()
904   - .viaTag(TKSipUtils.getNewViaTag())
905   - .fromTag(TKSipUtils.getNewFromTag())
906   - .build();
  944 + SipMessageHeaderDTO.builder()
  945 + .viaTag(TKSipUtils.getNewViaTag())
  946 + .fromTag(TKSipUtils.getNewFromTag())
  947 + .build();
907 948 commanderService.queryCatalog(
908   - deviceSessionCtx,
909   - catalogHeader,
910   - sn,
911   - ev -> {
912   - String errorMsg = String.format("同步通道失败,错误码: %s, %s", ev.statusCode, ev.msg);
913   - // catalogResponseMessageHandler.setChannelSyncEnd(device.getDeviceId(),
914   - // errorMsg);
915   - });
  949 + deviceSessionCtx,
  950 + catalogHeader,
  951 + sn,
  952 + ev -> {
  953 + String errorMsg = String.format("同步通道失败,错误码: %s, %s", ev.statusCode, ev.msg);
  954 + // catalogResponseMessageHandler.setChannelSyncEnd(device.getDeviceId(),
  955 + // errorMsg);
  956 + });
916 957 }
  958 +
917 959 private String rpcParamVal(JsonNode rpcBody, String key) {
918 960 if (rpcBody.has(key)) {
919 961 return rpcBody.get(key).asText();
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/processor/SIPProvider.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/SIPProvider.java
1   -package org.thingsboard.server.transport;
  1 +package org.thingsboard.server.transport.gbt28181.sip.processor;
2 2
3 3 import javax.sip.SipListener;
4 4
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/processor/SIPRequestProcessorParent.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/SIPRequestProcessorParent.java
1   -package org.thingsboard.server.transport.gbt28181;
  1 +package org.thingsboard.server.transport.gbt28181.sip.processor;
2 2
3 3 import gov.nist.javax.sip.message.SIPRequest;
4 4 import gov.nist.javax.sip.message.SIPResponse;
... ... @@ -20,7 +20,7 @@ import org.dom4j.DocumentException;
20 20 import org.dom4j.Element;
21 21 import org.dom4j.io.SAXReader;
22 22 import org.springframework.beans.factory.annotation.Autowired;
23   -import org.thingsboard.server.transport.SIPSender;
  23 +import org.thingsboard.server.transport.cmd.SIPSender;
24 24 import org.thingsboard.server.transport.util.TKSipUtils;
25 25
26 26 /** 处理接收IPCamera发来的SIP协议请求消息 */
... ...
common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/gbt28181/sip/processor/TimeoutProcessorImpl.java renamed from common/transport/gbt28181/src/main/java/org/thingsboard/server/transport/process/timeout/TimeoutProcessorImpl.java
1   -package org.thingsboard.server.transport.process.timeout;
  1 +package org.thingsboard.server.transport.gbt28181.sip.processor;
2 2
3 3 import javax.sip.TimeoutEvent;
4 4 import javax.sip.header.CallIdHeader;
... ... @@ -8,8 +8,6 @@ import org.springframework.beans.factory.InitializingBean;
8 8 import org.springframework.beans.factory.annotation.Autowired;
9 9 import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
10 10 import org.springframework.stereotype.Component;
11   -import org.thingsboard.server.transport.gbt28181.ITimeoutProcessor;
12   -import org.thingsboard.server.transport.SIPProcessorObserver;
13 11 import org.thingsboard.server.transport.gbt28181.SipSubscribe;
14 12
15 13 @Component
... ...
  1 +package org.thingsboard.server.transport.gbt28181.zlm;
  2 +
  3 +import com.google.protobuf.ByteString;
  4 +import java.net.InetAddress;
  5 +import java.net.UnknownHostException;
  6 +import java.util.List;
  7 +import lombok.Getter;
  8 +import lombok.RequiredArgsConstructor;
  9 +import lombok.extern.slf4j.Slf4j;
  10 +import org.springframework.beans.factory.annotation.Value;
  11 +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
  12 +import org.springframework.boot.context.event.ApplicationReadyEvent;
  13 +import org.springframework.context.event.EventListener;
  14 +import org.springframework.core.annotation.Order;
  15 +import org.springframework.stereotype.Component;
  16 +import org.thingsboard.common.util.JacksonUtil;
  17 +import org.thingsboard.server.common.data.StringUtils;
  18 +import org.thingsboard.server.common.data.yunteng.constant.FastIotConstants;
  19 +import org.thingsboard.server.common.data.yunteng.core.cache.CacheUtils;
  20 +import org.thingsboard.server.common.data.yunteng.utils.DataUtils;
  21 +import org.thingsboard.server.common.transport.TransportService;
  22 +import org.thingsboard.server.common.transport.util.DataDecodingEncodingService;
  23 +import org.thingsboard.server.gen.transport.TransportProtos;
  24 +import org.thingsboard.server.transport.config.MediaConfig;
  25 +import org.thingsboard.server.transport.config.SipConfig;
  26 +
  27 +@Component()
  28 +@Slf4j
  29 +@RequiredArgsConstructor
  30 +@ConditionalOnExpression(
  31 + "'${service.type:null}'=='tb-transport' || ('${service.type:null}'=='monolith' && '${transport.api_enabled:true}'=='true' && '${transport.gbt28181.enabled}'=='true')")
  32 +public class ZLMediaKitStateRunner {
  33 + private final MediaConfig mediaConfig;
  34 + private final SipConfig sipConfig;
  35 + private final DataDecodingEncodingService encodingService;
  36 + private final CacheUtils cacheUtils;
  37 +
  38 + @Value("${transport.gbt28181.media.defaultStateCheckIntervalInSec}")
  39 + @Getter
  40 + private int defaultStateCheckIntervalInSec;
  41 +
  42 + private final TransportService transportService;
  43 +
  44 + @EventListener(ApplicationReadyEvent.class)
  45 + @Order(value = 3)
  46 + public void init(ApplicationReadyEvent applicationReadyEvent) throws UnknownHostException {
  47 + TransportProtos.Gbt28181MediaServerMsg.Builder msgBuilder =
  48 + TransportProtos.Gbt28181MediaServerMsg.newBuilder();
  49 + cacheUtils.put(
  50 + FastIotConstants.CacheSipKey.TK_SIP_CACHE_NAME,
  51 + mediaConfig.getMediaServerId(),
  52 + sipConfig.getDomain());
  53 + if (StringUtils.isEmpty(mediaConfig.getHookIp())) {
  54 + mediaConfig.setHookIp(sipConfig.getIp().split(",")[0]);
  55 + }
  56 + if (StringUtils.isEmpty(mediaConfig.getStreamIp())) {
  57 + mediaConfig.setStreamIp(mediaConfig.getIp());
  58 + }
  59 + String sdpIp = mediaConfig.getSdpIp();
  60 + if (StringUtils.isEmpty(sdpIp)) {
  61 + sdpIp = mediaConfig.getIp();
  62 + } else if (!DataUtils.isIPAddress(sdpIp)) {
  63 + sdpIp = InetAddress.getByName(sdpIp).getHostAddress();
  64 + }
  65 + mediaConfig.setSdpIp(sdpIp);
  66 + byte[] mediaMsgBytes = encodingService.encode(JacksonUtil.valueToTree(mediaConfig));
  67 + msgBuilder.setProfile(ByteString.copyFrom(mediaMsgBytes));
  68 + // 从数据库获取所有的流媒体信息
  69 + List<TransportProtos.Gbt28181MediaServerMsg> dtoList =
  70 + transportService.freshGtb28181Media(msgBuilder.build());
  71 + }
  72 +}
... ...
1   -package org.thingsboard.server.transport.process.timeout;
2   -
3   -import javax.sip.TimeoutEvent;
4   -
5   -public interface ITimeoutProcessor {
6   - void process(TimeoutEvent event);
7   -}
... ... @@ -13,9 +13,7 @@ import lombok.Getter;
13 13 import lombok.Setter;
14 14 import lombok.extern.slf4j.Slf4j;
15 15 import org.thingsboard.server.common.transport.session.DeviceAwareSessionContext;
16   -import org.thingsboard.server.transport.GbtTransportContext;
17   -
18   -import javax.sip.RequestEvent;
  16 +import org.thingsboard.server.transport.gbt28181.session.GbtTransportContext;
19 17
20 18 /**
21 19 * @author Andrew Shvayka
... ...
... ... @@ -10,10 +10,10 @@ import javax.sip.SipFactory;
10 10 import javax.sip.header.UserAgentHeader;
11 11 import org.apache.commons.lang3.RandomStringUtils;
12 12 import org.springframework.util.ObjectUtils;
13   -import org.thingsboard.server.common.data.yunteng.config.media.ThingsKitVersionConfig;
14 13 import org.thingsboard.server.common.data.yunteng.dto.sip.PTZCmdDTO;
15 14 import org.thingsboard.server.common.data.yunteng.dto.sip.VideoChanelDTO;
16   -import org.thingsboard.server.transport.info.RemoteAddressInfo;
  15 +import org.thingsboard.server.transport.config.ThingsKitVersionConfig;
  16 +import org.thingsboard.server.transport.gbt28181.auth.RemoteAddressInfo;
17 17
18 18 public class TKSipUtils {
19 19 public static String getNewMessageViaBranchTag() {
... ... @@ -55,14 +55,14 @@ public class TKSipUtils {
55 55 builder.append(strTmp, 0, 2);
56 56 strTmp = String.format("%X", combineCode2);
57 57 builder.append(strTmp, 0, 1).append("0");
58   - //计算校验码
59   - int checkCode = (0XA5 + 0X0F + 0X01 + cmdCode + parameter1 + parameter2 + (combineCode2 & 0XF0)) % 0X100;
  58 + // 计算校验码
  59 + int checkCode =
  60 + (0XA5 + 0X0F + 0X01 + cmdCode + parameter1 + parameter2 + (combineCode2 & 0XF0)) % 0X100;
60 61 strTmp = String.format("%02X", checkCode);
61 62 builder.append(strTmp, 0, 2);
62 63 return builder.toString();
63 64 }
64 65
65   -
66 66 public static UserAgentHeader createUserAgentHeader(ThingsKitVersionConfig config)
67 67 throws PeerUnavailableException, ParseException {
68 68 List<String> agentParam = new ArrayList<>();
... ...
1 1 /**
2 2 * Copyright © 2016-2022 The Thingsboard Authors
3 3 *
4   - * Licensed under the Apache License, Version 2.0 (the "License");
5   - * you may not use this file except in compliance with the License.
6   - * You may obtain a copy of the License at
  4 + * <p>Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file
  5 + * except in compliance with the License. You may obtain a copy of the License at
7 6 *
8   - * http://www.apache.org/licenses/LICENSE-2.0
  7 + * <p>http://www.apache.org/licenses/LICENSE-2.0
9 8 *
10   - * Unless required by applicable law or agreed to in writing, software
11   - * distributed under the License is distributed on an "AS IS" BASIS,
12   - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   - * See the License for the specific language governing permissions and
  9 + * <p>Unless required by applicable law or agreed to in writing, software distributed under the
  10 + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
  11 + * express or implied. See the License for the specific language governing permissions and
14 12 * limitations under the License.
15 13 */
16 14 package org.thingsboard.server.common.transport;
17 15
  16 +import java.util.List;
  17 +import java.util.concurrent.ExecutorService;
  18 +import java.util.concurrent.atomic.AtomicInteger;
18 19 import org.thingsboard.server.common.data.DeviceProfile;
19 20 import org.thingsboard.server.common.data.DeviceTransportType;
20 21 import org.thingsboard.server.common.data.rpc.RpcStatus;
... ... @@ -40,10 +41,11 @@ import org.thingsboard.server.gen.transport.TransportProtos.GetSnmpDevicesRespon
40 41 import org.thingsboard.server.gen.transport.TransportProtos.LwM2MRequestMsg;
41 42 import org.thingsboard.server.gen.transport.TransportProtos.LwM2MResponseMsg;
42 43 import org.thingsboard.server.gen.transport.TransportProtos.PostAttributeMsg;
43   -import org.thingsboard.server.gen.transport.TransportProtos.PostTelemetryMsg;
44 44 import org.thingsboard.server.gen.transport.TransportProtos.PostEventMsg;
  45 +import org.thingsboard.server.gen.transport.TransportProtos.PostTelemetryMsg;
45 46 import org.thingsboard.server.gen.transport.TransportProtos.ProvisionDeviceRequestMsg;
46 47 import org.thingsboard.server.gen.transport.TransportProtos.ProvisionDeviceResponseMsg;
  48 +import org.thingsboard.server.gen.transport.TransportProtos.ScriptProto;
47 49 import org.thingsboard.server.gen.transport.TransportProtos.SessionEventMsg;
48 50 import org.thingsboard.server.gen.transport.TransportProtos.SessionInfoProto;
49 51 import org.thingsboard.server.gen.transport.TransportProtos.SubscribeToAttributeUpdatesMsg;
... ... @@ -57,104 +59,140 @@ import org.thingsboard.server.gen.transport.TransportProtos.ValidateBasicMqttCre
57 59 import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceLwM2MCredentialsRequestMsg;
58 60 import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceTokenRequestMsg;
59 61 import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceX509CertRequestMsg;
60   -import org.thingsboard.server.gen.transport.TransportProtos.ScriptProto;
61 62
62   -import java.util.List;
63   -import java.util.concurrent.ExecutorService;
64   -import java.util.concurrent.atomic.AtomicInteger;
65   -
66   -/**
67   - * Created by ashvayka on 04.10.18.
68   - */
  63 +/** Created by ashvayka on 04.10.18. */
69 64 public interface TransportService {
70 65
71   - GetEntityProfileResponseMsg getEntityProfile(GetEntityProfileRequestMsg msg);
72   -
73   - GetResourceResponseMsg getResource(GetResourceRequestMsg msg);
74   -
75   - GetSnmpDevicesResponseMsg getSnmpDevicesIds(GetSnmpDevicesRequestMsg requestMsg);
76   -
77   - GetDeviceResponseMsg getDevice(GetDeviceRequestMsg requestMsg);
78   -
79   - GetDeviceCredentialsResponseMsg getDeviceCredentials(GetDeviceCredentialsRequestMsg requestMsg);
  66 + GetEntityProfileResponseMsg getEntityProfile(GetEntityProfileRequestMsg msg);
80 67
  68 + GetResourceResponseMsg getResource(GetResourceRequestMsg msg);
81 69
  70 + GetSnmpDevicesResponseMsg getSnmpDevicesIds(GetSnmpDevicesRequestMsg requestMsg);
82 71
83   - void process(DeviceTransportType transportType, ValidateDeviceTokenRequestMsg msg,
84   - TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
  72 + GetDeviceResponseMsg getDevice(GetDeviceRequestMsg requestMsg);
85 73
86   - void process(DeviceTransportType transportType, ValidateBasicMqttCredRequestMsg msg,
87   - TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
  74 + GetDeviceCredentialsResponseMsg getDeviceCredentials(GetDeviceCredentialsRequestMsg requestMsg);
88 75
89   - void process(DeviceTransportType transportType, ValidateDeviceX509CertRequestMsg msg,
90   - TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
  76 + void process(
  77 + DeviceTransportType transportType,
  78 + ValidateDeviceTokenRequestMsg msg,
  79 + TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
91 80
92   - void process(ValidateDeviceLwM2MCredentialsRequestMsg msg,
93   - TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
  81 + void process(
  82 + DeviceTransportType transportType,
  83 + ValidateBasicMqttCredRequestMsg msg,
  84 + TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
94 85
95   - void process(GetOrCreateDeviceFromGatewayRequestMsg msg,
96   - TransportServiceCallback<GetOrCreateDeviceFromGatewayResponse> callback);
  86 + void process(
  87 + DeviceTransportType transportType,
  88 + ValidateDeviceX509CertRequestMsg msg,
  89 + TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
97 90
98   - void process(ProvisionDeviceRequestMsg msg,
99   - TransportServiceCallback<ProvisionDeviceResponseMsg> callback);
  91 + void process(
  92 + ValidateDeviceLwM2MCredentialsRequestMsg msg,
  93 + TransportServiceCallback<ValidateDeviceCredentialsResponse> callback);
100 94
101   - void onProfileUpdate(DeviceProfile deviceProfile);
  95 + void process(
  96 + GetOrCreateDeviceFromGatewayRequestMsg msg,
  97 + TransportServiceCallback<GetOrCreateDeviceFromGatewayResponse> callback);
102 98
103   - void process(LwM2MRequestMsg msg,
104   - TransportServiceCallback<LwM2MResponseMsg> callback);
  99 + void process(
  100 + ProvisionDeviceRequestMsg msg, TransportServiceCallback<ProvisionDeviceResponseMsg> callback);
105 101
106   - void process(SessionInfoProto sessionInfo, SessionEventMsg msg, TransportServiceCallback<Void> callback);
  102 + void onProfileUpdate(DeviceProfile deviceProfile);
107 103
108   - void process(SessionInfoProto sessionInfo, PostTelemetryMsg msg, TransportServiceCallback<Void> callback);
  104 + void process(LwM2MRequestMsg msg, TransportServiceCallback<LwM2MResponseMsg> callback);
109 105
110   - void process(SessionInfoProto sessionInfo, PostAttributeMsg msg, TransportServiceCallback<Void> callback);
  106 + void process(
  107 + SessionInfoProto sessionInfo, SessionEventMsg msg, TransportServiceCallback<Void> callback);
111 108
  109 + void process(
  110 + SessionInfoProto sessionInfo, PostTelemetryMsg msg, TransportServiceCallback<Void> callback);
112 111
113   - void process(SessionInfoProto sessionInfo, GetAttributeRequestMsg msg, TransportServiceCallback<Void> callback);
  112 + void process(
  113 + SessionInfoProto sessionInfo, PostAttributeMsg msg, TransportServiceCallback<Void> callback);
114 114
115   - void process(SessionInfoProto sessionInfo, SubscribeToAttributeUpdatesMsg msg, TransportServiceCallback<Void> callback);
  115 + void process(
  116 + SessionInfoProto sessionInfo,
  117 + GetAttributeRequestMsg msg,
  118 + TransportServiceCallback<Void> callback);
116 119
117   - void process(SessionInfoProto sessionInfo, SubscribeToRPCMsg msg, TransportServiceCallback<Void> callback);
  120 + void process(
  121 + SessionInfoProto sessionInfo,
  122 + SubscribeToAttributeUpdatesMsg msg,
  123 + TransportServiceCallback<Void> callback);
118 124
119   - void process(SessionInfoProto sessionInfo, ToDeviceRpcResponseMsg msg, TransportServiceCallback<Void> callback);
  125 + void process(
  126 + SessionInfoProto sessionInfo, SubscribeToRPCMsg msg, TransportServiceCallback<Void> callback);
120 127
121   - void process(SessionInfoProto sessionInfo, ToServerRpcRequestMsg msg, TransportServiceCallback<Void> callback);
  128 + void process(
  129 + SessionInfoProto sessionInfo,
  130 + ToDeviceRpcResponseMsg msg,
  131 + TransportServiceCallback<Void> callback);
122 132
123   - void process(SessionInfoProto sessionInfo, ToDeviceRpcRequestMsg msg, RpcStatus rpcStatus, TransportServiceCallback<Void> callback);
  133 + void process(
  134 + SessionInfoProto sessionInfo,
  135 + ToServerRpcRequestMsg msg,
  136 + TransportServiceCallback<Void> callback);
124 137
125   - void process(SessionInfoProto sessionInfo, SubscriptionInfoProto msg, TransportServiceCallback<Void> callback);
  138 + void process(
  139 + SessionInfoProto sessionInfo,
  140 + ToDeviceRpcRequestMsg msg,
  141 + RpcStatus rpcStatus,
  142 + TransportServiceCallback<Void> callback);
126 143
127   - void process(SessionInfoProto sessionInfo, ClaimDeviceMsg msg, TransportServiceCallback<Void> callback);
  144 + void process(
  145 + SessionInfoProto sessionInfo,
  146 + SubscriptionInfoProto msg,
  147 + TransportServiceCallback<Void> callback);
128 148
129   - void process(TransportToDeviceActorMsg msg, TransportServiceCallback<Void> callback);
  149 + void process(
  150 + SessionInfoProto sessionInfo, ClaimDeviceMsg msg, TransportServiceCallback<Void> callback);
130 151
131   - void process(SessionInfoProto sessionInfoProto, GetOtaPackageRequestMsg msg, TransportServiceCallback<GetOtaPackageResponseMsg> callback);
  152 + void process(TransportToDeviceActorMsg msg, TransportServiceCallback<Void> callback);
132 153
133   - SessionMetaData registerAsyncSession(SessionInfoProto sessionInfo, SessionMsgListener listener);
  154 + void process(
  155 + SessionInfoProto sessionInfoProto,
  156 + GetOtaPackageRequestMsg msg,
  157 + TransportServiceCallback<GetOtaPackageResponseMsg> callback);
134 158
135   - SessionMetaData registerSyncSession(SessionInfoProto sessionInfo, SessionMsgListener listener, long timeout);
  159 + SessionMetaData registerAsyncSession(SessionInfoProto sessionInfo, SessionMsgListener listener);
136 160
137   - void reportActivity(SessionInfoProto sessionInfo);
  161 + SessionMetaData registerSyncSession(
  162 + SessionInfoProto sessionInfo, SessionMsgListener listener, long timeout);
138 163
139   - void deregisterSession(SessionInfoProto sessionInfo);
  164 + void reportActivity(SessionInfoProto sessionInfo);
140 165
141   - void log(SessionInfoProto sessionInfo, String msg);
  166 + void deregisterSession(SessionInfoProto sessionInfo);
142 167
143   - void notifyAboutUplink(SessionInfoProto sessionInfo, TransportProtos.UplinkNotificationMsg build, TransportServiceCallback<Void> empty);
  168 + void log(SessionInfoProto sessionInfo, String msg);
144 169
145   - ExecutorService getCallbackExecutor();
  170 + void notifyAboutUplink(
  171 + SessionInfoProto sessionInfo,
  172 + TransportProtos.UplinkNotificationMsg build,
  173 + TransportServiceCallback<Void> empty);
146 174
147   - boolean hasSession(SessionInfoProto sessionInfo);
  175 + ExecutorService getCallbackExecutor();
148 176
149   - void createGaugeStats(String openConnections, AtomicInteger connectionsCounter);
  177 + boolean hasSession(SessionInfoProto sessionInfo);
150 178
  179 + void createGaugeStats(String openConnections, AtomicInteger connectionsCounter);
151 180
  181 + // Thingskit function:begin
  182 + List<ScriptProto> getScripts(ScriptProto msg);
152 183
  184 + void process(
  185 + SessionInfoProto sessionInfo,
  186 + PostEventMsg msg,
  187 + TransportServiceCallback<Void> callback,
  188 + String topicName);
153 189
  190 + void process(
  191 + SessionInfoProto sessionInfo,
  192 + TransportProtos.Gbt28181RequestMsg msg,
  193 + TransportServiceCallback<TransportProtos.Gbt28181ResponseMsg> callback);
154 194
155   - //Thingskit function:begin
156   - List<ScriptProto> getScripts(ScriptProto msg);
157   - void process(SessionInfoProto sessionInfo, PostEventMsg msg, TransportServiceCallback<Void> callback,String topicName);
158   - void process(SessionInfoProto sessionInfo, TransportProtos.Gbt28181RequestMsg msg, TransportServiceCallback<TransportProtos.Gbt28181ResponseMsg> callback);
159   - //Thingskit function:end
  195 + List<TransportProtos.Gbt28181MediaServerMsg> freshGtb28181Media(
  196 + TransportProtos.Gbt28181MediaServerMsg msg);
  197 + // Thingskit function:end
160 198 }
... ...