package org.robbins.raspberry.pi.service;

import com.pi4j.io.gpio.*;
import org.robbins.raspberry.pi.exceptions.RaspberryPiAppException;
import org.robbins.raspberry.pi.model.PiAction;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;

@Service("blinkLight")
public class BlinkLightActionImpl implements PiActionService {

    private static final Logger LOGGER = LoggerFactory.getLogger(BlinkLightActionImpl.class);

    @Override
    public void invokeAction(final PiAction action) throws RaspberryPiAppException {
        LOGGER.debug("Blinking Light service for action: {}", action);

        try {
            // create gpio controller
            final GpioController gpio = GpioFactory.getInstance();

            // provision gpio pin #01 as an output pin and turn on
            final GpioPinDigitalOutput pin = gpio.provisionDigitalOutputPin(RaspiPin.GPIO_01, "MyLED", PinState.HIGH);

            // set shutdown state for this pin
            pin.setShutdownOptions(true, PinState.LOW);

            blinkLight(pin, Integer.getInteger(action.getValue()));

            // stop all GPIO activity/threads by shutting down the GPIO controller
            // (this method will forcefully shutdown all GPIO monitoring threads and scheduled tasks)
            gpio.shutdown();
        }
        catch (Exception e) {
            throw new RaspberryPiAppException(e.getMessage());
        }
    }

    private void blinkLight(final GpioPinDigitalOutput pin, int blinkCount) throws RaspberryPiAppException {

        try {
            for (int i = 0; i < blinkCount; i++) {
                LOGGER.debug("--> GPIO state should be: ON");

                Thread.sleep(5000);

                // turn off gpio pin #01
                pin.low();
                LOGGER.debug("--> GPIO state should be: OFF");

                Thread.sleep(5000);
            }
        }
        catch (InterruptedException e) {
            throw new RaspberryPiAppException(e.getMessage());
        }
    }
}

@@ -462,24 +462,80 @@
 pl.class);%0A%0A
+    GpioController gpio;%0A    GpioPinDigitalOutput pin;%0A%0A
     @Overrid
@@ -536,16 +536,16 @@
 verride%0A
-
     publ
@@ -761,29 +761,8 @@
     
-final GpioController 
 gpio
@@ -875,35 +875,8 @@
     
-final GpioPinDigitalOutput 
 pin 
@@ -1124,17 +1124,147 @@
 ue()));%0A
+        %7D%0A        catch (Exception e) %7B%0A            throw new RaspberryPiAppException(e.getMessage());%0A        %7D%0A        finally %7B
 %0A
-
         
@@ -1440,16 +1440,104 @@
  tasks)%0A
+            if (gpio != null) %7B%0A                LOGGER.debug(%22Shutting down GPIO%22);%0A    
         
@@ -1561,34 +1561,32 @@
 ();%0A        
-%7D%0A
         
 catch (Excep
@@ -1577,92 +1577,165 @@
     
-catch (Exception e) %7B%0A            throw new RaspberryPiAppException(e.getMessage());
+gpio.unprovisionPin(pin);%0A            %7D%0A            else %7B%0A                LOGGER.debug(%22Unable to shutdown GPIO.  There is no GPIO instance%22);%0A            %7D
 %0A   

improve GPIO handling