n00b here. Trying to get to grips with AppDaemon. Either my Google-fu is lacking or I’m doing something stupid noone’s ever tried before. I’m guessing the former
The AppDaemon manual also doesn’t cover this use-case. So, I’m kinda stuck.
I have an AppDaemon app that consists of various modules to split functionality into logical groups. I can have the app start a callback to a function in one of the other modules, but then I loose access to the class’s “self” object.
Below is a minimal example of what I’m trying to do. I’m using a fast-firing sensor (CPU load) for testing.
qlisten.yaml
---
listen_cpuload:
module: qlisten
class: QListen
listen_for: sensor.system_monitor_load_1_min
attribute: state
priority: 100
qlisten.py
import appdaemon.plugins.hass.hassapi as hass
import qextern_cb as xt_cb
class QListen(hass.Hass):
def initialize(self):
entity = self.args.get("listen_for")
attribute = self.args.get("attribute")
self.listen_state(self.state_changed, entity, attribute=attribute). # <- this works
self.listen_state(xt_cb.state_changed, entity, attribute=attribute) # <- this doesn't work
self.log(f"\n\t*** Listening to entity: {entity}, attribute: {attribute}")
def state_changed(self, *args, **kwargs):
self.log(f"State changed in class ...")
qextern_cb.py
def state_changed(fles, *args, **kwargs):
fles.log(f"State changed in external ...")
Here’s the log that is generated:
2025-06-01 16:55:16.169566 INFO AppDaemon: Starting apps: {‘listen_cpuload’}
2025-06-01 16:55:16.172620 INFO AppDaemon: Calling initialize() for listen_cpuload
2025-06-01 16:55:16.175391 INFO listen_cpuload:
*** Listening to entity: sensor.system_monitor_load_1_min, attribute: state
2025-06-01 16:55:22.176067 INFO listen_cpuload: State changed in class …
2025-06-01 16:55:22.179788 ERROR listen_cpuload: ===== state_changed for listen_cpuload ==================================
2025-06-01 16:55:22.180068 ERROR listen_cpuload: StateCallbackFail: State callback failed for ‘sensor.system_monitor_load_1_min’ from ‘listen_cpuload’
2025-06-01 16:55:22.180220 ERROR listen_cpuload: args: (‘sensor.system_monitor_load_1_min’, ‘state’, ‘0.52’, ‘0.48’)
2025-06-01 16:55:22.180348 ERROR listen_cpuload: kwargs: {
2025-06-01 16:55:22.180463 ERROR listen_cpuload: “__thread_id”: “thread-5”
2025-06-01 16:55:22.180574 ERROR listen_cpuload: }
2025-06-01 16:55:22.181085 ERROR listen_cpuload: AttributeError: ‘str’ object has no attribute ‘log’
2025-06-01 16:55:22.181514 ERROR listen_cpuload: File “/usr/lib/python3.12/site-packages/appdaemon/threads.py”, line 1075, in safe_callback
2025-06-01 16:55:22.181633 ERROR listen_cpuload: funcref()
2025-06-01 16:55:22.181728 ERROR listen_cpuload: File “/config/apps/quicklisten/qextern_cb.py”, line 3, in state_changed
2025-06-01 16:55:22.181821 ERROR listen_cpuload: fles.log(f"State changed in external …")
2025-06-01 16:55:22.181907 ERROR listen_cpuload: ^^^^^^^^
2025-06-01 16:55:22.181993 ERROR listen_cpuload: ===========================================================================
Why is fles
suddenly a str
? I was expecting it to be the class’s self
object. And how do I pass access to self
to the other module?
Any insights and help appreciated.