Many tasks in Node-RED can be done with
the default core node set. And, when they're not enough there's often an
external package of nodes that you can install to fill in the gaps. But, some
applications just require more. In this workshop I'll talk a little bit about
function nodes and what they can do like access persistent variables as well as
the JavaScript object notation or JSON format that the flow message uses. And,
finally, I'll talk about some other nodes like 'link' and 'exec'. With all of this at
your disposal you'll be well equipped to build clean, powerful and sophisticated
Node-RED applications. Having the ability to write your own
JavaScript inside a flow is incredibly powerful. Just about all the tools of
JavaScript are available to you so if you already know the language you'll be
right at home. Otherwise, there are a ton of resources and books on the language
for you to learn. Since most other nodes are essentially pieces of JavaScript you
can use the function node to replicate their processes and even do multiple
tasks at once from the one function node. Of course, you can also go beyond that
and make full use of the JavaScript language to customize your processing on
the fly. As well as the conditional statements, loops, functions, string and
array manipulation tools that you can use in JavaScript there were also some
functions specific to Node-RED that are very useful. They're all in the
documentation on nodered.org. To give you a quick outline, function nodes are
able to send messages to multiple output ports, send out multiple messages on a
single port, or send out messages while processing before completing the code
block and exiting the node. There's also the ability to log messages and errors,
show status info during runtime, and store data persistently between function
calls or even between deploys. Context, flow and global are the three different
levels that you can use to set access and modify persistent variables where
the range of their access is referred to as that variable's 'scope'. lLet's head over
to Node-RED and see how this works. Here I have a function node that uses 'context
get' and 'context set' to keep a rolling count of how many times I inject this
function node. So, if I click done and inject a few times you can see the
counter go up in the debug window. If I try to access this context account from
another function node here where I context.get count from below. If I
inject this I get undefined since it hasn't actually been defined in the
scope of this function node, only within the one above it. To fix this I can
increase the scope of count by going into the function and changing 'context'
to 'flow'. Now the variable count will be available from anywhere within this flow. I'll click done and change the other
node to use the same. Now if I click done, deploy I'll see the number is reset
since it is now under a new scope. And, every time I inject the count goes up.
But, I can also request it from this node. Now I'll take it a step further and go
over to this other flow and try to inject 'flow.count'. Now when I try to
do it from here I still get undefined and that's because it isn't defined
within the scope of this flow only the other. To fix this I can level up the
flow once more, go into count and edit it to be 'global' instead of 'flow'. I'll hit
done, change over to the other tab, increasing this to get the global count.
Now, when I deploy and inject I can get the count from any flow that I would
like. So, while these global variables are universally accessible some applications
may be better off using a link node to share data between flows. Link nodes not
only share variables but can also trigger different flows across your
project in a sequenced predictable way. Here I'll bring in an inject and have
it throw in the time stamp. I'll go down to the function section and use a delay
node to set this off 5 seconds after I actually inject the message. I can send
this to a link output node. I'll call this link 'example' so I can
find it later. Now, I'll bring in a link input node, wire it to a debug and
connect to the 'link to example'. Now, you can see the link has found it's pair. And,
when I deploy and inject five seconds later I will see the timestamp appear in
the debug window. And, there it is. If I grab these two nodes, cut them and paste
them on another flow, then when I deploy and inject on this flow five seconds
later I can go back to this other tab, and when the time appears I can see by
the dashed line that it's coming from this debug node. When I select the link node I
can see it is connected to my other flow. While persistent variables can be
accessed across flows they will not move an inject or flow message only allow
you to access your stored values. To move the message across flows or to start one
flow from another you should use linked nodes. So far the messages I've been
moving around have been pretty simple though mostly a message object
containing a single property payload. This makes up the majority of Node-RED
objects. But, sometimes a node will require input or give output that is a
much more complex message object. To get an idea of what this can look like I'll
use this HTTP request node to get a Weather Underground API object. I have
this debug node set to display the complete message object in the debug
window so that I can see the full structure. So, I'll activate that and
inject the node to see the object. Now, when I expand it Node-RED is already
telling me that payload itself is an object not just a variable. So, I can
expand that out and see that it contains two more objects called a response and
forecast. Forecast itself is a pretty complex object with text forecasts and
simple forecast objects. Simple forecast itself expands into an array called 'forecast day' that holds four days worth of forecast data. Each of these objects
contains a lot of data about that forecast. Here I can expand 'high' and 'low'
to see Fahrenheit and Celsius for both. If I wanted to find the path to this
exact object I can use this button on the left from the debug pane. To copy the
path to my clipboard now if I go down to the function section and drag in a
function node, wire that in between the message and the HTTP request, I can paste
that path directly into my function node. Now, I'll find out how to reference JSON
objects first I use 'msg.' to reference the payload and then
'.forecast' to get that object then '.simple forecast' and '.forecast day'.
'Forecast day' then requires square brackets to reference the first item in
the list and index zero. Once I have that I can reference 'high' and 'Fahrenheit' using
the '.operator'. From there if I were to return a new object using this as the
msg.payload, hit done, deploy, and inject on this
message I can see that 76 degrees has come through. If I wanted to change this
to get the low centigrade for example all I have to do is change those fields. Now when I hit done and deploy and
inject I can see the number 15 appear from the payload. That's how easy it is
to reference different fields of JSON objects. Now this weather object is very
specifically organized and will be consistent with all calls from Weather
Underground. But different api's have different standards with what they
output and even what they may take as input. Take for example the email node.
You might remember this from the 'email alerts' video. I'll go and click on one
now so that we can look at what it says in the info tab. Here it says that you
can set the email body using msg.payload. The subject using msg.topic
and recipients using to, CC, and BCC.You can either apply these using the email
node static settings or you can hand them in every time you call the node
using dynamic message objects. By using message properties instead of node
settings to supply information you're able to use the node dynamically as
opposed to being restricted by your static settings. Another powerful node is
the 'exec node' which allows you to run a command line instruction from within
Node-RED. Be aware that this node is very powerful and if you enter the wrong
thing it's possible that you could damage your system. Do not execute
anything before you understand what it does. Here I have an exec node setting
off an exec node to read my groov box's CPU load using the top command. If I activate the debug node and inject
on this flow I can see that my cpu load of 1.5% appears in the debug tab. Now
that it's in Node-RED I could do anything with it like plot it in groov,
lock it to a database or anything else I would like. The possibilities are only
limited by what you want to do with your application. With these nodes and some
understanding of JSON objects and JavaScript at your disposal you'll be
able to use Node-RED to easily create powerful applications that meet your
need. You'll be able to do this no matter how straightforward or advanced your
problem is. Thanks for watching.