I have frequently used the node module called node-red-node-pi-gpio to read and write to the GPIO bus. However, the input node did not work reliably on my Pi W 2, particularly on Deploys. So I decided to try node-red-node-pi-gpiod (note the 'd' at the end).
This has the advantage of using a service (pigpiod.service) to interface with the GPIO via the pigpio library. This means that the link to the GPIO bus is not affected by Deploys and Node Red restarts.
However, it is important to understand that this GPIO system detects changes in state of the input, not its current value (0 or 1). Therefore the input node does not return anything after start-up until a change in state occurs. Because this delay in reading the input value until it changes might be undesirable in some situations, there is a node configuration setting labelled "Read initial state of pin on deploy/restart?". When checked it is intended to force an initial read of the absolute input condition and send its state out to the connected node(s). Once the initial state is determined, subsequent transitions of state will be transmitted as the occur.
The file that performs this function is called pi-gpiod.js and is found in the .node-red/node_modules/node-red-node-pi-gpiod folder. In this file, at line 20 in the 0.4.0 version, you will find a function called GPioInNode. It interfaces with the pigpiod.service via the js-pigpio library, found in .node-red/node_modules/js-pigpio, and its primary purpose is twofold. One, to set up a callback function to output the current input status whenever the latter changes. And two, to optionally determine and transmit the initial input status, based on the setting of the above-mentioned switch.
The function that performs the latter is inside a SetTimeout Javascript function configured to fire 20mS after it is established. I assume the delay was found necessary to give the GPIO system time to stabilize, as it will execute whenever Node Red is started or reloaded.
Experimentation has indicated that 20mS is too short to give reliable initialization. I do not know what the optimum value is, and it may vary with Pi model, but 1000 (ie: 1s) works well in my situation, and a delay of 1 second before initialization is unimportant to my system.
The line is question is 58, and my lines 52 - 59 now look like this:
if (node.read) {
setTimeout(function() {
PiGPIO.read(node.pin, function(err, level) {
node.send({ topic:"pi/"+node.pio, payload:Number(level), host:node.host });
node.status({fill:"green",shape:"dot",text:level});
});
}, 1000); // was 20mS, now 1S
}
I do not know if there is a race condition between the callback function reporting state changes and the one initial read of the input by the setTimeout function, if a state change should occur just as it’s being read by the latter. But I have not observed any issues. I assume the service will queue multiple reads appropriately.
Of course, any direct edit of the file will be removed if the node is updated by the authors, unless they read this and make the appropriate source change. However, the node has not been updated in over 5 years, so likely is not going to see further releases.
I hope this proves helpful.
Colin


