HABApp - Easy automation with openHAB

Both the logging and habapp config are reloaded on the fly so there is no need for a restart.

i did not pay attention that habapp does not yet support oh4 when i lately updated to 4.0.0.m1. i even did not realize that because with m1 (at least for me) everything seems to work. only when i tried to update to m2 habapp complained.

so i kindly want to ask if there is already a plan when oh4 will be supported, otherwise i would think about downgrading. thanks!

Be aware that there will still be breaking changes for OH4.0 and obviously HABApp might fail because Iā€™ve not yet tested these changes.
Most notably the new unit metadata which has yet to be introduced and where Iā€™m still salty about how everything went down.

I think Iā€™ll add support for the new ItemStateUpdatedEvent in the next couple of weeks. However since I was quite sick the last couple of weeks lotā€™s of other work piled on so I canā€™t make any promises because I donā€™t have much time to spend on HABApp. But once Iā€™ll have something on the dev branch Iā€™ll give you a ping so you can try it out and see if it works as expected.

3 Likes

I should add - this is indeed an ugly way to avoid habapp warnings about the time the function takes, but given it makes a mess of my logs IMO itā€™s useful.

But it does mean there will be zero log warnings/errors if anything goes wrong in the thread. I compensate for this with a simple decorator function:

def thread_error_handler(func):

    def wrapper(*args, **kwargs):
        global list_of_reported_errors

        try:
            return func(*args, **kwargs)
        except Exception as e:

            # Get the traceback information
            tb = traceback.extract_tb(e.__traceback__)

            # Get the most recent stack frame with the line number
            # where the error occurred
            frame = tb[-1]

            logger.info("*********************************")
            logger.info(f"ERROR: function {func.__name__} produced error {e} at line {frame.lineno}")
            logger.info("----------- Stack Trace -----------")
            logger.info(traceback.format_exc())

            logger.info("*********************************")
            raise  # this ensures the error still propagates
    return wrapper

so e.g. my doorbell thread function looks like this:

@thread_error_handler
def doorbell_thread(self, event_name, event_value):
   # do stuff

which ensures errors get visibly logged

(How) can I get the unit of measurement or the quantitytype of a NumberItem? Thxā€¦

What exactly are you trying to achieve? Currently the unit is stripped when the value is updated.

Currently I am writing a class that, depending on the unit or quantity type of number iterm, shall be able to apply a standard handler to persist a value history different from OH persistence.
I do not want to keep a history of power items values, but min/max values per time period, but I want to keep the history of energy items.

So I could use the unit, e.g. W vs. Wh, or, even better, the quantity type if provided by the openbab REST API, to apply a standard handler without addiitonal configuration.

With OH4 the UoM handling will change and Iā€™ll probably provide a unit handler there which will return the UoM.

Imho for your use case it should be enough to query the rest api for the items once and extract the unit from the item value. You can use the normal rule handler for the openHAB rest api which will return the value unfiltered.
Do you think thatā€™ll work?

I already have implemented a solution by extracting the unit from the label, before starting to deal with the quantity type. So no hurry.

Maybe it would be helpful to provide the openHAB type in the OpenHabItem interface as well, as provided as ā€œtypeā€ in the REST API.

Keep getting this error, not sure if I got it after upgrading to 3.4.4 :thinking:
Running latest habapp (1.0.8)

[2023-05-31 14:49:56,163] [HABApp.openhab.connection]    ERROR | ValueError: Chunk too big
[2023-05-31 14:49:56,164] [HABApp.openhab.connection]  WARNING | Disconnected! Uncaught error in process_sse_events: Chunk too big
[2023-05-31 14:49:56,324] [HABApp.openhab.connection]     INFO | Connected to OpenHAB version 3.4.4 (Release Build)
[2023-05-31 14:49:57,188] [                   HABApp]    ERROR | Error <class 'bytes'> in on_connect_function:
[2023-05-31 14:49:57,188] [                   HABApp]    ERROR | --------------------------------------------------------------------------------
[2023-05-31 14:49:57,188] [                   HABApp]    ERROR | Traceback (most recent call last):
[2023-05-31 14:49:57,188] [                   HABApp]    ERROR |   File "/opt/habapp/lib/python3.9/site-packages/HABApp/core/wrapper.py", line 70, in a
[2023-05-31 14:49:57,189] [                   HABApp]    ERROR |     return await func(*args, **kwargs)
[2023-05-31 14:49:57,189] [                   HABApp]    ERROR |   File "/opt/habapp/lib/python3.9/site-packages/HABApp/openhab/connection_logic/plugin_load_items.py", line 35, in on_connect_function
[2023-05-31 14:49:57,189] [                   HABApp]    ERROR |     add_to_registry(new_item, True)
[2023-05-31 14:49:57,189] [                   HABApp]    ERROR |   File "/opt/habapp/lib/python3.9/site-packages/HABApp/openhab/item_to_reg.py", line 31, in add_to_registry
[2023-05-31 14:49:57,189] [                   HABApp]    ERROR |     existing.set_value(item.value)
[2023-05-31 14:49:57,189] [                   HABApp]    ERROR |   File "/opt/habapp/lib/python3.9/site-packages/HABApp/openhab/items/image_item.py", line 55, in set_value
[2023-05-31 14:49:57,190] [                   HABApp]    ERROR |     assert isinstance(new_value, RawValue) or new_value is None, type(new_value)
[2023-05-31 14:49:57,190] [                   HABApp]    ERROR | AssertionError: <class 'bytes'>
.. and again and again..

