Introduction: DIY Low-Voltage Outdoor Lighting Controlled Using Raspberry Pi


I have to admit, I'm, like many others, a big fan of the internet of things (or IoT). I'm also still weary hooking up all my lights, appliances, front door, garage door and who knows what else to the exposed internet. Especially with events like the recent crash of Amazon S3 services and consistent security vulnerabilities. Or do we even own IoT devices that we use? What if your internet provider halts service or it goes down? Too many points of failure for me.

Over the past 3 years, I have had such a blast exploring and learning with the Raspberry Pi and throughout that time have had the opportunity to make everything from an automated gardening drip system, to revitalizing my old laser printer by adding network connectivity and catching up on some sweet retro gaming ( although Arduino is still my first love...).

During the past year, I've been working to add an enclosed back porch and improve my backyard. I knew I wanted some outdoor lighting but wasn't too impressed with the systems and their lack of connectivity. Gathering inspiration from around the web, I've hacked together a viable system for running a low-voltage outdoor lighting system, keeping the connectivity isolated to your local network (could expose if you wanted) and being flexible enough to expand and customize to your heart's content.


TheFreeElectron - Simple and Intuitive Web Interface for Your Raspberry Pi - if you get hung up on the web side, check here, inspiration for the server side

CodePen - amazing source for CSS inspiration and learning

Code Academy - I'm an old school HTML guy, with some .NET & C# thrown in. Python, CSS, Javascript, PHP - all boosted to a usable/hackable level with help from Code Academy.

Basic Overview:

Low-voltage power (12V lights/relays & 5V RPi/relays) provided from a single ATX power supply

Raspberry Pi setup with Apache (web server), WiringPi (GPIO management) using PHP (server-side) main page with Javascript (user side) & Python (scripts) for monitoring GPIO status and displaying relevant information for the main web page. Checkboxes (in disguise) used to control GPIO pins, which control relays, which control the lights! It is basically magic.

Along the way, you'll see infrastructure pictures (conduit, junction boxes, etc.) - a little outside the scope of this instructable. I'll be focusing in on the electronic guts of a system. Up to you to make it weather proof (if needed) or pretty (if needed) or both (desirable).

Excited to share and looking forward to this community's feedback. Let's get rolling - start to finish.

Step 1: Hardware, Parts & Tools

Are there better parts to use? Yes.

Did I get my system working adequately with these parts? Yes.

Should you try something a bit different? Why not?!


  1. RaspberryPi - the cleaner the better and RPi3 great since you'll need wifi
  2. ATX Power supply - recycled is the best, I had mine from old gaming rig - pay attention to watts when working out how many lights you want and ideally, look for a +5VSB@2.5+Amp power rail - this is the purple wire and will supply the RPi with power without having to run the whole power sucking system
  3. Outdoor Lights (12v) - these have been great : low wattage, decent output, reasonable price
  4. 5v and/or 12v Relay Modules
  5. Some type of housing - I used an 8X8X4 PVC Junction Box
  6. Notepad++ w/ NppFTP - used to load and edit RPi files quickly
  7. Putty - used to install a few extra packages on the RPi


  1. Outdoor rated 12v power cable
  2. Wire staples
  3. 1/2" PVC & some right angle joints - 2 feet and 2 right angles for each separate line you plan on running
  4. Some ethernet cable
  5. Wire jumpers - various male/female combos
  6. Make your own Molex connectors
  7. Heat shrink tubing
  8. Electrical Tape
  9. MicroUSB Cable
  10. Optional: These wire connectors are awesome - use these all the time (kids power vehicles, smart garden (solenoid connectors) and USB power cord connecting ATX to RPi)


  1. Good pair of wire cutters - on the smaller side
  2. Phillips Screwdriver
  3. Small pair of needle nose pliers
  4. Optional: Voltmeter with continuity tester - lots of wires and very helpful for diagnosing problems...
  5. Some time

Step 2: Get to Know Your Power Supply

