AppDaemon Q&A

there are a couple of sample files in the scripts directory for setting it up under init.d Those worked for me.

@hoffsta
Try this:

sudo systemctl --system daemon-reload
sudo systemctl enable appdaemon
sudo systemctl start appdaemon

big smile :wink:
i will really try another update soon, but between 0.29 and 0.35 there were some problems making ha run wild with my mysensors and thats a very big part of my automation.
right now i have backup images lying ready, so its more easy to update and go back if it doesnt work.

1 Like

Thanks! That did the trick. Now I have another issue. I’m trying to run my first app, called Flux (https://github.com/fronzbot/githass/blob/master/apps/flux.py)

When I launch AppDaemon with the systemd process I receive this error:

Jan 26 21:37:24 homeassistant appdaemon[27675]: raise TypeError(msg.format(name))
Jan 26 21:37:24 homeassistant appdaemon[27675]: TypeError: the 'package' argument is required to perform a relative import for '._flux'
Jan 26 21:37:24 homeassistant appdaemon[27675]: 2017-01-26 21:37:24.210709 WARNING ------------------------------------------------------------

I’m not sure what the “package argument” is all about. Thanks!

Can you post the whole error please.

Here is all the startup messages, after this it looks like it’s just a ton of pulling states from HASS components.

pi@homeassistant:~ $ appdaemon -c /home/homeassistant/.homeassistant/appdaemon/appdaemon.cfg -D DEBUG
2017-01-27 09:06:17.879072 DEBUG get_ha_config()
2017-01-27 09:06:18.185135 WARNING 'latitude' directive is deprecated, please remove
2017-01-27 09:06:18.186233 WARNING 'longitude' directive is deprecated, please remove
2017-01-27 09:06:18.341173 INFO AppDaemon Version 1.4.2 starting
2017-01-27 09:06:18.341912 DEBUG Entering run()
2017-01-27 09:06:18.446665 DEBUG Creating worker threads ...
2017-01-27 09:06:18.452958 DEBUG Done
2017-01-27 09:06:18.453669 DEBUG Calling HA for initial state
2017-01-27 09:06:18.454206 DEBUG Refreshing HA state
2017-01-27 09:06:18.454689 DEBUG get_ha_state: entity is None
2017-01-27 09:06:23.732083 INFO Got initial state
2017-01-27 09:06:23.732985 DEBUG Reading Apps
2017-01-27 09:06:23.739403 INFO Loading Module: /home/homeassistant/.homeassistant/appdaemon/apps/._flux.py
2017-01-27 09:06:23.740146 WARNING ------------------------------------------------------------
2017-01-27 09:06:23.740775 WARNING Unexpected error during loading of ._flux.py:
2017-01-27 09:06:23.741290 WARNING ------------------------------------------------------------
2017-01-27 09:06:23.746123 WARNING Traceback (most recent call last):
  File "/usr/local/lib/python3.4/dist-packages/appdaemon/appdaemon.py", line 717, in readApp
    conf.modules[module_name] = importlib.import_module(module_name)
  File "/usr/lib/python3.4/importlib/__init__.py", line 104, in import_module
    raise TypeError(msg.format(name))
TypeError: the 'package' argument is required to perform a relative import for '._flux'

2017-01-27 09:06:23.746887 WARNING ------------------------------------------------------------
2017-01-27 09:06:23.747646 INFO Loading Module: /home/homeassistant/.homeassistant/appdaemon/apps/hello.py
2017-01-27 09:06:23.751036 INFO Loading Object hello_world using class HelloWorld from module hello
2017-01-27 09:06:23.752623 INFO hello_world: Hello from AppDaemon
2017-01-27 09:06:23.753312 INFO hello_world: You are now ready to run Apps!
2017-01-27 09:06:23.753976 INFO Loading Module: /home/homeassistant/.homeassistant/appdaemon/apps/flux.py
2017-01-27 09:06:23.756815 INFO App initialization complete
2017-01-27 09:06:23.757581 DEBUG Starting timer thread
2017-01-27 09:06:23.758919 INFO Connecting to HA
2017-01-27 09:06:29.650450 DEBUG Event type:state_changed:
2017-01-27 09:06:29.651645 DEBUG {'old_state': {'state': '09:05', 'last_updated': '2017-01-27T17:05:27.507052+00:00', 'attributes': {'friendly_name': 'Time', 'icon': 'mdi:clock'}, 'last_changed': '2017-01-27T17:05:27.507052+00:00', 'entity_id': 'sensor.time'}, 'entity_id': 'sensor.time', 'new_state': {'state': '09:06', 'last_updated': '2017-01-27T17:06:29.506829+00:00', 'attributes': {'friendly_name': 'Time', 'icon': 'mdi:clock'}, 'last_changed': '2017-01-27T17:06:29.506829+00:00', 'entity_id': 'sensor.time'}}
2017-01-27 09:06:29.652439 DEBUG Entity ID:sensor.time:

AppDaemon is finding something called “._flux.py” that is confusing the import - is the actual app called flux.py ass in github? If so, what is this file?

The only files in my apps folder were “flux.py”, “hello.py”, and “pycache” directory with cache files for those two apps. There was nothing called “._flux” anywhere.

Your message got me thinking…I originally copied the flux.py code text from the github page and pasted it into a new file on my Macbook in Atom editor to make some changes for my environment. I then moved the file into place with Samba. I’ve seen those weird ghost files before when sharing documents between Windows and Mac file systems so I thought that might explain it. I went ahead and deleted flux.py and then used nano to create a new file from command line. Now, no more error on startup. I guess you learn something new everyday! Thank you for your reply

Cool - glad you got it working!

Do share! I saw the post and it disappeared from underneath me!

Sorry, beginner’s error. I failed to put the arguments about the app into appdaemon.cfg. Didn’t realize all of this was needed in .cfg:

[Flux]
module = flux
class = Flux
constrain_input_boolean = input_boolean.flux
light = light.bedroom, light.silas_lamp

That is one thing I have wondered about. Why do apps that are not in the cfg file, run? It is annoying when test applications I have written attempt to launch every time I restart AD.

Because so far for me it hasn’t been a big enough problem to make the effort to stop it :wink: The way it is coded I would have to write extra logic to stop it. Not saying I won’t, just saying that the output of an extra couple of lines in a log hasn’t motivated me to do so yet! Also, I generally don’t have apps I am not running in the directory,

1 Like

like I said it’s annoying. There are other things much more important to work on. Because of the “terminate” thing :wink: :blush: :smile: I’ve been writing programs in python to work out issues with SNMP and Google Calendar, etc. That way I don’t have to keep rebooting till most of my debugging is done. That’s why the code is in there.

What’s the best way of going about stopping a script?

I have a sequence of events happening, if a switch is turned on. I’d like this sequence to stop in its tracks, if the switch is turned off while the sequence is running.

Any tips? :grin:

Martin

Do you actually mean stopping a script or an App?

Since you posted this in here, I’m going to go with the assumption, you are doing this in AD. Best a relative term, but with my limited knowledge of python they all seem to come back to if statements at good stopping points in your app. Although maybe there is a way to kill an app from outside it, but that would leave your environment in a unknown, potentially messy state. If that is there you would definitely need to put in a terminate function to do the cleanup the next time the app is run.

I would setup an event to be triggered on the switch turning off.
Have the handler for that event set a variable for the app
then at logical stopping points, check the variable and dump out to a exit routine that does whatever cleanup is needed.

I agree with @turboc - there is no way to stop an App, but Apps can easily be made smart enough to handle incoming events that modify their behavior.

@turboc @aimc Does something along the lines of:

if self.args["switch"] == "off":
        cleanup()

interspersed strategically sound like the most efficient solution?
Thanks for your help! :slight_smile:

That that would look at the value in the config file. and changing that would bounce AD anyway. I thought you wanted to either flip a input binary switch in HA or a physical light switch to cause the automation to stop.

So I was thinking something like
(psudo code, there will be errors)

if get_state("input_boolean.stop_it)=="on"
  cleanup_and_stop()

interspersed through the code, or a more efficient solution might be (again psudo code

in initialize
  listen_event("callbackstop_it","input_boolean_stop_it")

def callbackstop_it(self,entity,kwargs)  i think
  if get_state(entity)=="on":
    self.stop_it=True
  else:
    self.stop_it=False


Then interspersed in your code
if self.stop_it==True:
  stop_it_and_exit()

it’s more code, but the get_state is only called when the state changes so it’s more efficient.