Edit: nevermind, seems its related to ValueError: Chunk too big Ā· Issue #352 Ā· spacemanspiff2007/HABApp Ā· GitHub and resolved by: Troubleshooting ā€” HABApp beta documentation

1 Like

Hi All,

i want to migrate from RulesDSL to HABApp but i canā€™t get the simplest Rule to work properly. Case description:

I want to create a rule which triggers on item changes or updates (doesnā€™t matter in a first step). In openHAB i have textual config for all my items and this item is configured as a switch item.

My *.items File:

Switch   MQTT_EG_Kinderzimmer_Links  "Links"  <poweroutlet>  (gStrom, gStromAbwesenheit) {channel="mqtt:topic:mqttbroker:StromKinderzimmer:Links"}

Karaf tells me:

openhab> openhab:status MQTT_EG_Kinderzimmer_Links
OFF

My HABApp rule.py

 import HABApp
 from HABApp.openhab.events import ItemStateEvent, ItemCommandEvent, ItemStateChangedEvent
 from HABApp.core.events import ValueUpdateEventFilter, ValueChangeEventFilter, ValueChangeEvent, ValueUpdateEvent
 from HABApp.openhab.items import SwitchItem, ContactItem, DatetimeItem

 class MySwitchRule(HABApp.Rule):

     def __init__(self):
         super().__init__()

         self.my_switch = SwitchItem.get_item('MQTT_EG_Kinderzimmer_Links')
         print("my_switch: " + self.my_switch.get_value())
         self.my_switch.listen_event(self.item_changed, ValueUpdateEventFilter())

    def item_changed(self, event: ValueUpdateEvent):
        print('Something changed')

 MySwitchRule()

I also tried nearly all other examples found on the documentation page, but i definitively canā€™t get it to work. The log reports