Taking a look at all the mess of wires that make their way out of your ATX power supply. Depending on the age of yours, you'll have a main mobo connector (20-22 pins - pinout pictured) plus power for all sorts of other stuff - drives, graphics cards, auxiliary power, etc.

  • +5VSB (Stand By) line is purple. This will be dedicated to your RPi - power all the time

  • PS_ON line is green. When this is connected to ground, it will turn on the red and yellow supplies
  • +5V lines are red. One line can power 2-3 5v relays
  • +12V lines are yellow. You will need 3-4 to power the outdoor lighting
  • GROUND/COMMON lines are black. You will need a few of these for each of the other colors
  • All other colors will not be used for this project

Step 3: Prep the Power Supply

First, I bit of a disclaimer:

You are dealing with line power, if you don't know/or respect what you are doing - you can really hurt yourself, or worse... Before you continue, make sure this time and EVERY TIME, you are working with an unplugged ATX power supply and give it time to discharge before you crack it open. I am not responsible for your failure to respect and follow some simple rules to keep you safe.

OK! Moving on!

  1. Unplug the power supply and wait 10-15 minutes for capacitors to discharge
  2. Use phillips screwdriver and take the screws off the power supply case (FYI, warranty voided - good reason to upcycle)
  3. Cut off all the Molex/connectors so you have a bunch of free wires
  4. Separate and organize the purple, green, yellow, red and black wires
  5. Carefully cut all the other wires inside the case - you will not need them and this will save space
  6. Cap the ends of the cut wires with a bit of electrical tape
  7. Seal that case back up with only the wires you need from the supply, make sure cut wires not near heatsinks or fans

Step 4: Power to the Pi!

Before you start controling relays, let's get the RPi all powered up.

Remember, I'm not covering the basics of getting the RPi initially set-up (Loading OS to SD card, setting a new password & enabling SSH) - check back on hardware/software section (step 2) for links to great links covering those things.

Take a look at the first picture - let's create the hybrid cord that will take the purple line from the ATX over to the RPi:

USB to ATX Power Cord

  1. Using your wire cutters, cut your micro USB cord closer to the USB end than the micro USB end
  2. Carefully strip the exterior sleeve of the cable
  3. You should have 4 wires (Black, Red, Green & White)
  4. Leave 1/2" to 3/4" of the black and red and strip those ends to expose the copper
  5. Cut the Green & White completely, you won't need them - this is just for power only, no data
  6. Take a few of the wires you cut from your ATX power supply (Red & Black)
  7. Connect them up to the USB cord
    • A few ways to do this - in order of longevity:
      • (A) Stripped both ends, soldered them together and then used some heat shrink it all
      • (B) Twist two stripped ends lengthwise, then heat shrink
      • (C) Connect two stripped ends with some small wire nuts
      • (D) Twist two stripped ends together and wrap with some electrical tape
  8. If you are using the connectors, strip the other ends and poke 1/4" - 3/8" worth of exposed in into the connector (be sure to match the positive and negative sides)
  9. If you are using the connector, strip the purple wire from the ATX and a black one and again, watch positive and negative (purple to red and black to black)
  10. If you are not using a connector, just wire nut them up.

Once connected to the power supply and the RPi, double check to make sure you don't have any other stripped wires hanging around and plug the power supply back in. When you turn on the power supply, you should have a working Raspberry Pi!

If not - double check your connections, positives, ground, etc.

No dice? Use your voltmeter's continuity tester to check your cord. Should hear a beep when touching both ends. Also, check that purple line from ATX power supply is +5v.

Still no go? Try a red wire for +5v, could use that but will change next step a bit and consume greater wattage.

Now let's take a break from the hardware and work on our soft skillz.

Step 5: SSH Into RPi & Grab Some Software

Ah, the beauty of open source... so great...

Let's start with a little Putty.

There are a ton of great resources out there on this tiny but power little program. If you've got SSH enabled and your default password changed then you are all set. Let's fire it up and pull down some new packages & software.

Open Source is the Best Source

Let's start with the all important:

$ sudo apt-get update
$ sudo apt-get upgrade

Yes to all the questions.

Now let's get the WiringPi Library - makes the GPIO much more manageable.

$ sudo apt-get install git-core

Yes to all the questions - now to build it:

