Flow Exception Recovery For Dynamic RegEx Syntax Error

While testing different regex for THIS TOPIC, I created a flow to permit easy entry of strings and regex for validation in a Switch Node. This worked great until I put in an invalid regex. This caused an exception ("SyntaxError: Invalid regular expression") in the Switch Node and rendered It inoperable until doing a flow restart. The other nodes continued to process normally but the Switch Node no longer provided any output.

No problem, I thought. I will just add a catch-all and clear out the bad regex. Sadly, this does not work. Here are the exception details as written to debug by my handler:

EXCEPTION
PAYLOAD:^\d$\
TOPIC: 
MESSAGE: SyntaxError: Invalid regular expression: /^\d$\/: \ at end of pattern
ID: b3061e66.00584
TYPE: switch
NAME: VALIDATE
COUNT: 1

Is this a recoverable error and, if so, how? Or is it maybe possible to restart an individual node or the whole flow from within the flow? This is not critical to my current development, just an inconvenience to what could be a useful tool. But it also has me thinking about other scenarios where exceptions might occur so thought I'd post here.

Here is my RegEx Tester flow:

[{"id":"a3cfa7e5.854208","type":"tab","label":"RegEx Tester","disabled":false,"info":""},{"id":"65ddf528.b9e03c","type":"ui_text_input","z":"a3cfa7e5.854208","name":"Get String","label":"Enter string","tooltip":"","group":"5eeb116e.bcdaa","order":2,"width":16,"height":1,"passthru":false,"mode":"text","delay":"500","topic":"topic","topicType":"msg","x":750,"y":360,"wires":[["81438305.7c07c"]]},{"id":"81438305.7c07c","type":"change","z":"a3cfa7e5.854208","name":"","rules":[{"t":"set","p":"string","pt":"flow","to":"payload","tot":"msg"}],"action":"","property":"","from":"","to":"","reg":false,"x":960,"y":360,"wires":[["5b132ece.12048"]]},{"id":"dcda1e70.ab5a4","type":"ui_text_input","z":"a3cfa7e5.854208","name":"Get RegEx","label":"Enter regex","tooltip":"","group":"5eeb116e.bcdaa","order":3,"width":16,"height":1,"passthru":false,"mode":"text","delay":"500","topic":"topic","topicType":"msg","x":750,"y":320,"wires":[["447f2c34.88c044"]]},{"id":"447f2c34.88c044","type":"change","z":"a3cfa7e5.854208","name":"","rules":[{"t":"set","p":"regex","pt":"flow","to":"payload","tot":"msg"}],"action":"","property":"","from":"","to":"","reg":false,"x":960,"y":320,"wires":[["5b132ece.12048"]]},{"id":"80e4de31.025b8","type":"ui_text","z":"a3cfa7e5.854208","group":"5eeb116e.bcdaa","order":4,"width":16,"height":1,"name":"Result","label":"{{msg.label}}","format":"{{msg.payload}}","layout":"col-center","x":1650,"y":340,"wires":[]},{"id":"b3061e66.00584","type":"switch","z":"a3cfa7e5.854208","name":"VALIDATE","property":"string","propertyType":"flow","rules":[{"t":"regex","v":"regex","vt":"flow","case":false},{"t":"else"}],"checkall":"true","repair":false,"outputs":2,"x":1320,"y":340,"wires":[["c0d00ce6.19f86"],["fd75b71d.49c2c8"]],"outputLabels":["MATCH","NOT MATCH "]},{"id":"c0d00ce6.19f86","type":"change","z":"a3cfa7e5.854208","name":"MATCH","rules":[{"t":"set","p":"payload","pt":"msg","to":"MATCH","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":1480,"y":320,"wires":[["80e4de31.025b8"]]},{"id":"fd75b71d.49c2c8","type":"change","z":"a3cfa7e5.854208","name":"NO MATCH","rules":[{"t":"set","p":"payload","pt":"msg","to":"NO MATCH","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":1490,"y":360,"wires":[["80e4de31.025b8"]]},{"id":"5b132ece.12048","type":"change","z":"a3cfa7e5.854208","name":"","rules":[{"t":"set","p":"label","pt":"msg","to":"$flowContext('string') & '~=' & $flowContext('regex')","tot":"jsonata"}],"action":"","property":"","from":"","to":"","reg":false,"x":1150,"y":340,"wires":[["b3061e66.00584"]]},{"id":"e29dc3ef.7f272","type":"change","z":"a3cfa7e5.854208","name":"CLEAR regex","rules":[{"t":"set","p":"payload","pt":"msg","to":"","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":760,"y":280,"wires":[["447f2c34.88c044"]]},{"id":"c7a610d6.435af","type":"comment","z":"a3cfa7e5.854208","name":"+++++++++++++++++++++++++ REGEX TESTER +++++++++++++++++++++++++","info":"","x":1090,"y":140,"wires":[]},{"id":"3510c421.20fa9c","type":"ui_text","z":"a3cfa7e5.854208","group":"5eeb116e.bcdaa","order":1,"width":0,"height":0,"name":"","label":"REGEX TESTER","format":"","layout":"row-center","x":1120,"y":200,"wires":[]},{"id":"f3b4e24b.e2042","type":"catch","z":"a3cfa7e5.854208","name":"Catch All Errors","scope":null,"uncaught":false,"x":340,"y":260,"wires":[["eeceb4b2.bbdfc8"]]},{"id":"eeceb4b2.bbdfc8","type":"change","z":"a3cfa7e5.854208","name":"Format Exception","rules":[{"t":"set","p":"payload","pt":"msg","to":"\"EXCEPTION\"     & \t\"\\nPAYLOAD:\"    &   msg.payload & \t\"\\nTOPIC: \"     &   msg.topic &\t\"\\nMESSAGE: \"   &   msg.error.message &\t\"\\nID: \"        &   msg.error.source.id &\t\"\\nTYPE: \"      &   msg.error.source.type &\t\"\\nNAME: \"      &   msg.error.source.name &\t\"\\nCOUNT: \"     &   msg.error.source.count","tot":"jsonata"}],"action":"","property":"","from":"","to":"","reg":false,"x":550,"y":260,"wires":[["17fec17b.26f6ff","e29dc3ef.7f272"]]},{"id":"17fec17b.26f6ff","type":"debug","z":"a3cfa7e5.854208","name":"EXCEPTION","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","statusVal":"","statusType":"auto","x":750,"y":240,"wires":[]},{"id":"5eeb116e.bcdaa","type":"ui_group","name":"RegEx Tester","tab":"3dc7d05e.02791","order":1,"disp":false,"width":16,"collapse":false},{"id":"3dc7d05e.02791","type":"ui_tab","name":"RegEx Tester","icon":"dashboard","order":14,"disabled":false,"hidden":false}]

If it matters, this is Node-RED v1.2.7 on Raspbian 10.8 on a Pi4 B1.2.

Thanks!

Peter

I think that may be a bug in the Switch node, that once it gets given an invalid regex via a flow variable that changing the flow variable does not allow it to recover. Perhaps @dceejay would like to comment (Dave, is it ok to tag you in cases such as this, I am never sure).

Definitely a bug in the switch node. I did further testing to narrow this down and a blocking exception occurs in a switch node if the following conditions are both met:

  1. The Switch Property is specified by msg., flow., global.*
  2. The regex is invalid

By blocking exception I mean the switch node will no longer respond or process incoming messages. An exception is raised but is not recoverable without a flow restart or redeploy of the switch node after making a change to it.

Note that to encounter a bad regex the regex must be dynamic (msg. flow. or global. variable). If you specify it as a string or expression it is flagged on deploy.

So my original assumption that this was caused by using a flow. variable for the regex is wrong.

I was unable to edit my original post with these new details so here they are. The flow below contains three test cases.

The first case uses a jsonata expression to define the source string (Switch Node Property) and works fine - after encountering a bad regex you can continue injecting tests through the node.

The second and third cases use msg.string and msg.payload as the Switch Node Property and result in blocking exceptions once a bad regex is encountered.

[{"id":"26f5fb49.791c54","type":"tab","label":"BAD REGEX","disabled":false,"info":""},{"id":"94fa80a9.96479","type":"inject","z":"26f5fb49.791c54","name":"GOOD REGEX - MATCH YES","props":[{"p":"string","v":"foo","vt":"str"},{"p":"regex","v":"foo","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","x":360,"y":380,"wires":[["1738b231.f9025e"]]},{"id":"1738b231.f9025e","type":"switch","z":"26f5fb49.791c54","name":"msg.string ~  msg.regex","property":"string","propertyType":"msg","rules":[{"t":"regex","v":"regex","vt":"msg","case":false},{"t":"else"}],"checkall":"false","repair":false,"outputs":2,"x":690,"y":420,"wires":[["9708b837.5dc0e8"],["f0dbaae1.e6e608"]],"outputLabels":["TRUE","FALSE"]},{"id":"9708b837.5dc0e8","type":"debug","z":"26f5fb49.791c54","name":"MATCH","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"'MATCH'","targetType":"jsonata","statusVal":"","statusType":"auto","x":980,"y":400,"wires":[]},{"id":"f0dbaae1.e6e608","type":"debug","z":"26f5fb49.791c54","name":"NO MATCH","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"'NO MATCH'","targetType":"jsonata","statusVal":"","statusType":"auto","x":990,"y":440,"wires":[]},{"id":"65d1ddbd.8cdd14","type":"inject","z":"26f5fb49.791c54","name":"GOOD REGEX MATCH NO","props":[{"p":"string","v":"foo","vt":"str"},{"p":"regex","v":"bar","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","x":360,"y":420,"wires":[["1738b231.f9025e"]]},{"id":"92ae5657.35f878","type":"inject","z":"26f5fb49.791c54","name":"BAD REGEX EXCEPTION","props":[{"p":"payload"},{"p":"regex","v":"[\\[","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"foobar","payloadType":"str","x":350,"y":460,"wires":[["1738b231.f9025e"]]},{"id":"5c1ead9e.719d84","type":"inject","z":"26f5fb49.791c54","name":"GOOD REGEX - MATCH YES","props":[{"p":"payload"},{"p":"regex","v":"foo","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"foo","payloadType":"str","x":360,"y":520,"wires":[["6f63530f.e737cc"]]},{"id":"6f63530f.e737cc","type":"switch","z":"26f5fb49.791c54","name":"msg.payload ~  msg.regex","property":"payload","propertyType":"msg","rules":[{"t":"regex","v":"regex","vt":"msg","case":false},{"t":"else"}],"checkall":"false","repair":false,"outputs":2,"x":690,"y":560,"wires":[["ab999332.1d4e7"],["2d28b3d4.76fabc"]],"outputLabels":["TRUE","FALSE"]},{"id":"ab999332.1d4e7","type":"debug","z":"26f5fb49.791c54","name":"MATCH","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"'MATCH'","targetType":"jsonata","statusVal":"","statusType":"auto","x":980,"y":540,"wires":[]},{"id":"2d28b3d4.76fabc","type":"debug","z":"26f5fb49.791c54","name":"NO MATCH","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"'NO MATCH'","targetType":"jsonata","statusVal":"","statusType":"auto","x":990,"y":580,"wires":[]},{"id":"8fddbc13.49e18","type":"inject","z":"26f5fb49.791c54","name":"GOOD REGEX MATCH NO","props":[{"p":"payload"},{"p":"regex","v":"bar","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"foo","payloadType":"str","x":360,"y":560,"wires":[["6f63530f.e737cc"]]},{"id":"279c010b.ab231e","type":"inject","z":"26f5fb49.791c54","name":"BAD REGEX EXCEPTION","props":[{"p":"string","v":"foobar","vt":"str"},{"p":"regex","v":"[\\[","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payloadType":"str","x":350,"y":600,"wires":[["6f63530f.e737cc"]]},{"id":"158bf56c.c5e10b","type":"inject","z":"26f5fb49.791c54","name":"GOOD REGEX - MATCH YES","props":[{"p":"regex","v":"foo","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","x":360,"y":120,"wires":[["288c9672.db581a"]]},{"id":"288c9672.db581a","type":"switch","z":"26f5fb49.791c54","name":"j:exp ~ msg.regex","property":"'foo'","propertyType":"jsonata","rules":[{"t":"regex","v":"regex","vt":"msg","case":false},{"t":"else"}],"checkall":"false","repair":false,"outputs":2,"x":670,"y":160,"wires":[["f7050f94.0ddef"],["e10c107d.2ac0b"]],"outputLabels":["TRUE","FALSE"]},{"id":"f7050f94.0ddef","type":"debug","z":"26f5fb49.791c54","name":"MATCH","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"'MATCH'","targetType":"jsonata","statusVal":"","statusType":"auto","x":980,"y":140,"wires":[]},{"id":"e10c107d.2ac0b","type":"debug","z":"26f5fb49.791c54","name":"NO MATCH","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"'NO MATCH'","targetType":"jsonata","statusVal":"","statusType":"auto","x":990,"y":180,"wires":[]},{"id":"f0c9f7cd.90fc38","type":"inject","z":"26f5fb49.791c54","name":"GOOD REGEX MATCH NO","props":[{"p":"regex","v":"bar","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","x":360,"y":160,"wires":[["288c9672.db581a"]]},{"id":"aefa8f7e.cfc59","type":"inject","z":"26f5fb49.791c54","name":"BAD REGEX EXCEPTION","props":[{"p":"regex","v":"[\\[","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payloadType":"str","x":350,"y":200,"wires":[["288c9672.db581a"]]},{"id":"13cf2eb5.279e61","type":"comment","z":"26f5fb49.791c54","name":"JSONata String Works Fine","info":"","x":710,"y":60,"wires":[]},{"id":"cefaeb81.3e7c78","type":"comment","z":"26f5fb49.791c54","name":"msg.* Strings Yield Blocking Exception","info":"","x":730,"y":300,"wires":[]}]

Peter

Could you create an issue against node red please? Then it will not be forgotten.

GitHub issue raised.
Node-RED Issue 2905

Fixed in Node-RED v1.3.2.

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.