2023-06-08 22:56:42.302 [INFO ] [HABApp                    ] - HABApp Version 0.31.2
2023-06-08 22:56:42.307 [INFO ] [HABApp.openhab.thing      ] - Config folder does not exist - textual thing config disabled!
2023-06-08 22:56:42.308 [INFO ] [HABApp.RuleParameters     ] - Parameter files disabled: Folder /etc/openhab/habapp/params does not exist!
2023-06-08 22:56:42.313 [INFO ] [HABApp.mqtt.connection    ] - Connecting to 192.168.x.x:8883
2023-06-08 22:56:42.426 [INFO ] [HABApp.openhab.connection ] - Connected to OpenHAB instance 32cb88d8-459d-4eea-98ee-a2cc48edafbd
2023-06-08 22:56:42.426 [INFO ] [HABApp.openhab.connection ] - OpenHAB version 3.4.4 (Release Build)
2023-06-08 22:56:43.570 [INFO ] [HABApp.openhab.items      ] - Updated 1059 Items
2023-06-08 22:56:44.064 [INFO ] [HABApp.openhab.items      ] - Updated 136 Things
2023-06-08 22:56:48.041 [ERROR] [HABApp.Rules] - Error "__init__() missing 1 required positional argument: 'value'" in load:
2023-06-08 22:56:48.042 [ERROR] [HABApp.Rules] - Could not load /etc/openhab/habapp/rules/switchrule.py!
2023-06-08 22:56:48.042 [ERROR] [HABApp.Rules] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/rule_manager/rule_file.py", line 80, in load
2023-06-08 22:56:48.042 [ERROR] [HABApp.Rules] -     self.create_rules(created_rules)
2023-06-08 22:56:48.042 [ERROR] [HABApp.Rules] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/rule_manager/rule_file.py", line 69, in create_rules
2023-06-08 22:56:48.042 [ERROR] [HABApp.Rules] -     '__HABAPP__RULES': created_rules,
2023-06-08 22:56:48.042 [ERROR] [HABApp.Rules] - File "/usr/lib/python3.7/runpy.py", line 263, in run_path
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] -     pkg_name=pkg_name, script_name=fname)
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] - File "/usr/lib/python3.7/runpy.py", line 96, in _run_module_code
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] -     mod_name, mod_spec, pkg_name, script_name)
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] - File "/usr/lib/python3.7/runpy.py", line 85, in _run_code
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] -     exec(code, run_globals)
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] - File "/etc/openhab/habapp/rules/switchrule.py", line 19, in switchrule.py
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] -     15       def item_changed(self, event: ValueUpdateEvent):
2023-06-08 22:56:48.043 [ERROR] [HABApp.Rules] -     16           assert isinstance(event, ValueUpdateEvent), type(event)
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] -     17           print('Something changed')
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] -     18
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] - --> 19   MySwitchRule()
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] -     ..................................................
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] -      ValueUpdateEvent = <class 'HABApp.core.events.events.ValueUpdateEvent'>
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] -      MySwitchRule = <class '/etc/openhab/habapp/rules/switchrule.py.MySwitchRule'>
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] -     ..................................................
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] -
2023-06-08 22:56:48.044 [ERROR] [HABApp.Rules] - File "/etc/openhab/habapp/rules/switchrule.py", line 13, in __init__
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] -     8    def __init__(self):
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] -     9        super().__init__()
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] -     10
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] -     11       self.my_switch = SwitchItem.get_item('MQTT_EG_Kinderzimmer_Links')
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] -     12       print("my_switch: " + self.my_switch.get_value())
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] - --> 13       self.my_switch.listen_event(self.item_changed, ValueUpdateEventFilter())
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] -     ..................................................
2023-06-08 22:56:48.045 [ERROR] [HABApp.Rules] -      self = </etc/openhab/habapp/rules/switchrule.py.MySwitchRule object at 0xb3f77630>
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -      self.my_switch = <SwitchItem name: MQTT_EG_Kinderzimmer_Links, value: ON, last_change: 2023-06-08T22:56:43.567025, last_update: 2023-06-08T22:56:43.567025>
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -      SwitchItem.get_item = <method 'BaseItem.get_item' of <class 'HABApp.openhab.items.switch_item.SwitchItem'> base_item.py:18>
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -      self.my_switch.get_value = <method 'BaseValueItem.get_value' of ON base_valueitem.py:62>
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -      self.my_switch.listen_event = <method 'BaseItem.listen_event' of ON base_item.py:102>
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -      self.item_changed = <method 'MySwitchRule.item_changed' of </etc/openhab/habapp/rules/switchrule.py.MySwitchRule object at 0xb3f77630> switchrule.py:15>
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -      ValueUpdateEventFilter = <class 'HABApp.core.events.event_filters.ValueUpdateEventFilter'>
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -     ..................................................
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] -
2023-06-08 22:56:48.046 [ERROR] [HABApp.Rules] - TypeError: __init__() missing 1 required positional argument: 'value'
2023-06-08 22:56:48.049 [WARN ] [HABApp.Rules] - Failed to load /etc/openhab/habapp/rules/switchrule.py!
2023-06-08 22:56:52.213 [ERROR] [HABApp      ] - Error 'topic' in on_sse_event:
2023-06-08 22:56:52.214 [ERROR] [HABApp      ] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/openhab/connection_handler/sse_handler.py", line 25, in on_sse_event
2023-06-08 22:56:52.214 [ERROR] [HABApp      ] -     22   def on_sse_event(event_dict: dict):
2023-06-08 22:56:52.214 [ERROR] [HABApp      ] -     23       try:
2023-06-08 22:56:52.214 [ERROR] [HABApp      ] -     24           # Lookup corresponding OpenHAB event
2023-06-08 22:56:52.214 [ERROR] [HABApp      ] - --> 25           event = get_event(event_dict)
2023-06-08 22:56:52.214 [ERROR] [HABApp      ] -     26
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] -      event_dict = {'type': 'ALIVE',
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] -                    'interval': 10}
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] -
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/openhab/map_events.py", line 29, in get_event
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] -     27   def get_event(_in_dict: dict) -> OpenhabEvent:
2023-06-08 22:56:52.215 [ERROR] [HABApp      ] -     28       event_type: str = _in_dict['type']
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] - --> 29       topic: str = _in_dict['topic']
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -     30
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -      _in_dict = {'type': 'ALIVE',
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -                  'interval': 10}
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -      OpenhabEvent = <class 'HABApp.openhab.events.base_event.OpenhabEvent'>
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -      event_type = 'ALIVE'
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:56:52.216 [ERROR] [HABApp      ] -
2023-06-08 22:56:52.217 [ERROR] [HABApp      ] - KeyError: 'topic'
2023-06-08 22:57:02.212 [ERROR] [HABApp      ] - Error 'topic' in on_sse_event:
2023-06-08 22:57:02.212 [ERROR] [HABApp      ] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/openhab/connection_handler/sse_handler.py", line 25, in on_sse_event
2023-06-08 22:57:02.213 [ERROR] [HABApp      ] -     22   def on_sse_event(event_dict: dict):
2023-06-08 22:57:02.213 [ERROR] [HABApp      ] -     23       try:
2023-06-08 22:57:02.213 [ERROR] [HABApp      ] -     24           # Lookup corresponding OpenHAB event
2023-06-08 22:57:02.213 [ERROR] [HABApp      ] - --> 25           event = get_event(event_dict)
2023-06-08 22:57:02.213 [ERROR] [HABApp      ] -     26
2023-06-08 22:57:02.213 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:02.214 [ERROR] [HABApp      ] -      event_dict = {'type': 'ALIVE',
2023-06-08 22:57:02.214 [ERROR] [HABApp      ] -                    'interval': 10}
2023-06-08 22:57:02.214 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:02.214 [ERROR] [HABApp      ] -
2023-06-08 22:57:02.214 [ERROR] [HABApp      ] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/openhab/map_events.py", line 29, in get_event
2023-06-08 22:57:02.214 [ERROR] [HABApp      ] -     27   def get_event(_in_dict: dict) -> OpenhabEvent:
2023-06-08 22:57:02.215 [ERROR] [HABApp      ] -     28       event_type: str = _in_dict['type']
2023-06-08 22:57:02.215 [ERROR] [HABApp      ] - --> 29       topic: str = _in_dict['topic']
2023-06-08 22:57:02.215 [ERROR] [HABApp      ] -     30
2023-06-08 22:57:02.215 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:02.215 [ERROR] [HABApp      ] -      _in_dict = {'type': 'ALIVE',
2023-06-08 22:57:02.215 [ERROR] [HABApp      ] -                  'interval': 10}
2023-06-08 22:57:02.216 [ERROR] [HABApp      ] -      OpenhabEvent = <class 'HABApp.openhab.events.base_event.OpenhabEvent'>
2023-06-08 22:57:02.216 [ERROR] [HABApp      ] -      event_type = 'ALIVE'
2023-06-08 22:57:02.216 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:02.216 [ERROR] [HABApp      ] -
2023-06-08 22:57:02.216 [ERROR] [HABApp      ] - KeyError: 'topic'
2023-06-08 22:57:12.214 [ERROR] [HABApp      ] - Error 'topic' in on_sse_event:
2023-06-08 22:57:12.214 [ERROR] [HABApp      ] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/openhab/connection_handler/sse_handler.py", line 25, in on_sse_event
2023-06-08 22:57:12.215 [ERROR] [HABApp      ] -     22   def on_sse_event(event_dict: dict):
2023-06-08 22:57:12.215 [ERROR] [HABApp      ] -     23       try:
2023-06-08 22:57:12.215 [ERROR] [HABApp      ] -     24           # Lookup corresponding OpenHAB event
2023-06-08 22:57:12.215 [ERROR] [HABApp      ] - --> 25           event = get_event(event_dict)
2023-06-08 22:57:12.215 [ERROR] [HABApp      ] -     26
2023-06-08 22:57:12.216 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:12.216 [ERROR] [HABApp      ] -      event_dict = {'type': 'ALIVE',
2023-06-08 22:57:12.216 [ERROR] [HABApp      ] -                    'interval': 10}
2023-06-08 22:57:12.216 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:12.216 [ERROR] [HABApp      ] -
2023-06-08 22:57:12.216 [ERROR] [HABApp      ] - File "/opt/habapp/lib/python3.7/site-packages/HABApp/openhab/map_events.py", line 29, in get_event
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] -     27   def get_event(_in_dict: dict) -> OpenhabEvent:
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] -     28       event_type: str = _in_dict['type']
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] - --> 29       topic: str = _in_dict['topic']
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] -     30
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] -      _in_dict = {'type': 'ALIVE',
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] -                  'interval': 10}
2023-06-08 22:57:12.217 [ERROR] [HABApp      ] -      OpenhabEvent = <class 'HABApp.openhab.events.base_event.OpenhabEvent'>
2023-06-08 22:57:12.218 [ERROR] [HABApp      ] -      event_type = 'ALIVE'
2023-06-08 22:57:12.218 [ERROR] [HABApp      ] -     ..................................................
2023-06-08 22:57:12.218 [ERROR] [HABApp      ] -
2023-06-08 22:57:12.218 [ERROR] [HABApp      ] - KeyError: 'topic'

