Python error handling with touchphat script

I set up my touchphat a while ago and it works well on the whole. The only issue I have with it is the Python script that works with it. My script switches on and off my amplifier over Telnet and this works well most of the time. But if for some reason there is a problem with the amp…it could be that the telnet session hadn’t closed properly or that the amp is powered off for some reason…then the script exits with an error.

Is there anyway I can add to the code in the script and tell it to carry on even if there is a problem connecting over telnet? Tell it to just ignore the issue. Otherwise I have to get my laptop, log into the touchphat pi and restart the script…which is obviously not ideal.

Here is my script:

#!/usr/bin/env python

import signal
import time
import touchphat
import os
import telnetlib
from kodijson import Kodi
#from time import sleep

my_kodi = Kodi(‘http://192.168.0.8:8080/jsonrpc’)
tn = telnetlib.Telnet(‘192.168.0.2’)

@touchphat.on_release([‘A’])
def handle_touch(event):
print(“Kitchen Amp Off”)
time.sleep(.1)

tn.close()
time.sleep(.2)
tn.open(‘192.168.0.2’)
tn.write(“ST04OFF\r\n”)
tn.close()
time.sleep(.2)

@touchphat.on_touch([‘A’])
def handle_touch(event):
print(“Kitchen Room Amp On”)
my_kodi.Settings.SetSettingValue({ “setting”:“audiooutput.audiodevice”,“value”:“ALSA:sysdefault:CARD=IQaudIODAC” })
time.sleep(.1)

tn.close()
time.sleep(.2)
tn.open(‘192.168.0.2’)
tn.write(“ST04ASIG\r\n”)
tn.close()
time.sleep(.2)

signal.pause()

And here is the error message I get when the script has ‘crashed’:

Exception in thread Thread-1:
Traceback (most recent call last):
File “/usr/lib/python2.7/threading.py”, line 801, in __bootstrap_inner
self.run()
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 231, in run
if self.todo() == False:
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 457, in _poll
self._handle_alert()
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 450, in _handle_alert
self._trigger_handler(x, inputs)
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 464, in _trigger_hand ler
self.handlers[event][channel](CapTouchEvent(channel, event, self.input_delta [channel]))
File “/usr/lib/python2.7/dist-packages/touchphat/init.py”, line 103, in _h andle_press
_on_presschannel
File “kitchen.py”, line 72, in handle_touch
my_kodi.Settings.SetSettingValue({ “setting”:“audiooutput.audiodevice”,“valu e”:“ALSA:sysdefault:CARD=IQaudIODAC” })
File “/home/pi/.local/lib/python2.7/site-packages/kodijson/kodijson.py”, line 121, in hook
return self.kodi.execute(kodimethod, *args, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/kodijson/kodijson.py”, line 71, in execute
auth=(self.username, self.password))
File “/home/pi/.local/lib/python2.7/site-packages/requests/api.py”, line 112, in post
return request(‘post’, url, data=data, json=json, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/api.py”, line 58, i n request
return session.request(method=method, url=url, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/sessions.py”, line 508, in request
resp = self.send(prep, **send_kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/sessions.py”, line 618, in send
r = adapter.send(request, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/adapters.py”, line 508, in send
raise ConnectionError(e, request=request)
ConnectionError: HTTPConnectionPool(host=‘192.168.0.8’, port=8080): Max retries exceeded with url: /jsonrpc (Caused by NewConnectionError(’<urllib3.connection.H TTPConnection object at 0xb5a97790>: Failed to establish a new connection: [Errn o 111] Connection refused’,))

^CTraceback (most recent call last):
File “kitchen.py”, line 149, in
signal.pause()

I’m going to be captain obvious, lol, no way around it. Not trying to be a smart @ss etc.
I would think you’ll need to add error handling. I’ve seen it in some of the Pimoroni examples I’ve played with. Well I think thats what it was? I’m not sure I have the skills to set it up myself from scratch though? I’ll go see if I can find one and post back.

Thank you! That would be most appreciated :)

Ok the stuff I was seeing is stuff like Try and Except

https://www.pythonforbeginners.com/error-handling/python-try-and-except

and except ImportError: > Its in the Drums.py for explorer phat.

Phil @gadgetoid likely knows way more on this than I do. I think he actually writes up a lot of the example code here.

Thank you so much for that! And I really need Captain Obvious so there’s absolutely no offence :) Your first post helped me by identifying the language I need to search for help (ie error handling!). I came across the page you’ve just sent after you gave me the correct jargon. So I’ve had a go at adding that code into my script. I’m not sure I’ve done this correctly and it’s hard to replicate the amp to crash! But here’s what I’ve added

@touchphat.on_release([‘A’])
def handle_touch(event):
print(“Kitchen Amp Off”)
time.sleep(.1)

tn.close()
time.sleep(.2)
tn.open(‘192.168.0.2’)
tn.write(“ST04OFF\r\n”)
tn.close()
time.sleep(.2)
while True:
try:
break
except ValueError:ConnectionError
print(“Connection Error”)

Do you think that will do it?

Looks ok to me, but I know next to nothing about this stuff. Thats one of those scenarios you hate testing, at least I do. Something has to fail for something else to happen or not happen.
Ideally I guess, you want it to keep on trying even if it gets an error. At repeated intervals or something. Its the way I would try to do it, let it recover on its own with no human intervention. If its possible that is.
I’ve never done any error handling other than scratching my head when my code fails lol. Or used what was in code I scoured off the internet.
I’ve done a lot of Python coding, and learned a lot on the way. I still consider myself about average skill level or maybe a little higher. Not much higher though. ;)
If you can edit the thread title, change it to reflect what you now need help with “Python error handling”. That might get those that know in here for some real help. or just start a new thread with a new title.

Thanks for your help. You’ve been great at pointing me in the right direction. What I didn’t say in my first post is that my script does two things…switches on the amp and controls Kodi. Again it’s the same issue with Kodi…if there’s a problem with that…then the script crashes out with the error

Exception in thread Thread-1:
Traceback (most recent call last):
File “/usr/lib/python2.7/threading.py”, line 801, in __bootstrap_inner
self.run()
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 231, in run
if self.todo() == False:
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 457, in _poll
self._handle_alert()
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 450, in _handle_alert
self._trigger_handler(x, inputs)
File “/usr/lib/python2.7/dist-packages/cap1xxx.py”, line 464, in _trigger_handler
self.handlers[event][channel](CapTouchEvent(channel, event, self.input_delta[channel]))
File “/usr/lib/python2.7/dist-packages/touchphat/init.py”, line 103, in _handle_press
_on_presschannel
File “kitchen.py”, line 74, in handle_touch
my_kodi.Settings.SetSettingValue({ “setting”:“audiooutput.audiodevice”,“value”:“ALSA:sysdefault:CARD=IQaudIODAC” })
File “/home/pi/.local/lib/python2.7/site-packages/kodijson/kodijson.py”, line 121, in hook
return self.kodi.execute(kodimethod, *args, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/kodijson/kodijson.py”, line 71, in execute
auth=(self.username, self.password))
File “/home/pi/.local/lib/python2.7/site-packages/requests/api.py”, line 112, in post
return request(‘post’, url, data=data, json=json, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/api.py”, line 58, in request
return session.request(method=method, url=url, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/sessions.py”, line 508, in request
resp = self.send(prep, **send_kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/sessions.py”, line 618, in send
r = adapter.send(request, **kwargs)
File “/home/pi/.local/lib/python2.7/site-packages/requests/adapters.py”, line 508, in send
raise ConnectionError(e, request=request)
ConnectionError: HTTPConnectionPool(host=‘192.168.0.8’, port=8080): Max retries exceeded with url: /jsonrpc (Caused by NewConnectionError(’<urllib3.connection.HTTPConnection object at 0xb5b13730>: Failed to establish a new connection: [Errno 111] Connection refused’,))

^CTraceback (most recent call last):
File “kitchen.py”, line 176, in
signal.pause()
KeyboardInterrupt

I added the additional error handling code into the Kodi parts of my python script but to no avail :(

PS Thanks for tip…I’ve change my subject title.

It’s something I should tackle myself. I have a headless battery powered setup that every once in a while crashes, my python file errors out. When that happens my python file stops and my shutdown button doesn’t work. Raspbian is still running but I can’t shut it down properly. I end up just killing the power and hoping it boots up and runs correctly next time.

That’s exactly what happens with me! Because it’s a zero with a phat on top I haven’t fitted a shutdown button so I also end up killing the power…which never feels good. Hopefully somebody else might have an idea.

So I got some help from MrYsLab on the Pi forum who directed me to https://realpython.com/python-exceptions/ This really helped and I seemed to have sorted it with:

@touchphat.on_release([‘B’])
def handle_touch(event):
print (“Party Time”)
try:
my_kodi.Player.Open({“item”:{“partymode”:“music”}})
except:
pass

So far this seems to have fixed it! :)

Good stuff. I’m also a member of the Pi foundation forum, same username I use here.

Oh yes :) I think you helped with my Logitech keyboard question on there! Thanks and have a good weekend :)