$ git clone git://

$ cd ~/wiringPi

$ ./build

Last, but not least - one amazing web server:

$ sudo apt-get install apache2 php5 libapache2-mod-php5

If all goes well, you should be able to type in the IP address of the RPi and see "It Works!"

Then give yourself access:

$ sudo chown pi:pi /var/www/html/ 
$ sudo chmod 755 /var/www/html/

Side Note On IP Addresses

One of the reasons I like this IoT design is it is mine. iIoT if you will. Don't have to worry about 'the cloud' or other services. BUT, you'll need to determine how you want it to work for yourself. Key to any option is the need for a solid, stable IP address - otherwise, you'll never know where to go to turn your lights on and off. I personally use option (C), but your call.

A few options:

Step 6: Connect to RPi Via NotePad++ SSH

I'll be using Notepad++ to edit the HTML, PHP, Python, Javascript & CSS files and a plug-in called NppFTP to quickly and easily get those changes on to your RPi - elegant, simple and quick. NppFTP comes default in the 32-bit version, but if you go 64-bit, it is now supported as well, but you'll have to manually install it.

  1. Open up Notepadd++
  2. Plugins --> NppFTP --> Show NppFTP Window (can also select little folder with a chain link icon)
  3. In the NppFTP window, select the COG icon and 'Profile Settings'
  4. This should be blank for you if you've never used this, select 'Add New'
  5. Hostname = RPi IP Address on your local network
  6. SFTP is the type, with Port 22 (SSH)
  7. Username is 'Pi' and Password is your newly updated password... right?!
  8. Also, set your default directory to '/var/www/html/' - will make things easier
  9. Hit the connect icon and select the profile you just made - should zip you right to your new directory

Opening a file will bring a local file to your machine, saving it will automatically load your changes to the RPi.

Open the index.php, gpio.php, css.css and script.js in Notepad++, then you can upload them to the html folder.

Give it a test by inputting the IP address of your RPi - you should see your default control page load.

If not, check and make sure all the files are actually on the RPi, also, make sure no other 'index" in the html folder.

If you see the page load, success! Let's talk more about the files you place on your RPi and how they help you control your lighting!

Step 7: The Interface Overview & Index.php

My primary goal was to have control of the lighting from a simple, web-based interface which could be loaded from any device. The result is a page with a good number of features, a LOT of room for you to make it your own and many colorful languages.

As you can see from the first picture - Javascript included in index.php is used to call gpio.php when the state of our checkbox (i.e. switch) changes. gpio.php then writes and reads the gpio pins.

Let's start with the index.php in the attachments. I'll take it one section at a time, pointing out the areas and some specific notes to help you along.

First links are to the CSS stylesheet & a custom icon that is a 32X32 bitmap with the extension of '.ico'

Second is a bit of Javascript, an adjust clocked example from w3schools tweaked to add some AM/PM and a blinking colon (just how I wanted it displayed for me, maybe you want it different?)

First up, a bit of PHP - this will run first - only on the server (cannot see it in the source once page loaded) - also the reason cannot continue to use it to write pin states.

$nm_array = array("Your Switch 1", "Your Switch 2", etc..); 
//this is where you add the areas you'll want seperate control over lights
//You can add as many as you want/need - it is set-up to count and create switches accordingly 
$wthr_array = array(); //empty now, but holds a data point populated by a Python script

The next loop is going to use PHP's 'system' and 'exec' functions to set all the pin modes using WiringPi (all outputs) and then read them. With multiple sources able to make changes, I wanted to make sure new pages would see the actual current status. A Javascript later will read these and set the checkboxes to checked or unchecked accordingly.

Finally, if you want to execute the Python script to pull in a data point and populate the $wthr_array.

Next Up the div class "header" - each on of the list items represents the contents of the containers in the header of the web page (Time, Title & Temp.)

The PHP loop that will loop based on the number of switch names you've added to the $nm_array.

What's important here is that it also assigns PIN numbers in sequential order. Starting with PIN0 up to any number, but really limited based on the number of GPIO pins available on your RPi, so 16. This will be very important in the next step when we actual start controlling stuff.