So i see
KeyError: ā€˜topicā€™
Error ā€˜topicā€™ in on_sse_event:
and
TypeError: init() missing 1 required positional argument: ā€˜valueā€™

After 3 hours i made no progress at all and i lost all my power. Would anybody be so keen and post a working example and tell me, what my issue is?

Additional question: I am still confused about the ā€œinternalā€ items and the ā€œopenHABā€ items. Which one should i use and why? Is there a benefit using the internals over the openHAB ones or vice versa? I dont get it.

Third question: Is there a habapp plugin for vscode available? Or any other plugin for vscode you would recommend?

Thanks so much for your support
Patrick

Your rule is correct. However HABApp requires Python >= 3.8 and you are still on 3.7.
So you installed the last version that was supported on 3.7 which is from the end of 2021.
The latest version is 1.0.8.
You have to upgrade you python version (e.g. through an updated version of you distribution if you are on linux or through a manual update).

Maybe run HABApp on your dev machine first - itā€™s no problem to connect to openHAB remotely.
There you can try out everything without a hastle.

OpenHAB items are probably clear. HABApp items are HABApp internal items that donā€™t get propagated.
Think about them e.g. as global variables that you can share across multiple rules but you can also trigger on changes / on update / on no change / etc. . That makes them very powerful to split complex logic into smaller peaces.
Additionally there are internal item types that makes different things for you very easy, e.g. the aggregation item, the multimode item which allows you to overlay multiple states (e.g. manual and automatic mode).

