Help with logic filtering of message


#2

If you need to make decisions based on the current state of two variables then feed them both into a Join node set to Key/Value pair mode, identified by topic, wait for 2 messages and send on every new message after that, so you then get one message with both values in it each time either of them changes. Then you can perform whatever logic you want on the result.


#3

Thanks, but I can't find that setting in the join node.

All I can see is: Automatic, Manual and Reduce sequence.


#4

Having selected Manual, what other options do you see?


#5

Yeah, ok.......

But reading the info on the node it kind of says it is to be used with the split node.

It joins the two strings. I am missing how I can use this to assign weight to which message is shown.

Could you please expand on how this node is supposed to get two messages and "select" one of the two to on-send. Which one is not fixed. Either in message position or "who" sends it.


#6

Don't use string mode, use key/value mode (as I said, go back and read the original mail again).
Once you have both of them you can look at them and send whatever you want.


#7

I can't see:

a key/value object ?

That's the part where I am stuck.

Preforming the logic.


#8

key/value object is one of the options.

Do you mean you don't even know what you want to do, never mind how to do it? Can't help much there I am afraid.


#9

Here is a basic example of what I am wanting to do:

Machine 1 sending: Machine1 modem online
Machine 2 sending: Machine2 modem online

Great.
For now, let's say I want Machine1's message to be weighted and sent.

Then the messages change to:
Machine1 modem offline
Machine2 modem online

Machine 2's message needs to be sent, as it is the online message.

But if it changes where machine1 is sending the online and machine2 is sending offline, machine 1's message is sent.

If both are offline, machine 1's message is sent.

So as best I can resolve it:

  • If both online, machine 1 priority.
  • If one of the machines shows offline (and the other online) the online is sent.
  • If both are offline, machine 1 priority.

Does that help?


#10

Maybe you need something like https://flows.nodered.org/node/node-red-contrib-nools to establish some rules & priorities.


#11

Get the join working then you can easily do that in a function node.


#12

Colin,

Ok, with the join node working and set how you say I get alternate outputs of both machines with their messages.
Though it (from my example above) I am getting:
Machine1 modem online
Machine2 modem online
Machine1 modem online
and so on.

(by edit)
Ok, looked at it again a bit harder, but gee it is difficult to see the difference.
(I am not getting it.)
I can't see how that is useful.

Paul:
Thanks.

That looks interesting.
Seems I have to (maybe) learn about that language/syntax now too.


#13

You should see the payload from both messages identified by the topic you passed in with each. You did make sure they had different topics didn't you?


#14

Yes. That was the "oops" moment.

But I am not seeing much of an advantage.

I am (just now) setting contexts dependant on the messages.
Now I am working on the logic on the context to what is then sent on as the message.


#15

So have you now got both messages in one? If so you can test them and send on what you want.


#16

Colin, yes. But "testing them" is not something I understand.

This is what I have made in the mean time:

var BP = context.get('BedPi')||0;        //  Has data come in from BedPi?
var TP = context.get('TimePi')||0;       //  Has data come in from TimePi?

var new_message;
if (msg.topic == 'BedPi Modem')
{
    //      BedPi message received.
    if (msg.state === true)
    {
        //
        context.set('BedPi',1);
        context.set('BedPi_message',msg.payload);
    } else
    {
        context.set('BedPi',0)
        context.set('BedPi_message',msg.payload);
    }
} else
if (msg.topic == 'TimePi Modem')
{
    //      TimePi message received.
    if (msg.state === true)
    {
        //
        context.set('TimePi',1);
        context.set('TimePi_message',msg.payload);
    } else
    {
        context.set('TimePi',0)
        context.set('TimePi_message',msg.payload);
    }
}
//  Now The contexts have been set, act depending on what is set.
if (TP == 1)
{
    //
    //      Use TP status and display it.
    //
    msg.payload = context.get('TimePi_message');
    return msg;
} else
if (BP == 1)
{
    //
    //  BedPi is online.
    //
    msg.payload = context.get('BedPi_message');
    return msg;
}

Is this looking ok?


#17

Why are you using context. Both inputs are available in the message.


#18

Because scanning one message for substrings is just too complicated for me.

I get the messages and save them as contexts, so it gets the messages, stores them and then acts on what the contexts are.

I also think I goofed with the line:

msg.payload = context.get('TimePi_message');

And it should be:

msg = context.get('TimePi_message');

Because the entire message is stored. Not just the message.


#19

OK, do it the way you want then.


#20

I don't mind trying things, but sorry what you explained was too vague for what I understand.


#21

Did you see both messages in the incoming payload?

[Edit] As something like {Machine1: "Machine1 modem online", Machine2: "Machine2 modem online"}