Generate and send MQTT message in a rule via "execute an inline script" ECMAScript 262 Edition 11

Hi Experts,

a stupid beginner’s question I’m afraid but I’m stuck with my first controlling-a-MQTT-device task. It is about setting output power of a solar battery Marstek B2500 aka HMA1 as per energy consumption reported by a Shelly EM3 by sending new setpoint to the battery via MQTT. Broker and communication between OH4.3.3 and HMA1 via Mosquitto is set up and working fine.

What I need to do is:

  1. Calculate new setpoint (required battery power) - done, and stored in an item
  2. Generate MQTT payload message for HMA1 by replacing setpoint with value from 1. in below string
    cd=20,md=0,a1=1,b1=0:00,e1=23:59,v1=setpoint,a2=0,b2=00:00,e2=23:59,v2=80,a3=0,b3=00:00,e3=23:59,v3=80
  3. Publish to MQTT. The built-in MQTT publish in the rule setup options seems to accept only static text, no variables(?)

Is there an easy way to do 2+3 in an “execute an inline script” ECMAScript 262 Edition 11? Any help is greatly appreciated!

Thanks,
Georg

please give a bit more input on how you setup the MQTT-binding, and how you connected it to an item.

Normally it would be very easy:

  1. create an mqtt-channel including the “MQTT Command Topic”
  2. link the channel to an item
  3. update the value of that item with your text (of course the text can contain variables)
  4. the command topic will receive the payload, and thus your device
actions.get("mqtt","mqtt:broker:mqtt_broker").publishMQTT("your/topic/goes/here", "payload", true);

You’ll need to replace mqtt_broker with the name of your broker UID listed under things. Or you can command a string item which is connected to an MQTT channel. I use the script method in a niche case, but would otherwise recommend a string item

Many thanks for trying to help me with this!

I have made two items and two rules now, first rule is calculating a new setpoint from Shelly3EM consumption reading when required and storing into HMA1_DC_OUT_SOLL. This one is working fine.

The second rule is the code below.
Idea is that when setpoint changes (id1), next step id2 puts the template MQTT message to update the battery into item HMA1_SetpointMessage, then id3 to add the setpoint to the string item by replacing “sollwert” and finally id4 to send the string item as MQTT.

I got it working as far as id2 :-), id3 I couldn’t do the string update despite some trial and error and id4 seems to accept static value only, could not convince it to send the string item instead.

configuration: {}
triggers:

  • id: “1”
    configuration:
    itemName: HMA1_DC_OUT_SOLL
    type: core.ItemStateChangeTrigger
    conditions:
    actions:
  • inputs: {}
    id: “2”
    configuration:
    command: cd=20,md=0,a1=1,b1=0:00,e1=23:59,v1=sollwert,a2=0,b2=00:00,e2=23:59,v2=80,a3=0,b3=00:00,e3=23:59,v3=80
    itemName: HMA1_SetpointMessage
    type: core.ItemCommandAction
  • inputs: {}
    id: “3”
    configuration:
    type: application/javascript
    script: |
    item(‘HMA1_SetpointMessage’).—replace “sollwert” with numeric value in item HMA1_DC_OUT_SOLL—;
    type: script.ScriptAction
  • inputs: {}
    id: “4”
    configuration:
    topic: hame_energy/HMA-1/App/7ce712af5e99/ctrl
    config: mqtt:broker:39c6de0dc2
    value: —String in HMA1_SetpointMessage after id3 modification—
    type: mqtt.publishMQTT#26aa5ea09027ad2b11b752652e808c6a

That’s not, how you should do it. :wink:
first off: please copy your code in Code fences (there’s icons in the editor one says “openHAB rules code fence”. Makes it easier to read - and copy for others.

then a short introduction on how openHAB works with rules:

you mixed two things: “item actions” and “script actions”.
In your case, if you like to change the state of an item within the rule with some calculations, you should use only script actions. Within the script you simply put together the complete payload you like to send via mqtt and then update the item, which is linked to the corresponding channel in your mqtt-thing.

so, what you do is:

  1. setup your trigger in the rule
  2. chose “inline script” as an action

put something like this in the script:

// do some magic before and set fill the variable setPoint
var setPoint = 27.5;

// build the whole payload (you can "insert" the setPoint-variable with "+")
var mqttPayload = "cd=20,md=0,a1=1,b1=0:00,e1=23:59,v1=" + setPoint + ",a2=0,b2=00:00,e2=23:59,v2=80,a3=0,b3=00:00,e3=23:59,v3=80";

// update your mqtt-command item with the payload
items.getItem("yourMqttItem").sendCommand(setPoint);

That’s all you need to do. After the sendCommand, the item will then send the payload to your mqtt-broker, which will then trigger you device.

1 Like

Hi Thomas,

thanks very much once more! I got it working as per your instructions, battery is nicely following electricity demand. As they say, “kaum macht man’s richtig, schon funktioniert’s” :slight_smile:

Cheers,
Georg

1 Like