I use the multimode item for my shutters:
I have an automatic mode which opens in the morning and closes in the night, another mode which does shading if itā€™ll be too hot, a frost protection mode which prevents from moving the shutters when they are likely frozen together and a venting mode if I open the window at night (all triggered from HABApp rules).
Then I have a manual mode that gets triggered from openHAB items which overrides the current logic but will also automatically get disabled if the manual state matches the target stateā€¦
All these modes gut into one multimode item which does the processing and selects the appropriate output value.

The multimode item allows me to split the logic across various smaller rules and I trigger then on a ValueUpdateEvent on the multimode item to send the command to the openHAB shutter item.

So as a rule of thumb:
If you want to pass values across multiple rule files (e.g. an intermediate value) or you want to use the HABApp internal items itā€™s a HABApp internal item.
If you want to see the value in the gui or if you want to send commands itā€™s an openHAB item.

You just have to install HABApp in your python interpreter that you have configured in vscode.
Then youā€™ll get all the highlighting.

Hey @Spaceman_Spiff

you are really awesome. Your answer was very explanatory to me and i did understand a lot. It took now the whole evening but i am now on python3.11.4 and i also reinstalled habapp. My config there remained (cool), but now i do get some Errors reported and still the rule seems not to work (no output visible) So the HABApp.log says