A few quick notes on some of the other files:


Your own colors (web, rgb, etc.) for the page are set on lines 68, 111 and 134. I chose these because they are the same colors my super maker of a wife picked out for me to paint the new back porch, so it helps to tie the interface into where the interface is typically executed.

Starting on line 194 is where you can tweak the look and feel of the toggle switches

This super simple Python script is ready to rock as soon as you get your own API key from weather underground, plus will show you some statistics about the usage of your page (everytime the page loads a call is made - so you can see some data)

Step 8: Control Stuff With 12V

You've probably noticed that your power supply isn't making much of a sound. The fan isn't on, no voltage to the yellow or red lines, etc.

That is because we'll need to get the GREEN (PS_ON) connected to a ground to actual turn on the main power.

Let's get one of those relays out.

  1. Strip & connect the GREEN wire into one of the relay terminals
  2. Strip & connect a BLACK wire into one of the relay terminals next to the green one

Ok, now take a few of your jumper cables - a RED & BLACK both female& ANY COLOR female on one side and male on the other.

  1. Strip one end of both a RED & BLACK leaving one female side and connect with a wire nut the RED to the PURPLE (same one your RPi is connected to) and BLACK to BLACK
  2. The female side of these will go to the relay RED to positive, and BLACK to negative
  3. The COLOR you chose will go male to GPIO (see picture - we'll go with WiringPi PIN 0)
    1. NOTE: I'm using a ribbon cable to connect up the GPIO, but you could go directly to the header of the RPi.
  4. The female side will go to the "signal" or S pin of the relay

Head back over to your main page (IP address of your RPi) - the first switch, perhaps the only switch, should now take the ATX PS out of standby, kick the fan on and start sending juice to all the 12V, 5V & 3.3V wires.

What is cool, is that you could stop here. Simply wire up your lighting to a couple 12V lines and you'd have a simple, digital switch to control it.

But where is the fun in that? Next up, I'll talk the lighting wiring as well as a method for adding more switches and more control over your lighting.

Step 9: More Control With Power (and Data) Over Ethernet (P(&D)oE)

You might have been wondering what all that ethernet cable is that I added to the supply list.

Using the ethernet, we can send 5V along with a GPIO signal right along to other relay connections to further increase the control over our lighting system. Perhaps you want separate control of certain areas of the yard? Or front and back sections? This will enable that.

I'll lay out the concept and some best practices and you can customize it to fit your needs.

Take a look at the first and second picture. Taking a +5V line from our power supply, I send that down a set of twisted ethernet cable.

  1. Carefully strip the outer sheathing from the ethernet cable - you do not want to damage the 24-23 AWG wires
  2. Pick two color sets and carefully untwist them - one will be the voltage and the other the ground
    1. NOTE: Very good idea to document what color is what for when you wire up the other side!
  3. Strip the ends of both wires and wire up to a RED (+5v) and a BLACK ground on your power supply (picture 2)
  4. Do the same for another wire color, but wire up a jumper from a GPIO Pin instead

The Molex connectors I linked to in the supplies section really come in handy here. Take the 3 sets of twisted pairs, crimp them into the female Molex connectors along with a 3 prong connector and they will attach right to the relay. (picture 3). Make sure you watch the ordering, my relay needed them to be in +, - & S. If you make a Molex cable not in that order, it might be tough to rearrange them.

If you "pigtail" the ethernet power rail to your relay then you can run this line wherever you'd like and tap into it at various locations.

I've tested this with over 100ft of ethernet with limited voltage drop and a good GPIO signal that, because of the twisted pair, is relatively stable and protected from interference.

Step 10: Light Up That Yard!

There are SO many ways you can do this. I'll cover some general concepts and steps to make sure your system stays working and is safe.

Keep-in-mind that you will be burying cable for this. The cable I linked to is what I used and is rated for underground burial which means be extra careful not to cut into cable lines, internet lines OR WORST CASE, power lines... please contact local "call before you dig" if you are uncertain. Also, keep track of what is positive and what is negative. I always knew the cable with the "words" (white lettering) was the negative and blank was the positive line)

