Added proper handling of edge event save methods - clients aware of failures
This commit is contained in:
parent
d3eda0c473
commit
bb588ac238
@ -107,6 +107,7 @@ import java.util.Objects;
|
|||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
import java.util.concurrent.ExecutionException;
|
||||||
import java.util.function.Consumer;
|
import java.util.function.Consumer;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@ -200,8 +201,13 @@ class DeviceActorMessageProcessor extends AbstractContextAwareMsgProcessor {
|
|||||||
boolean sent = false;
|
boolean sent = false;
|
||||||
if (systemContext.isEdgesEnabled() && edgeId != null) {
|
if (systemContext.isEdgesEnabled() && edgeId != null) {
|
||||||
log.debug("[{}][{}] device is related to edge [{}]. Saving RPC request to edge queue", tenantId, deviceId, edgeId.getId());
|
log.debug("[{}][{}] device is related to edge [{}]. Saving RPC request to edge queue", tenantId, deviceId, edgeId.getId());
|
||||||
saveRpcRequestToEdgeQueue(request, rpcRequest.getRequestId());
|
try {
|
||||||
|
saveRpcRequestToEdgeQueue(request, rpcRequest.getRequestId()).get();
|
||||||
sent = true;
|
sent = true;
|
||||||
|
} catch (InterruptedException | ExecutionException e) {
|
||||||
|
String errMsg = String.format("[%s][%s][%s] Failed to save rpc request to edge queue %s", tenantId, deviceId, edgeId.getId(), request);
|
||||||
|
log.error(errMsg, e);
|
||||||
|
}
|
||||||
} else if (isSendNewRpcAvailable()) {
|
} else if (isSendNewRpcAvailable()) {
|
||||||
sent = rpcSubscriptions.size() > 0;
|
sent = rpcSubscriptions.size() > 0;
|
||||||
Set<UUID> syncSessionSet = new HashSet<>();
|
Set<UUID> syncSessionSet = new HashSet<>();
|
||||||
@ -810,7 +816,7 @@ class DeviceActorMessageProcessor extends AbstractContextAwareMsgProcessor {
|
|||||||
systemContext.getTbCoreToTransportService().process(nodeId, msg);
|
systemContext.getTbCoreToTransportService().process(nodeId, msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void saveRpcRequestToEdgeQueue(ToDeviceRpcRequest msg, Integer requestId) {
|
private ListenableFuture<Void> saveRpcRequestToEdgeQueue(ToDeviceRpcRequest msg, Integer requestId) {
|
||||||
ObjectNode body = mapper.createObjectNode();
|
ObjectNode body = mapper.createObjectNode();
|
||||||
body.put("requestId", requestId);
|
body.put("requestId", requestId);
|
||||||
body.put("requestUUID", msg.getId().toString());
|
body.put("requestUUID", msg.getId().toString());
|
||||||
@ -821,17 +827,9 @@ class DeviceActorMessageProcessor extends AbstractContextAwareMsgProcessor {
|
|||||||
|
|
||||||
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, EdgeEventType.DEVICE, EdgeEventActionType.RPC_CALL, deviceId, body);
|
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, EdgeEventType.DEVICE, EdgeEventActionType.RPC_CALL, deviceId, body);
|
||||||
|
|
||||||
Futures.addCallback(systemContext.getEdgeEventService().saveAsync(edgeEvent), new FutureCallback<>() {
|
return Futures.transform(systemContext.getEdgeEventService().saveAsync(edgeEvent), unused -> {
|
||||||
@Override
|
|
||||||
public void onSuccess(Void unused) {
|
|
||||||
systemContext.getClusterService().onEdgeEventUpdate(tenantId, edgeId);
|
systemContext.getClusterService().onEdgeEventUpdate(tenantId, edgeId);
|
||||||
}
|
return null;
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
String errMsg = String.format("Failed to save edge event. msg [%s], edge event [%s]", msg, edgeEvent);
|
|
||||||
log.warn(errMsg, t);
|
|
||||||
}
|
|
||||||
}, systemContext.getDbCallbackExecutor());
|
}, systemContext.getDbCallbackExecutor());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -180,7 +180,7 @@ public class EdgeController extends BaseController {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void onEdgeCreatedOrUpdated(TenantId tenantId, Edge edge, RuleChain edgeTemplateRootRuleChain, boolean updated, SecurityUser user) throws IOException, ThingsboardException {
|
private void onEdgeCreatedOrUpdated(TenantId tenantId, Edge edge, RuleChain edgeTemplateRootRuleChain, boolean updated, SecurityUser user) throws Exception {
|
||||||
if (!updated) {
|
if (!updated) {
|
||||||
ruleChainService.assignRuleChainToEdge(tenantId, edgeTemplateRootRuleChain.getId(), edge.getId());
|
ruleChainService.assignRuleChainToEdge(tenantId, edgeTemplateRootRuleChain.getId(), edge.getId());
|
||||||
edgeNotificationService.setEdgeRootRuleChain(tenantId, edge, edgeTemplateRootRuleChain.getId());
|
edgeNotificationService.setEdgeRootRuleChain(tenantId, edge, edgeTemplateRootRuleChain.getId());
|
||||||
|
|||||||
@ -18,6 +18,7 @@ package org.thingsboard.server.service.edge;
|
|||||||
import com.fasterxml.jackson.databind.JsonNode;
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
import com.google.common.util.concurrent.FutureCallback;
|
import com.google.common.util.concurrent.FutureCallback;
|
||||||
import com.google.common.util.concurrent.Futures;
|
import com.google.common.util.concurrent.Futures;
|
||||||
|
import com.google.common.util.concurrent.ListenableFuture;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
@ -46,7 +47,6 @@ import org.thingsboard.server.service.edge.rpc.processor.RelationEdgeProcessor;
|
|||||||
|
|
||||||
import javax.annotation.PostConstruct;
|
import javax.annotation.PostConstruct;
|
||||||
import javax.annotation.PreDestroy;
|
import javax.annotation.PreDestroy;
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
import java.util.concurrent.ExecutorService;
|
import java.util.concurrent.ExecutorService;
|
||||||
import java.util.concurrent.Executors;
|
import java.util.concurrent.Executors;
|
||||||
@ -95,14 +95,14 @@ public class DefaultEdgeNotificationService implements EdgeNotificationService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Edge setEdgeRootRuleChain(TenantId tenantId, Edge edge, RuleChainId ruleChainId) throws IOException {
|
public Edge setEdgeRootRuleChain(TenantId tenantId, Edge edge, RuleChainId ruleChainId) throws Exception {
|
||||||
edge.setRootRuleChainId(ruleChainId);
|
edge.setRootRuleChainId(ruleChainId);
|
||||||
Edge savedEdge = edgeService.saveEdge(edge);
|
Edge savedEdge = edgeService.saveEdge(edge);
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.RULE_CHAIN, EdgeEventActionType.UPDATED, ruleChainId, null);
|
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.RULE_CHAIN, EdgeEventActionType.UPDATED, ruleChainId, null).get();
|
||||||
return savedEdge;
|
return savedEdge;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void saveEdgeEvent(TenantId tenantId,
|
private ListenableFuture<Void> saveEdgeEvent(TenantId tenantId,
|
||||||
EdgeId edgeId,
|
EdgeId edgeId,
|
||||||
EdgeEventType type,
|
EdgeEventType type,
|
||||||
EdgeEventActionType action,
|
EdgeEventActionType action,
|
||||||
@ -113,17 +113,9 @@ public class DefaultEdgeNotificationService implements EdgeNotificationService {
|
|||||||
|
|
||||||
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, type, action, entityId, body);
|
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, type, action, entityId, body);
|
||||||
|
|
||||||
Futures.addCallback(edgeEventService.saveAsync(edgeEvent), new FutureCallback<>() {
|
return Futures.transform(edgeEventService.saveAsync(edgeEvent), unused -> {
|
||||||
@Override
|
|
||||||
public void onSuccess(@Nullable Void unused) {
|
|
||||||
clusterService.onEdgeEventUpdate(tenantId, edgeId);
|
clusterService.onEdgeEventUpdate(tenantId, edgeId);
|
||||||
}
|
return null;
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
String errMsg = String.format("Failed to save edge event. edge event [%s]", edgeEvent);
|
|
||||||
log.warn(errMsg, t);
|
|
||||||
}
|
|
||||||
}, dbCallBackExecutor);
|
}, dbCallBackExecutor);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -133,9 +125,10 @@ public class DefaultEdgeNotificationService implements EdgeNotificationService {
|
|||||||
try {
|
try {
|
||||||
TenantId tenantId = TenantId.fromUUID(new UUID(edgeNotificationMsg.getTenantIdMSB(), edgeNotificationMsg.getTenantIdLSB()));
|
TenantId tenantId = TenantId.fromUUID(new UUID(edgeNotificationMsg.getTenantIdMSB(), edgeNotificationMsg.getTenantIdLSB()));
|
||||||
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
||||||
|
ListenableFuture<Void> future;
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case EDGE:
|
case EDGE:
|
||||||
edgeProcessor.processEdgeNotification(tenantId, edgeNotificationMsg);
|
future = edgeProcessor.processEdgeNotification(tenantId, edgeNotificationMsg);
|
||||||
break;
|
break;
|
||||||
case USER:
|
case USER:
|
||||||
case ASSET:
|
case ASSET:
|
||||||
@ -144,31 +137,45 @@ public class DefaultEdgeNotificationService implements EdgeNotificationService {
|
|||||||
case ENTITY_VIEW:
|
case ENTITY_VIEW:
|
||||||
case DASHBOARD:
|
case DASHBOARD:
|
||||||
case RULE_CHAIN:
|
case RULE_CHAIN:
|
||||||
entityProcessor.processEntityNotification(tenantId, edgeNotificationMsg);
|
future = entityProcessor.processEntityNotification(tenantId, edgeNotificationMsg);
|
||||||
break;
|
break;
|
||||||
case CUSTOMER:
|
case CUSTOMER:
|
||||||
customerProcessor.processCustomerNotification(tenantId, edgeNotificationMsg);
|
future = customerProcessor.processCustomerNotification(tenantId, edgeNotificationMsg);
|
||||||
break;
|
break;
|
||||||
case WIDGETS_BUNDLE:
|
case WIDGETS_BUNDLE:
|
||||||
case WIDGET_TYPE:
|
case WIDGET_TYPE:
|
||||||
entityProcessor.processEntityNotificationForAllEdges(tenantId, edgeNotificationMsg);
|
future = entityProcessor.processEntityNotificationForAllEdges(tenantId, edgeNotificationMsg);
|
||||||
break;
|
break;
|
||||||
case ALARM:
|
case ALARM:
|
||||||
alarmProcessor.processAlarmNotification(tenantId, edgeNotificationMsg);
|
future = alarmProcessor.processAlarmNotification(tenantId, edgeNotificationMsg);
|
||||||
break;
|
break;
|
||||||
case RELATION:
|
case RELATION:
|
||||||
relationProcessor.processRelationNotification(tenantId, edgeNotificationMsg);
|
future = relationProcessor.processRelationNotification(tenantId, edgeNotificationMsg);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
log.warn("Edge event type [{}] is not designed to be pushed to edge", type);
|
log.warn("Edge event type [{}] is not designed to be pushed to edge", type);
|
||||||
|
future = Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
Futures.addCallback(future, new FutureCallback<>() {
|
||||||
callback.onFailure(e);
|
@Override
|
||||||
String errMsg = String.format("Can't push to edge updates, edgeNotificationMsg [%s]", edgeNotificationMsg);
|
public void onSuccess(@Nullable Void unused) {
|
||||||
log.error(errMsg, e);
|
|
||||||
} finally {
|
|
||||||
callback.onSuccess();
|
callback.onSuccess();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onFailure(Throwable throwable) {
|
||||||
|
callBackFailure(edgeNotificationMsg, callback, throwable);
|
||||||
|
}
|
||||||
|
}, dbCallBackExecutor);
|
||||||
|
} catch (Exception e) {
|
||||||
|
callBackFailure(edgeNotificationMsg, callback, e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void callBackFailure(TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg, TbCallback callback, Throwable throwable) {
|
||||||
|
String errMsg = String.format("Can't push to edge updates, edgeNotificationMsg [%s]", edgeNotificationMsg);
|
||||||
|
log.error(errMsg, throwable);
|
||||||
|
callback.onFailure(throwable);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -21,11 +21,9 @@ import org.thingsboard.server.common.data.id.TenantId;
|
|||||||
import org.thingsboard.server.common.msg.queue.TbCallback;
|
import org.thingsboard.server.common.msg.queue.TbCallback;
|
||||||
import org.thingsboard.server.gen.transport.TransportProtos;
|
import org.thingsboard.server.gen.transport.TransportProtos;
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
public interface EdgeNotificationService {
|
public interface EdgeNotificationService {
|
||||||
|
|
||||||
Edge setEdgeRootRuleChain(TenantId tenantId, Edge edge, RuleChainId ruleChainId) throws IOException;
|
Edge setEdgeRootRuleChain(TenantId tenantId, Edge edge, RuleChainId ruleChainId) throws Exception;
|
||||||
|
|
||||||
void pushNotificationToEdge(TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg, TbCallback callback);
|
void pushNotificationToEdge(TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg, TbCallback callback);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -16,11 +16,9 @@
|
|||||||
package org.thingsboard.server.service.edge.rpc.processor;
|
package org.thingsboard.server.service.edge.rpc.processor;
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||||
import com.google.common.util.concurrent.FutureCallback;
|
|
||||||
import com.google.common.util.concurrent.Futures;
|
import com.google.common.util.concurrent.Futures;
|
||||||
import com.google.common.util.concurrent.ListenableFuture;
|
import com.google.common.util.concurrent.ListenableFuture;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.thingsboard.server.common.data.EdgeUtils;
|
import org.thingsboard.server.common.data.EdgeUtils;
|
||||||
import org.thingsboard.server.common.data.EntityType;
|
import org.thingsboard.server.common.data.EntityType;
|
||||||
@ -43,6 +41,8 @@ import org.thingsboard.server.gen.edge.v1.UpdateMsgType;
|
|||||||
import org.thingsboard.server.gen.transport.TransportProtos;
|
import org.thingsboard.server.gen.transport.TransportProtos;
|
||||||
import org.thingsboard.server.queue.util.TbCoreComponent;
|
import org.thingsboard.server.queue.util.TbCoreComponent;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
@ -148,49 +148,44 @@ public class AlarmEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
return downlinkMsg;
|
return downlinkMsg;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processAlarmNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) throws JsonProcessingException {
|
public ListenableFuture<Void> processAlarmNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) throws JsonProcessingException {
|
||||||
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
||||||
AlarmId alarmId = new AlarmId(new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
AlarmId alarmId = new AlarmId(new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
||||||
switch (actionType) {
|
switch (actionType) {
|
||||||
case DELETED:
|
case DELETED:
|
||||||
EdgeId edgeId = new EdgeId(new UUID(edgeNotificationMsg.getEdgeIdMSB(), edgeNotificationMsg.getEdgeIdLSB()));
|
EdgeId edgeId = new EdgeId(new UUID(edgeNotificationMsg.getEdgeIdMSB(), edgeNotificationMsg.getEdgeIdLSB()));
|
||||||
Alarm alarm = mapper.readValue(edgeNotificationMsg.getBody(), Alarm.class);
|
Alarm deletedAlarm = mapper.readValue(edgeNotificationMsg.getBody(), Alarm.class);
|
||||||
saveEdgeEvent(tenantId, edgeId, EdgeEventType.ALARM, actionType, alarmId, mapper.valueToTree(alarm));
|
return saveEdgeEvent(tenantId, edgeId, EdgeEventType.ALARM, actionType, alarmId, mapper.valueToTree(deletedAlarm));
|
||||||
break;
|
|
||||||
default:
|
default:
|
||||||
ListenableFuture<Alarm> alarmFuture = alarmService.findAlarmByIdAsync(tenantId, alarmId);
|
ListenableFuture<Alarm> alarmFuture = alarmService.findAlarmByIdAsync(tenantId, alarmId);
|
||||||
Futures.addCallback(alarmFuture, new FutureCallback<Alarm>() {
|
return Futures.transformAsync(alarmFuture, alarm -> {
|
||||||
@Override
|
if (alarm == null) {
|
||||||
public void onSuccess(@Nullable Alarm alarm) {
|
return Futures.immediateFuture(null);
|
||||||
if (alarm != null) {
|
}
|
||||||
EdgeEventType type = EdgeUtils.getEdgeEventTypeByEntityType(alarm.getOriginator().getEntityType());
|
EdgeEventType type = EdgeUtils.getEdgeEventTypeByEntityType(alarm.getOriginator().getEntityType());
|
||||||
if (type != null) {
|
if (type == null) {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<EdgeId> pageData;
|
PageData<EdgeId> pageData;
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
do {
|
do {
|
||||||
pageData = edgeService.findRelatedEdgeIdsByEntityId(tenantId, alarm.getOriginator(), pageLink);
|
pageData = edgeService.findRelatedEdgeIdsByEntityId(tenantId, alarm.getOriginator(), pageLink);
|
||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
for (EdgeId edgeId : pageData.getData()) {
|
for (EdgeId relatedEdgeId : pageData.getData()) {
|
||||||
saveEdgeEvent(tenantId,
|
futures.add(saveEdgeEvent(tenantId,
|
||||||
edgeId,
|
relatedEdgeId,
|
||||||
EdgeEventType.ALARM,
|
EdgeEventType.ALARM,
|
||||||
EdgeEventActionType.valueOf(edgeNotificationMsg.getAction()),
|
EdgeEventActionType.valueOf(edgeNotificationMsg.getAction()),
|
||||||
alarmId,
|
alarmId,
|
||||||
null);
|
null));
|
||||||
}
|
}
|
||||||
if (pageData.hasNext()) {
|
if (pageData.hasNext()) {
|
||||||
pageLink = pageLink.nextPageLink();
|
pageLink = pageLink.nextPageLink();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (pageData != null && pageData.hasNext());
|
} while (pageData != null && pageData.hasNext());
|
||||||
}
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
log.warn("[{}] can't find alarm by id [{}] {}", tenantId.getId(), alarmId.getId(), t);
|
|
||||||
}
|
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -17,10 +17,9 @@ package org.thingsboard.server.service.edge.rpc.processor;
|
|||||||
|
|
||||||
import com.fasterxml.jackson.databind.JsonNode;
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
import com.google.common.util.concurrent.FutureCallback;
|
|
||||||
import com.google.common.util.concurrent.Futures;
|
import com.google.common.util.concurrent.Futures;
|
||||||
|
import com.google.common.util.concurrent.ListenableFuture;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.thingsboard.server.cluster.TbClusterService;
|
import org.thingsboard.server.cluster.TbClusterService;
|
||||||
import org.thingsboard.server.common.data.Device;
|
import org.thingsboard.server.common.data.Device;
|
||||||
@ -71,6 +70,9 @@ import org.thingsboard.server.service.executors.DbCallbackExecutorService;
|
|||||||
import org.thingsboard.server.service.profile.TbDeviceProfileCache;
|
import org.thingsboard.server.service.profile.TbDeviceProfileCache;
|
||||||
import org.thingsboard.server.service.state.DeviceStateService;
|
import org.thingsboard.server.service.state.DeviceStateService;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
@Slf4j
|
@Slf4j
|
||||||
public abstract class BaseEdgeProcessor {
|
public abstract class BaseEdgeProcessor {
|
||||||
|
|
||||||
@ -183,7 +185,7 @@ public abstract class BaseEdgeProcessor {
|
|||||||
@Autowired
|
@Autowired
|
||||||
protected DbCallbackExecutorService dbCallbackExecutorService;
|
protected DbCallbackExecutorService dbCallbackExecutorService;
|
||||||
|
|
||||||
protected void saveEdgeEvent(TenantId tenantId,
|
protected ListenableFuture<Void> saveEdgeEvent(TenantId tenantId,
|
||||||
EdgeId edgeId,
|
EdgeId edgeId,
|
||||||
EdgeEventType type,
|
EdgeEventType type,
|
||||||
EdgeEventActionType action,
|
EdgeEventActionType action,
|
||||||
@ -195,17 +197,9 @@ public abstract class BaseEdgeProcessor {
|
|||||||
|
|
||||||
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, type, action, entityId, body);
|
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, type, action, entityId, body);
|
||||||
|
|
||||||
Futures.addCallback(edgeEventService.saveAsync(edgeEvent), new FutureCallback<>() {
|
return Futures.transform(edgeEventService.saveAsync(edgeEvent), unused -> {
|
||||||
@Override
|
|
||||||
public void onSuccess(@Nullable Void unused) {
|
|
||||||
tbClusterService.onEdgeEventUpdate(tenantId, edgeId);
|
tbClusterService.onEdgeEventUpdate(tenantId, edgeId);
|
||||||
}
|
return null;
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
String errMsg = String.format("Failed to save edge event. edge event [%s]", edgeEvent);
|
|
||||||
log.warn(errMsg, t);
|
|
||||||
}
|
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -217,19 +211,21 @@ public abstract class BaseEdgeProcessor {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void processActionForAllEdges(TenantId tenantId, EdgeEventType type, EdgeEventActionType actionType, EntityId entityId) {
|
protected ListenableFuture<Void> processActionForAllEdges(TenantId tenantId, EdgeEventType type, EdgeEventActionType actionType, EntityId entityId) {
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<Edge> pageData;
|
PageData<Edge> pageData;
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
do {
|
do {
|
||||||
pageData = edgeService.findEdgesByTenantId(tenantId, pageLink);
|
pageData = edgeService.findEdgesByTenantId(tenantId, pageLink);
|
||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
for (Edge edge : pageData.getData()) {
|
for (Edge edge : pageData.getData()) {
|
||||||
saveEdgeEvent(tenantId, edge.getId(), type, actionType, entityId, null);
|
futures.add(saveEdgeEvent(tenantId, edge.getId(), type, actionType, entityId, null));
|
||||||
}
|
}
|
||||||
if (pageData.hasNext()) {
|
if (pageData.hasNext()) {
|
||||||
pageLink = pageLink.nextPageLink();
|
pageLink = pageLink.nextPageLink();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (pageData != null && pageData.hasNext());
|
} while (pageData != null && pageData.hasNext());
|
||||||
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -15,6 +15,8 @@
|
|||||||
*/
|
*/
|
||||||
package org.thingsboard.server.service.edge.rpc.processor;
|
package org.thingsboard.server.service.edge.rpc.processor;
|
||||||
|
|
||||||
|
import com.google.common.util.concurrent.Futures;
|
||||||
|
import com.google.common.util.concurrent.ListenableFuture;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.thingsboard.server.common.data.Customer;
|
import org.thingsboard.server.common.data.Customer;
|
||||||
@ -35,6 +37,8 @@ import org.thingsboard.server.gen.edge.v1.UpdateMsgType;
|
|||||||
import org.thingsboard.server.gen.transport.TransportProtos;
|
import org.thingsboard.server.gen.transport.TransportProtos;
|
||||||
import org.thingsboard.server.queue.util.TbCoreComponent;
|
import org.thingsboard.server.queue.util.TbCoreComponent;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
@ -70,7 +74,7 @@ public class CustomerEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
return downlinkMsg;
|
return downlinkMsg;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processCustomerNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
public ListenableFuture<Void> processCustomerNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
||||||
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
||||||
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
||||||
UUID uuid = new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB());
|
UUID uuid = new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB());
|
||||||
@ -79,22 +83,24 @@ public class CustomerEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
case UPDATED:
|
case UPDATED:
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<Edge> pageData;
|
PageData<Edge> pageData;
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
do {
|
do {
|
||||||
pageData = edgeService.findEdgesByTenantIdAndCustomerId(tenantId, customerId, pageLink);
|
pageData = edgeService.findEdgesByTenantIdAndCustomerId(tenantId, customerId, pageLink);
|
||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
for (Edge edge : pageData.getData()) {
|
for (Edge edge : pageData.getData()) {
|
||||||
saveEdgeEvent(tenantId, edge.getId(), type, actionType, customerId, null);
|
futures.add(saveEdgeEvent(tenantId, edge.getId(), type, actionType, customerId, null));
|
||||||
}
|
}
|
||||||
if (pageData.hasNext()) {
|
if (pageData.hasNext()) {
|
||||||
pageLink = pageLink.nextPageLink();
|
pageLink = pageLink.nextPageLink();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (pageData != null && pageData.hasNext());
|
} while (pageData != null && pageData.hasNext());
|
||||||
break;
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
case DELETED:
|
case DELETED:
|
||||||
EdgeId edgeId = new EdgeId(new UUID(edgeNotificationMsg.getEdgeIdMSB(), edgeNotificationMsg.getEdgeIdLSB()));
|
EdgeId edgeId = new EdgeId(new UUID(edgeNotificationMsg.getEdgeIdMSB(), edgeNotificationMsg.getEdgeIdLSB()));
|
||||||
saveEdgeEvent(tenantId, edgeId, type, actionType, customerId, null);
|
return saveEdgeEvent(tenantId, edgeId, type, actionType, customerId, null);
|
||||||
break;
|
default:
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -84,7 +84,7 @@ public class DeviceEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
if (deviceAlreadyExistsForThisEdge) {
|
if (deviceAlreadyExistsForThisEdge) {
|
||||||
log.info("[{}] Device with name '{}' already exists on the cloud, and related to this edge [{}]. " +
|
log.info("[{}] Device with name '{}' already exists on the cloud, and related to this edge [{}]. " +
|
||||||
"deviceUpdateMsg [{}], Updating device", tenantId, deviceName, edge.getId(), deviceUpdateMsg);
|
"deviceUpdateMsg [{}], Updating device", tenantId, deviceName, edge.getId(), deviceUpdateMsg);
|
||||||
updateDevice(tenantId, edge, deviceUpdateMsg);
|
return updateDevice(tenantId, edge, deviceUpdateMsg);
|
||||||
} else {
|
} else {
|
||||||
log.info("[{}] Device with name '{}' already exists on the cloud, but not related to this edge [{}]. deviceUpdateMsg [{}]." +
|
log.info("[{}] Device with name '{}' already exists on the cloud, but not related to this edge [{}]. deviceUpdateMsg [{}]." +
|
||||||
"Creating a new device with random prefix and relate to this edge", tenantId, deviceName, edge.getId(), deviceUpdateMsg);
|
"Creating a new device with random prefix and relate to this edge", tenantId, deviceName, edge.getId(), deviceUpdateMsg);
|
||||||
@ -99,8 +99,10 @@ public class DeviceEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
}
|
}
|
||||||
ObjectNode body = mapper.createObjectNode();
|
ObjectNode body = mapper.createObjectNode();
|
||||||
body.put("conflictName", deviceName);
|
body.put("conflictName", deviceName);
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.ENTITY_MERGE_REQUEST, newDevice.getId(), body);
|
ListenableFuture<Void> input = saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.ENTITY_MERGE_REQUEST, newDevice.getId(), body);
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.CREDENTIALS_REQUEST, newDevice.getId(), null);
|
return Futures.transformAsync(input, unused ->
|
||||||
|
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.CREDENTIALS_REQUEST, newDevice.getId(), null),
|
||||||
|
dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
log.info("[{}] Creating new device and replacing device entity on the edge [{}]", tenantId, deviceUpdateMsg);
|
log.info("[{}] Creating new device and replacing device entity on the edge [{}]", tenantId, deviceUpdateMsg);
|
||||||
@ -111,24 +113,22 @@ public class DeviceEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
log.error(errMsg, e);
|
log.error(errMsg, e);
|
||||||
return Futures.immediateFuture(null);
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.CREDENTIALS_REQUEST, device.getId(), null);
|
return saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.CREDENTIALS_REQUEST, device.getId(), null);
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case ENTITY_UPDATED_RPC_MESSAGE:
|
case ENTITY_UPDATED_RPC_MESSAGE:
|
||||||
updateDevice(tenantId, edge, deviceUpdateMsg);
|
return updateDevice(tenantId, edge, deviceUpdateMsg);
|
||||||
break;
|
|
||||||
case ENTITY_DELETED_RPC_MESSAGE:
|
case ENTITY_DELETED_RPC_MESSAGE:
|
||||||
DeviceId deviceId = new DeviceId(new UUID(deviceUpdateMsg.getIdMSB(), deviceUpdateMsg.getIdLSB()));
|
DeviceId deviceId = new DeviceId(new UUID(deviceUpdateMsg.getIdMSB(), deviceUpdateMsg.getIdLSB()));
|
||||||
Device deviceToDelete = deviceService.findDeviceById(tenantId, deviceId);
|
Device deviceToDelete = deviceService.findDeviceById(tenantId, deviceId);
|
||||||
if (deviceToDelete != null) {
|
if (deviceToDelete != null) {
|
||||||
deviceService.unassignDeviceFromEdge(tenantId, deviceId, edge.getId());
|
deviceService.unassignDeviceFromEdge(tenantId, deviceId, edge.getId());
|
||||||
}
|
}
|
||||||
break;
|
return Futures.immediateFuture(null);
|
||||||
case UNRECOGNIZED:
|
case UNRECOGNIZED:
|
||||||
|
default:
|
||||||
log.error("Unsupported msg type {}", deviceUpdateMsg.getMsgType());
|
log.error("Unsupported msg type {}", deviceUpdateMsg.getMsgType());
|
||||||
return Futures.immediateFailedFuture(new RuntimeException("Unsupported msg type " + deviceUpdateMsg.getMsgType()));
|
return Futures.immediateFailedFuture(new RuntimeException("Unsupported msg type " + deviceUpdateMsg.getMsgType()));
|
||||||
}
|
}
|
||||||
return Futures.immediateFuture(null);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean isDeviceAlreadyExistsOnCloudForThisEdge(TenantId tenantId, Edge edge, Device device) {
|
private boolean isDeviceAlreadyExistsOnCloudForThisEdge(TenantId tenantId, Edge edge, Device device) {
|
||||||
@ -174,7 +174,7 @@ public class DeviceEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void updateDevice(TenantId tenantId, Edge edge, DeviceUpdateMsg deviceUpdateMsg) {
|
private ListenableFuture<Void> updateDevice(TenantId tenantId, Edge edge, DeviceUpdateMsg deviceUpdateMsg) {
|
||||||
DeviceId deviceId = new DeviceId(new UUID(deviceUpdateMsg.getIdMSB(), deviceUpdateMsg.getIdLSB()));
|
DeviceId deviceId = new DeviceId(new UUID(deviceUpdateMsg.getIdMSB(), deviceUpdateMsg.getIdLSB()));
|
||||||
Device device = deviceService.findDeviceById(tenantId, deviceId);
|
Device device = deviceService.findDeviceById(tenantId, deviceId);
|
||||||
if (device != null) {
|
if (device != null) {
|
||||||
@ -194,9 +194,11 @@ public class DeviceEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
}
|
}
|
||||||
Device savedDevice = deviceService.saveDevice(device);
|
Device savedDevice = deviceService.saveDevice(device);
|
||||||
tbClusterService.onDeviceUpdated(savedDevice, device);
|
tbClusterService.onDeviceUpdated(savedDevice, device);
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.CREDENTIALS_REQUEST, deviceId, null);
|
return saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.CREDENTIALS_REQUEST, deviceId, null);
|
||||||
} else {
|
} else {
|
||||||
log.warn("[{}] can't find device [{}], edge [{}]", tenantId, deviceUpdateMsg, edge.getId());
|
String errMsg = String.format("[%s] can't find device [%s], edge [%s]", tenantId, deviceUpdateMsg, edge.getId());
|
||||||
|
log.warn(errMsg);
|
||||||
|
return Futures.immediateFailedFuture(new RuntimeException(errMsg));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -15,11 +15,9 @@
|
|||||||
*/
|
*/
|
||||||
package org.thingsboard.server.service.edge.rpc.processor;
|
package org.thingsboard.server.service.edge.rpc.processor;
|
||||||
|
|
||||||
import com.google.common.util.concurrent.FutureCallback;
|
|
||||||
import com.google.common.util.concurrent.Futures;
|
import com.google.common.util.concurrent.Futures;
|
||||||
import com.google.common.util.concurrent.ListenableFuture;
|
import com.google.common.util.concurrent.ListenableFuture;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.thingsboard.server.common.data.User;
|
import org.thingsboard.server.common.data.User;
|
||||||
import org.thingsboard.server.common.data.edge.Edge;
|
import org.thingsboard.server.common.data.edge.Edge;
|
||||||
@ -33,6 +31,8 @@ import org.thingsboard.server.common.data.page.PageLink;
|
|||||||
import org.thingsboard.server.gen.transport.TransportProtos;
|
import org.thingsboard.server.gen.transport.TransportProtos;
|
||||||
import org.thingsboard.server.queue.util.TbCoreComponent;
|
import org.thingsboard.server.queue.util.TbCoreComponent;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
@Component
|
@Component
|
||||||
@ -40,7 +40,7 @@ import java.util.UUID;
|
|||||||
@TbCoreComponent
|
@TbCoreComponent
|
||||||
public class EdgeProcessor extends BaseEdgeProcessor {
|
public class EdgeProcessor extends BaseEdgeProcessor {
|
||||||
|
|
||||||
public void processEdgeNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
public ListenableFuture<Void> processEdgeNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
||||||
try {
|
try {
|
||||||
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
||||||
EdgeId edgeId = new EdgeId(new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
EdgeId edgeId = new EdgeId(new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
||||||
@ -49,11 +49,12 @@ public class EdgeProcessor extends BaseEdgeProcessor {
|
|||||||
case ASSIGNED_TO_CUSTOMER:
|
case ASSIGNED_TO_CUSTOMER:
|
||||||
CustomerId customerId = mapper.readValue(edgeNotificationMsg.getBody(), CustomerId.class);
|
CustomerId customerId = mapper.readValue(edgeNotificationMsg.getBody(), CustomerId.class);
|
||||||
edgeFuture = edgeService.findEdgeByIdAsync(tenantId, edgeId);
|
edgeFuture = edgeService.findEdgeByIdAsync(tenantId, edgeId);
|
||||||
Futures.addCallback(edgeFuture, new FutureCallback<Edge>() {
|
return Futures.transformAsync(edgeFuture, edge -> {
|
||||||
@Override
|
if (edge == null || customerId.isNullUid()) {
|
||||||
public void onSuccess(@Nullable Edge edge) {
|
return Futures.immediateFuture(null);
|
||||||
if (edge != null && !customerId.isNullUid()) {
|
}
|
||||||
saveEdgeEvent(edge.getTenantId(), edge.getId(), EdgeEventType.CUSTOMER, EdgeEventActionType.ADDED, customerId, null);
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
|
futures.add(saveEdgeEvent(edge.getTenantId(), edge.getId(), EdgeEventType.CUSTOMER, EdgeEventActionType.ADDED, customerId, null));
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<User> pageData;
|
PageData<User> pageData;
|
||||||
do {
|
do {
|
||||||
@ -61,42 +62,30 @@ public class EdgeProcessor extends BaseEdgeProcessor {
|
|||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
log.trace("[{}] [{}] user(s) are going to be added to edge.", edge.getId(), pageData.getData().size());
|
log.trace("[{}] [{}] user(s) are going to be added to edge.", edge.getId(), pageData.getData().size());
|
||||||
for (User user : pageData.getData()) {
|
for (User user : pageData.getData()) {
|
||||||
saveEdgeEvent(edge.getTenantId(), edge.getId(), EdgeEventType.USER, EdgeEventActionType.ADDED, user.getId(), null);
|
futures.add(saveEdgeEvent(edge.getTenantId(), edge.getId(), EdgeEventType.USER, EdgeEventActionType.ADDED, user.getId(), null));
|
||||||
}
|
}
|
||||||
if (pageData.hasNext()) {
|
if (pageData.hasNext()) {
|
||||||
pageLink = pageLink.nextPageLink();
|
pageLink = pageLink.nextPageLink();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (pageData != null && pageData.hasNext());
|
} while (pageData != null && pageData.hasNext());
|
||||||
}
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
log.error("Can't find edge by id [{}]", edgeNotificationMsg, t);
|
|
||||||
}
|
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
break;
|
|
||||||
case UNASSIGNED_FROM_CUSTOMER:
|
case UNASSIGNED_FROM_CUSTOMER:
|
||||||
CustomerId customerIdToDelete = mapper.readValue(edgeNotificationMsg.getBody(), CustomerId.class);
|
CustomerId customerIdToDelete = mapper.readValue(edgeNotificationMsg.getBody(), CustomerId.class);
|
||||||
edgeFuture = edgeService.findEdgeByIdAsync(tenantId, edgeId);
|
edgeFuture = edgeService.findEdgeByIdAsync(tenantId, edgeId);
|
||||||
Futures.addCallback(edgeFuture, new FutureCallback<Edge>() {
|
return Futures.transformAsync(edgeFuture, edge -> {
|
||||||
@Override
|
if (edge == null || customerIdToDelete.isNullUid()) {
|
||||||
public void onSuccess(@Nullable Edge edge) {
|
return Futures.immediateFuture(null);
|
||||||
if (edge != null && !customerIdToDelete.isNullUid()) {
|
|
||||||
saveEdgeEvent(edge.getTenantId(), edge.getId(), EdgeEventType.CUSTOMER, EdgeEventActionType.DELETED, customerIdToDelete, null);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
log.error("Can't find edge by id [{}]", edgeNotificationMsg, t);
|
|
||||||
}
|
}
|
||||||
|
return saveEdgeEvent(edge.getTenantId(), edge.getId(), EdgeEventType.CUSTOMER, EdgeEventActionType.DELETED, customerIdToDelete, null);
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
break;
|
default:
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("Exception during processing edge event", e);
|
log.error("Exception during processing edge event", e);
|
||||||
|
return Futures.immediateFailedFuture(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -15,11 +15,9 @@
|
|||||||
*/
|
*/
|
||||||
package org.thingsboard.server.service.edge.rpc.processor;
|
package org.thingsboard.server.service.edge.rpc.processor;
|
||||||
|
|
||||||
import com.google.common.util.concurrent.FutureCallback;
|
|
||||||
import com.google.common.util.concurrent.Futures;
|
import com.google.common.util.concurrent.Futures;
|
||||||
import com.google.common.util.concurrent.ListenableFuture;
|
import com.google.common.util.concurrent.ListenableFuture;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.thingsboard.server.common.data.Device;
|
import org.thingsboard.server.common.data.Device;
|
||||||
import org.thingsboard.server.common.data.EdgeUtils;
|
import org.thingsboard.server.common.data.EdgeUtils;
|
||||||
@ -45,6 +43,7 @@ import org.thingsboard.server.gen.edge.v1.UpdateMsgType;
|
|||||||
import org.thingsboard.server.gen.transport.TransportProtos;
|
import org.thingsboard.server.gen.transport.TransportProtos;
|
||||||
import org.thingsboard.server.queue.util.TbCoreComponent;
|
import org.thingsboard.server.queue.util.TbCoreComponent;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
@ -89,25 +88,49 @@ public class EntityEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
return downlinkMsg;
|
return downlinkMsg;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processEntityNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
public ListenableFuture<Void> processEntityNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
||||||
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
||||||
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
||||||
EntityId entityId = EntityIdFactory.getByEdgeEventTypeAndUuid(type,
|
EntityId entityId = EntityIdFactory.getByEdgeEventTypeAndUuid(type,
|
||||||
new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
||||||
EdgeId edgeId = null;
|
EdgeId edgeId = safeGetEdgeId(edgeNotificationMsg);
|
||||||
if (edgeNotificationMsg.getEdgeIdMSB() != 0 && edgeNotificationMsg.getEdgeIdLSB() != 0) {
|
|
||||||
edgeId = new EdgeId(new UUID(edgeNotificationMsg.getEdgeIdMSB(), edgeNotificationMsg.getEdgeIdLSB()));
|
|
||||||
}
|
|
||||||
switch (actionType) {
|
switch (actionType) {
|
||||||
case ADDED: // used only for USER entity
|
case ADDED: // used only for USER entity
|
||||||
case UPDATED:
|
case UPDATED:
|
||||||
case CREDENTIALS_UPDATED:
|
case CREDENTIALS_UPDATED:
|
||||||
pushNotificationToAllRelatedEdges(tenantId, entityId, type, actionType);
|
return pushNotificationToAllRelatedEdges(tenantId, entityId, type, actionType);
|
||||||
break;
|
|
||||||
case ASSIGNED_TO_CUSTOMER:
|
case ASSIGNED_TO_CUSTOMER:
|
||||||
case UNASSIGNED_FROM_CUSTOMER:
|
case UNASSIGNED_FROM_CUSTOMER:
|
||||||
|
return pushNotificationToAllRelatedCustomerEdges(tenantId, edgeNotificationMsg, entityId, actionType, type);
|
||||||
|
case DELETED:
|
||||||
|
if (edgeId != null) {
|
||||||
|
return saveEdgeEvent(tenantId, edgeId, type, actionType, entityId, null);
|
||||||
|
} else {
|
||||||
|
return pushNotificationToAllRelatedEdges(tenantId, entityId, type, actionType);
|
||||||
|
}
|
||||||
|
case ASSIGNED_TO_EDGE:
|
||||||
|
case UNASSIGNED_FROM_EDGE:
|
||||||
|
ListenableFuture<Void> future = saveEdgeEvent(tenantId, edgeId, type, actionType, entityId, null);
|
||||||
|
return Futures.transformAsync(future, unused -> {
|
||||||
|
if (type.equals(EdgeEventType.RULE_CHAIN)) {
|
||||||
|
return updateDependentRuleChains(tenantId, new RuleChainId(entityId.getId()), edgeId);
|
||||||
|
} else {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
|
}, dbCallbackExecutorService);
|
||||||
|
default:
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private ListenableFuture<Void> pushNotificationToAllRelatedCustomerEdges(TenantId tenantId,
|
||||||
|
TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg,
|
||||||
|
EntityId entityId,
|
||||||
|
EdgeEventActionType actionType,
|
||||||
|
EdgeEventType type) {
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<EdgeId> pageData;
|
PageData<EdgeId> pageData;
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
do {
|
do {
|
||||||
pageData = edgeService.findRelatedEdgeIdsByEntityId(tenantId, entityId, pageLink);
|
pageData = edgeService.findRelatedEdgeIdsByEntityId(tenantId, entityId, pageLink);
|
||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
@ -115,22 +138,17 @@ public class EntityEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
try {
|
try {
|
||||||
CustomerId customerId = mapper.readValue(edgeNotificationMsg.getBody(), CustomerId.class);
|
CustomerId customerId = mapper.readValue(edgeNotificationMsg.getBody(), CustomerId.class);
|
||||||
ListenableFuture<Edge> future = edgeService.findEdgeByIdAsync(tenantId, relatedEdgeId);
|
ListenableFuture<Edge> future = edgeService.findEdgeByIdAsync(tenantId, relatedEdgeId);
|
||||||
Futures.addCallback(future, new FutureCallback<>() {
|
futures.add(Futures.transformAsync(future, edge -> {
|
||||||
@Override
|
|
||||||
public void onSuccess(@Nullable Edge edge) {
|
|
||||||
if (edge != null && edge.getCustomerId() != null &&
|
if (edge != null && edge.getCustomerId() != null &&
|
||||||
!edge.getCustomerId().isNullUid() && edge.getCustomerId().equals(customerId)) {
|
!edge.getCustomerId().isNullUid() && edge.getCustomerId().equals(customerId)) {
|
||||||
saveEdgeEvent(tenantId, relatedEdgeId, type, actionType, entityId, null);
|
return saveEdgeEvent(tenantId, relatedEdgeId, type, actionType, entityId, null);
|
||||||
|
} else {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
}
|
}, dbCallbackExecutorService));
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
log.error("Failed to find edge by id [{}] {}", edgeNotificationMsg, t);
|
|
||||||
}
|
|
||||||
}, dbCallbackExecutorService);
|
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("Can't parse customer id from entity body [{}]", edgeNotificationMsg, e);
|
log.error("Can't parse customer id from entity body [{}]", edgeNotificationMsg, e);
|
||||||
|
return Futures.immediateFailedFuture(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (pageData.hasNext()) {
|
if (pageData.hasNext()) {
|
||||||
@ -138,43 +156,39 @@ public class EntityEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (pageData != null && pageData.hasNext());
|
} while (pageData != null && pageData.hasNext());
|
||||||
break;
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
case DELETED:
|
}
|
||||||
if (edgeId != null) {
|
|
||||||
saveEdgeEvent(tenantId, edgeId, type, actionType, entityId, null);
|
private EdgeId safeGetEdgeId(TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
||||||
|
if (edgeNotificationMsg.getEdgeIdMSB() != 0 && edgeNotificationMsg.getEdgeIdLSB() != 0) {
|
||||||
|
return new EdgeId(new UUID(edgeNotificationMsg.getEdgeIdMSB(), edgeNotificationMsg.getEdgeIdLSB()));
|
||||||
} else {
|
} else {
|
||||||
pushNotificationToAllRelatedEdges(tenantId, entityId, type, actionType);
|
return null;
|
||||||
}
|
|
||||||
break;
|
|
||||||
case ASSIGNED_TO_EDGE:
|
|
||||||
case UNASSIGNED_FROM_EDGE:
|
|
||||||
saveEdgeEvent(tenantId, edgeId, type, actionType, entityId, null);
|
|
||||||
if (type.equals(EdgeEventType.RULE_CHAIN)) {
|
|
||||||
updateDependentRuleChains(tenantId, new RuleChainId(entityId.getId()), edgeId);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void pushNotificationToAllRelatedEdges(TenantId tenantId, EntityId entityId, EdgeEventType type, EdgeEventActionType actionType) {
|
private ListenableFuture<Void> pushNotificationToAllRelatedEdges(TenantId tenantId, EntityId entityId, EdgeEventType type, EdgeEventActionType actionType) {
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<EdgeId> pageData;
|
PageData<EdgeId> pageData;
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
do {
|
do {
|
||||||
pageData = edgeService.findRelatedEdgeIdsByEntityId(tenantId, entityId, pageLink);
|
pageData = edgeService.findRelatedEdgeIdsByEntityId(tenantId, entityId, pageLink);
|
||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
for (EdgeId relatedEdgeId : pageData.getData()) {
|
for (EdgeId relatedEdgeId : pageData.getData()) {
|
||||||
saveEdgeEvent(tenantId, relatedEdgeId, type, actionType, entityId, null);
|
futures.add(saveEdgeEvent(tenantId, relatedEdgeId, type, actionType, entityId, null));
|
||||||
}
|
}
|
||||||
if (pageData.hasNext()) {
|
if (pageData.hasNext()) {
|
||||||
pageLink = pageLink.nextPageLink();
|
pageLink = pageLink.nextPageLink();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (pageData != null && pageData.hasNext());
|
} while (pageData != null && pageData.hasNext());
|
||||||
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateDependentRuleChains(TenantId tenantId, RuleChainId processingRuleChainId, EdgeId edgeId) {
|
private ListenableFuture<Void> updateDependentRuleChains(TenantId tenantId, RuleChainId processingRuleChainId, EdgeId edgeId) {
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<RuleChain> pageData;
|
PageData<RuleChain> pageData;
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
do {
|
do {
|
||||||
pageData = ruleChainService.findRuleChainsByTenantIdAndEdgeId(tenantId, edgeId, pageLink);
|
pageData = ruleChainService.findRuleChainsByTenantIdAndEdgeId(tenantId, edgeId, pageLink);
|
||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
@ -185,12 +199,12 @@ public class EntityEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
if (connectionInfos != null && !connectionInfos.isEmpty()) {
|
if (connectionInfos != null && !connectionInfos.isEmpty()) {
|
||||||
for (RuleChainConnectionInfo connectionInfo : connectionInfos) {
|
for (RuleChainConnectionInfo connectionInfo : connectionInfos) {
|
||||||
if (connectionInfo.getTargetRuleChainId().equals(processingRuleChainId)) {
|
if (connectionInfo.getTargetRuleChainId().equals(processingRuleChainId)) {
|
||||||
saveEdgeEvent(tenantId,
|
futures.add(saveEdgeEvent(tenantId,
|
||||||
edgeId,
|
edgeId,
|
||||||
EdgeEventType.RULE_CHAIN_METADATA,
|
EdgeEventType.RULE_CHAIN_METADATA,
|
||||||
EdgeEventActionType.UPDATED,
|
EdgeEventActionType.UPDATED,
|
||||||
ruleChain.getId(),
|
ruleChain.getId(),
|
||||||
null);
|
null));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -201,9 +215,10 @@ public class EntityEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (pageData != null && pageData.hasNext());
|
} while (pageData != null && pageData.hasNext());
|
||||||
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processEntityNotificationForAllEdges(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
public ListenableFuture<Void> processEntityNotificationForAllEdges(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) {
|
||||||
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
EdgeEventActionType actionType = EdgeEventActionType.valueOf(edgeNotificationMsg.getAction());
|
||||||
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
EdgeEventType type = EdgeEventType.valueOf(edgeNotificationMsg.getType());
|
||||||
EntityId entityId = EntityIdFactory.getByEdgeEventTypeAndUuid(type, new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
EntityId entityId = EntityIdFactory.getByEdgeEventTypeAndUuid(type, new UUID(edgeNotificationMsg.getEntityIdMSB(), edgeNotificationMsg.getEntityIdLSB()));
|
||||||
@ -211,8 +226,9 @@ public class EntityEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
case ADDED:
|
case ADDED:
|
||||||
case UPDATED:
|
case UPDATED:
|
||||||
case DELETED:
|
case DELETED:
|
||||||
processActionForAllEdges(tenantId, type, actionType, entityId);
|
return processActionForAllEdges(tenantId, type, actionType, entityId);
|
||||||
break;
|
default:
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -126,24 +126,29 @@ public class RelationEdgeProcessor extends BaseEdgeProcessor {
|
|||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void processRelationNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) throws JsonProcessingException {
|
public ListenableFuture<Void> processRelationNotification(TenantId tenantId, TransportProtos.EdgeNotificationMsgProto edgeNotificationMsg) throws JsonProcessingException {
|
||||||
EntityRelation relation = mapper.readValue(edgeNotificationMsg.getBody(), EntityRelation.class);
|
EntityRelation relation = mapper.readValue(edgeNotificationMsg.getBody(), EntityRelation.class);
|
||||||
if (!relation.getFrom().getEntityType().equals(EntityType.EDGE) &&
|
if (relation.getFrom().getEntityType().equals(EntityType.EDGE) ||
|
||||||
!relation.getTo().getEntityType().equals(EntityType.EDGE)) {
|
relation.getTo().getEntityType().equals(EntityType.EDGE)) {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
|
|
||||||
Set<EdgeId> uniqueEdgeIds = new HashSet<>();
|
Set<EdgeId> uniqueEdgeIds = new HashSet<>();
|
||||||
uniqueEdgeIds.addAll(findRelatedEdgeIds(tenantId, relation.getTo()));
|
uniqueEdgeIds.addAll(findRelatedEdgeIds(tenantId, relation.getTo()));
|
||||||
uniqueEdgeIds.addAll(findRelatedEdgeIds(tenantId, relation.getFrom()));
|
uniqueEdgeIds.addAll(findRelatedEdgeIds(tenantId, relation.getFrom()));
|
||||||
if (!uniqueEdgeIds.isEmpty()) {
|
if (uniqueEdgeIds.isEmpty()) {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
for (EdgeId edgeId : uniqueEdgeIds) {
|
for (EdgeId edgeId : uniqueEdgeIds) {
|
||||||
saveEdgeEvent(tenantId,
|
futures.add(saveEdgeEvent(tenantId,
|
||||||
edgeId,
|
edgeId,
|
||||||
EdgeEventType.RELATION,
|
EdgeEventType.RELATION,
|
||||||
EdgeEventActionType.valueOf(edgeNotificationMsg.getAction()),
|
EdgeEventActionType.valueOf(edgeNotificationMsg.getAction()),
|
||||||
null,
|
null,
|
||||||
mapper.valueToTree(relation));
|
mapper.valueToTree(relation)));
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
|
|
||||||
private List<EdgeId> findRelatedEdgeIds(TenantId tenantId, EntityId entityId) {
|
private List<EdgeId> findRelatedEdgeIds(TenantId tenantId, EntityId entityId) {
|
||||||
|
|||||||
@ -26,6 +26,7 @@ import lombok.extern.slf4j.Slf4j;
|
|||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
import org.thingsboard.server.cluster.TbClusterService;
|
||||||
import org.thingsboard.server.common.data.Device;
|
import org.thingsboard.server.common.data.Device;
|
||||||
import org.thingsboard.server.common.data.DeviceProfile;
|
import org.thingsboard.server.common.data.DeviceProfile;
|
||||||
import org.thingsboard.server.common.data.EdgeUtils;
|
import org.thingsboard.server.common.data.EdgeUtils;
|
||||||
@ -72,7 +73,6 @@ import org.thingsboard.server.gen.edge.v1.RuleChainMetadataRequestMsg;
|
|||||||
import org.thingsboard.server.gen.edge.v1.UserCredentialsRequestMsg;
|
import org.thingsboard.server.gen.edge.v1.UserCredentialsRequestMsg;
|
||||||
import org.thingsboard.server.gen.edge.v1.WidgetBundleTypesRequestMsg;
|
import org.thingsboard.server.gen.edge.v1.WidgetBundleTypesRequestMsg;
|
||||||
import org.thingsboard.server.service.executors.DbCallbackExecutorService;
|
import org.thingsboard.server.service.executors.DbCallbackExecutorService;
|
||||||
import org.thingsboard.server.cluster.TbClusterService;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
@ -121,14 +121,14 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
@Override
|
@Override
|
||||||
public ListenableFuture<Void> processRuleChainMetadataRequestMsg(TenantId tenantId, Edge edge, RuleChainMetadataRequestMsg ruleChainMetadataRequestMsg) {
|
public ListenableFuture<Void> processRuleChainMetadataRequestMsg(TenantId tenantId, Edge edge, RuleChainMetadataRequestMsg ruleChainMetadataRequestMsg) {
|
||||||
log.trace("[{}] processRuleChainMetadataRequestMsg [{}][{}]", tenantId, edge.getName(), ruleChainMetadataRequestMsg);
|
log.trace("[{}] processRuleChainMetadataRequestMsg [{}][{}]", tenantId, edge.getName(), ruleChainMetadataRequestMsg);
|
||||||
if (ruleChainMetadataRequestMsg.getRuleChainIdMSB() != 0 && ruleChainMetadataRequestMsg.getRuleChainIdLSB() != 0) {
|
if (ruleChainMetadataRequestMsg.getRuleChainIdMSB() == 0 || ruleChainMetadataRequestMsg.getRuleChainIdLSB() == 0) {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
RuleChainId ruleChainId =
|
RuleChainId ruleChainId =
|
||||||
new RuleChainId(new UUID(ruleChainMetadataRequestMsg.getRuleChainIdMSB(), ruleChainMetadataRequestMsg.getRuleChainIdLSB()));
|
new RuleChainId(new UUID(ruleChainMetadataRequestMsg.getRuleChainIdMSB(), ruleChainMetadataRequestMsg.getRuleChainIdLSB()));
|
||||||
saveEdgeEvent(tenantId, edge.getId(),
|
return saveEdgeEvent(tenantId, edge.getId(),
|
||||||
EdgeEventType.RULE_CHAIN_METADATA, EdgeEventActionType.ADDED, ruleChainId, null);
|
EdgeEventType.RULE_CHAIN_METADATA, EdgeEventActionType.ADDED, ruleChainId, null);
|
||||||
}
|
}
|
||||||
return Futures.immediateFuture(null);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ListenableFuture<Void> processAttributesRequestMsg(TenantId tenantId, Edge edge, AttributesRequestMsg attributesRequestMsg) {
|
public ListenableFuture<Void> processAttributesRequestMsg(TenantId tenantId, Edge edge, AttributesRequestMsg attributesRequestMsg) {
|
||||||
@ -137,14 +137,25 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
EntityType.valueOf(attributesRequestMsg.getEntityType()),
|
EntityType.valueOf(attributesRequestMsg.getEntityType()),
|
||||||
new UUID(attributesRequestMsg.getEntityIdMSB(), attributesRequestMsg.getEntityIdLSB()));
|
new UUID(attributesRequestMsg.getEntityIdMSB(), attributesRequestMsg.getEntityIdLSB()));
|
||||||
final EdgeEventType type = EdgeUtils.getEdgeEventTypeByEntityType(entityId.getEntityType());
|
final EdgeEventType type = EdgeUtils.getEdgeEventTypeByEntityType(entityId.getEntityType());
|
||||||
if (type != null) {
|
if (type == null) {
|
||||||
|
log.warn("[{}] Type doesn't supported {}", tenantId, entityId.getEntityType());
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
SettableFuture<Void> futureToSet = SettableFuture.create();
|
SettableFuture<Void> futureToSet = SettableFuture.create();
|
||||||
String scope = attributesRequestMsg.getScope();
|
String scope = attributesRequestMsg.getScope();
|
||||||
ListenableFuture<List<AttributeKvEntry>> findAttrFuture = attributesService.findAll(tenantId, entityId, scope);
|
ListenableFuture<List<AttributeKvEntry>> findAttrFuture = attributesService.findAll(tenantId, entityId, scope);
|
||||||
Futures.addCallback(findAttrFuture, new FutureCallback<List<AttributeKvEntry>>() {
|
Futures.addCallback(findAttrFuture, new FutureCallback<>() {
|
||||||
@Override
|
@Override
|
||||||
public void onSuccess(@Nullable List<AttributeKvEntry> ssAttributes) {
|
public void onSuccess(@Nullable List<AttributeKvEntry> ssAttributes) {
|
||||||
if (ssAttributes != null && !ssAttributes.isEmpty()) {
|
if (ssAttributes == null || ssAttributes.isEmpty()) {
|
||||||
|
log.trace("[{}][{}] No attributes found for entity {} [{}]", tenantId,
|
||||||
|
edge.getName(),
|
||||||
|
entityId.getEntityType(),
|
||||||
|
entityId.getId());
|
||||||
|
futureToSet.set(null);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
Map<String, Object> entityData = new HashMap<>();
|
Map<String, Object> entityData = new HashMap<>();
|
||||||
ObjectNode attributes = mapper.createObjectNode();
|
ObjectNode attributes = mapper.createObjectNode();
|
||||||
@ -163,37 +174,35 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
entityData.put("scope", scope);
|
entityData.put("scope", scope);
|
||||||
JsonNode body = mapper.valueToTree(entityData);
|
JsonNode body = mapper.valueToTree(entityData);
|
||||||
log.debug("Sending attributes data msg, entityId [{}], attributes [{}]", entityId, body);
|
log.debug("Sending attributes data msg, entityId [{}], attributes [{}]", entityId, body);
|
||||||
saveEdgeEvent(tenantId,
|
ListenableFuture<Void> future = saveEdgeEvent(tenantId, edge.getId(), type, EdgeEventActionType.ATTRIBUTES_UPDATED, entityId, body);
|
||||||
edge.getId(),
|
Futures.addCallback(future, new FutureCallback<>() {
|
||||||
type,
|
@Override
|
||||||
EdgeEventActionType.ATTRIBUTES_UPDATED,
|
public void onSuccess(@Nullable Void unused) {
|
||||||
entityId,
|
|
||||||
body);
|
|
||||||
} catch (Exception e) {
|
|
||||||
log.error("[{}] Failed to save attribute updates to the edge", edge.getName(), e);
|
|
||||||
futureToSet.setException(new RuntimeException("[" + edge.getName() + "] Failed to send attribute updates to the edge", e));
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
log.trace("[{}][{}] No attributes found for entity {} [{}]", tenantId,
|
|
||||||
edge.getName(),
|
|
||||||
entityId.getEntityType(),
|
|
||||||
entityId.getId());
|
|
||||||
}
|
|
||||||
futureToSet.set(null);
|
futureToSet.set(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onFailure(Throwable throwable) {
|
||||||
|
String errMsg = String.format("[%s] Failed to save edge event [%s]", edge.getId(), attributesRequestMsg);
|
||||||
|
log.error(errMsg, throwable);
|
||||||
|
futureToSet.setException(new RuntimeException(errMsg, throwable));
|
||||||
|
}
|
||||||
|
}, dbCallbackExecutorService);
|
||||||
|
} catch (Exception e) {
|
||||||
|
String errMsg = String.format("[%s] Failed to save attribute updates to the edge [%s]", edge.getId(), attributesRequestMsg);
|
||||||
|
log.error(errMsg, e);
|
||||||
|
futureToSet.setException(new RuntimeException(errMsg, e));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onFailure(Throwable t) {
|
public void onFailure(Throwable t) {
|
||||||
log.error("Can't find attributes [{}]", attributesRequestMsg, t);
|
String errMsg = String.format("[%s] Can't find attributes [%s]", edge.getId(), attributesRequestMsg);
|
||||||
futureToSet.setException(t);
|
log.error(errMsg, t);
|
||||||
|
futureToSet.setException(new RuntimeException(errMsg, t));
|
||||||
}
|
}
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
return futureToSet;
|
return futureToSet;
|
||||||
} else {
|
|
||||||
log.warn("[{}] Type doesn't supported {}", tenantId, entityId.getEntityType());
|
|
||||||
return Futures.immediateFuture(null);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -208,33 +217,49 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
futures.add(findRelationByQuery(tenantId, edge, entityId, EntitySearchDirection.TO));
|
futures.add(findRelationByQuery(tenantId, edge, entityId, EntitySearchDirection.TO));
|
||||||
ListenableFuture<List<List<EntityRelation>>> relationsListFuture = Futures.allAsList(futures);
|
ListenableFuture<List<List<EntityRelation>>> relationsListFuture = Futures.allAsList(futures);
|
||||||
SettableFuture<Void> futureToSet = SettableFuture.create();
|
SettableFuture<Void> futureToSet = SettableFuture.create();
|
||||||
Futures.addCallback(relationsListFuture, new FutureCallback<List<List<EntityRelation>>>() {
|
Futures.addCallback(relationsListFuture, new FutureCallback<>() {
|
||||||
@Override
|
@Override
|
||||||
public void onSuccess(@Nullable List<List<EntityRelation>> relationsList) {
|
public void onSuccess(@Nullable List<List<EntityRelation>> relationsList) {
|
||||||
try {
|
try {
|
||||||
if (relationsList != null && !relationsList.isEmpty()) {
|
if (relationsList != null && !relationsList.isEmpty()) {
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
for (List<EntityRelation> entityRelations : relationsList) {
|
for (List<EntityRelation> entityRelations : relationsList) {
|
||||||
log.trace("[{}] [{}] [{}] relation(s) are going to be pushed to edge.", edge.getId(), entityId, entityRelations.size());
|
log.trace("[{}] [{}] [{}] relation(s) are going to be pushed to edge.", edge.getId(), entityId, entityRelations.size());
|
||||||
for (EntityRelation relation : entityRelations) {
|
for (EntityRelation relation : entityRelations) {
|
||||||
try {
|
try {
|
||||||
if (!relation.getFrom().getEntityType().equals(EntityType.EDGE) &&
|
if (!relation.getFrom().getEntityType().equals(EntityType.EDGE) &&
|
||||||
!relation.getTo().getEntityType().equals(EntityType.EDGE)) {
|
!relation.getTo().getEntityType().equals(EntityType.EDGE)) {
|
||||||
saveEdgeEvent(tenantId,
|
futures.add(saveEdgeEvent(tenantId,
|
||||||
edge.getId(),
|
edge.getId(),
|
||||||
EdgeEventType.RELATION,
|
EdgeEventType.RELATION,
|
||||||
EdgeEventActionType.ADDED,
|
EdgeEventActionType.ADDED,
|
||||||
null,
|
null,
|
||||||
mapper.valueToTree(relation));
|
mapper.valueToTree(relation)));
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("Exception during loading relation [{}] to edge on sync!", relation, e);
|
String errMsg = String.format("[%s] Exception during loading relation [%s] to edge on sync!", edge.getId(), relation);
|
||||||
futureToSet.setException(e);
|
log.error(errMsg, e);
|
||||||
|
futureToSet.setException(new RuntimeException(errMsg, e));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
Futures.addCallback(Futures.allAsList(futures), new FutureCallback<>() {
|
||||||
|
@Override
|
||||||
|
public void onSuccess(@Nullable List<Void> voids) {
|
||||||
futureToSet.set(null);
|
futureToSet.set(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onFailure(Throwable throwable) {
|
||||||
|
String errMsg = String.format("[%s] Exception during saving edge events [%s]!", edge.getId(), relationRequestMsg);
|
||||||
|
log.error(errMsg, throwable);
|
||||||
|
futureToSet.setException(new RuntimeException(errMsg, throwable));
|
||||||
|
}
|
||||||
|
}, dbCallbackExecutorService);
|
||||||
|
} else {
|
||||||
|
futureToSet.set(null);
|
||||||
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("Exception during loading relation(s) to edge on sync!", e);
|
log.error("Exception during loading relation(s) to edge on sync!", e);
|
||||||
futureToSet.setException(e);
|
futureToSet.setException(e);
|
||||||
@ -243,8 +268,9 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onFailure(Throwable t) {
|
public void onFailure(Throwable t) {
|
||||||
log.error("[{}] Can't find relation by query. Entity id [{}]", tenantId, entityId, t);
|
String errMsg = String.format("[%s] Can't find relation by query. Entity id [%s]!", tenantId, entityId);
|
||||||
futureToSet.setException(t);
|
log.error(errMsg, t);
|
||||||
|
futureToSet.setException(new RuntimeException(errMsg, t));
|
||||||
}
|
}
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
return futureToSet;
|
return futureToSet;
|
||||||
@ -260,40 +286,42 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
@Override
|
@Override
|
||||||
public ListenableFuture<Void> processDeviceCredentialsRequestMsg(TenantId tenantId, Edge edge, DeviceCredentialsRequestMsg deviceCredentialsRequestMsg) {
|
public ListenableFuture<Void> processDeviceCredentialsRequestMsg(TenantId tenantId, Edge edge, DeviceCredentialsRequestMsg deviceCredentialsRequestMsg) {
|
||||||
log.trace("[{}] processDeviceCredentialsRequestMsg [{}][{}]", tenantId, edge.getName(), deviceCredentialsRequestMsg);
|
log.trace("[{}] processDeviceCredentialsRequestMsg [{}][{}]", tenantId, edge.getName(), deviceCredentialsRequestMsg);
|
||||||
if (deviceCredentialsRequestMsg.getDeviceIdMSB() != 0 && deviceCredentialsRequestMsg.getDeviceIdLSB() != 0) {
|
if (deviceCredentialsRequestMsg.getDeviceIdMSB() == 0 || deviceCredentialsRequestMsg.getDeviceIdLSB() == 0) {
|
||||||
DeviceId deviceId = new DeviceId(new UUID(deviceCredentialsRequestMsg.getDeviceIdMSB(), deviceCredentialsRequestMsg.getDeviceIdLSB()));
|
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE,
|
|
||||||
EdgeEventActionType.CREDENTIALS_UPDATED, deviceId, null);
|
|
||||||
}
|
|
||||||
return Futures.immediateFuture(null);
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
|
DeviceId deviceId = new DeviceId(new UUID(deviceCredentialsRequestMsg.getDeviceIdMSB(), deviceCredentialsRequestMsg.getDeviceIdLSB()));
|
||||||
|
return saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE,
|
||||||
|
EdgeEventActionType.CREDENTIALS_UPDATED, deviceId, null);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ListenableFuture<Void> processUserCredentialsRequestMsg(TenantId tenantId, Edge edge, UserCredentialsRequestMsg userCredentialsRequestMsg) {
|
public ListenableFuture<Void> processUserCredentialsRequestMsg(TenantId tenantId, Edge edge, UserCredentialsRequestMsg userCredentialsRequestMsg) {
|
||||||
log.trace("[{}] processUserCredentialsRequestMsg [{}][{}]", tenantId, edge.getName(), userCredentialsRequestMsg);
|
log.trace("[{}] processUserCredentialsRequestMsg [{}][{}]", tenantId, edge.getName(), userCredentialsRequestMsg);
|
||||||
if (userCredentialsRequestMsg.getUserIdMSB() != 0 && userCredentialsRequestMsg.getUserIdLSB() != 0) {
|
if (userCredentialsRequestMsg.getUserIdMSB() == 0 || userCredentialsRequestMsg.getUserIdLSB() == 0) {
|
||||||
UserId userId = new UserId(new UUID(userCredentialsRequestMsg.getUserIdMSB(), userCredentialsRequestMsg.getUserIdLSB()));
|
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.USER,
|
|
||||||
EdgeEventActionType.CREDENTIALS_UPDATED, userId, null);
|
|
||||||
}
|
|
||||||
return Futures.immediateFuture(null);
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
|
UserId userId = new UserId(new UUID(userCredentialsRequestMsg.getUserIdMSB(), userCredentialsRequestMsg.getUserIdLSB()));
|
||||||
|
return saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.USER,
|
||||||
|
EdgeEventActionType.CREDENTIALS_UPDATED, userId, null);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ListenableFuture<Void> processDeviceProfileDevicesRequestMsg(TenantId tenantId, Edge edge, DeviceProfileDevicesRequestMsg deviceProfileDevicesRequestMsg) {
|
public ListenableFuture<Void> processDeviceProfileDevicesRequestMsg(TenantId tenantId, Edge edge, DeviceProfileDevicesRequestMsg deviceProfileDevicesRequestMsg) {
|
||||||
log.trace("[{}] processDeviceProfileDevicesRequestMsg [{}][{}]", tenantId, edge.getName(), deviceProfileDevicesRequestMsg);
|
log.trace("[{}] processDeviceProfileDevicesRequestMsg [{}][{}]", tenantId, edge.getName(), deviceProfileDevicesRequestMsg);
|
||||||
if (deviceProfileDevicesRequestMsg.getDeviceProfileIdMSB() != 0 && deviceProfileDevicesRequestMsg.getDeviceProfileIdLSB() != 0) {
|
if (deviceProfileDevicesRequestMsg.getDeviceProfileIdMSB() == 0 || deviceProfileDevicesRequestMsg.getDeviceProfileIdLSB() == 0) {
|
||||||
DeviceProfileId deviceProfileId = new DeviceProfileId(new UUID(deviceProfileDevicesRequestMsg.getDeviceProfileIdMSB(), deviceProfileDevicesRequestMsg.getDeviceProfileIdLSB()));
|
|
||||||
DeviceProfile deviceProfileById = deviceProfileService.findDeviceProfileById(tenantId, deviceProfileId);
|
|
||||||
if (deviceProfileById != null) {
|
|
||||||
syncDevices(tenantId, edge, deviceProfileById.getName());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return Futures.immediateFuture(null);
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
|
DeviceProfileId deviceProfileId = new DeviceProfileId(new UUID(deviceProfileDevicesRequestMsg.getDeviceProfileIdMSB(), deviceProfileDevicesRequestMsg.getDeviceProfileIdLSB()));
|
||||||
|
DeviceProfile deviceProfileById = deviceProfileService.findDeviceProfileById(tenantId, deviceProfileId);
|
||||||
|
if (deviceProfileById == null) {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
|
}
|
||||||
|
return syncDevices(tenantId, edge, deviceProfileById.getName());
|
||||||
|
}
|
||||||
|
|
||||||
private void syncDevices(TenantId tenantId, Edge edge, String deviceType) {
|
private ListenableFuture<Void> syncDevices(TenantId tenantId, Edge edge, String deviceType) {
|
||||||
log.trace("[{}] syncDevices [{}][{}]", tenantId, edge.getName(), deviceType);
|
log.trace("[{}] syncDevices [{}][{}]", tenantId, edge.getName(), deviceType);
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
try {
|
try {
|
||||||
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
PageLink pageLink = new PageLink(DEFAULT_PAGE_SIZE);
|
||||||
PageData<Device> pageData;
|
PageData<Device> pageData;
|
||||||
@ -302,7 +330,7 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
if (pageData != null && pageData.getData() != null && !pageData.getData().isEmpty()) {
|
||||||
log.trace("[{}] [{}] device(s) are going to be pushed to edge.", edge.getId(), pageData.getData().size());
|
log.trace("[{}] [{}] device(s) are going to be pushed to edge.", edge.getId(), pageData.getData().size());
|
||||||
for (Device device : pageData.getData()) {
|
for (Device device : pageData.getData()) {
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.ADDED, device.getId(), null);
|
futures.add(saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.DEVICE, EdgeEventActionType.ADDED, device.getId(), null));
|
||||||
}
|
}
|
||||||
if (pageData.hasNext()) {
|
if (pageData.hasNext()) {
|
||||||
pageLink = pageLink.nextPageLink();
|
pageLink = pageLink.nextPageLink();
|
||||||
@ -312,25 +340,26 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("Exception during loading edge device(s) on sync!", e);
|
log.error("Exception during loading edge device(s) on sync!", e);
|
||||||
}
|
}
|
||||||
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ListenableFuture<Void> processWidgetBundleTypesRequestMsg(TenantId tenantId, Edge edge,
|
public ListenableFuture<Void> processWidgetBundleTypesRequestMsg(TenantId tenantId, Edge edge,
|
||||||
WidgetBundleTypesRequestMsg widgetBundleTypesRequestMsg) {
|
WidgetBundleTypesRequestMsg widgetBundleTypesRequestMsg) {
|
||||||
log.trace("[{}] processWidgetBundleTypesRequestMsg [{}][{}]", tenantId, edge.getName(), widgetBundleTypesRequestMsg);
|
log.trace("[{}] processWidgetBundleTypesRequestMsg [{}][{}]", tenantId, edge.getName(), widgetBundleTypesRequestMsg);
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
if (widgetBundleTypesRequestMsg.getWidgetBundleIdMSB() != 0 && widgetBundleTypesRequestMsg.getWidgetBundleIdLSB() != 0) {
|
if (widgetBundleTypesRequestMsg.getWidgetBundleIdMSB() != 0 && widgetBundleTypesRequestMsg.getWidgetBundleIdLSB() != 0) {
|
||||||
WidgetsBundleId widgetsBundleId = new WidgetsBundleId(new UUID(widgetBundleTypesRequestMsg.getWidgetBundleIdMSB(), widgetBundleTypesRequestMsg.getWidgetBundleIdLSB()));
|
WidgetsBundleId widgetsBundleId = new WidgetsBundleId(new UUID(widgetBundleTypesRequestMsg.getWidgetBundleIdMSB(), widgetBundleTypesRequestMsg.getWidgetBundleIdLSB()));
|
||||||
WidgetsBundle widgetsBundleById = widgetsBundleService.findWidgetsBundleById(tenantId, widgetsBundleId);
|
WidgetsBundle widgetsBundleById = widgetsBundleService.findWidgetsBundleById(tenantId, widgetsBundleId);
|
||||||
if (widgetsBundleById != null) {
|
if (widgetsBundleById != null) {
|
||||||
List<WidgetType> widgetTypesToPush =
|
List<WidgetType> widgetTypesToPush =
|
||||||
widgetTypeService.findWidgetTypesByTenantIdAndBundleAlias(widgetsBundleById.getTenantId(), widgetsBundleById.getAlias());
|
widgetTypeService.findWidgetTypesByTenantIdAndBundleAlias(widgetsBundleById.getTenantId(), widgetsBundleById.getAlias());
|
||||||
|
|
||||||
for (WidgetType widgetType : widgetTypesToPush) {
|
for (WidgetType widgetType : widgetTypesToPush) {
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.WIDGET_TYPE, EdgeEventActionType.ADDED, widgetType.getId(), null);
|
futures.add(saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.WIDGET_TYPE, EdgeEventActionType.ADDED, widgetType.getId(), null));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return Futures.immediateFuture(null);
|
return Futures.transform(Futures.allAsList(futures), voids -> null, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -343,46 +372,35 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
Futures.addCallback(entityViewService.findEntityViewsByTenantIdAndEntityIdAsync(tenantId, entityId), new FutureCallback<>() {
|
Futures.addCallback(entityViewService.findEntityViewsByTenantIdAndEntityIdAsync(tenantId, entityId), new FutureCallback<>() {
|
||||||
@Override
|
@Override
|
||||||
public void onSuccess(@Nullable List<EntityView> entityViews) {
|
public void onSuccess(@Nullable List<EntityView> entityViews) {
|
||||||
try {
|
if (entityViews == null || entityViews.isEmpty()) {
|
||||||
if (entityViews != null && !entityViews.isEmpty()) {
|
futureToSet.set(null);
|
||||||
List<ListenableFuture<Boolean>> futures = new ArrayList<>();
|
return;
|
||||||
|
}
|
||||||
|
List<ListenableFuture<Void>> futures = new ArrayList<>();
|
||||||
for (EntityView entityView : entityViews) {
|
for (EntityView entityView : entityViews) {
|
||||||
ListenableFuture<Boolean> future = relationService.checkRelation(tenantId, edge.getId(), entityView.getId(),
|
ListenableFuture<Boolean> future = relationService.checkRelation(tenantId, edge.getId(), entityView.getId(),
|
||||||
EntityRelation.CONTAINS_TYPE, RelationTypeGroup.EDGE);
|
EntityRelation.CONTAINS_TYPE, RelationTypeGroup.EDGE);
|
||||||
futures.add(future);
|
futures.add(Futures.transformAsync(future, result -> {
|
||||||
Futures.addCallback(future, new FutureCallback<>() {
|
|
||||||
@Override
|
|
||||||
public void onSuccess(@Nullable Boolean result) {
|
|
||||||
if (Boolean.TRUE.equals(result)) {
|
if (Boolean.TRUE.equals(result)) {
|
||||||
saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.ENTITY_VIEW,
|
return saveEdgeEvent(tenantId, edge.getId(), EdgeEventType.ENTITY_VIEW,
|
||||||
EdgeEventActionType.ADDED, entityView.getId(), null);
|
EdgeEventActionType.ADDED, entityView.getId(), null);
|
||||||
|
} else {
|
||||||
|
return Futures.immediateFuture(null);
|
||||||
}
|
}
|
||||||
}
|
}, dbCallbackExecutorService));
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
// Do nothing - error handles in allAsList
|
|
||||||
}
|
|
||||||
}, dbCallbackExecutorService);
|
|
||||||
}
|
}
|
||||||
Futures.addCallback(Futures.allAsList(futures), new FutureCallback<>() {
|
Futures.addCallback(Futures.allAsList(futures), new FutureCallback<>() {
|
||||||
@Override
|
@Override
|
||||||
public void onSuccess(@Nullable List<Boolean> result) {
|
public void onSuccess(@Nullable List<Void> result) {
|
||||||
futureToSet.set(null);
|
futureToSet.set(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onFailure(Throwable t) {
|
public void onFailure(Throwable t) {
|
||||||
log.error("Exception during loading relation [{}] to edge on sync!", t, t);
|
log.error("Exception during loading relation to edge on sync!", t);
|
||||||
futureToSet.setException(t);
|
futureToSet.setException(t);
|
||||||
}
|
}
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
} else {
|
|
||||||
futureToSet.set(null);
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
log.error("Exception during loading relation(s) to edge on sync!", e);
|
|
||||||
futureToSet.setException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -394,7 +412,7 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
return futureToSet;
|
return futureToSet;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void saveEdgeEvent(TenantId tenantId,
|
private ListenableFuture<Void> saveEdgeEvent(TenantId tenantId,
|
||||||
EdgeId edgeId,
|
EdgeId edgeId,
|
||||||
EdgeEventType type,
|
EdgeEventType type,
|
||||||
EdgeEventActionType action,
|
EdgeEventActionType action,
|
||||||
@ -405,17 +423,9 @@ public class DefaultEdgeRequestsService implements EdgeRequestsService {
|
|||||||
|
|
||||||
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, type, action, entityId, body);
|
EdgeEvent edgeEvent = EdgeUtils.constructEdgeEvent(tenantId, edgeId, type, action, entityId, body);
|
||||||
|
|
||||||
Futures.addCallback(edgeEventService.saveAsync(edgeEvent), new FutureCallback<>() {
|
return Futures.transform(edgeEventService.saveAsync(edgeEvent), unused -> {
|
||||||
@Override
|
|
||||||
public void onSuccess(@Nullable Void unused) {
|
|
||||||
tbClusterService.onEdgeEventUpdate(tenantId, edgeId);
|
tbClusterService.onEdgeEventUpdate(tenantId, edgeId);
|
||||||
}
|
return null;
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onFailure(Throwable t) {
|
|
||||||
String errMsg = String.format("Failed to save edge event. edge event [%s]", edgeEvent);
|
|
||||||
log.warn(errMsg, t);
|
|
||||||
}
|
|
||||||
}, dbCallbackExecutorService);
|
}, dbCallbackExecutorService);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user