2023-06-09 22:47:02.659 [INFO ] [HABApp        ] - HABApp Version 1.0.8
2023-06-09 22:47:02.659 [ERROR] [HABApp.Config ] - "logging.handlers.MemoryHandler" is no longer required. Please remove from config (BufferEventFile)!
2023-06-09 22:47:02.660 [WARN ] [HABApp.Config ] - Removed BufferEventFile from handlers
2023-06-09 22:47:02.660 [WARN ] [HABApp.Config ] - Replaced BufferEventFile with EventFile for logger HABApp.EventBus
2023-06-09 22:47:02.694 [ERROR] [HABApp.Config ] - 6 validation errors for ApplicationConfig
2023-06-09 22:47:02.694 [ERROR] [HABApp.Config ] - mqtt -> connection -> tls
2023-06-09 22:47:02.694 [ERROR] [HABApp.Config ] -   value is not a valid dict (type=type_error.dict)
2023-06-09 22:47:02.694 [ERROR] [HABApp.Config ] - mqtt -> connection -> tls_ca_cert
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] -   extra fields not permitted (type=value_error.extra)
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] - mqtt -> connection -> tls_insecure
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] -   extra fields not permitted (type=value_error.extra)
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] - mqtt -> subscribe -> topics
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] -   'int' object is not iterable (type=type_error)
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] - openhab -> connection -> host
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] -   extra fields not permitted (type=value_error.extra)
2023-06-09 22:47:02.695 [ERROR] [HABApp.Config ] - openhab -> connection -> port
2023-06-09 22:47:02.696 [ERROR] [HABApp.Config ] -   extra fields not permitted (type=value_error.extra)

I only have two config files at /etc/openhab/habapp

config.yml (anonymized)

directories:
  logging: /var/log/openhab  # Folder where the logs will be written to
  rules: rules # Folder from which the rule files will be loaded
  param: params # Folder from which the parameter files will be loaded
  config: config # Folder from which configuration files (e.g. for textual thing configuration) will be loaded
  lib: lib # Folder where additional libraries can be placed
location:
  latitude: 0
  longitude: 0
  elevation: 0
mqtt:
  connection:
    client_id: HABApp
    host: '192.168.x.x'
    port: 8883
    user: 'myuser'
    password: 'mypassword'
    tls: true
    tls_ca_cert: ''  # Path to a CA certificate that will be treated as trusted
    tls_insecure: false
  general:
    listen_only: false  # If True HABApp will not publish any value to the broker
  publish:
    qos: 0  # Default QoS when publishing values
    retain: true # Default retain flag when publishing values
  subscribe:
    qos: 0  # Default QoS for subscribing
    topics:
    - '#'
    - 0
openhab:
  connection:
    host: localhost
    port: 8080
    user: 'myuser'
    password: 'mypassword'
  general:
    listen_only: false  # If True HABApp will not change anything on the openHAB instance.
    wait_for_openhab: true # If True HABApp will wait for items from the openHAB instance before loading any rules on startup
  ping:
    enabled: true  # If enabled the configured item will show how long it takes to send an update from HABApp and get the updated value back from openhabin milliseconds
    item: HABApp_Ping # Name of the Numberitem
    interval: 300 # Seconds between two pings

logging.yml


levels:
  WARNING: WARN

formatters:
  HABApp_format:
    format: '[%(asctime)s] [%(name)25s] %(levelname)8s | %(message)s'

  Frontail_format:
    format: '%(asctime)s.%(msecs)03d [%(levelname)-5s] [%(name)-36s] - %(message)s'
    datefmt: '%Y-%m-%d %H:%M:%S'

handlers:
  # There are several Handlers available:
  #  - logging.handlers.RotatingFileHandler:
  #    Will rotate when the file reaches a certain size (see python logging documentation for args)
  #  - HABApp.core.lib.handler.MidnightRotatingFileHandler:
  #    Will wait until the file reaches a certain size and then rotate on midnight
  #  - More handlers:
  #    https://docs.python.org/3/library/logging.handlers.html#rotatingfilehandler

  HABApp_default:
    #class: HABApp.core.lib.handler.MidnightRotatingFileHandler
    class: HABApp.config.logging.MidnightRotatingFileHandler
    filename: '/var/log/openhab/HABApp.log'
    maxBytes: 1_048_576
    backupCount: 3

    formatter: Frontail_format
    level: DEBUG

  EventFile:
    #class: HABApp.core.lib.handler.MidnightRotatingFileHandler
    class: HABApp.config.logging.MidnightRotatingFileHandler
    filename: 'HABApp_events.log'
    maxBytes: 1_048_576
    backupCount: 3

    formatter: HABApp_format
    level: DEBUG

  BufferEventFile:
    class: logging.handlers.MemoryHandler
    capacity: 10
    formatter: HABApp_format
    target: EventFile
    level: DEBUG


loggers:
  HABApp:
    level: INFO
    handlers:
      - HABApp_default
    propagate: False

  HABApp.EventBus:
    level: INFO
    handlers:
      - BufferEventFile
    propagate: False

