Can I route a msg depending on its key name with basic nodes?
e.g
msg.payload is arriving on http in node as {"s3gpiocommand":"xxxx"} or {"s3gpioread":"yyyy"}
I'd like to process them differently in two separate branches
Can I route a msg depending on its key name with basic nodes?
e.g
msg.payload is arriving on http in node as {"s3gpiocommand":"xxxx"} or {"s3gpioread":"yyyy"}
I'd like to process them differently in two separate branches
JSONata, I just did something similar. Switch node with JSONata set for both routes.
The syntax you're looking for is
"s3gpiocommand" in $keys(payload)
and
"s3gpioread" in $keys(payload)
In 1.0 a new option has been added to the Switch node that lets you check for the presence of a given key name - which is just what you'd want.
An alternative JSONata approach to that suggested by @afelix is:
$exists($.payload.s3gpiocommand)
Tried your solution but it didn't seem to work
Amazing, I couldn't find anything like an $exists
in the JSONata docs so this is what I came up with:
[{"id":"2fc7d678.856452","type":"switch","z":"66c886df.ede628","name":"","property":"responseCookies","propertyType":"msg","rules":[{"t":"jsonata_exp","v":"\"user_credentials\" in $keys($.responseCookies)","vt":"jsonata"},{"t":"else"}],"checkall":"true","repair":false,"outputs":2,"x":1410,"y":280,"wires":[["af6cd6cd.9c90b8","36d7fc85.f5c98c"],["55648ccd.d1538c"]]}]
can you see this is my first day using JSONata in pracice
I had to do a POST request to a login endpoint on a server, and one of the ways I could see if the login succeeded was the presence of a cookie "user_credentials"
in the response cookies. This is how I'm routing that exact situation.
I have patent rights on that phrase
My test flow
[{"id":"2218a743.32e468","type":"inject","z":"aea6ecba.48c11","name":"","topic":"","payload":"{\"s3gpiocommand\":\"commandtest\"}","payloadType":"json","repeat":"","crontab":"","once":false,"onceDelay":0.1,"x":210,"y":660,"wires":[["73b0a755.159208"]]},{"id":"870eb8c1.d32ce8","type":"debug","z":"aea6ecba.48c11","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"true","targetType":"full","x":770,"y":640,"wires":[]},{"id":"73b0a755.159208","type":"switch","z":"aea6ecba.48c11","name":"","property":"payload","propertyType":"msg","rules":[{"t":"eq","v":"$exists($.payload.s3gpiocommand)","vt":"jsonata"},{"t":"eq","v":"$exists($.payload.s3gpioread)","vt":"jsonata"}],"checkall":"true","repair":false,"outputs":2,"x":470,"y":680,"wires":[["870eb8c1.d32ce8"],["7bca6c62.cb4c94"]]},{"id":"7bca6c62.cb4c94","type":"debug","z":"aea6ecba.48c11","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"true","targetType":"full","x":770,"y":720,"wires":[]},{"id":"cf532957.da2818","type":"inject","z":"aea6ecba.48c11","name":"","topic":"","payload":"{\"s3gpioread\":\"readtest\"}","payloadType":"json","repeat":"","crontab":"","once":false,"onceDelay":0.1,"x":210,"y":720,"wires":[["73b0a755.159208"]]}]
No, it's easier. Rather than testing with ==
set it to JSONata exp(ression)
What ==
with JSONata does is test if the contents of msg.payload
are identical to the output of that expression (which will be true or false)
Why not just use the 'has key' option in the switch
@knolleary - in 1.0 the JSONata exp
looks non-functional, when entering an expression, ok > deploy, doubleclick the switch, the expression is gone.
@zenofmud that is only available in the beta.
Yup, just noticed that myself. On the todo list.
I refer you all to my original reply:
just the more reason to start moving to 1.0
I ran into exactly this problem about half an hour ago, and as I had just started playing with JSONata (regex matching inside it actually) I tried to see if I could do this without a function node too. Just found the $exists
in the docs, put as "boolean functions" while I tried to look for "object functions". Just realised the boolean functions is more about the return type than the type of content it works on, whereas the object functions are specifically about acting on objects
I'm playing with the Node-RED Desktop app which is currently using 0.20.7 so I need to use the JSONata approaches until 1.0 becomes official and it gets updated to it
Here are some other ways I know of to verify the existence of that field in JSONata:
payload.s3gpioread != null
$lookup(payload, "s3gpioread") ? true : false
payload.s3gpioread.$length() > 0
$boolean($keys(payload)~>$filter(/^s3gpioread$/)~>$count())
Not all are valid for all possible values of that key -- for instance, if a blank string is possible, and you just want to branch depending on the presence of the field key, only the first and last expressions will work (besides the $exists version that Nick mentioned).