mirror of
https://github.com/node-red/node-red.git
synced 2025-03-01 10:36:34 +00:00
update UI for SORT node (#1567)
* update UI of SORT node * fix maxKeptMsgsCount of SORT node
This commit is contained in:
committed by
Nick O'Leary
parent
00dcb304c7
commit
6b466d217a
@@ -871,55 +871,55 @@
|
||||
"complete":"After a message with the <code>msg.complete</code> property set",
|
||||
"tip":"This mode assumes this node is either paired with a <i>split</i> node or the received messages will have a properly configured <code>msg.parts</code> property.",
|
||||
"too-many" : "too many pending messages in join node",
|
||||
"merge": {
|
||||
"topics-label":"Merged Topics",
|
||||
"topics":"topics",
|
||||
"merge": {
|
||||
"topics-label":"Merged Topics",
|
||||
"topics":"topics",
|
||||
"topic" : "topic",
|
||||
"on-change":"Send merged message on arrival of a new topic"
|
||||
},
|
||||
},
|
||||
"reduce": {
|
||||
"exp": "Reduce exp",
|
||||
"exp-value": "exp",
|
||||
"init": "Initial value",
|
||||
"right": "Evaluate in reverse order (right to left)",
|
||||
"fixup": "Fixup exp"
|
||||
"exp": "Reduce exp",
|
||||
"exp-value": "exp",
|
||||
"init": "Initial value",
|
||||
"right": "Evaluate in reverse order (right to left)",
|
||||
"fixup": "Fixup exp"
|
||||
},
|
||||
"errors": {
|
||||
"invalid-expr": "Invalid JSONata expression: __error__"
|
||||
}
|
||||
},
|
||||
"sort" : {
|
||||
"key-type" : "Key type",
|
||||
"payload" : "payload or element",
|
||||
"exp" : "expression",
|
||||
"key-exp" : "Key exp.",
|
||||
"order" : "Order",
|
||||
"ascending" : "ascending",
|
||||
"descending" : "descending",
|
||||
"as-number" : "as number",
|
||||
"target" : "Sort",
|
||||
"seq" : "message sequence",
|
||||
"key" : "Key",
|
||||
"elem" : "element value",
|
||||
"order" : "Order",
|
||||
"ascending" : "ascending",
|
||||
"descending" : "descending",
|
||||
"as-number" : "as number",
|
||||
"invalid-exp" : "invalid JSONata expression in sort node",
|
||||
"too-many" : "too many pending messages in sort node",
|
||||
"clear" : "clear pending message in sort node"
|
||||
},
|
||||
"batch" : {
|
||||
"mode": {
|
||||
"label" : "Mode",
|
||||
"num-msgs" : "number of messages",
|
||||
"interval" : "interval in seconds",
|
||||
"mode": {
|
||||
"label" : "Mode",
|
||||
"num-msgs" : "number of messages",
|
||||
"interval" : "interval in seconds",
|
||||
"concat" : "concatenate sequences"
|
||||
},
|
||||
"count": {
|
||||
"label" : "Number of msgs",
|
||||
"overwrap" : "Overwrap",
|
||||
"count" : "count",
|
||||
},
|
||||
"count": {
|
||||
"label" : "Number of msgs",
|
||||
"overwrap" : "Overwrap",
|
||||
"count" : "count",
|
||||
"invalid" : "Invalid count and overwrap"
|
||||
},
|
||||
"interval": {
|
||||
"label" : "Interval (sec)",
|
||||
"seconds" : "seconds",
|
||||
"sec" : "sec",
|
||||
},
|
||||
"interval": {
|
||||
"label" : "Interval (sec)",
|
||||
"seconds" : "seconds",
|
||||
"sec" : "sec",
|
||||
"empty" : "send empty message when no message arrives"
|
||||
},
|
||||
},
|
||||
"concat": {
|
||||
"topics-label": "Topics",
|
||||
"topic" : "topic"
|
||||
|
@@ -19,17 +19,24 @@
|
||||
<script type="text/x-red" data-template-name="sort">
|
||||
|
||||
<div class="form-row">
|
||||
<label><i class="fa fa-dot-circle-o"></i> <span data-i18n="sort.key-type"></span></label>
|
||||
<select id="node-input-keyType" style="width:200px;">
|
||||
<option value="payload" data-i18n="sort.payload"></option>
|
||||
<option value="exp" data-i18n="sort.exp"></option>
|
||||
</select>
|
||||
<label for="node-input-target"><i class="fa fa-dot-circle-o"></i> <span data-i18n="sort.target"></span></label>
|
||||
<input type="text" id="node-input-target" style="width:70%;">
|
||||
<input type="hidden" id="node-input-targetType">
|
||||
</div>
|
||||
|
||||
<div class="node-row-sort-key">
|
||||
<div class="node-row-sort-msg-key">
|
||||
<div class="form-row">
|
||||
<label><i class="fa fa-filter"></i> <span data-i18n="sort.key-exp"></span></label>
|
||||
<input type="text" id="node-input-key" style="width:70%;">
|
||||
<label for="node-input-msgKey"><i class="fa fa-filter"></i> <span data-i18n="sort.key"></span></label>
|
||||
<input type="text" id="node-input-msgKey" style="width:70%;">
|
||||
<input type="hidden" id="node-input-msgKeyType">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="node-row-sort-seq-key">
|
||||
<div class="form-row">
|
||||
<label for="node-input-seqKey"><i class="fa fa-filter"></i> <span data-i18n="sort.key"></span></label>
|
||||
<input type="text" id="node-input-seqKey" style="width:70%;">
|
||||
<input type="hidden" id="node-input-seqKeyType">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -54,17 +61,17 @@
|
||||
</script>
|
||||
|
||||
<script type="text/x-red" data-help-name="sort">
|
||||
<p>A function that sorts a sequence of messages or payload of array type.</p>
|
||||
<p>When paired with the <b>split</b> node, it will reorder the
|
||||
messages.</p>
|
||||
<p>A function that sorts message property or a sequence of messages.</p>
|
||||
<p>When configured to sort message property, the node sorts array data pointed to by specified message property.</p>
|
||||
<p>When configured to sort a sequence of messages, it will reorder the messages.</p>
|
||||
<p>The sorting order can be:</p>
|
||||
<ul>
|
||||
<li><b>ascending</b>,</li>
|
||||
<li><b>descending</b>.</li>
|
||||
</ul>
|
||||
<p>For numbers, numerical ordering can be specified by a checkbox.</p>
|
||||
<p>Sort key can be <code>payload</code> or any JSONata expression for sorting messages, element value or any JSONata expression for sorting payload of array type.</p>
|
||||
<p>The sort node relies on the received messages to have <code>msg.parts</code> set for sorting messages. The split node generates this property, but can be manually created. It has the following properties:</p>
|
||||
<p>Sort key can be element value or JSONata expression for sorting property value, or message property or JSONata expression for sorting a message sequence.<p>
|
||||
<p>When sorting a message sequence, the sort node relies on the received messages to have <code>msg.parts</code> set. The split node generates this property, but can be manually created. It has the following properties:</p>
|
||||
<p>
|
||||
<ul>
|
||||
<li><code>id</code> - an identifier for the group of messages</li>
|
||||
@@ -74,7 +81,7 @@
|
||||
</p>
|
||||
<p><b>Note:</b> This node internally keeps messages for its operation. In order to prevent unexpected memory usage, maximum number of messages kept can be specified. Default is no limit on number of messages.
|
||||
<ul>
|
||||
<li><code>sortMaxKeptMsgsCount</code> property set in <b>settings.js</b>.</li>
|
||||
<li><code>maxKeptMsgsCount</code> property set in <b>settings.js</b>.</li>
|
||||
</ul>
|
||||
</p>
|
||||
</script>
|
||||
@@ -86,9 +93,13 @@
|
||||
defaults: {
|
||||
name: { value:"" },
|
||||
order: { value:"ascending" },
|
||||
as_num : { value:false },
|
||||
keyType : { value:"payload" },
|
||||
key : { value:"" }
|
||||
as_num: { value:false },
|
||||
target: { value:"payload" },
|
||||
targetType: { value:"msg" },
|
||||
msgKey: { value:"payload" },
|
||||
msgKeyType: { value:"elem" },
|
||||
seqKey: { value:"payload" },
|
||||
seqKeyType: { value:"msg" }
|
||||
},
|
||||
inputs:1,
|
||||
outputs:1,
|
||||
@@ -100,13 +111,37 @@
|
||||
return this.name ? "node_label_italic" : "";
|
||||
},
|
||||
oneditprepare: function() {
|
||||
$("#node-input-key").typedInput({default:'jsonata', types:['jsonata']});
|
||||
$("#node-input-keyType").change(function(e) {
|
||||
var val = $(this).val();
|
||||
$(".node-row-sort-key").toggle(val === 'exp');
|
||||
var seq = {
|
||||
value: "seq",
|
||||
label: RED._("node-red:sort.seq"),
|
||||
hasValue: false
|
||||
};
|
||||
var elem = {
|
||||
value: "elem",
|
||||
label: RED._("node-red:sort.elem"),
|
||||
hasValue: false
|
||||
};
|
||||
$("#node-input-target").typedInput({
|
||||
default:'msg',
|
||||
typeField: $("#node-input-targetType"),
|
||||
types:['msg', seq]
|
||||
});
|
||||
$("#node-input-keyType").change();
|
||||
$("#node-input-order").change();
|
||||
$("#node-input-msgKey").typedInput({
|
||||
default:'elem',
|
||||
typeField: $("#node-input-msgKeyType"),
|
||||
types:[elem, 'jsonata']
|
||||
});
|
||||
$("#node-input-seqKey").typedInput({
|
||||
default:'msg',
|
||||
typeField: $("#node-input-seqKeyType"),
|
||||
types:['msg', 'jsonata']
|
||||
});
|
||||
$("#node-input-target").change(function(e) {
|
||||
var val = $("#node-input-target").typedInput('type');
|
||||
$(".node-row-sort-msg-key").toggle(val === "msg");
|
||||
$(".node-row-sort-seq-key").toggle(val === "seq");
|
||||
});
|
||||
$("#node-input-target").change();
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
@@ -21,7 +21,7 @@ module.exports = function(RED) {
|
||||
|
||||
function max_kept_msgs_count(node) {
|
||||
if (_max_kept_msgs_count === undefined) {
|
||||
var name = "sortMaxKeptMsgsCount";
|
||||
var name = "maxKeptMsgsCount";
|
||||
if (RED.settings.hasOwnProperty(name)) {
|
||||
_max_kept_msgs_count = RED.settings[name];
|
||||
}
|
||||
@@ -60,11 +60,15 @@ module.exports = function(RED) {
|
||||
var pending_id = 0;
|
||||
var order = n.order || "ascending";
|
||||
var as_num = n.as_num || false;
|
||||
var key_is_payload = (n.keyType === 'payload');
|
||||
var key_exp = undefined;
|
||||
if (!key_is_payload) {
|
||||
var target_prop = n.target || "payload";
|
||||
var target_is_prop = (n.targetType === 'msg');
|
||||
var key_is_exp = target_is_prop ? (n.msgKeyType === "jsonata") : (n.seqKeyType === "jsonata");
|
||||
var key_prop = n.seqKey || "payload";
|
||||
var key_exp = target_is_prop ? n.msgKey : n.seqKey;
|
||||
|
||||
if (key_is_exp) {
|
||||
try {
|
||||
key_exp = RED.util.prepareJSONataExpression(n.key, this);
|
||||
key_exp = RED.util.prepareJSONataExpression(key_exp, this);
|
||||
}
|
||||
catch (e) {
|
||||
node.error(RED._("sort.invalid-exp"));
|
||||
@@ -87,10 +91,12 @@ module.exports = function(RED) {
|
||||
}
|
||||
|
||||
function send_group(group) {
|
||||
var key = key_is_payload
|
||||
? function(msg) { return msg.payload; }
|
||||
: function(msg) {
|
||||
var key = key_is_exp
|
||||
? function(msg) {
|
||||
return eval_jsonata(node, key_exp, msg);
|
||||
}
|
||||
: function(msg) {
|
||||
return RED.util.getMessageProperty(msg, key_prop);
|
||||
};
|
||||
var comp = gen_comp(key);
|
||||
var msgs = group.msgs;
|
||||
@@ -108,16 +114,16 @@ module.exports = function(RED) {
|
||||
}
|
||||
|
||||
function sort_payload(msg) {
|
||||
var payload = msg.payload;
|
||||
if (Array.isArray(payload)) {
|
||||
var key = key_is_payload
|
||||
? function(elem) { return elem; }
|
||||
: function(elem) {
|
||||
var data = RED.util.getMessageProperty(msg, target_prop);
|
||||
if (Array.isArray(data)) {
|
||||
var key = key_is_exp
|
||||
? function(elem) {
|
||||
return eval_jsonata(node, key_exp, elem);
|
||||
};
|
||||
}
|
||||
: function(elem) { return elem; };
|
||||
var comp = gen_comp(key);
|
||||
try {
|
||||
payload.sort(comp);
|
||||
data.sort(comp);
|
||||
}
|
||||
catch (e) {
|
||||
return false;
|
||||
@@ -162,7 +168,7 @@ module.exports = function(RED) {
|
||||
}
|
||||
|
||||
function process_msg(msg) {
|
||||
if (!msg.hasOwnProperty("parts")) {
|
||||
if (target_is_prop) {
|
||||
if (sort_payload(msg)) {
|
||||
node.send(msg);
|
||||
}
|
||||
|
Reference in New Issue
Block a user