Could you tell me, what i have to do to fix the issues?

Second question to your fantastic explanation on ā€œinternalā€ and ā€œopenHABā€ items in HABApp: Is it than true, that updating / commanding an internal item is not populated to openHAB?
How is the other way round? Are openHAB states populated to the internal items?

Thanks soooo much for your support, really appreciate it! Really!
Patrick

The config format of the config.yml changed. Just rename your old config to e.g. config_old and let HABApp recreate a new config. Then you can copy paste the values from your old config (see example of new config, especially mqtt -> connection -> tls and openhab -> connection -> url)

All items are HABApp items (obviously since we are in the HABApp context).
However there are openHAB items in HABApp, MQTT items and internal items.
The items from HABApp reflect the state from openHAB thus if the item changes in openHAB it changes in HABApp. If you send a command to the openHAB item it will send the command to openHAB.

Internal items will not be propagated or updated from external sources since they are internal.

Itā€™s always clear what is what because the item name has to be unique.
E.g. if you have an openHAB item in HABApp you can not create an internal item with the same name.

@Spaceman_Spiff ! You are great. Everything now runs as intended and i do get the output.

Just two final question:

First: When using Karaf the EventListener triggers once as intended, but when i use the sitemap and toggle the item, the EventListener triggers twice

Frontail log

2023-06-10 08:22:55.097 [INFO ] [openhab.event.ItemCommandEvent      ] - Item 'MQTT_EG_Kinderzimmer_Links' received command OFF
2023-06-10 08:22:55.099 [INFO ] [penhab.event.ItemStatePredictedEvent] - Item 'MQTT_EG_Kinderzimmer_Links' predicted to become OFF
2023-06-10 08:22:55.115 [INFO ] [openhab.event.ItemStateChangedEvent ] - Item 'MQTT_EG_Kinderzimmer_Links' changed from ON to OFF

Second: Is there a way to output the names of all internal items (which are created during initialization)?

Thanks for your fantastic support and your contribution to this project
Patrick

All openHAB items are synced into HABApp during start up so you can use all of them.

I donā€™t understand that question. Can you rephrase or post an example where I can see how something doesnā€™t work as expected?

Hi @Spaceman_Spiff

sure i do have an example. I just slightly changed the rule to

import HABApp
from HABApp.openhab.events import ItemStateEvent, ItemCommandEvent, ItemStateChangedEvent
from HABApp.core.events import ValueUpdateEventFilter, ValueChangeEventFilter, ValueChangeEvent, ValueUpdateEvent
from HABApp.openhab.items import SwitchItem, ContactItem, DatetimeItem

class MySwitchRule(HABApp.Rule):

    def __init__(self):
        super().__init__()

        self.my_switch = SwitchItem.get_item('MQTT_EG_Kinderzimmer_Links')
        print("my_switch: " + self.my_switch.get_value())
        self.my_switch.listen_event(self.item_changed, ValueUpdateEventFilter())

    def item_changed(self, event: ValueUpdateEvent):
        # Check if event is ValueUpdateEvent
        assert isinstance(event, ValueUpdateEvent), type(event)


        print('Changed '+event.name+' to: '+event.value)

MySwitchRule()

Which then gives in the console when i toggle the Switch in openHAB twice (toggeling ON and following OFF). See that the phrase ā€œChanged ā€¦ā€ is repeated.

 14:14:10 ī‚° patrick@openHAB ī‚° ~ ī‚° 33s ī‚°
$ /opt/habapp/bin/habapp -c /etc/openhab/habapp
  _   _    _    ____    _
 | | | |  / \  | __ )  / \   _ __  _ __
 | |_| | / _ \ |  _ \ / _ \ | '_ \| '_ \
 |  _  |/ ___ \| |_) / ___ \| |_) | |_) |
 |_| |_/_/   \_|____/_/   \_| .__/| .__/
                            |_|   |_|
                                        1.0.8
my_switch: OFF
Changed MQTT_EG_Kinderzimmer_Links to: ON
Changed MQTT_EG_Kinderzimmer_Links to: ON
Changed MQTT_EG_Kinderzimmer_Links to: OFF
Changed MQTT_EG_Kinderzimmer_Links to: OFF

Frontail gives:

2023-06-10 14:13:57.750 [INFO ] [openhab.event.ItemCommandEvent      ] - Item 'MQTT_EG_Kinderzimmer_Links' received command ON
2023-06-10 14:13:57.752 [INFO ] [penhab.event.ItemStatePredictedEvent] - Item 'MQTT_EG_Kinderzimmer_Links' predicted to become ON
2023-06-10 14:13:57.769 [INFO ] [openhab.event.ItemStateChangedEvent ] - Item 'MQTT_EG_Kinderzimmer_Links' changed from OFF to ON
2023-06-10 14:14:33.497 [INFO ] [openhab.event.ItemCommandEvent      ] - Item 'MQTT_EG_Kinderzimmer_Links' received command OFF
2023-06-10 14:14:33.499 [INFO ] [penhab.event.ItemStatePredictedEvent] - Item 'MQTT_EG_Kinderzimmer_Links' predicted to become OFF
2023-06-10 14:14:33.513 [INFO ] [openhab.event.ItemStateChangedEvent ] - Item 'MQTT_EG_Kinderzimmer_Links' changed from ON to OFF

What do you think where this is coming from.

Thx
Patrick

Edit: I also see this in HABApp.log. How can i fix this?

160 2023-06-10 14:15:27.367 [WARN ] [HABApp.Rule ] - /opt/habapp/lib/python3.11/site-packages/paho/mqtt/client.py:1782: ResourceWarning:unclosed <ssl.SSLSocket fd=10, family=2, type=1, proto=6, laddr=('192.168.x.x', 3    2923)>
161 2023-06-10 14:16:31.371 [WARN ] [HABApp.Rule ] - /opt/habapp/lib/python3.11/site-packages/paho/mqtt/client.py:1782: ResourceWarning:unclosed <ssl.SSLSocket fd=10, family=2, type=1, proto=6, laddr=('192.168.x.x, 3    7687)>
162 2023-06-10 14:18:31.375 [WARN ] [HABApp.Rule ] - /opt/habapp/lib/python3.11/site-packages/paho/mqtt/client.py:1782: ResourceWarning:unclosed <ssl.SSLSocket fd=10, family=2, type=1, proto=6, laddr=('192.168.x.x', 4    4707)>
163 2023-06-10 14:20:31.378 [WARN ] [HABApp.Rule ] - /opt/habapp/lib/python3.11/site-packages/paho/mqtt/client.py:1782: ResourceWarning:unclosed <ssl.SSLSocket fd=10, family=2, type=1, proto=6, laddr=('192.168.x.x', 4    0557)>

It should be

print(f'my_switch: {self.my_switch.value}')

You listen to the item state update events. These events are not shown in fronttail.
Check the HABApp_events.log, there you will find all events.
Then youā€™ll probably see thet it gets issued twice.
If not then you have probably a duplicate rule running

Changed the print as recommended.

You were right, HABApp_events.log mentions 2 Item State Events. Why is this the case? There is only 1 file in the rules folder, i.e. the one posted above. In addition, i have deactivated mqtt so that the other issue mentioned above does not occur anymore.

I would expect just one ā€œChanged MQTT_EG_Kinderzimmer_Links to: ā€¦ā€

173 [2023-06-10 20:43:33,131] [HABApp.EventBus] INFO | MQTT_EG_Kinderzimmer_Links: <ItemCommandEvent name: MQTT_EG_Kinderzimmer_Links, value: OFF>
174 [2023-06-10 20:43:33,147] [HABApp.EventBus] INFO | MQTT_EG_Kinderzimmer_Links: <ItemStatePredictedEvent name: MQTT_EG_Kinderzimmer_Links, value: OFF>
175 [2023-06-10 20:43:33,147] [HABApp.EventBus] INFO | MQTT_EG_Kinderzimmer_Links: <ItemStateEvent name: MQTT_EG_Kinderzimmer_Links, value: OFF>
176 [2023-06-10 20:43:33,151] [HABApp.EventBus] INFO | MQTT_EG_Kinderzimmer_Links: <ItemStateChangedEvent name: MQTT_EG_Kinderzimmer_Links, value: OFF, old_value: ON>
177 [2023-06-10 20:43:33,162] [HABApp.EventBus] INFO | MQTT_EG_Kinderzimmer_Links: <ItemStateEvent name: MQTT_EG_Kinderzimmer_Links, value: OFF>

The HABApp_event log shows the events from openHAB. I can not answer why there are two ItemStateEvents. Itā€™s probably specific to your openHAB installation

Then you need to trigger on a ItemStateChengedEvend or a ValueChangedEvent.
Currently you you listening to a ValueUpdateEvent