Since I was adding on a back porch, I had planned a bit ahead and place junction boxes all around the perimeter of my new foundation, which made this really much simpler. You could just as easy run lines under your deck, paving stones, etc. just be sure to put any wired connects, especially relays into a weatherproof junction box.

First up, I ran the 12V lines through the junction box (picture 2).

That wire ran down into the ground, through a 1/2" PVC conduit with a right angle on the bottom, down into the ground about 6-8". A trench that is tough with our rocky soil (had to use a pickaxe) but maybe you live somewhere with real dirt...

The line comes up (picture 4), again with a right angle and a 1/2" PVC and attached to the tree. I've ended up filling the top of the PVC with a bit of silicon to keep the wire from being tugged on by kiddos.

For some installations, you can stop here and have your light point up towards the tree. Test it out at night to get the look you want. If you want the lighting coming down... continue on.

I used wire staples, being careful not to puncture the wire to lead it up behind the tree (picture 5)

Once you have the line, you'll need to screw the mounting bracket onto the tree. Once secure, use wire nuts to connect the positive to the red and negative to the blue or black of the light fixture. Wrap the connections in a bit of electrical tape to help keep out moister.

Rinse and repeat for however many lights you want to run!

Test it out by firing up a phone, iPad or computer and navigating to your RPi IP address.

The last thing that needs to happen is making sure your RPi and the connections are are nice and snug in a junction box or other type of arrangement - again, beyond the scope here.

Step 11: Improvements In-progress & Wrapping Up

So what next and how to improve? Looking for this community to help, but also a few ideas I've implemented since putting this together or am working to in between other projects around the house.

Updating Weather Service

Started using Accuweather API instead of WeatherUnderground (discontinued API service) - '' added to show how!

Adding Physical Buttons

I picked up a 4 button unit similar to what I see around our office conference room and have since, wired it up to 4 GPIOs which are monitored by a python script when the unit is on. Now can also use these as another method for turning it all one and off and the way I've programmed the main page, it will check to see what the current state of the GPIO pin is first so you don't have conflicting input signals. The folks at were super helpful in answer my questions getting it work - thank you!

Different Data from Weather Underground

I've started to pull down astrological data from WU (sunrise, sunset, etc). I'm working to have the lights come on and off 30 minutes before sunset and off at certain times as well. Could use some analog sensors for this, but not the RPi's best use, so playing with a software solution.

Adding Auto-On/OFF

My back porch is a solid 10 yards of concrete that we poured about 2 years ago. This past year we had some erratic weather - one day it would be 35-40F outside, then the next, 70-80F with 60-80% humidity. This caused condensation on the slab, making it very slippery. To combat this issue, I've added a python script to pull down prior days temp (to determine an approximate temperature for the slab) and dewpoint to determine if the conditions are right to create condensation on the porch ( If temp. is less than the dewpoint - then the fans come on, if not, they stay off. It also won't overwrite if the fans have been turned on manually and the web page interface changes a bit if the 'AI' has turned on the fans. I've added 4 files:, & (place in python folder) and an updated index.php (place in main folder) - you'll need to update your weatherunderground API key.

In the terminal:

$ sudo crontab -e

Then add the following to the bottom:

<p>#every hour, check temp/dewpoint to see if need to turn on fans</p>0 * * * * /usr/bin/python  /var/www/html/python/

Now every hour, will run. OR you can use this as a template for another function, perhaps turning the lights on and off using another trigger? Sunset/sunrise time? OR if it is just hot outside and you want the fans to come on automatically if the temp. reaches XX degrees?

Adding Motion Sensors

Placing a few motion sensors near entrances, using the ethernet structure to route power and data I/O would be a breeze. Then a simple python script to monitor and trigger lights on and off. Could be a fun little add-on project.

Hope that this at least gives you and idea that this is viable and at most, you can replicate what I've now been using successfully for over a month. Loads of great responses from friends and family and know you will get the same if you got out there and get to making! Thanks for walking along with me and please let me know of any feedback, tweaks or questions you may have! - thecleaner

Lights Contest 2017

Participated in the
Lights Contest 2017