mirror of
https://github.com/node-red/node-red.git
synced 2025-03-01 10:36:34 +00:00
Compare commits
58 Commits
2.1.0-beta
...
fix-delay-
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
6ac0c0a367 | ||
|
|
3e0f080ea7 | ||
|
|
679e07189d | ||
|
|
d3efb9d7cc | ||
|
|
84a237d3f5 | ||
|
|
e6de52eede | ||
|
|
98aee964d7 | ||
|
|
570e5442e0 | ||
|
|
b77a2dc353 | ||
|
|
87af31de20 | ||
|
|
cfe201dbe1 | ||
|
|
6ccdab35e0 | ||
|
|
55b9f36b45 | ||
|
|
fbcb1130c9 | ||
|
|
d4f7a6d2bc | ||
|
|
8a19f71abe | ||
|
|
fb153757b5 | ||
|
|
4f175fc93e | ||
|
|
2d4ca7cec0 | ||
|
|
bf0ea89969 | ||
|
|
073f0c2a20 | ||
|
|
ba83be9062 | ||
|
|
2e7188ea4f | ||
|
|
5a012182d9 | ||
|
|
b855438af6 | ||
|
|
2ffea143e7 | ||
|
|
61d85b49e6 | ||
|
|
35f617e96c | ||
|
|
6b6ad47c35 | ||
|
|
e57183ed0e | ||
|
|
ecfd61a822 | ||
|
|
153f87704b | ||
|
|
836f7d2163 | ||
|
|
d4d6f71cf4 | ||
|
|
42a9da006e | ||
|
|
2bd5c4f527 | ||
|
|
6a49b5c106 | ||
|
|
23e14d1b72 | ||
|
|
f4f11c8884 | ||
|
|
2b220abdb7 | ||
|
|
c1d947ebe3 | ||
|
|
d695cf392e | ||
|
|
21304a695c | ||
|
|
fa51b06c46 | ||
|
|
7560bb8d7b | ||
|
|
fc9d65abcc | ||
|
|
a7413cccd0 | ||
|
|
7610353f07 | ||
|
|
d3f978c90c | ||
|
|
8d79deffb5 | ||
|
|
8158487c3e | ||
|
|
0cc061196d | ||
|
|
d0ec055222 | ||
|
|
ae12ddd32b | ||
|
|
31da3adaa9 | ||
|
|
9fd5213f13 | ||
|
|
de882f5849 | ||
|
|
fded1e0021 |
56
CHANGELOG.md
56
CHANGELOG.md
@@ -1,3 +1,57 @@
|
||||
#### 2.1.3: Maintenance Release
|
||||
|
||||
Runtime
|
||||
|
||||
- Update gen-publish script to update 'next' tag for main releases
|
||||
- Add environment variable to enable/disable tours (#3221) @hardillb
|
||||
- Fix loading non-default language files leaving runtime in wrong locale (#3225) @knolleary
|
||||
|
||||
Editor
|
||||
|
||||
- Refresh editor settings whenever a node is added or enabled (#3227) @knolleary
|
||||
- Revert spinner css change that made it shrink in some cases (#3229) @knolleary
|
||||
- Fix import notification message when importing config nodes (#3224) @knolleary
|
||||
- Handle changing types of TypedInput repeatedly (#3223) @knolleary
|
||||
|
||||
|
||||
#### 2.1.2: Maintenance Release
|
||||
|
||||
|
||||
Runtime
|
||||
|
||||
- node-red-pi: Remove bash dependency (#3216) @a16bitsysop
|
||||
|
||||
Editor
|
||||
|
||||
- Improved regex for markdown renderer (#3213) @GerwinvBeek
|
||||
- Fix TypedInput initialisation (#3220) @knolleary
|
||||
|
||||
Nodes
|
||||
|
||||
- MQTT: fix datatype in node config not used. fixes #3215 (#3219) @Steve-Mcl
|
||||
|
||||
#### 2.1.1: Maintenance Release
|
||||
|
||||
Editor
|
||||
|
||||
- Ensure tourGuide popover doesn't fall offscreen (#3212) @knolleary
|
||||
- Fix issue with old inject nodes that migrated topic to 'string' type (#3210) @knolleary
|
||||
- Add cache-busting query params to index.mst (#3211) @knolleary
|
||||
- Fix TypedInput validation of type without options (#3207) @knolleary
|
||||
|
||||
#### 2.1.0: Milestone Release
|
||||
|
||||
Editor
|
||||
|
||||
- Position popover properly on a scrolled page
|
||||
- Fixes from 2.1.0-beta.2 (#3202) @knolleary
|
||||
|
||||
Nodes
|
||||
|
||||
- Link Out: Fix saving link out node links (#3201) @knolleary
|
||||
- Switch: Refix #3170 - copy switch rule type when adding new rule
|
||||
- TCP Request: Add string option to TCP request node output (#3204) @dceejay
|
||||
|
||||
#### 2.1.0-beta.2: Beta Release
|
||||
|
||||
Editor
|
||||
@@ -26,8 +80,6 @@ Nodes
|
||||
- Inject: Widen Inject interval box for >1 digit (#3184) @knolleary
|
||||
- Switch: Fix rule focus when switch 'otherwise' rule is used (#3185) @knolleary
|
||||
|
||||
|
||||
|
||||
#### 2.1.0-beta.1: Beta Release
|
||||
|
||||
Editor
|
||||
|
||||
@@ -583,7 +583,7 @@ module.exports = function(grunt) {
|
||||
grunt.registerMultiTask('attachCopyright', function() {
|
||||
var files = this.data.src;
|
||||
var copyright = "/**\n"+
|
||||
" * Copyright JS Foundation and other contributors, http://js.foundation\n"+
|
||||
" * Copyright OpenJS Foundation and other contributors, https://openjsf.org/\n"+
|
||||
" *\n"+
|
||||
" * Licensed under the Apache License, Version 2.0 (the \"License\");\n"+
|
||||
" * you may not use this file except in compliance with the License.\n"+
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "node-red",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"description": "Low-code programming for event-driven applications",
|
||||
"homepage": "http://nodered.org",
|
||||
"license": "Apache-2.0",
|
||||
|
||||
@@ -48,9 +48,10 @@ module.exports = {
|
||||
var prevLang = i18n.i.language;
|
||||
// Trigger a load from disk of the language if it is not the default
|
||||
i18n.i.changeLanguage(lang, function(){
|
||||
var catalog = loadResource(lang, namespace);
|
||||
res.json(catalog||{});
|
||||
i18n.i.changeLanguage(prevLang, function() {
|
||||
var catalog = loadResource(lang, namespace);
|
||||
res.json(catalog||{});
|
||||
});
|
||||
});
|
||||
i18n.i.changeLanguage(prevLang);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -27,7 +27,8 @@ var defaultContext = {
|
||||
tabicon: {
|
||||
icon: "red/images/node-red-icon-black.svg",
|
||||
colour: "#8f0000"
|
||||
}
|
||||
},
|
||||
version: require(path.join(__dirname,"../../package.json")).version
|
||||
},
|
||||
header: {
|
||||
title: "Node-RED",
|
||||
@@ -227,6 +228,11 @@ module.exports = {
|
||||
if (theme.theme) {
|
||||
themeSettings.theme = theme.theme;
|
||||
}
|
||||
|
||||
if (theme.hasOwnProperty("tours")) {
|
||||
themeSettings.tours = theme.tours;
|
||||
}
|
||||
|
||||
return themeApp;
|
||||
},
|
||||
context: async function() {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@node-red/editor-api",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"license": "Apache-2.0",
|
||||
"main": "./lib/index.js",
|
||||
"repository": {
|
||||
@@ -16,8 +16,8 @@
|
||||
}
|
||||
],
|
||||
"dependencies": {
|
||||
"@node-red/util": "2.1.0-beta.2",
|
||||
"@node-red/editor-client": "2.1.0-beta.2",
|
||||
"@node-red/util": "2.1.3",
|
||||
"@node-red/editor-client": "2.1.3",
|
||||
"bcryptjs": "2.4.3",
|
||||
"body-parser": "1.19.0",
|
||||
"clone": "2.1.2",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@node-red/editor-client",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"license": "Apache-2.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
|
||||
@@ -475,31 +475,33 @@ var RED = (function() {
|
||||
var typeList;
|
||||
var info;
|
||||
if (topic == "notification/node/added") {
|
||||
var addedTypes = [];
|
||||
msg.forEach(function(m) {
|
||||
var id = m.id;
|
||||
RED.nodes.addNodeSet(m);
|
||||
addedTypes = addedTypes.concat(m.types);
|
||||
RED.i18n.loadNodeCatalog(id, function() {
|
||||
var lang = localStorage.getItem("editor-language")||RED.i18n.detectLanguage();
|
||||
$.ajax({
|
||||
headers: {
|
||||
"Accept":"text/html",
|
||||
"Accept-Language": lang
|
||||
},
|
||||
cache: false,
|
||||
url: 'nodes/'+id,
|
||||
success: function(data) {
|
||||
appendNodeConfig(data);
|
||||
}
|
||||
RED.settings.refreshSettings(function(err, data) {
|
||||
var addedTypes = [];
|
||||
msg.forEach(function(m) {
|
||||
var id = m.id;
|
||||
RED.nodes.addNodeSet(m);
|
||||
addedTypes = addedTypes.concat(m.types);
|
||||
RED.i18n.loadNodeCatalog(id, function() {
|
||||
var lang = localStorage.getItem("editor-language")||RED.i18n.detectLanguage();
|
||||
$.ajax({
|
||||
headers: {
|
||||
"Accept":"text/html",
|
||||
"Accept-Language": lang
|
||||
},
|
||||
cache: false,
|
||||
url: 'nodes/'+id,
|
||||
success: function(data) {
|
||||
appendNodeConfig(data);
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
if (addedTypes.length) {
|
||||
typeList = "<ul><li>"+addedTypes.map(RED.utils.sanitize).join("</li><li>")+"</li></ul>";
|
||||
RED.notify(RED._("palette.event.nodeAdded", {count:addedTypes.length})+typeList,"success");
|
||||
}
|
||||
loadIconList();
|
||||
if (addedTypes.length) {
|
||||
typeList = "<ul><li>"+addedTypes.map(RED.utils.sanitize).join("</li><li>")+"</li></ul>";
|
||||
RED.notify(RED._("palette.event.nodeAdded", {count:addedTypes.length})+typeList,"success");
|
||||
}
|
||||
loadIconList();
|
||||
})
|
||||
} else if (topic == "notification/node/removed") {
|
||||
for (i=0;i<msg.length;i++) {
|
||||
m = msg[i];
|
||||
@@ -512,27 +514,29 @@ var RED = (function() {
|
||||
loadIconList();
|
||||
} else if (topic == "notification/node/enabled") {
|
||||
if (msg.types) {
|
||||
info = RED.nodes.getNodeSet(msg.id);
|
||||
if (info.added) {
|
||||
RED.nodes.enableNodeSet(msg.id);
|
||||
typeList = "<ul><li>"+msg.types.map(RED.utils.sanitize).join("</li><li>")+"</li></ul>";
|
||||
RED.notify(RED._("palette.event.nodeEnabled", {count:msg.types.length})+typeList,"success");
|
||||
} else {
|
||||
var lang = localStorage.getItem("editor-language")||RED.i18n.detectLanguage();
|
||||
$.ajax({
|
||||
headers: {
|
||||
"Accept":"text/html",
|
||||
"Accept-Language": lang
|
||||
},
|
||||
cache: false,
|
||||
url: 'nodes/'+msg.id,
|
||||
success: function(data) {
|
||||
appendNodeConfig(data);
|
||||
typeList = "<ul><li>"+msg.types.map(RED.utils.sanitize).join("</li><li>")+"</li></ul>";
|
||||
RED.notify(RED._("palette.event.nodeAdded", {count:msg.types.length})+typeList,"success");
|
||||
}
|
||||
});
|
||||
}
|
||||
RED.settings.refreshSettings(function(err, data) {
|
||||
info = RED.nodes.getNodeSet(msg.id);
|
||||
if (info.added) {
|
||||
RED.nodes.enableNodeSet(msg.id);
|
||||
typeList = "<ul><li>"+msg.types.map(RED.utils.sanitize).join("</li><li>")+"</li></ul>";
|
||||
RED.notify(RED._("palette.event.nodeEnabled", {count:msg.types.length})+typeList,"success");
|
||||
} else {
|
||||
var lang = localStorage.getItem("editor-language")||RED.i18n.detectLanguage();
|
||||
$.ajax({
|
||||
headers: {
|
||||
"Accept":"text/html",
|
||||
"Accept-Language": lang
|
||||
},
|
||||
cache: false,
|
||||
url: 'nodes/'+msg.id,
|
||||
success: function(data) {
|
||||
appendNodeConfig(data);
|
||||
typeList = "<ul><li>"+msg.types.map(RED.utils.sanitize).join("</li><li>")+"</li></ul>";
|
||||
RED.notify(RED._("palette.event.nodeAdded", {count:msg.types.length})+typeList,"success");
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
} else if (topic == "notification/node/disabled") {
|
||||
if (msg.types) {
|
||||
|
||||
@@ -125,7 +125,7 @@ RED.settings = (function () {
|
||||
load(done);
|
||||
}
|
||||
|
||||
var load = function(done) {
|
||||
var refreshSettings = function(done) {
|
||||
$.ajax({
|
||||
headers: {
|
||||
"Accept": "application/json"
|
||||
@@ -135,6 +135,23 @@ RED.settings = (function () {
|
||||
url: 'settings',
|
||||
success: function (data) {
|
||||
setProperties(data);
|
||||
done(null, data);
|
||||
},
|
||||
error: function(jqXHR,textStatus,errorThrown) {
|
||||
if (jqXHR.status === 401) {
|
||||
if (/[?&]access_token=(.*?)(?:$|&)/.test(window.location.search)) {
|
||||
window.location.search = "";
|
||||
}
|
||||
RED.user.login(function() { refreshSettings(done); });
|
||||
} else {
|
||||
console.log("Unexpected error loading settings:",jqXHR.status,textStatus);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
var load = function(done) {
|
||||
refreshSettings(function(err, data) {
|
||||
if (!err) {
|
||||
if (!RED.settings.user || RED.settings.user.anonymous) {
|
||||
RED.settings.remove("auth-tokens");
|
||||
}
|
||||
@@ -147,18 +164,8 @@ RED.settings = (function () {
|
||||
console.log("D3",d3.version);
|
||||
console.groupEnd();
|
||||
loadUserSettings(done);
|
||||
},
|
||||
error: function(jqXHR,textStatus,errorThrown) {
|
||||
if (jqXHR.status === 401) {
|
||||
if (/[?&]access_token=(.*?)(?:$|&)/.test(window.location.search)) {
|
||||
window.location.search = "";
|
||||
}
|
||||
RED.user.login(function() { load(done); });
|
||||
} else {
|
||||
console.log("Unexpected error loading settings:",jqXHR.status,textStatus);
|
||||
}
|
||||
}
|
||||
});
|
||||
})
|
||||
};
|
||||
|
||||
function loadUserSettings(done) {
|
||||
@@ -234,6 +241,7 @@ RED.settings = (function () {
|
||||
init: init,
|
||||
load: load,
|
||||
loadUserSettings: loadUserSettings,
|
||||
refreshSettings: refreshSettings,
|
||||
set: set,
|
||||
get: get,
|
||||
remove: remove,
|
||||
|
||||
@@ -603,7 +603,7 @@ RED.popover = (function() {
|
||||
var panelWidth = panel.width();
|
||||
|
||||
var top = (targetHeight+pos.top) + offset[1];
|
||||
if (top+panelHeight > $(window).height()) {
|
||||
if (top+panelHeight-$(document).scrollTop() > $(window).height()) {
|
||||
top -= (top+panelHeight)-$(window).height() + 5;
|
||||
}
|
||||
if (top < 0) {
|
||||
|
||||
@@ -118,6 +118,9 @@
|
||||
switch(evt.keyCode) {
|
||||
case 32: // SPACE
|
||||
case 13: // ENTER
|
||||
if (evt.altKey || evt.ctrlKey || evt.metaKey || evt.shiftKey) {
|
||||
return
|
||||
}
|
||||
evt.preventDefault();
|
||||
evt.stopPropagation();
|
||||
if (focussed.checkbox) {
|
||||
@@ -337,7 +340,7 @@
|
||||
if (child.depth !== parent.depth+1) {
|
||||
child.depth = parent.depth+1;
|
||||
// var labelPaddingWidth = ((child.gutter ? child.gutter[0].offsetWidth + 2 : 0) + (child.depth * 20));
|
||||
var labelPaddingWidth = ((child.gutter?child.gutter.width()+2:0)+(child.depth*20));
|
||||
var labelPaddingWidth = (((child.gutter&&!child.gutter.hasClass("red-ui-treeList-gutter-float"))?child.gutter.width()+2:0)+(child.depth*20));
|
||||
child.treeList.labelPadding.width(labelPaddingWidth+'px');
|
||||
if (child.element) {
|
||||
$(child.element).css({
|
||||
@@ -559,8 +562,9 @@
|
||||
}).appendTo(label)
|
||||
|
||||
}
|
||||
// var labelPaddingWidth = (item.gutter?item.gutter.width()+2:0)+(depth*20);
|
||||
var labelPaddingWidth = (item.gutter ? item.gutter[0].offsetWidth + 2 : 0) + (depth * 20)
|
||||
|
||||
var labelPaddingWidth = ((item.gutter&&!item.gutter.hasClass("red-ui-treeList-gutter-float"))?item.gutter.width()+2:0)+(depth*20);
|
||||
|
||||
item.treeList.labelPadding = $('<span>').css({
|
||||
display: "inline-block",
|
||||
"flex-shrink": 0,
|
||||
|
||||
@@ -345,6 +345,47 @@
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// For a type with options, check value is a valid selection
|
||||
// If !opt.multiple, returns the valid option object
|
||||
// if opt.multiple, returns an array of valid option objects
|
||||
// If not valid, returns null;
|
||||
|
||||
function isOptionValueValid(opt, currentVal) {
|
||||
if (!opt.multiple) {
|
||||
for (var i=0;i<opt.options.length;i++) {
|
||||
op = opt.options[i];
|
||||
if (typeof op === "string" && op === currentVal) {
|
||||
return {value:currentVal}
|
||||
} else if (op.value === currentVal) {
|
||||
return op;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// Check to see if value is a valid csv of
|
||||
// options.
|
||||
var currentValues = {};
|
||||
var selected = [];
|
||||
currentVal.split(",").forEach(function(v) {
|
||||
if (v) {
|
||||
currentValues[v] = true;
|
||||
}
|
||||
});
|
||||
for (var i=0;i<opt.options.length;i++) {
|
||||
op = opt.options[i];
|
||||
var val = typeof op === "string" ? op : op.value;
|
||||
if (currentValues.hasOwnProperty(val)) {
|
||||
delete currentValues[val];
|
||||
selected.push(typeof op === "string" ? {value:op} : op.value)
|
||||
}
|
||||
}
|
||||
if (!$.isEmptyObject(currentValues)) {
|
||||
return null;
|
||||
}
|
||||
return selected
|
||||
}
|
||||
}
|
||||
|
||||
var nlsd = false;
|
||||
|
||||
$.widget( "nodered.typedInput", {
|
||||
@@ -378,7 +419,8 @@
|
||||
}
|
||||
nlsd = true;
|
||||
var that = this;
|
||||
|
||||
this.identifier = this.element.attr('id') || "TypedInput-"+Math.floor(Math.random()*100);
|
||||
if (this.options.debug) { console.log(this.identifier,"Create",{defaultType:this.options.default, value:this.element.val()}) }
|
||||
this.disarmClick = false;
|
||||
this.input = $('<input class="red-ui-typedInput-input" type="text"></input>');
|
||||
this.input.insertAfter(this.element);
|
||||
@@ -408,6 +450,8 @@
|
||||
});
|
||||
|
||||
this.defaultInputType = this.input.attr('type');
|
||||
// Used to remember selections per-type to restore them when switching between types
|
||||
this.oldValues = {};
|
||||
|
||||
this.uiSelect.addClass("red-ui-typedInput-container");
|
||||
|
||||
@@ -490,9 +534,9 @@
|
||||
// explicitly set optionSelectTrigger display to inline-block otherwise jQ sets it to 'inline'
|
||||
this.optionSelectTrigger = $('<button tabindex="0" class="red-ui-typedInput-option-trigger" style="display:inline-block"><span class="red-ui-typedInput-option-caret"><i class="red-ui-typedInput-icon fa fa-caret-down"></i></span></button>').appendTo(this.uiSelect);
|
||||
this.optionSelectLabel = $('<span class="red-ui-typedInput-option-label"></span>').prependTo(this.optionSelectTrigger);
|
||||
RED.popover.tooltip(this.optionSelectLabel,function() {
|
||||
return that.optionValue;
|
||||
});
|
||||
// RED.popover.tooltip(this.optionSelectLabel,function() {
|
||||
// return that.optionValue;
|
||||
// });
|
||||
this.optionSelectTrigger.on("click", function(event) {
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
@@ -512,10 +556,8 @@
|
||||
this.optionExpandButton = $('<button tabindex="0" class="red-ui-typedInput-option-expand" style="display:inline-block"></button>').appendTo(this.uiSelect);
|
||||
this.optionExpandButtonIcon = $('<i class="red-ui-typedInput-icon fa fa-ellipsis-h"></i>').appendTo(this.optionExpandButton);
|
||||
|
||||
// Used to remember selections per-type to restore them when switching between types
|
||||
this.oldValues = {};
|
||||
|
||||
this.type(this.options.default||this.typeList[0].value);
|
||||
this.typeChanged = !!this.options.default;
|
||||
}catch(err) {
|
||||
console.log(err.stack);
|
||||
}
|
||||
@@ -806,7 +848,10 @@
|
||||
},
|
||||
value: function(value) {
|
||||
var that = this;
|
||||
var opt = this.typeMap[this.propertyType];
|
||||
// If the default type has been set to an invalid type, then on first
|
||||
// creation, the current propertyType will not exist. Default to an
|
||||
// empty object on the assumption the corrent type will be set shortly
|
||||
var opt = this.typeMap[this.propertyType] || {};
|
||||
if (!arguments.length) {
|
||||
var v = this.input.val();
|
||||
if (opt.export) {
|
||||
@@ -814,27 +859,38 @@
|
||||
}
|
||||
return v;
|
||||
} else {
|
||||
if (this.options.debug) { console.log(this.identifier,"----- SET VALUE ------",value) }
|
||||
var selectedOption = [];
|
||||
var valueToCheck = value;
|
||||
if (opt.options) {
|
||||
var checkValues = [value];
|
||||
if (opt.hasValue && opt.parse) {
|
||||
var parts = opt.parse(value);
|
||||
if (this.options.debug) { console.log(this.identifier,"new parse",parts) }
|
||||
value = parts.value;
|
||||
valueToCheck = parts.option || parts.value;
|
||||
}
|
||||
|
||||
var checkValues = [valueToCheck];
|
||||
if (opt.multiple) {
|
||||
selectedOption = [];
|
||||
checkValues = value.split(",");
|
||||
checkValues = valueToCheck.split(",");
|
||||
}
|
||||
checkValues.forEach(function(value) {
|
||||
checkValues.forEach(function(valueToCheck) {
|
||||
for (var i=0;i<opt.options.length;i++) {
|
||||
var op = opt.options[i];
|
||||
if (typeof op === "string") {
|
||||
if (op === value || op === ""+value) {
|
||||
if (op === valueToCheck || op === ""+valueToCheck) {
|
||||
selectedOption.push(that.activeOptions[op]);
|
||||
break;
|
||||
}
|
||||
} else if (op.value === value) {
|
||||
} else if (op.value === valueToCheck) {
|
||||
selectedOption.push(op);
|
||||
break;
|
||||
}
|
||||
}
|
||||
})
|
||||
if (this.options.debug) { console.log(this.identifier,"set value to",value) }
|
||||
|
||||
this.input.val(value);
|
||||
if (!opt.multiple) {
|
||||
if (selectedOption.length === 0) {
|
||||
@@ -859,23 +915,56 @@
|
||||
return this.propertyType;
|
||||
} else {
|
||||
var that = this;
|
||||
if (this.options.debug) { console.log(this.identifier,"----- SET TYPE -----",type) }
|
||||
var previousValue = null;
|
||||
var opt = this.typeMap[type];
|
||||
if (opt && this.propertyType !== type) {
|
||||
// If previousType is !null, then this is a change of the type, rather than the initialisation
|
||||
var previousType = this.typeMap[this.propertyType];
|
||||
var typeChanged = !!previousType;
|
||||
previousValue = this.input.val();
|
||||
|
||||
if (typeChanged) {
|
||||
if (previousType && this.typeChanged) {
|
||||
if (this.options.debug) { console.log(this.identifier,"typeChanged",{previousType,previousValue}) }
|
||||
if (previousType.options && opt.hasValue !== true) {
|
||||
this.oldValues[previousType.value] = this.input.val();
|
||||
this.oldValues[previousType.value] = previousValue;
|
||||
} else if (previousType.hasValue === false) {
|
||||
this.oldValues[previousType.value] = this.input.val();
|
||||
this.oldValues[previousType.value] = previousValue;
|
||||
} else {
|
||||
this.oldValues["_"] = this.input.val();
|
||||
this.oldValues["_"] = previousValue;
|
||||
}
|
||||
if ((opt.options && opt.hasValue !== true) || opt.hasValue === false) {
|
||||
this.input.val(this.oldValues.hasOwnProperty(opt.value)?this.oldValues[opt.value]:(opt.default||[]).join(","))
|
||||
if (this.oldValues.hasOwnProperty(opt.value)) {
|
||||
if (this.options.debug) { console.log(this.identifier,"restored previous (1)",this.oldValues[opt.value]) }
|
||||
this.input.val(this.oldValues[opt.value]);
|
||||
} else if (opt.options) {
|
||||
// No old value for the option type.
|
||||
// It is possible code has called 'value' then 'type'
|
||||
// to set the selected option. This is what the Inject/Switch/Change
|
||||
// nodes did before 2.1.
|
||||
// So we need to be careful to not reset the value if it is a valid option.
|
||||
var validOptions = isOptionValueValid(opt,previousValue);
|
||||
if (this.options.debug) { console.log(this.identifier,{previousValue,opt,validOptions}) }
|
||||
if ((previousValue || previousValue === '') && validOptions) {
|
||||
if (this.options.debug) { console.log(this.identifier,"restored previous (2)") }
|
||||
this.input.val(previousValue);
|
||||
} else {
|
||||
if (typeof opt.default === "string") {
|
||||
if (this.options.debug) { console.log(this.identifier,"restored previous (3)",opt.default) }
|
||||
this.input.val(opt.default);
|
||||
} else if (Array.isArray(opt.default)) {
|
||||
if (this.options.debug) { console.log(this.identifier,"restored previous (4)",opt.default.join(",")) }
|
||||
this.input.val(opt.default.join(","))
|
||||
} else {
|
||||
if (this.options.debug) { console.log(this.identifier,"restored previous (5)") }
|
||||
this.input.val("");
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (this.options.debug) { console.log(this.identifier,"restored default/blank",opt.default||"") }
|
||||
this.input.val(opt.default||"")
|
||||
}
|
||||
} else {
|
||||
if (this.options.debug) { console.log(this.identifier,"restored old/default/blank") }
|
||||
this.input.val(this.oldValues.hasOwnProperty("_")?this.oldValues["_"]:(opt.default||""))
|
||||
}
|
||||
if (previousType.autoComplete) {
|
||||
@@ -883,6 +972,7 @@
|
||||
}
|
||||
}
|
||||
this.propertyType = type;
|
||||
this.typeChanged = true;
|
||||
if (this.typeField) {
|
||||
this.typeField.val(type);
|
||||
}
|
||||
@@ -951,22 +1041,12 @@
|
||||
|
||||
var op;
|
||||
if (!opt.hasValue) {
|
||||
var validValue = false;
|
||||
var currentVal = this.input.val();
|
||||
// Check the value is valid for the available options
|
||||
var validValues = isOptionValueValid(opt,this.input.val());
|
||||
if (!opt.multiple) {
|
||||
for (var i=0;i<opt.options.length;i++) {
|
||||
op = opt.options[i];
|
||||
if (typeof op === "string" && op === currentVal) {
|
||||
that._updateOptionSelectLabel({value:currentVal});
|
||||
validValue = true;
|
||||
break;
|
||||
} else if (op.value === currentVal) {
|
||||
that._updateOptionSelectLabel(op);
|
||||
validValue = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!validValue) {
|
||||
if (validValues) {
|
||||
that._updateOptionSelectLabel(validValues)
|
||||
} else {
|
||||
op = opt.options[0];
|
||||
if (typeof op === "string") {
|
||||
this.value(op);
|
||||
@@ -977,31 +1057,19 @@
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// Check to see if value is a valid csv of
|
||||
// options.
|
||||
var currentValues = {};
|
||||
var selected = [];
|
||||
currentVal.split(",").forEach(function(v) {
|
||||
if (v) {
|
||||
selected.push(v);
|
||||
currentValues[v] = true;
|
||||
}
|
||||
});
|
||||
for (var i=0;i<opt.options.length;i++) {
|
||||
op = opt.options[i];
|
||||
delete currentValues[op.value||op];
|
||||
if (!validValues) {
|
||||
validValues = (opt.default || []).map(function(v) {
|
||||
return typeof v === "string"?v:v.value
|
||||
});
|
||||
this.value(validValues.join(","));
|
||||
}
|
||||
if (!$.isEmptyObject(currentValues)) {
|
||||
selected = opt.default || [];
|
||||
// Invalid, set to default/empty
|
||||
this.value(selected.join(","));
|
||||
}
|
||||
that._updateOptionSelectLabel(selected);
|
||||
that._updateOptionSelectLabel(validValues);
|
||||
}
|
||||
} else {
|
||||
var selectedOption = this.optionValue||opt.options[0];
|
||||
if (opt.parse) {
|
||||
var parts = opt.parse(this.input.val(),selectedOption);
|
||||
var selectedOptionObj = typeof selectedOption === "string"?{value:selectedOption}:selectedOption
|
||||
var parts = opt.parse(this.input.val(),selectedOptionObj);
|
||||
if (parts.option) {
|
||||
selectedOption = parts.option;
|
||||
if (!this.activeOptions.hasOwnProperty(selectedOption)) {
|
||||
@@ -1025,6 +1093,7 @@
|
||||
this._updateOptionSelectLabel(this.activeOptions[selectedOption]);
|
||||
}
|
||||
} else if (selectedOption) {
|
||||
if (this.options.debug) { console.log(this.identifier,"HERE",{optionValue:selectedOption.value}) }
|
||||
this.optionValue = selectedOption.value;
|
||||
this._updateOptionSelectLabel(selectedOption);
|
||||
} else {
|
||||
|
||||
@@ -563,7 +563,7 @@ RED.sidebar.info.outliner = (function() {
|
||||
}
|
||||
}
|
||||
function getGutter(n) {
|
||||
var span = $("<span>",{class:"red-ui-info-outline-gutter"});
|
||||
var span = $("<span>",{class:"red-ui-info-outline-gutter red-ui-treeList-gutter-float"});
|
||||
var revealButton = $('<button type="button" class="red-ui-info-outline-item-control-reveal red-ui-button red-ui-button-small"><i class="fa fa-search"></i></button>').appendTo(span).on("click",function(evt) {
|
||||
evt.preventDefault();
|
||||
evt.stopPropagation();
|
||||
|
||||
@@ -348,7 +348,12 @@ RED.tourGuide = (function() {
|
||||
maxWidth: maxWidth+"px",
|
||||
direction: direction,
|
||||
})
|
||||
|
||||
setTimeout(function() {
|
||||
var pos = popover.element.position()
|
||||
if (pos.left < 0) {
|
||||
popover.element.css({left: 0});
|
||||
}
|
||||
},100);
|
||||
if (nextButton) {
|
||||
setTimeout(function() {
|
||||
nextButton.focus();
|
||||
|
||||
@@ -27,7 +27,7 @@ RED.utils = (function() {
|
||||
level: 'block', // Is this a block-level or inline-level tokenizer?
|
||||
start(src) {
|
||||
if (!src) { return null; }
|
||||
let m = src.match(/:[^:\n]/);
|
||||
let m = src.match(/:[^:\n]/g);
|
||||
return m && m.index; // Hint to Marked.js to stop and check for a match
|
||||
},
|
||||
tokenizer(src, tokens) {
|
||||
@@ -53,7 +53,7 @@ RED.utils = (function() {
|
||||
level: 'inline', // Is this a block-level or inline-level tokenizer?
|
||||
start(src) {
|
||||
if (!src) { return null; }
|
||||
let m = src.match(/:/);
|
||||
let m = src.match(/:/g);
|
||||
return m && m.index; // Hint to Marked.js to stop and check for a match
|
||||
},
|
||||
tokenizer(src, tokens) {
|
||||
|
||||
@@ -4957,7 +4957,7 @@ RED.view = (function() {
|
||||
counts.push(RED._("clipboard.group",{count:newGroupCount}));
|
||||
}
|
||||
if (newConfigNodeCount > 0) {
|
||||
counts.push(RED._("clipboard.configNode",{count:newNodeCount}));
|
||||
counts.push(RED._("clipboard.configNode",{count:newConfigNodeCount}));
|
||||
}
|
||||
if (new_subflows.length > 0) {
|
||||
counts.push(RED._("clipboard.subflow",{count:new_subflows.length}));
|
||||
|
||||
@@ -137,10 +137,10 @@
|
||||
padding: 0;
|
||||
border: 1px solid $form-input-border-color;
|
||||
}
|
||||
.ui-spinner input[type=text] {
|
||||
.ui-spinner input {
|
||||
background: $form-input-background;
|
||||
margin: 0 17px 0 0;
|
||||
padding: 8px;
|
||||
padding: 6px;
|
||||
border: none;
|
||||
border-top-right-radius: 0px;
|
||||
border-bottom-right-radius: 0px;
|
||||
|
||||
@@ -93,6 +93,8 @@ export default {
|
||||
{
|
||||
title: {"en-US":"Link Call node added"},
|
||||
prepare(done) {
|
||||
this.paletteWasClosed = $("#red-ui-main-container").hasClass("red-ui-palette-closed");
|
||||
RED.actions.invoke("core:toggle-palette",true)
|
||||
$('[data-palette-type="link call"]')[0].scrollIntoView({block:"center"})
|
||||
setTimeout(done,100);
|
||||
},
|
||||
@@ -100,13 +102,27 @@ export default {
|
||||
direction: "right",
|
||||
description: { "en-US": '<p>The <code>Link Call</code> node lets you call another flow that begins with a <code>Link In</code> node and get the result back when the message reaches a <code>Link Out</code> node.</p>' },
|
||||
},
|
||||
|
||||
{
|
||||
title: {"en-US":"MQTT nodes support dynamic connections"},
|
||||
prepare(done) {
|
||||
$('[data-palette-type="mqtt out"]')[0].scrollIntoView({block:"center"})
|
||||
setTimeout(done,100);
|
||||
},
|
||||
element: '[data-palette-type="mqtt out"]',
|
||||
direction: "right",
|
||||
description: { "en-US": '<p>The <code>MQTT</code> nodes now support creating their connections and subscriptions dynamically.</p>' },
|
||||
},
|
||||
{
|
||||
title: {"en-US":"File nodes renamed"},
|
||||
prepare(done) {
|
||||
$('[data-palette-type="file"]')[0].scrollIntoView({block:"center"})
|
||||
setTimeout(done,100);
|
||||
},
|
||||
complete() {
|
||||
if (this.paletteWasClosed) {
|
||||
RED.actions.invoke("core:toggle-palette",false)
|
||||
}
|
||||
},
|
||||
element: '[data-palette-type="file"]',
|
||||
direction: "right",
|
||||
description: { "en-US": '<p>The file nodes have been renamed to make it clearer which node does what.</p>' },
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
<meta name="apple-mobile-web-app-capable" content="yes">
|
||||
<meta name="mobile-web-app-capable" content="yes">
|
||||
<!--
|
||||
Copyright JS Foundation and other contributors, http://js.foundation
|
||||
Copyright OpenJS Foundation and other contributors, https://openjsf.org/
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
@@ -24,24 +24,24 @@
|
||||
<title>{{ page.title }}</title>
|
||||
<link rel="icon" type="image/png" href="{{ page.favicon }}">
|
||||
<link rel="mask-icon" href="{{ page.tabicon.icon }}" color="{{ page.tabicon.colour }}">
|
||||
<link rel="stylesheet" href="vendor/jquery/css/base/jquery-ui.min.css">
|
||||
<link rel="stylesheet" href="vendor/font-awesome/css/font-awesome.min.css">
|
||||
<link rel="stylesheet" href="red/style.min.css">
|
||||
<link rel="stylesheet" href="vendor/jquery/css/base/jquery-ui.min.css?v={{ page.version }}">
|
||||
<link rel="stylesheet" href="vendor/font-awesome/css/font-awesome.min.css?v={{ page.version }}">
|
||||
<link rel="stylesheet" href="red/style.min.css?v={{ page.version }}">
|
||||
{{#page.css}}
|
||||
<link rel="stylesheet" href="{{.}}">
|
||||
{{/page.css}}
|
||||
{{#asset.vendorMonaco}}
|
||||
<link rel="stylesheet" href="vendor/monaco/style.css">
|
||||
<link rel="stylesheet" href="vendor/monaco/style.css?v={{ page.version }}">
|
||||
{{/asset.vendorMonaco}}
|
||||
</head>
|
||||
<body spellcheck="false">
|
||||
<div id="red-ui-editor"></div>
|
||||
<script src="vendor/vendor.js"></script>
|
||||
<script src="vendor/vendor.js?v={{ page.version }}"></script>
|
||||
{{#asset.vendorMonaco}}
|
||||
<script src="{{ asset.vendorMonaco }}"></script>
|
||||
<script src="{{ asset.vendorMonaco }}?v={{ page.version }}"></script>
|
||||
{{/asset.vendorMonaco}}
|
||||
<script src="{{ asset.red }}"></script>
|
||||
<script src="{{ asset.main }}"></script>
|
||||
<script src="{{ asset.red }}?v={{ page.version }}"></script>
|
||||
<script src="{{ asset.main }}?v={{ page.version }}"></script>
|
||||
{{# page.scripts }}
|
||||
<script src="{{.}}"></script>
|
||||
{{/ page.scripts }}
|
||||
|
||||
@@ -353,14 +353,16 @@
|
||||
},
|
||||
oneditprepare: function() {
|
||||
var node = this;
|
||||
var payloadType = node.payloadType;
|
||||
|
||||
if (node.payloadType == null) {
|
||||
if (node.payload == "") {
|
||||
node.payloadType = "date";
|
||||
payloadType = "date";
|
||||
} else {
|
||||
node.payloadType = "str";
|
||||
payloadType = "str";
|
||||
}
|
||||
} else if (node.payloadType === 'string' || node.payloadType === 'none') {
|
||||
node.payloadType = "str";
|
||||
payloadType = "str";
|
||||
}
|
||||
|
||||
$("#inject-time-type-select").on("change", function() {
|
||||
@@ -539,12 +541,10 @@
|
||||
var propertyValue = $('<input/>',{class:"node-input-prop-property-value",type:"text"})
|
||||
.css("width","calc(70% - 30px)")
|
||||
.appendTo(row)
|
||||
.typedInput({default:'str',types:['flow','global','str','num','bool','json','bin','date','jsonata','env','msg']});
|
||||
.typedInput({default:prop.vt || 'str',types:['flow','global','str','num','bool','json','bin','date','jsonata','env','msg']});
|
||||
|
||||
propertyName.typedInput('value',prop.p);
|
||||
|
||||
propertyValue.typedInput('value',prop.v);
|
||||
propertyValue.typedInput('type',prop.vt);
|
||||
},
|
||||
removable: true,
|
||||
sortable: true
|
||||
@@ -559,12 +559,12 @@
|
||||
var payload = {
|
||||
p:'payload',
|
||||
v: node.payload ? node.payload : '',
|
||||
vt:node.payloadType ? node.payloadType : 'date'
|
||||
vt:payloadType ? payloadType : 'date'
|
||||
};
|
||||
var topic = {
|
||||
p:'topic',
|
||||
v: node.topic ? node.topic : '',
|
||||
vt:'string'
|
||||
vt:'str'
|
||||
}
|
||||
node.props = [payload,topic];
|
||||
}
|
||||
@@ -575,11 +575,16 @@
|
||||
if (newProp.v === undefined) {
|
||||
if (prop.p === 'payload') {
|
||||
newProp.v = node.payload ? node.payload : '';
|
||||
newProp.vt = node.payloadType ? node.payloadType : 'date';
|
||||
newProp.vt = payloadType ? payloadType : 'date';
|
||||
} else if (prop.p === 'topic' && prop.vt === "str") {
|
||||
newProp.v = node.topic ? node.topic : '';
|
||||
}
|
||||
}
|
||||
if (newProp.vt === "string") {
|
||||
// Fix bug in pre 2.1 where an old Inject node might have
|
||||
// a migrated rule with type 'string' not 'str'
|
||||
newProp.vt = "str";
|
||||
}
|
||||
eList.editableList('addItem',newProp);
|
||||
}
|
||||
|
||||
|
||||
@@ -52,7 +52,7 @@
|
||||
treeList = $("<div>")
|
||||
.css({width: "100%", height: "100%"})
|
||||
.appendTo(".node-input-link-row")
|
||||
.treeList({})
|
||||
.treeList({autoSelect:false})
|
||||
.on('treelistitemmouseover',function(e,item) {
|
||||
if (item.node) {
|
||||
item.node.highlighted = true;
|
||||
@@ -157,7 +157,7 @@
|
||||
function onEditSave(node) {
|
||||
var flows = treeList.treeList('data');
|
||||
node.links = [];
|
||||
if (node.type !== "link out" || $("node-input-mode").val() === 'link') {
|
||||
if (node.type !== "link out" || $("#node-input-mode").val() === 'link') {
|
||||
flows.forEach(function(f) {
|
||||
f.children.forEach(function(n) {
|
||||
if (n.selected) {
|
||||
|
||||
@@ -117,30 +117,35 @@
|
||||
return r;
|
||||
}
|
||||
|
||||
function createValueField(row){
|
||||
return $('<input/>',{class:"node-input-rule-value",type:"text",style:"width: 100%;"}).appendTo(row).typedInput({default:'str',types:['msg','flow','global','str','num','jsonata','env',previousValueType]});
|
||||
function createValueField(row, defaultType){
|
||||
return $('<input/>',{class:"node-input-rule-value",type:"text",style:"width: 100%;"}).appendTo(row)
|
||||
.typedInput({default:defaultType||'str',types:['msg','flow','global','str','num','jsonata','env',previousValueType]});
|
||||
}
|
||||
|
||||
function createNumValueField(row){
|
||||
return $('<input/>',{class:"node-input-rule-num-value",type:"text",style:"width: 100%;"}).appendTo(row).typedInput({default:'num',types:['flow','global','num','jsonata','env']});
|
||||
function createNumValueField(row, defaultType){
|
||||
return $('<input/>',{class:"node-input-rule-num-value",type:"text",style:"width: 100%;"}).appendTo(row)
|
||||
.typedInput({default:defaultType||'num',types:['flow','global','num','jsonata','env']});
|
||||
}
|
||||
|
||||
function createExpValueField(row){
|
||||
return $('<input/>',{class:"node-input-rule-exp-value",type:"text",style:"width: 100%;"}).appendTo(row).typedInput({default:'jsonata',types:['jsonata']});
|
||||
return $('<input/>',{class:"node-input-rule-exp-value",type:"text",style:"width: 100%;"}).appendTo(row)
|
||||
.typedInput({default:'jsonata',types:['jsonata']});
|
||||
}
|
||||
|
||||
function createBtwnValueField(row){
|
||||
return $('<input/>',{class:"node-input-rule-btwn-value",type:"text",style:"width: 100%;"}).appendTo(row).typedInput({default:'num',types:['msg','flow','global','str','num','jsonata','env',previousValueType]});
|
||||
function createBtwnValueField(row, defaultType){
|
||||
return $('<input/>',{class:"node-input-rule-btwn-value",type:"text",style:"width: 100%;"}).appendTo(row)
|
||||
.typedInput({default:defaultType||'num',types:['msg','flow','global','str','num','jsonata','env',previousValueType]});
|
||||
}
|
||||
|
||||
function createBtwnValue2Field(row3, andLabel){
|
||||
function createBtwnValue2Field(row3, andLabel, defaultType){
|
||||
$('<div/>',{class:"node-input-rule-btwn-label", style:"width: 120px; text-align: right;"}).text(" "+andLabel+" ").appendTo(row3);
|
||||
var row3InputCell = $('<div/>',{style:"flex-grow:1; margin-left: 5px;"}).appendTo(row3);
|
||||
return $('<input/>',{class:"node-input-rule-btwn-value2",type:"text",style:"width: 100%"}).appendTo(row3InputCell).typedInput({default:'num',types:['msg','flow','global','str','num','jsonata','env',previousValueType]});
|
||||
return $('<input/>',{class:"node-input-rule-btwn-value2",type:"text",style:"width: 100%"}).appendTo(row3InputCell)
|
||||
.typedInput({default:defaultType||'num',types:['msg','flow','global','str','num','jsonata','env',previousValueType]});
|
||||
}
|
||||
|
||||
function createTypeValueField(){
|
||||
return $('<input/>',{class:"node-input-rule-type-value",type:"text",style:"width: 100%;"}).appendTo(row).typedInput({default:'string',types:[
|
||||
function createTypeValueField(row, defaultType){
|
||||
return $('<input/>',{class:"node-input-rule-type-value",type:"text",style:"width: 100%;"}).appendTo(row).typedInput({default:defaultType || 'string',types:[
|
||||
{value:"string",label:RED._("common.type.string"),hasValue:false,icon:"red/images/typedInput/az.png"},
|
||||
{value:"number",label:RED._("common.type.number"),hasValue:false,icon:"red/images/typedInput/09.png"},
|
||||
{value:"boolean",label:RED._("common.type.boolean"),hasValue:false,icon:"red/images/typedInput/bool.png"},
|
||||
@@ -211,6 +216,7 @@
|
||||
var lastRule = $("#node-input-rule-container").editableList('getItemAt',i-1);
|
||||
var exportedRule = exportRule(lastRule.element);
|
||||
opt.r.vt = exportedRule.vt;
|
||||
opt.r.v = "";
|
||||
// We could copy the value over as well and preselect it (see the 'activeElement' code below)
|
||||
// But not sure that feels right. Is copying over the last value 'expected' behaviour?
|
||||
// It would make sense for an explicit 'copy' action, but not sure where the copy button would
|
||||
@@ -278,24 +284,12 @@
|
||||
selectField.on("change", function() {
|
||||
var fieldToFocus;
|
||||
var type = selectField.val();
|
||||
if (valueField){
|
||||
valueField.typedInput('hide');
|
||||
}
|
||||
if (expValueField){
|
||||
expValueField.typedInput('hide');
|
||||
}
|
||||
if (numValueField){
|
||||
numValueField.typedInput('hide');
|
||||
}
|
||||
if (typeValueField){
|
||||
typeValueField.typedInput('hide');
|
||||
}
|
||||
if (btwnValueField){
|
||||
btwnValueField.typedInput('hide');
|
||||
}
|
||||
if (btwnValue2Field){
|
||||
btwnValue2Field.typedInput('hide');
|
||||
}
|
||||
if (valueField) { valueField.typedInput('hide'); }
|
||||
if (expValueField) { expValueField.typedInput('hide'); }
|
||||
if (numValueField) { numValueField.typedInput('hide'); }
|
||||
if (typeValueField) { typeValueField.typedInput('hide'); }
|
||||
if (btwnValueField) { btwnValueField.typedInput('hide'); }
|
||||
if (btwnValue2Field) { btwnValue2Field.typedInput('hide'); }
|
||||
|
||||
if ((type === "btwn") || (type === "index")) {
|
||||
if (!btwnValueField){
|
||||
@@ -318,7 +312,7 @@
|
||||
|
||||
} else if (type === "istype") {
|
||||
if (!typeValueField){
|
||||
typeValueField = createTypeValueField();
|
||||
typeValueField = createTypeValueField(rowInputCell);
|
||||
}
|
||||
typeValueField.typedInput('show');
|
||||
fieldToFocus = typeValueField;
|
||||
@@ -361,48 +355,26 @@
|
||||
// }
|
||||
});
|
||||
selectField.val(rule.t);
|
||||
if ((rule.t == "btwn") || (rule.t == "index")) {
|
||||
if (!btwnValueField){
|
||||
btwnValueField = createBtwnValueField(rowInputCell);
|
||||
}
|
||||
btwnValueField.typedInput('value',rule.v);
|
||||
btwnValueField.typedInput('type',rule.vt||'num');
|
||||
|
||||
if (!btwnValue2Field){
|
||||
btwnValue2Field = createBtwnValue2Field(row3, andLabel);
|
||||
}
|
||||
if ((rule.t == "btwn") || (rule.t == "index")) {
|
||||
btwnValueField = createBtwnValueField(rowInputCell,rule.vt||'num');
|
||||
btwnValueField.typedInput('value',rule.v);
|
||||
btwnValue2Field = createBtwnValue2Field(row3, andLabel,rule.v2t||'num');
|
||||
btwnValue2Field.typedInput('value',rule.v2);
|
||||
btwnValue2Field.typedInput('type',rule.v2t||'num');
|
||||
} else if ((rule.t === "head") || (rule.t === "tail")) {
|
||||
if (!numValueField){
|
||||
numValueField = createNumValueField(row);
|
||||
}
|
||||
numValueField = createNumValueField(rowInputCell,rule.vt||'num');
|
||||
numValueField.typedInput('value',rule.v);
|
||||
numValueField.typedInput('type',rule.vt||'num');
|
||||
} else if (rule.t === "istype") {
|
||||
if (!typeValueField){
|
||||
typeValueField =createTypeValueField();
|
||||
}
|
||||
typeValueField = createTypeValueField(rowInputCell,rule.vt);
|
||||
typeValueField.typedInput('value',rule.vt);
|
||||
typeValueField.typedInput('type',rule.vt);
|
||||
} else if (rule.t === "jsonata_exp") {
|
||||
if (!expValueField){
|
||||
expValueField = createExpValueField(row);
|
||||
}
|
||||
expValueField = createExpValueField(rowInputCell,rule.vt||'jsonata');
|
||||
expValueField.typedInput('value',rule.v);
|
||||
expValueField.typedInput('type',rule.vt||'jsonata');
|
||||
} else if (typeof rule.v != "undefined") {
|
||||
if (!valueField){
|
||||
valueField = createValueField(rowInputCell);
|
||||
}
|
||||
valueField = createValueField(rowInputCell,rule.vt||'str');
|
||||
valueField.typedInput('value',rule.v);
|
||||
valueField.typedInput('type',rule.vt||'str');
|
||||
}
|
||||
if (rule.case) {
|
||||
caseSensitive.prop('checked',true);
|
||||
} else {
|
||||
caseSensitive.prop('checked',false);
|
||||
}
|
||||
caseSensitive.prop('checked',!!rule.case);
|
||||
selectField.change();
|
||||
|
||||
var currentOutputs = JSON.parse(outputCount.val()||"{}");
|
||||
|
||||
@@ -115,12 +115,12 @@
|
||||
var regex = this._("change.label.regex");
|
||||
var deepCopyLabel = this._("change.label.deepCopy");
|
||||
|
||||
function createPropertyValue(row2_1,row2_2) {
|
||||
function createPropertyValue(row2_1, row2_2, defaultType) {
|
||||
var propValInput = $('<input/>',{class:"node-input-rule-property-value",type:"text"})
|
||||
.appendTo(row2_1)
|
||||
.typedInput({default:'str',types:['msg','flow','global','str','num','bool','json','bin','date','jsonata','env']});
|
||||
.typedInput({default:defaultType||'str',types:['msg','flow','global','str','num','bool','json','bin','date','jsonata','env']});
|
||||
|
||||
var dcLabel = $('<label style="padding-left: 130px; display: flex; align-items: center "></label>').appendTo(row2_2);
|
||||
var dcLabel = $('<label style="padding-left: 130px;"></label>').appendTo(row2_2);
|
||||
var deepCopy = $('<input type="checkbox" class="node-input-rule-property-deepCopy" style="width: auto; margin: 0 6px 0 0">').appendTo(dcLabel)
|
||||
$('<span>').text(deepCopyLabel).appendTo(dcLabel)
|
||||
|
||||
@@ -129,20 +129,20 @@
|
||||
})
|
||||
return [propValInput, deepCopy];
|
||||
}
|
||||
function createFromValue(row3_1) {
|
||||
function createFromValue(row3_1, defaultType) {
|
||||
return $('<input/>',{class:"node-input-rule-property-search-value",type:"text"})
|
||||
.appendTo(row3_1)
|
||||
.typedInput({default:'str',types:['msg','flow','global','str','re','num','bool','env']});
|
||||
.typedInput({default:defaultType||'str',types:['msg','flow','global','str','re','num','bool','env']});
|
||||
}
|
||||
function createToValue(row3_2) {
|
||||
function createToValue(row3_2, defaultType) {
|
||||
return $('<input/>',{class:"node-input-rule-property-replace-value",type:"text"})
|
||||
.appendTo(row3_2)
|
||||
.typedInput({default:'str',types:['msg','flow','global','str','num','bool','json','bin','env']});
|
||||
.typedInput({default:defaultType||'str',types:['msg','flow','global','str','num','bool','json','bin','env']});
|
||||
}
|
||||
function createMoveValue(row4) {
|
||||
function createMoveValue(row4, defaultType) {
|
||||
return $('<input/>',{class:"node-input-rule-property-move-value",type:"text"})
|
||||
.appendTo(row4)
|
||||
.typedInput({default:'msg',types:['msg','flow','global']});
|
||||
.typedInput({default:defaultType||'msg',types:['msg','flow','global']});
|
||||
}
|
||||
|
||||
$('#node-input-rule-container').css('min-height','150px').css('min-width','450px').editableList({
|
||||
@@ -268,33 +268,22 @@
|
||||
propertyName.typedInput('value',rule.p);
|
||||
propertyName.typedInput('type',rule.pt);
|
||||
if (rule.t == "set") {
|
||||
if(!propertyValue) {
|
||||
var parts = createPropertyValue(row2_1, row2_2);
|
||||
propertyValue = parts[0];
|
||||
deepCopy = parts[1];
|
||||
}
|
||||
var parts = createPropertyValue(row2_1, row2_2, rule.tot);
|
||||
propertyValue = parts[0];
|
||||
deepCopy = parts[1];
|
||||
propertyValue.typedInput('value',rule.to);
|
||||
propertyValue.typedInput('type',rule.tot);
|
||||
deepCopy.prop("checked", !!rule.dc);
|
||||
}
|
||||
if (rule.t == "move") {
|
||||
if(!moveValue) {
|
||||
moveValue = createMoveValue(row4);
|
||||
}
|
||||
moveValue = createMoveValue(row4,rule.tot);
|
||||
moveValue.typedInput('value',rule.to);
|
||||
moveValue.typedInput('type',rule.tot);
|
||||
}
|
||||
if (rule.t == "change") {
|
||||
if(!fromValue) {
|
||||
fromValue = createFromValue(row3_1);
|
||||
}
|
||||
fromValue = createFromValue(row3_1, rule.fromt);
|
||||
fromValue.typedInput('value',rule.from);
|
||||
fromValue.typedInput('type',rule.fromt);
|
||||
if (!toValue) {
|
||||
toValue = createToValue(row3_2);
|
||||
}
|
||||
|
||||
toValue = createToValue(row3_2,rule.tot);
|
||||
toValue.typedInput('value',rule.to);
|
||||
toValue.typedInput('type',rule.tot);
|
||||
}
|
||||
selectField.change();
|
||||
container[0].appendChild(fragment);
|
||||
|
||||
@@ -372,6 +372,7 @@ module.exports = function(RED) {
|
||||
hit = false;
|
||||
for (var b in node.buffer) { // check if already in queue
|
||||
if (msg.topic === node.buffer[b].msg.topic) {
|
||||
if (node.outputs === 2) { send([null,node.buffer[b].msg]) }
|
||||
node.buffer[b].done();
|
||||
node.buffer[b] = {msg, send, done}; // if so - replace existing entry
|
||||
hit = true;
|
||||
|
||||
@@ -1040,7 +1040,7 @@ module.exports = function(RED) {
|
||||
|
||||
//subscribe to sub.topic & hook up subscriptionHandler
|
||||
node.brokerConn.subscribe(sub.topic, options, function (topic, payload, packet) {
|
||||
subscriptionHandler(node, sub.datatype, topic, payload, packet);
|
||||
subscriptionHandler(node, sub.datatype || node.datatype, topic, payload, packet);
|
||||
}, node.id);
|
||||
node.dynamicSubs[sub.topic] = sub; //save for later unsubscription & 'list' action
|
||||
})
|
||||
|
||||
@@ -298,18 +298,14 @@ in your Node-RED user directory (${RED.settings.userDir}).
|
||||
}
|
||||
if (Object.keys(this.credentials).length != 0) {
|
||||
if (this.authType === "basic") {
|
||||
// Workaround for https://github.com/sindresorhus/got/issues/1169
|
||||
var cred = ""
|
||||
if (this.credentials.user) {
|
||||
// opts.username = this.credentials.user;
|
||||
cred = this.credentials.user
|
||||
}
|
||||
if (this.credentials.password) {
|
||||
// opts.password = this.credentials.password;
|
||||
cred += ":" + this.credentials.password
|
||||
// Workaround for https://github.com/sindresorhus/got/issues/1169 (fixed in got v12)
|
||||
// var cred = ""
|
||||
if (this.credentials.user || this.credentials.password) {
|
||||
// cred = `${this.credentials.user}:${this.credentials.password}`;
|
||||
opts.headers.Authorization = "Basic " + Buffer.from(`${this.credentials.user}:${this.credentials.password}`).toString("base64");
|
||||
}
|
||||
// build own basic auth header
|
||||
opts.headers.Authorization = "Basic " + Buffer.from(cred).toString("base64");
|
||||
// opts.headers.Authorization = "Basic " + Buffer.from(cred).toString("base64");
|
||||
} else if (this.authType === "digest") {
|
||||
let digestCreds = this.credentials;
|
||||
let sentCreds = false;
|
||||
|
||||
@@ -196,6 +196,13 @@
|
||||
</div>
|
||||
<div class="form-row">
|
||||
<label for="node-input-out"><i class="fa fa-sign-out"></i> <span data-i18n="tcpin.label.return"></span></label>
|
||||
<select type="text" id="node-input-ret" style="width:54%;">
|
||||
<option value="buffer" data-i18n="tcpin.output.buffer"></option>
|
||||
<option value="string" data-i18n="tcpin.output.string"></option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="form-row">
|
||||
<label for="node-input-out"> </label>
|
||||
<select type="text" id="node-input-out" style="width:54%;">
|
||||
<option value="time" data-i18n="tcpin.return.timeout"></option>
|
||||
<option value="char" data-i18n="tcpin.return.character"></option>
|
||||
@@ -220,6 +227,7 @@
|
||||
server: {value:""},
|
||||
port: {value:"",validate:RED.validators.regex(/^(\d*|)$/)},
|
||||
out: {value:"time",required:true},
|
||||
ret: {value:"buffer"},
|
||||
splitc: {value:"0",required:true},
|
||||
name: {value:""}
|
||||
},
|
||||
@@ -234,6 +242,10 @@
|
||||
},
|
||||
oneditprepare: function() {
|
||||
var previous = null;
|
||||
if ($("#node-input-ret").val() == undefined) {
|
||||
$("#node-input-ret").val("buffer");
|
||||
this.ret = "buffer";
|
||||
}
|
||||
$("#node-input-out").on('focus', function () { previous = this.value; }).on("change", function() {
|
||||
$("#node-input-splitc").show();
|
||||
if (previous === null) { previous = $("#node-input-out").val(); }
|
||||
|
||||
@@ -311,7 +311,7 @@ module.exports = function(RED) {
|
||||
}
|
||||
setupTcpClient();
|
||||
|
||||
node.on("input", function(msg,nodeSend,nodeDone) {
|
||||
node.on("input", function(msg, nodeSend, nodeDone) {
|
||||
if (node.connected && msg.payload != null) {
|
||||
if (Buffer.isBuffer(msg.payload)) {
|
||||
client.write(msg.payload);
|
||||
@@ -444,6 +444,7 @@ module.exports = function(RED) {
|
||||
this.server = n.server;
|
||||
this.port = Number(n.port);
|
||||
this.out = n.out;
|
||||
this.ret = n.ret || "buffer";
|
||||
this.splitc = n.splitc;
|
||||
|
||||
if (this.out === "immed") { this.splitc = -1; this.out = "time"; }
|
||||
@@ -488,7 +489,7 @@ module.exports = function(RED) {
|
||||
connected: false,
|
||||
connecting: false
|
||||
};
|
||||
enqueue(clients[connection_id].msgQueue, {msg:msg,nodeSend:nodeSend, nodeDone: nodeDone});
|
||||
enqueue(clients[connection_id].msgQueue, {msg:msg, nodeSend:nodeSend, nodeDone:nodeDone});
|
||||
clients[connection_id].lastMsg = msg;
|
||||
|
||||
if (!clients[connection_id].connecting && !clients[connection_id].connected) {
|
||||
@@ -532,8 +533,12 @@ module.exports = function(RED) {
|
||||
if (node.out === "sit") { // if we are staying connected just send the buffer
|
||||
if (clients[connection_id]) {
|
||||
const msg = clients[connection_id].lastMsg || {};
|
||||
msg.payload = data;
|
||||
nodeSend(RED.util.cloneMessage(msg));
|
||||
msg.payload = RED.util.cloneMessage(data);
|
||||
if (node.ret === "string") {
|
||||
try { msg.payload = msg.payload.toString(); }
|
||||
catch(e) { node.error("Failed to create string", msg); }
|
||||
}
|
||||
nodeSend(msg);
|
||||
}
|
||||
}
|
||||
// else if (node.splitc === 0) {
|
||||
@@ -556,6 +561,10 @@ module.exports = function(RED) {
|
||||
const msg = clients[connection_id].lastMsg || {};
|
||||
msg.payload = Buffer.alloc(i+1);
|
||||
buf.copy(msg.payload,0,0,i+1);
|
||||
if (node.ret === "string") {
|
||||
try { msg.payload = msg.payload.toString(); }
|
||||
catch(e) { node.error("Failed to create string", msg); }
|
||||
}
|
||||
nodeSend(msg);
|
||||
if (clients[connection_id].client) {
|
||||
node.status({});
|
||||
@@ -578,6 +587,10 @@ module.exports = function(RED) {
|
||||
const msg = clients[connection_id].lastMsg || {};
|
||||
msg.payload = Buffer.alloc(i);
|
||||
buf.copy(msg.payload,0,0,i);
|
||||
if (node.ret === "string") {
|
||||
try { msg.payload = msg.payload.toString(); }
|
||||
catch(e) { node.error("Failed to create string", msg); }
|
||||
}
|
||||
nodeSend(msg);
|
||||
if (clients[connection_id].client) {
|
||||
node.status({});
|
||||
@@ -597,6 +610,10 @@ module.exports = function(RED) {
|
||||
const msg = clients[connection_id].lastMsg || {};
|
||||
msg.payload = Buffer.alloc(i);
|
||||
buf.copy(msg.payload,0,0,i);
|
||||
if (node.ret === "string") {
|
||||
try { msg.payload = msg.payload.toString(); }
|
||||
catch(e) { node.error("Failed to create string", msg); }
|
||||
}
|
||||
nodeSend(msg);
|
||||
if (clients[connection_id].client) {
|
||||
node.status({});
|
||||
|
||||
@@ -25,7 +25,7 @@
|
||||
<dd>Optional nutzbare Nachrichten-Eigenschaft.</dd>
|
||||
</dl>
|
||||
<h3>Details</h3>
|
||||
<p>Der <span style="background-color:Gainsboro">inject</span>-Node kann einen Flow mit einstellbaren Nutzdaten (Payload) starten.
|
||||
<p>Der inject-Node kann einen Flow mit einstellbaren Nutzdaten (Payload) starten.
|
||||
Der voreingestellte Payload ist die aktuelle Zeit als Zeitstempel in Millisekunden
|
||||
seit Beginn der Unix-Zeitrechnung (1. Januar 1970 UTC).</p>
|
||||
<p>Der Node unterstützt auch die Injektion von Zeichenfolgen, Zahlenwerten, Booleschen Werten,
|
||||
@@ -34,7 +34,7 @@
|
||||
Er kann auch in regelmäßigen Intervallen oder nach einem Zeitplan injizieren.</p>
|
||||
<p>Er kann auch so eingestellt werden, dass er jedes Mal einen Wert injiziert, wenn der Flow gestartet wird.</p>
|
||||
<p>Das maximal einstellbare Intervall beträgt etwa 596 Stunden bzw. 24 Tage.
|
||||
Wenn jedoch Intervalle größer als 24h benötigt werden, sollte ein <span style="background-color:Gainsboro">scheduler</span>-Node verwendet werden,
|
||||
Wenn jedoch Intervalle größer als 24h benötigt werden, sollte ein scheduler-Node verwendet werden,
|
||||
der mit Stromausfällen und Neustarts besser umgehen kann.</p>
|
||||
<p><b>Hinweis</b>: Die Optionen <i>"Intervall zwischen Uhrzeiten"</i> und <i>"Täglicher Zeitpunkt"</i>
|
||||
verwenden das Standard-Cron-System.</p>
|
||||
|
||||
@@ -23,10 +23,10 @@
|
||||
<p>JavaScript-Objekte und -Arrays können nach Bedarf ein- und ausgeblendet werden.
|
||||
Binäre Puffer-Objekte (buffer objects) können nach Möglichkeit als Rohdaten oder als Zeichenfolge (string) angezeigt werden.</p>
|
||||
<p>Neben der eigentlichen Nachricht werden im Debug-Tab auch der Empfangszeitpunkt,
|
||||
der empfangende <span style="background-color:Gainsboro">debug</span>-Node, sowie Name und Typ der Nachricht protokolliert.
|
||||
Durch Klicken auf die Node-ID wird der entsprechende <span style="background-color:Gainsboro">debug</span>-Node im Arbeitsbereich angezeigt.</p>
|
||||
<p>Die Schaltfläche des <span style="background-color:Gainsboro">debug</span>-Nodes kann verwendet werden, um die Debug-Ausgabe ein- und auszuschalten.
|
||||
Es ist empfehlenswert, alle nicht verwendeten <span style="background-color:Gainsboro">debug</span>-Nodes zu deaktivieren oder gleich zu entfernen.</p>
|
||||
<p>Der <span style="background-color:Gainsboro">debug</span>-Node kann auch so eingestellt werden, dass außerdem alle Nachrichten in der Systemkonsole ausgegeben und/oder
|
||||
als kurze Statustexte (max. 32 Zeichen) unter dem <span style="background-color:Gainsboro">debug</span>-Node angezeigt werden.</p>
|
||||
der empfangende debug-Node, sowie Name und Typ der Nachricht protokolliert.
|
||||
Durch Klicken auf die Node-ID wird der entsprechende debug-Node im Arbeitsbereich angezeigt.</p>
|
||||
<p>Die Schaltfläche des debug-Nodes kann verwendet werden, um die Debug-Ausgabe ein- und auszuschalten.
|
||||
Es ist empfehlenswert, alle nicht verwendeten debug-Nodes zu deaktivieren oder gleich zu entfernen.</p>
|
||||
<p>Der debug-Node kann auch so eingestellt werden, dass außerdem alle Nachrichten in der Systemkonsole ausgegeben und/oder
|
||||
als kurze Statustexte (max. 32 Zeichen) unter dem debug-Node angezeigt werden.</p>
|
||||
</script>
|
||||
|
||||
@@ -18,11 +18,11 @@
|
||||
<p>Anstoß eines weiteren Flows, wenn ein anderer Node seine Nachrichtenbearbeitung abgeschlossen hat.</p>
|
||||
<h3>Details</h3>
|
||||
<p>Wenn ein Node die Bearbeitung seiner Nachrichten abgeschlossen hat,
|
||||
kann der <span style="background-color:Gainsboro">complete</span>-Node dazu benutzt werden, einen weiteren Flow anzustoßen.</p>
|
||||
kann der complete-Node dazu benutzt werden, einen weiteren Flow anzustoßen.</p>
|
||||
<p>Der Node kann z.B. mit einem anderen Node ohne Ausgang verknüpft werden
|
||||
(z.B. E-Mail-Sende-Node), um den Flow fortzusetzen.</p>
|
||||
<p>Im Node werden dazu die zu überwachenden Nodes des selben Flows ausgewählt.
|
||||
Im Gegensatz zum <span style="background-color:Gainsboro">catch</span>-Node besteht hier jedoch nicht die Auswahlmöglichkeit aller Nodes des Flows.</p>
|
||||
Im Gegensatz zum catch-Node besteht hier jedoch nicht die Auswahlmöglichkeit aller Nodes des Flows.</p>
|
||||
<p>Nicht alle Nodes können diesen Node anstoßen.
|
||||
Es hängt davon ab, ob die auslösenden Knoten diese Funktion unterstützen,
|
||||
welche erst mit Node-RED 1.0 eingeführt wurde.</p>
|
||||
|
||||
@@ -29,13 +29,13 @@
|
||||
</dl>
|
||||
<h3>Details</h3>
|
||||
<p>Wenn ein Node bei der Verarbeitung einer Nachricht einen Fehler verursacht, wird der Flow in der Regel angehalten.
|
||||
Der <span style="background-color:Gainsboro">catch</span>-Node kann verwendet werden, um diese Fehler abzufangen und sie mit einem dedizierten Flow zu bearbeiten.</p>
|
||||
Der catch-Node kann verwendet werden, um diese Fehler abzufangen und sie mit einem dedizierten Flow zu bearbeiten.</p>
|
||||
<p>Der Node fängt standardmäßig die Fehler aller Nodes im selben Flow ab.
|
||||
Alternativ kann er auch an bestimmte Nodes gebunden werden.</p>
|
||||
<p>Wenn ein Fehler ausgelöst wird, empfangen alle angebundenen <span style="background-color:Gainsboro">catch</span>-Nodes die Fehlermeldung.</p>
|
||||
<p>Wenn ein Fehler in einem Subflow ausgelöst wird, wird der Fehler von einem <span style="background-color:Gainsboro">catch</span>-Node
|
||||
<p>Wenn ein Fehler ausgelöst wird, empfangen alle angebundenen catch-Nodes die Fehlermeldung.</p>
|
||||
<p>Wenn ein Fehler in einem Subflow ausgelöst wird, wird der Fehler von einem catch-Node
|
||||
innerhalb des Subflows abgefangen.
|
||||
Wenn im Subflow keine <span style="background-color:Gainsboro">catch</span>-Nodes vorhanden sind, wird die Fehlermeldung eine Ebene höher zum Flow weitergereicht,
|
||||
Wenn im Subflow keine catch-Nodes vorhanden sind, wird die Fehlermeldung eine Ebene höher zum Flow weitergereicht,
|
||||
in der sich die Subflow-Instanz befindet.</p>
|
||||
<p>Wenn die Nachricht bereits über eine <code>error</code>-Eigenschaft verfügt, wird sie nach <code>_error</code> kopiert.</p>
|
||||
</script>
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
<script type="text/html" data-help-name="link in">
|
||||
<p>Erstellung virtueller Verbindungen (Links) zwischen Flows.</p>
|
||||
<h3>Details</h3>
|
||||
<p>Der Node kann mit jedem beliebigen <span style="background-color:Gainsboro">link out</span>-Node in einen beliebigen Flow-Tab verlinkt werden.
|
||||
<p>Der Node kann mit jedem beliebigen link out-Node in einen beliebigen Flow-Tab verlinkt werden.
|
||||
Sobald sie verlinkt sind, verhalten sie sich so, als wären sie direkt miteinander verbunden.</p>
|
||||
<p>Die Links zwischen Link-Nodes werden nur angezeigt, wenn ein Link-Node ausgewählt ist.
|
||||
Wenn Links zu anderen Flow-Tabs vorhanden sind, werden virtuelle Link-Nodes als Gegenparts angezeigt,
|
||||
@@ -28,7 +28,7 @@
|
||||
<script type="text/html" data-help-name="link out">
|
||||
<p>Erstellung virtueller Verbindungen (Links) zwischen Flows.</p>
|
||||
<h3>Details</h3>
|
||||
<p>Der Node kann mit jedem beliebigen <span style="background-color:Gainsboro">link in</span>-Node in einen beliebigen Flow-Tab verlinkt werden.
|
||||
<p>Der Node kann mit jedem beliebigen link in-Node in einen beliebigen Flow-Tab verlinkt werden.
|
||||
Sobald sie verlinkt sind, verhalten sie sich so, als wären sie direkt miteinander verbunden.</p>
|
||||
<p>Die Links zwischen Link-Nodes werden nur angezeigt, wenn ein Link-Node ausgewählt ist.
|
||||
Wenn Links zu anderen Flow-Tabs vorhanden sind, werden virtuelle Link-Nodes als Gegenparts angezeigt,
|
||||
|
||||
@@ -47,7 +47,7 @@
|
||||
<li><code>node.error("Fehlermeldungstext")</code></li>
|
||||
</ul>
|
||||
</p>
|
||||
<p>Der <span style="background-color:Gainsboro">catch</span>-Node kann auch zur Bearbeitung von Fehlern verwendet werden.
|
||||
<p>Der catch-Node kann auch zur Bearbeitung von Fehlern verwendet werden.
|
||||
Er wird aufgerufen, indem <code>msg</code> als zweites Argument an <code>node.error</code> übergeben wird:</p>
|
||||
<pre>node.error("Fehlermeldungstext" ,msg);</pre>
|
||||
<h4><b>Zugriff auf Node-Informationen</b></h4>
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
<ol>
|
||||
<li><b>value rules</b>: Regeln werden hinsichtlich einer eingestellten Eigenschaft ausgewertet</li>
|
||||
<li><b>sequence rules</b>: Regeln beziehen sich auf Nachrichtensequenzen,
|
||||
wie sie beispielsweise durch den <span style="background-color:Gainsboro">split</span>-Node erzeugt werden</li>
|
||||
wie sie beispielsweise durch den split-Node erzeugt werden</li>
|
||||
<li>Ein <b>JSONata-Ausdruck</b> kann die gesamte Eingangsnachricht auswerten und einen <code>true</code>-Wert zurückliefern,
|
||||
um eine Regelerfüllung zu signalisieren</li>
|
||||
<li>Die <b>ansonsten</b>-Regel wird angewendet, wenn keine vorhergehende Regel übereinstimmt</li>
|
||||
|
||||
@@ -25,9 +25,9 @@
|
||||
<dt class="optional">payload <span class="property-type">string</span></dt>
|
||||
<dd>Wird an auszuführenden Befehl angehängt, sofern im Node aktiviert.</dd>
|
||||
<dt class="optional">kill <span class="property-type">string</span></dt>
|
||||
<dd>Typ des Kill-Signals, das an den zu beendenden <span style="background-color:Gainsboro">exec</span>-Node-Prozess gesendet wird.</dd>
|
||||
<dd>Typ des Kill-Signals, das an den zu beendenden exec-Node-Prozess gesendet wird.</dd>
|
||||
<dt class="optional">pid <span class="property-type">number | string</span></dt>
|
||||
<dd>Prozess-ID des zu beendenden <span style="background-color:Gainsboro">exec</span>-Node-Prozesses.</dd>
|
||||
<dd>Prozess-ID des zu beendenden exec-Node-Prozesses.</dd>
|
||||
</dl>
|
||||
<h3>Ausgangsdaten</h3>
|
||||
<ol class="node-ports">
|
||||
@@ -75,7 +75,7 @@
|
||||
<p>Die zurückgegebenen Daten (Payload) sind in der Regel eine <i>Zeichenfolge (string)</i>,
|
||||
außer es werden nicht UTF-8-Zeichen wie bei einem <i>binären Puffer (buffer)</i> erkannt.</p>
|
||||
<p>Bei einem aktiven Node werden Status und die PID angezeigt.
|
||||
Änderungen können mittels <span style="background-color:Gainsboro">status</span>-Node gelesen werden.</p>
|
||||
Änderungen können mittels status-Node gelesen werden.</p>
|
||||
<h4><b>Prozesse beenden</b></h4>
|
||||
<p>Durch Senden von <code>msg.kill</code> wird ein einzelner aktiver Prozess beendet.
|
||||
<code>msg.kill</code> sollte als Zeichenfolge (string) den Signaltyp enthalten,
|
||||
|
||||
@@ -94,7 +94,7 @@
|
||||
"label": {
|
||||
"source": "Fehler abfangen von",
|
||||
"selectAll": "Alles auswählen",
|
||||
"uncaught": "Fehler ignorieren, die von anderen <span style=\"background-color:Gainsboro\">catch</span>-Nodes behandelt wurden"
|
||||
"uncaught": "Fehler ignorieren, die von anderen catch-Nodes behandelt wurden"
|
||||
},
|
||||
"scope": {
|
||||
"all": "allen Nodes",
|
||||
@@ -475,12 +475,12 @@
|
||||
"json": "Ein parsed JSON-Objekt",
|
||||
"tip": {
|
||||
"in": "Die URL ist relativ zu ",
|
||||
"res": "Die an diesen Node gesendeten Nachrichten <b>müssen</b> von einem <span style=\"background-color:Gainsboro\">http in</span>-Node stammen",
|
||||
"res": "Die an diesen Node gesendeten Nachrichten <b>müssen</b> von einem http in-Node stammen",
|
||||
"req": "Tipp: Wenn die JSON-Syntax-Analyse fehlschlägt, wird die abgerufene Zeichenfolge zurückgegeben, wie sie ist."
|
||||
},
|
||||
"httpreq": "http request",
|
||||
"errors": {
|
||||
"not-created": "<span style=\"background-color:Gainsboro\">http in</span>-Node kann nicht erstellt werden, wenn httpNodeRoot auf 'false' gesetzt ist.",
|
||||
"not-created": "http in-Node kann nicht erstellt werden, wenn httpNodeRoot auf 'false' gesetzt ist.",
|
||||
"missing-path": "Fehlender Pfad",
|
||||
"no-response": "Kein Antwort-Objekt",
|
||||
"json-error": "JSON-Parse-Fehler",
|
||||
@@ -684,7 +684,7 @@
|
||||
},
|
||||
"errors": {
|
||||
"invalid-expr": "Ungültiger JSONata-Ausdruck: __error__",
|
||||
"too-many": "Zu viele anstehende Nachrichten im <span style=\"background-color:Gainsboro\">switch</span>-Node"
|
||||
"too-many": "Zu viele anstehende Nachrichten im switch-Node"
|
||||
}
|
||||
},
|
||||
"change": {
|
||||
@@ -940,8 +940,8 @@
|
||||
"afterTimeout": "Bei Zeitablauf nach erster Nachricht von",
|
||||
"seconds": "Sekunden",
|
||||
"complete": "Nach Nachricht mit <code>msg.complete</code>-Eigenschaft",
|
||||
"tip": "Dieser Modus setzt voraus, dass dieser Node entweder mit einem <span style=\"background-color:Gainsboro\">split</span>-Node kombiniert ist oder dass die empfangenen Nachrichten über eine ordnungsgemäß konfigurierte <code>msg.parts</code>-Eigenschaft verfügen.",
|
||||
"too-many": "Zu viele anstehende Nachrichten im <span style=\"background-color:Gainsboro\">join</span>-Node",
|
||||
"tip": "Dieser Modus setzt voraus, dass dieser Node entweder mit einem split-Node kombiniert ist oder dass die empfangenen Nachrichten über eine ordnungsgemäß konfigurierte <code>msg.parts</code>-Eigenschaft verfügen.",
|
||||
"too-many": "Zu viele anstehende Nachrichten im join-Node",
|
||||
"merge": {
|
||||
"topics-label": "Zusammengeführte Topics",
|
||||
"topics": "Topics",
|
||||
@@ -970,9 +970,9 @@
|
||||
"ascending": "aufsteigend",
|
||||
"descending": "absteigend",
|
||||
"as-number": "als Zahlenwert",
|
||||
"invalid-exp": "Ungültiger JSONata-Ausdruck in <span style=\"background-color:Gainsboro\">sort</span>-Node: __message__",
|
||||
"too-many": "Zu viele anstehende Nachrichten in <span style=\"background-color:Gainsboro\">sort</span>-Node",
|
||||
"clear": "Anstehende Nachricht in <span style=\"background-color:Gainsboro\">sort</span>-Node löschen"
|
||||
"invalid-exp": "Ungültiger JSONata-Ausdruck in sort-Node: __message__",
|
||||
"too-many": "Zu viele anstehende Nachrichten in sort-Node",
|
||||
"clear": "Anstehende Nachricht in sort-Node löschen"
|
||||
},
|
||||
"batch": {
|
||||
"batch": "batch",
|
||||
@@ -997,7 +997,7 @@
|
||||
"topics-label": "Topics",
|
||||
"topic": "Topic"
|
||||
},
|
||||
"too-many": "Zu viele anstehende Nachrichten im <span style=\"background-color:Gainsboro\">batch</span>-Node",
|
||||
"too-many": "Zu viele anstehende Nachrichten im batch-Node",
|
||||
"unexpected": "Unerwarteter Modus",
|
||||
"no-parts": "Keine parts-Eigenschaft in Nachricht"
|
||||
},
|
||||
|
||||
@@ -94,8 +94,8 @@
|
||||
<script type="text/html" data-help-name="mqtt-broker">
|
||||
<p>Konfiguration der Verbindung zu einem MQTT-Broker.</p>
|
||||
<p>Diese Konfiguration erstellt eine einzelne Verbindung zu einem Broker,
|
||||
welche anschließend von den <span style="background-color:Gainsboro">mqtt in</span>- und
|
||||
<span style="background-color:Gainsboro">mqtt out</span>-Nodes verwendet werden.</p>
|
||||
welche anschließend von den mqtt in- und
|
||||
mqtt out-Nodes verwendet werden.</p>
|
||||
<p>Der Node generiert eine beliebige Client-ID, falls sie nicht vorgegeben ist und der
|
||||
Node eine bereinigte Sitzung (clean session) verwenden soll.
|
||||
Wenn eine Client-ID vorgegeben wird, muss sie für den Broker eindeutig sein, zu dem die Verbindung hergestellt werden soll.</p>
|
||||
|
||||
@@ -36,7 +36,7 @@
|
||||
<dt>res <span class="property-type">object</span></dt>
|
||||
<dd>HTTP-Antwortobjekt.<br/>
|
||||
Diese Eigenschaft sollte nicht direkt verwendet werden.
|
||||
Im <span style="background-color:Gainsboro">http response</span>-Node ist dokumentiert, wie auf eine Anforderung reagiert wird.
|
||||
Im http response-Node ist dokumentiert, wie auf eine Anforderung reagiert wird.
|
||||
Diese Eigenschaft muss an der Nachricht angehängt bleiben, die an den Antwort-Node übergeben wird.</dd>
|
||||
</dl>
|
||||
<h3>Details</h3>
|
||||
@@ -50,12 +50,12 @@
|
||||
<p>Wenn der Inhaltstyp der Anforderung ermittelt werden kann, wird der Hauptteil als passender Typ analysiert.
|
||||
Z.B. <code>application/json</code> wird zu einem JavaScript-Objekt analysiert.</p>
|
||||
<p><b>Hinweis</b>: Dieser Node sendet keine Antwort an die Anforderung.
|
||||
Der Flow muss einen <span style="background-color:Gainsboro">http response</span>-Node enthalten,
|
||||
Der Flow muss einen http response-Node enthalten,
|
||||
um die Anforderung zu vervollständigen.</p>
|
||||
</script>
|
||||
|
||||
<script type="text/html" data-help-name="http response">
|
||||
<p>Senden von Antworten auf Anforderungen, die von einem <span style="background-color:Gainsboro">http in</span>-Node empfangen wurden.</p>
|
||||
<p>Senden von Antworten auf Anforderungen, die von einem http in-Node empfangen wurden.</p>
|
||||
<h3>Eingangsdaten</h3>
|
||||
<dl class="message-properties">
|
||||
<dt>payload <span class="property-type">string</span></dt>
|
||||
|
||||
@@ -34,17 +34,17 @@
|
||||
</ul>
|
||||
</dd>
|
||||
<dt>schemaError <span class="property-type">array</span></dt>
|
||||
<dd>Wenn die JSON-Schema-Validierung fehlschlägt, wird für den <span style="background-color:Gainsboro">catch</span>-Node eine <code>schemaError</code>-Eigenschaft erstellt,
|
||||
<dd>Wenn die JSON-Schema-Validierung fehlschlägt, wird für den catch-Node eine <code>schemaError</code>-Eigenschaft erstellt,
|
||||
die ein Array von Fehlern enthält.</dd>
|
||||
</dl>
|
||||
<h3>Details</h3>
|
||||
<p>Standardmäßig verarbeitet der Node <code>msg.payload</code>,
|
||||
kann aber auch eine beliebige Nachrichteneigenschaft konvertieren.</p>
|
||||
<p>Die Konvertierungsrichtung kann im Node auch vorgegeben werden, um eine bestimmte Ziel-Kodierung sicherzustellen.
|
||||
Dies kann z.B. zusammen mit dem <span style="background-color:Gainsboro">http in</span>-Node benutzt werden, um sicherzustellen,
|
||||
Dies kann z.B. zusammen mit dem http in-Node benutzt werden, um sicherzustellen,
|
||||
dass die Nutzdaten (Payload) ein analysiertes (parsed) Objekt ist,
|
||||
auch wenn eine eingehende Anfrage seinen Inhaltstyp nicht korrekt eingestellt hat,
|
||||
damit der <span style="background-color:Gainsboro">http in</span>-Node die Konvertierung durchführen kann.</p>
|
||||
damit der http in-Node die Konvertierung durchführen kann.</p>
|
||||
<p>Wenn der Node auf Zeichenfolgen-Eingang (string) eingestellt ist und es einen String empfängt,
|
||||
werden keine weiteren Prüfungen der Eigenschaft durchgeführt.
|
||||
Der Node prüft weder, ob die Zeichenfolge (string) ein gültiges JSON enthält, noch wird er ihn neu formatieren,
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
<dl class="message-properties">
|
||||
<dt>parts <span class="property-type">object</span></dt>
|
||||
<dd>Diese Eigenschaft enthält Informationen darüber, wie die Nachricht von der ursprünglichen Nachricht abgeteilt wurde.
|
||||
Bei Übergabe an ein <span style="background-color:Gainsboro">join</span>-Node kann die Sequenz wieder zu einer einzigen Nachricht zusammengeführt werden.
|
||||
Bei Übergabe an ein join-Node kann die Sequenz wieder zu einer einzigen Nachricht zusammengeführt werden.
|
||||
Diese Eigenschaft hat die folgenden Eigenschaften:
|
||||
<ul>
|
||||
<li><code>id</code>: Identifikator der Nachrichten-Gruppe</li>
|
||||
@@ -48,7 +48,7 @@
|
||||
</dl>
|
||||
<h3>Details</h3>
|
||||
<p>Dieser Node macht es einfach, einen Flow zu erstellen, der gemeinsame Aktionen über eine Sequenz von Nachrichten ausführt,
|
||||
bevor die Sequenz mittels <span style="background-color:Gainsboro">join</span>-Node wieder zu einer einzigen Nachricht neu kombiniert wird.</p>
|
||||
bevor die Sequenz mittels join-Node wieder zu einer einzigen Nachricht neu kombiniert wird.</p>
|
||||
<p>Der Node verwendet die <code>msg.parts</code>-Eigenschaft, um die einzelnen Sequenzteile nachzuverfolgen.</p>
|
||||
<h4><b>Streaming-Modus</b></h4>
|
||||
<p>Der Node kann auch zum Aufbereiten eines Nachrichtenstroms verwendet werden.
|
||||
@@ -59,7 +59,7 @@
|
||||
so wird es im Node aufbewahrt und der nächsten empfangenen Nachricht vorangestellt.</p>
|
||||
<p>In diesem Modus wird die <code>msg.parts.count</code>-Eigenschaft nicht gesetzt,
|
||||
da die Anzahl der zu erwartenden Nachrichten im Stream unbekannt ist.
|
||||
Das bedeutet, dass ein nachfolgender <span style="background-color:Gainsboro">join</span>-Node nicht im Automatikmodus verwendet werden kann.</p>
|
||||
Das bedeutet, dass ein nachfolgender join-Node nicht im Automatikmodus verwendet werden kann.</p>
|
||||
</script>
|
||||
|
||||
<script type="text/html" data-help-name="join">
|
||||
@@ -67,7 +67,7 @@
|
||||
<p>Es sind drei Modi verfügbar:</p>
|
||||
<dl>
|
||||
<dt>Automatisch</dt>
|
||||
<dd>In Kombination mit dem <span style="background-color:Gainsboro">split</span>-Node verbindet es automatisch die Nachrichten, um die zuvor durchgeführte Aufteilung rückgängig zu machen.</dd>
|
||||
<dd>In Kombination mit dem split-Node verbindet es automatisch die Nachrichten, um die zuvor durchgeführte Aufteilung rückgängig zu machen.</dd>
|
||||
<dt>Manuell</dt>
|
||||
<dd>Die Nachrichtensequenzen können auf verschiedene Weisen verbunden werden.</dd>
|
||||
<dt>Sequenz reduzieren</dt>
|
||||
@@ -77,7 +77,7 @@
|
||||
<dl class="message-properties">
|
||||
<dt class="optional">parts <span class="property-type">object</span></dt>
|
||||
<dd>Zur automatischen Verbindung einer Nachrichtensequenz sollten alle über diese Eigenschaft verfügen.
|
||||
Der <span style="background-color:Gainsboro">split</span>-Node erzeugt diese Eigenschaft, sie kann aber auch manuell erstellt werden.
|
||||
Der split-Node erzeugt diese Eigenschaft, sie kann aber auch manuell erstellt werden.
|
||||
Sie hat die folgenden Eigenschaften:
|
||||
<ul>
|
||||
<li><code>id</code>: Identifikator der Nachrichten-Gruppe</li>
|
||||
@@ -98,7 +98,7 @@
|
||||
<h4><b>Automatischer Modus</b></h4>
|
||||
<p>Der automatische Modus verwendet die <code>parts</code>-Eigenschaften der eingehenden Nachrichten,
|
||||
um die Sequenz in richtiger Reihenfolge zu verknüpften.
|
||||
Dies ermöglicht die Aufteilung des <span style="background-color:Gainsboro">split</span>-Nodes automatisch rückgängig zu machen.</p>
|
||||
Dies ermöglicht die Aufteilung des split-Nodes automatisch rückgängig zu machen.</p>
|
||||
|
||||
<h4><b>Manueller Modus</b></h4>
|
||||
<p>Im manuellen Modus werden Nachrichtensequenzen auf verschiedenen Arten zusammengefügt:</p>
|
||||
|
||||
@@ -26,8 +26,8 @@
|
||||
<p>Für Zahlenwerte kann die numerische Sortierreihenfolge festgelegt werden.</p>
|
||||
<p>Der Sortierschlüssel kann ein Elementwert oder ein JSONata-Ausdruck beim Sortieren einer Nachrichteneigenschaft
|
||||
bzw. eine Nachrichteneigenschaft oder ein JSONata-Ausdruck beim Sortieren einer Nachrichtensequenz sein.<p>
|
||||
<p>Zum Sortieren einer Nachrichtensequenz benötigt der <span style="background-color:Gainsboro">sort</span>-Node die gesetzte <code>msg.parts</code>-Eigenschaft bei den empfangenen Nachrichten.
|
||||
Diese Eigenschaft wird vom <span style="background-color:Gainsboro">split</span>-Node erzeugt und kann aber auch manuell erzeugt werden.
|
||||
<p>Zum Sortieren einer Nachrichtensequenz benötigt der sort-Node die gesetzte <code>msg.parts</code>-Eigenschaft bei den empfangenen Nachrichten.
|
||||
Diese Eigenschaft wird vom split-Node erzeugt und kann aber auch manuell erzeugt werden.
|
||||
Sie hat die folgenden Eigenschaften:</p>
|
||||
<p>
|
||||
<ul>
|
||||
|
||||
@@ -58,5 +58,5 @@
|
||||
aber typischerweise 64k (Linux/Mac) oder 41k (Windows).</p>
|
||||
<p>Bei Aufteilung in mehrere Nachrichten besitzt jede eine <code>parts</code>-Eigenschaft,
|
||||
welche eine komplette Nachrichten-Sequenz bildet.</p>
|
||||
<p>Fehler sollten mittels <span style="background-color:Gainsboro">catch</span>-Nodes abgefangen und behandelt werden.</p>
|
||||
<p>Fehler sollten mittels catch-Nodes abgefangen und behandelt werden.</p>
|
||||
</script>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@node-red/nodes",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"license": "Apache-2.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@node-red/registry",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"license": "Apache-2.0",
|
||||
"main": "./lib/index.js",
|
||||
"repository": {
|
||||
@@ -16,7 +16,7 @@
|
||||
}
|
||||
],
|
||||
"dependencies": {
|
||||
"@node-red/util": "2.1.0-beta.2",
|
||||
"@node-red/util": "2.1.3",
|
||||
"clone": "2.1.2",
|
||||
"fs-extra": "10.0.0",
|
||||
"semver": "7.3.5",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@node-red/runtime",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"license": "Apache-2.0",
|
||||
"main": "./lib/index.js",
|
||||
"repository": {
|
||||
@@ -16,8 +16,8 @@
|
||||
}
|
||||
],
|
||||
"dependencies": {
|
||||
"@node-red/registry": "2.1.0-beta.2",
|
||||
"@node-red/util": "2.1.0-beta.2",
|
||||
"@node-red/registry": "2.1.3",
|
||||
"@node-red/util": "2.1.3",
|
||||
"async-mutex": "0.3.2",
|
||||
"clone": "2.1.2",
|
||||
"express": "4.17.1",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@node-red/util",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"license": "Apache-2.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
|
||||
19
packages/node_modules/node-red/bin/node-red-pi
vendored
19
packages/node_modules/node-red/bin/node-red-pi
vendored
@@ -1,4 +1,4 @@
|
||||
#!/bin/bash
|
||||
#!/bin/sh
|
||||
#
|
||||
# Copyright JS Foundation and other contributors, http://js.foundation
|
||||
#
|
||||
@@ -29,15 +29,16 @@ do
|
||||
done
|
||||
|
||||
# Find the real location of this script
|
||||
CURRENT_PATH=`pwd`
|
||||
SCRIPT_PATH="${BASH_SOURCE[0]}";
|
||||
CURRENT_PATH=$(pwd)
|
||||
SCRIPT_PATH=$(readlink -f "$0")
|
||||
while [ -h "${SCRIPT_PATH}" ]; do
|
||||
cd "`dirname "${SCRIPT_PATH}"`"
|
||||
SCRIPT_PATH="$(readlink "`basename "${SCRIPT_PATH}"`")";
|
||||
cd "$(dirname "${SCRIPT_PATH}")" || exit 1
|
||||
P=$(basename "${SCRIPT_PATH}")
|
||||
SCRIPT_PATH=$(readlink "${P}")
|
||||
done
|
||||
cd "`dirname "${SCRIPT_PATH}"`" > /dev/null
|
||||
SCRIPT_PATH="`pwd`";
|
||||
cd $CURRENT_PATH
|
||||
cd "$(dirname "${SCRIPT_PATH}")" > /dev/null || exit 1
|
||||
SCRIPT_PATH=$(pwd)
|
||||
cd "$CURRENT_PATH" || exit 1
|
||||
|
||||
# Run Node-RED
|
||||
exec /usr/bin/env node $OPTIONS $SCRIPT_PATH/../red.js $ARGS
|
||||
exec /usr/bin/env node ${OPTIONS} ${SCRIPT_PATH}/../red.js ${ARGS}
|
||||
|
||||
10
packages/node_modules/node-red/package.json
vendored
10
packages/node_modules/node-red/package.json
vendored
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "node-red",
|
||||
"version": "2.1.0-beta.2",
|
||||
"version": "2.1.3",
|
||||
"description": "Low-code programming for event-driven applications",
|
||||
"homepage": "http://nodered.org",
|
||||
"license": "Apache-2.0",
|
||||
@@ -31,10 +31,10 @@
|
||||
"flow"
|
||||
],
|
||||
"dependencies": {
|
||||
"@node-red/editor-api": "2.1.0-beta.2",
|
||||
"@node-red/runtime": "2.1.0-beta.2",
|
||||
"@node-red/util": "2.1.0-beta.2",
|
||||
"@node-red/nodes": "2.1.0-beta.2",
|
||||
"@node-red/editor-api": "2.1.3",
|
||||
"@node-red/runtime": "2.1.3",
|
||||
"@node-red/util": "2.1.3",
|
||||
"@node-red/nodes": "2.1.3",
|
||||
"basic-auth": "2.0.1",
|
||||
"bcryptjs": "2.4.3",
|
||||
"express": "4.17.1",
|
||||
|
||||
5
packages/node_modules/node-red/red.js
vendored
5
packages/node_modules/node-red/red.js
vendored
@@ -194,6 +194,11 @@ if (process.env.NODE_RED_ENABLE_PROJECTS) {
|
||||
settings.editorTheme.projects.enabled = !/^false$/i.test(process.env.NODE_RED_ENABLE_PROJECTS);
|
||||
}
|
||||
|
||||
if (process.env.NODE_RED_ENABLE_TOURS) {
|
||||
settings.editorTheme = settings.editorTheme || {};
|
||||
settings.editorTheme.tours = !/^false$/i.test(process.env.NODE_RED_ENABLE_TOURS);
|
||||
}
|
||||
|
||||
|
||||
var defaultServerSettings = {
|
||||
"x-powered-by": false
|
||||
|
||||
@@ -9,29 +9,36 @@ const LATEST = "2";
|
||||
function generateScript() {
|
||||
return new Promise((resolve, reject) => {
|
||||
const packages = [
|
||||
"node-red-util",
|
||||
"node-red-runtime",
|
||||
"node-red-registry",
|
||||
"node-red-nodes",
|
||||
"node-red-editor-client",
|
||||
"node-red-editor-api",
|
||||
"@node-red/util",
|
||||
"@node-red/runtime",
|
||||
"@node-red/registry",
|
||||
"@node-red/nodes",
|
||||
"@node-red/editor-client",
|
||||
"@node-red/editor-api",
|
||||
"node-red"
|
||||
];
|
||||
const rootPackage = require(path.join(__dirname,"..","package.json"));
|
||||
const version = rootPackage.version;
|
||||
|
||||
const versionParts = version.split(".");
|
||||
let updateNextToLatest = false;
|
||||
let tagArg = "";
|
||||
if (versionParts[0] !== LATEST) {
|
||||
tagArg = `--tag v${versionParts[0]}-maintenance`
|
||||
} else if (/-/.test(version)) {
|
||||
tagArg = "--tag next"
|
||||
} else {
|
||||
updateNextToLatest = true;
|
||||
}
|
||||
|
||||
const lines = [];
|
||||
|
||||
packages.forEach(name => {
|
||||
lines.push(`npm publish ${name}-${version}.tgz ${tagArg}\n`);
|
||||
const tarName = name.replace(/@/,"").replace(/\//,"-")
|
||||
lines.push(`npm publish ${tarName}-${version}.tgz ${tagArg}\n`);
|
||||
if (updateNextToLatest) {
|
||||
lines.push(`npm dist-tag add ${name}@${version} next\n`);
|
||||
}
|
||||
})
|
||||
resolve(lines.join(""))
|
||||
});
|
||||
|
||||
@@ -60,9 +60,9 @@ describe('TCP Request Node', function() {
|
||||
n2.on("input", function(msg) {
|
||||
try {
|
||||
if (typeof val1 === 'object') {
|
||||
msg.should.have.properties(Object.assign({}, val1, {payload: Buffer(val1.payload)}));
|
||||
msg.should.have.properties(Object.assign({}, val1, {payload: Buffer.from(val1.payload)}));
|
||||
} else {
|
||||
msg.should.have.property('payload', Buffer(val1));
|
||||
msg.should.have.property('payload', Buffer.from(val1));
|
||||
}
|
||||
done();
|
||||
} catch(err) {
|
||||
@@ -84,9 +84,9 @@ describe('TCP Request Node', function() {
|
||||
n2.on("input", msg => {
|
||||
try {
|
||||
if (typeof result === 'object') {
|
||||
msg.should.have.properties(Object.assign({}, result, {payload: Buffer(result.payload)}));
|
||||
msg.should.have.properties(Object.assign({}, result, {payload: Buffer.from(result.payload)}));
|
||||
} else {
|
||||
msg.should.have.property('payload', Buffer(result));
|
||||
msg.should.have.property('payload', Buffer.from(result));
|
||||
}
|
||||
done();
|
||||
} catch(err) {
|
||||
|
||||
Reference in New Issue
Block a user