HiveBrain v1.2.0
Get Started
← Back to all entries
patternpythonMinor

Raspberry Pi GPIO safe clean up

Submitted by: @import:stackexchange-codereview··
0
Viewed 0 times
raspberrygpiosafeclean

Problem

We are always told to call GPIO.cleanup() before we exit our Pi programs. I've seen people using try ... catch ... finally to achieve this. But hey, we are doing python here, an elegant programming language. Do you guys think this is a more elegant solution?

# SafeGPIO.py

from RPi import GPIO

class SafeGPIO(object):
    def __enter__(self):
        return GPIO

    def __exit__(self, *args, **kwargs):
        GPIO.cleanup()


Use like this:

from SafeGPIO import SafeGPIO
import time

with SafeGPIO() as GPIO:
    GPIO.setmode(GPIO.BOARD)
    GPIO.setup(7, GPIO.OUT)
    GPIO.output(7, True)
    GPIO.setup(8, GPIO.OUT)
    GPIO.output(8, True)

    val = 0
    for i in xrange(10):
        val = (val + 1) % 2
        active_pin = 7 + val
        inactive_pin = 7 + (val + 1) % 2
        GPIO.output(active_pin,True)
        GPIO.output(inactive_pin,False)
        time.sleep(2)

Solution

Intuitively I think that I don't like to encapsulate all of my program in a with SafeGPIO() as GPIO call, so I searched the library and found at_exit. Using this you should be able to have something like the following in SafeGPIO.py:

import at_exit
from RPi import GPIO as RPi_GPIO

# Something useful to re-export GPIO?! Possibly the following?
GPIO = RPi_GPIO

@atexit.register
def cleanup():
    RPI_GPIO.cleanup()


Not sure on how to re-export the GPIO, but if this construct works you only need to do from SafeGPIO import GPIO, and then when Python exits it will call the original GPIO.cleanup().

Now the real question is why don't the RPi module automatically do this if this is a best practice when using RPi? Sadly, I don't know the answer to that, but it could be a reason for it, which might affect whether this is actually a good solution or not.

PS! I've addressed some more variants related to how to do cleanup in this answer, where I also focus a little more on choosing different options related to use cases.

Code Snippets

import at_exit
from RPi import GPIO as RPi_GPIO

# Something useful to re-export GPIO?! Possibly the following?
GPIO = RPi_GPIO

@atexit.register
def cleanup():
    RPI_GPIO.cleanup()

Context

StackExchange Code Review Q#113486, answer score: 3

Revisions (0)

No revisions yet.