diff --git a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/deduplication/TbMsgDeduplicationNode.java b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/deduplication/TbMsgDeduplicationNode.java
index defc3fed0a..043cc7793f 100644
--- a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/deduplication/TbMsgDeduplicationNode.java
+++ b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/deduplication/TbMsgDeduplicationNode.java
@@ -49,10 +49,10 @@ import java.util.concurrent.TimeUnit;
configClazz = TbMsgDeduplicationNodeConfiguration.class,
nodeDescription = "Deduplicate messages within the same originator entity for a configurable period " +
"based on a specified deduplication strategy.",
- nodeDetails = "Deduplication strategy:
- FIRST - return first message that arrived during deduplication period.
" +
+ nodeDetails = "Deduplication strategies: - FIRST - return first message that arrived during deduplication period.
" +
"- LAST - return last message that arrived during deduplication period.
" +
"- ALL - return all messages as a single JSON array message. " +
- "Where each element represents object with msg and metadata inner properties.
",
+ "Where each element represents object with msg and metadata inner properties.
",
icon = "content_copy",
uiResources = {"static/rulenode/rulenode-core-config.js"},
configDirective = "tbActionNodeMsgDeduplicationConfig"
diff --git a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNode.java b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNode.java
index f16d5bc666..cb7b7d118b 100644
--- a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNode.java
+++ b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNode.java
@@ -16,7 +16,6 @@
package org.thingsboard.rule.engine.mail;
import com.fasterxml.jackson.core.type.TypeReference;
-import com.fasterxml.jackson.databind.JsonNode;
import lombok.extern.slf4j.Slf4j;
import org.thingsboard.common.util.JacksonUtil;
import org.thingsboard.rule.engine.api.RuleNode;
@@ -30,7 +29,6 @@ import org.thingsboard.server.common.data.StringUtils;
import org.thingsboard.server.common.data.msg.TbMsgType;
import org.thingsboard.server.common.data.msg.TbNodeConnectionType;
import org.thingsboard.server.common.data.plugin.ComponentType;
-import org.thingsboard.server.common.data.util.TbPair;
import org.thingsboard.server.common.msg.TbMsg;
import java.util.HashMap;
@@ -42,9 +40,13 @@ import java.util.Map;
name = "to email",
configClazz = TbMsgToEmailNodeConfiguration.class,
nodeDescription = "Transforms message to email message",
- nodeDetails = "Transforms message to email message. All email fields support templatization. " +
- "Supports adding inline base64 images to the mail body from message metadata by checking for the images metadata key " +
- "that should represent a map of entries: contentId to based64 image value.
" +
+ nodeDetails = "Transforms message to email message. All email fields support templatization.
" +
+ "Additionally, supports adding inline base64 images to the mail body from message metadata " +
+ "by extracting them from images metadata key-value.
" +
+ "images key-value should represent a map of entries: cid --> encodedImage.
" +
+ "E.g., cid is a tb.example.png and
" +
+ "encodedImage is a data:image/png;base64,..., " +
+ "then you can use img HTML tag with src: cid:tb.example.png.
" +
"Set SEND_EMAIL output message type if transformation completed successfully.
" +
"Output connections: Success, Failure.",
uiResources = {"static/rulenode/rulenode-core-config.js"},
diff --git a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbChangeOriginatorNode.java b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbChangeOriginatorNode.java
index a26cec57ee..a88a87b400 100644
--- a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbChangeOriginatorNode.java
+++ b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbChangeOriginatorNode.java
@@ -44,10 +44,10 @@ import java.util.NoSuchElementException;
name = "change originator",
configClazz = TbChangeOriginatorNodeConfiguration.class,
nodeDescription = "Change message originator to Tenant/Customer/Related Entity/Alarm Originator/Entity by name pattern.",
- nodeDetails = "Configuration: - Tenant - use current tenant as new originator.
" +
- "- Customer - use customer of incoming message originator as new originator. " +
- "Only for originators with one of the following type: 'User', 'Asset', 'Device' that assigned to customers.
" +
- "- Related Entity - use related entity as new originator. Lookup based on configured relation direction and relation type. " +
+ nodeDetails = "Configuration:
- Customer - use customer of incoming message originator as new originator. " +
+ "Only for assigned to customer originators with one of the following type: 'User', 'Asset', 'Device'.
" +
+ "- Tenant - use current tenant as new originator.
" +
+ "- Related Entity - use related entity as new originator. Lookup based on configured relation type and direction. " +
"If multiple related entities are found, only first entity is used as new originator, other entities are discarded.
" +
"- Alarm Originator - use alarm originator as new originator. Only if incoming message originator is alarm entity.
" +
"- Entity by name pattern - new originator lookup requires selection one of the following entity types: " +
diff --git a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbCopyKeysNode.java b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbCopyKeysNode.java
index 25467caf5a..e346c6a0cd 100644
--- a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbCopyKeysNode.java
+++ b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbCopyKeysNode.java
@@ -81,7 +81,7 @@ public class TbCopyKeysNode extends TbAbstractTransformNodeWithTbMsgSource {
Map metaDataMap = metaDataCopy.getData();
for (Map.Entry entry : metaDataMap.entrySet()) {
String keyData = entry.getKey();
- if (checkKey(keyData)) {
+ if (matches(keyData)) {
msgChanged = true;
msgDataNode.put(keyData, entry.getValue());
}
@@ -93,7 +93,7 @@ public class TbCopyKeysNode extends TbAbstractTransformNodeWithTbMsgSource {
while (iteratorNode.hasNext()) {
Map.Entry entry = iteratorNode.next();
String keyData = entry.getKey();
- if (checkKey(keyData)) {
+ if (matches(keyData)) {
msgChanged = true;
metaDataCopy.putValue(keyData, JacksonUtil.toString(entry.getValue()));
}
@@ -112,7 +112,7 @@ public class TbCopyKeysNode extends TbAbstractTransformNodeWithTbMsgSource {
return "copyFrom";
}
- boolean checkKey(String key) {
+ boolean matches(String key) {
return patternKeys.stream().anyMatch(pattern -> pattern.matcher(key).matches());
}
diff --git a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbDeleteKeysNode.java b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbDeleteKeysNode.java
index 15ed71b0ae..30e182a254 100644
--- a/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbDeleteKeysNode.java
+++ b/rule-engine/rule-engine-components/src/main/java/org/thingsboard/rule/engine/transform/TbDeleteKeysNode.java
@@ -76,7 +76,7 @@ public class TbDeleteKeysNode extends TbAbstractTransformNodeWithTbMsgSource {
case METADATA:
Map metaDataMap = metaDataCopy.getData();
metaDataMap.forEach((keyMetaData, valueMetaData) -> {
- if (checkKey(keyMetaData)) {
+ if (matches(keyMetaData)) {
keysToDelete.add(keyMetaData);
}
});
@@ -89,7 +89,7 @@ public class TbDeleteKeysNode extends TbAbstractTransformNodeWithTbMsgSource {
ObjectNode msgDataObject = (ObjectNode) dataNode;
dataNode.fields().forEachRemaining(entry -> {
String keyData = entry.getKey();
- if (checkKey(keyData)) {
+ if (matches(keyData)) {
keysToDelete.add(keyData);
}
});
@@ -109,7 +109,7 @@ public class TbDeleteKeysNode extends TbAbstractTransformNodeWithTbMsgSource {
return "deleteFrom";
}
- boolean checkKey(String key) {
+ boolean matches(String key) {
return patternKeys.stream().anyMatch(pattern -> pattern.matcher(key).matches());
}
diff --git a/rule-engine/rule-engine-components/src/test/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNodeTest.java b/rule-engine/rule-engine-components/src/test/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNodeTest.java
index 4f1b0488d7..a351022341 100644
--- a/rule-engine/rule-engine-components/src/test/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNodeTest.java
+++ b/rule-engine/rule-engine-components/src/test/java/org/thingsboard/rule/engine/mail/TbMsgToEmailNodeTest.java
@@ -84,16 +84,6 @@ public class TbMsgToEmailNodeTest {
assertThat(config.getBodyTemplate()).isEqualTo("Device ${deviceName} has high temperature $[temperature]");
}
- static Stream MailBodyTypeTestConfig() {
- return Stream.of(
- new MailBodyTypeTestConfig(false, "false", null),
- new MailBodyTypeTestConfig(false, null, null),
- new MailBodyTypeTestConfig(false, DYNAMIC_MAIL_BODY_TYPE, "false"),
- new MailBodyTypeTestConfig(true, DYNAMIC_MAIL_BODY_TYPE, "true"),
- new MailBodyTypeTestConfig(true, "true", null)
- );
- }
-
@ParameterizedTest
@MethodSource("MailBodyTypeTestConfig")
public void givenMailBodyTypeTestConfig_whenOnMsg_thenVerify(MailBodyTypeTestConfig testConfig) throws TbNodeException {
@@ -109,8 +99,8 @@ public class TbMsgToEmailNodeTest {
md.putValue("userEmail", EXPECTED_TO_EMAIL);
md.putValue("deviceType", EXPECTED_DEVICE_TYPE);
md.putValue("deviceName", EXPECTED_DEVICE_NAME);
- if (testConfig.getMdValue() != null) {
- md.putValue("html", testConfig.getMdValue());
+ if (testConfig.getIsHtmlTemplateMdValue() != null) {
+ md.putValue("html", testConfig.getIsHtmlTemplateMdValue());
}
var msgDataStr = "{\"temperature\": " + EXPECTED_TEMPERATURE + "}";
@@ -154,12 +144,22 @@ public class TbMsgToEmailNodeTest {
.build();
}
+ static Stream MailBodyTypeTestConfig() {
+ return Stream.of(
+ new MailBodyTypeTestConfig(false, "false", null),
+ new MailBodyTypeTestConfig(false, null, null),
+ new MailBodyTypeTestConfig(false, DYNAMIC_MAIL_BODY_TYPE, "false"),
+ new MailBodyTypeTestConfig(true, DYNAMIC_MAIL_BODY_TYPE, "true"),
+ new MailBodyTypeTestConfig(true, "true", null)
+ );
+ }
+
@Data
@RequiredArgsConstructor
static class MailBodyTypeTestConfig {
private final boolean expectedHtmlValue;
private final String mailBodyType;
- private final String mdValue;
+ private final String isHtmlTemplateMdValue;
}
}