Alexa LIRC Entertainment Remote

1,648

18

12

Introduction: Alexa LIRC Entertainment Remote

About: I like to make stuff.

I made a project Raspberry Pi Zero Universal Remote that uses a website that interfaces with LIRC so you can control your TV from your phone's browser. Well someone said what if they lost their phone and the remote. So I thought, oh let us see if we can get Alexa to at least do simple commands to control the television.

Turns out, Amazon has got your covered for that but, you still have to put a bit of work in. Amazon can provide you with all the services you need. I'm not going to lie, seems a bit daunting if you read through this Instructable once. But, I try to make things as easy as possible with step by step instructions. Hopefully you won't need to know much programming to complete this project. You will need to do a bit of soldering though.

Before we go on. I have to caveat this project. This project is for very simple voice control of dumb televisions or cable boxes. You will be able to do the following voice commands:

  • Power on/off
  • Change channels
  • Volume controls
  • Change input source

Adding more to the caveats since we cannot get the state of a dumb TV/cable box.

  • Commands are as if you pushed that button on the remote.
  • Power on/off is as if you pushed the power button on the remote. So if the TV is on you say 'Alexa, turn on the television', the television will turn off.
  • Quirk of Alexa input skill is that you have to give an input name. So to change the TV input you have to say 'Alexa, change input to HDMI on television' and repeat that till you get to the input you want.
  • I couldn't get the SkipChannels to skip in multiples, not sure what the correct utterance is. So you can only go up/down a channel at a time.
  • You can change to channels by number but not by channel name. So you can say 'Alexa, change channel 1440 on cable' but not 'Alexa, change channel cartoon network on cable'. That would require keeping some sort of name to channel number configuration which is not worth it. Oh, be careful when uttering 'Alexa change channel to # on cable', sometimes Alexa changes 'to' to the number '2', so best to just skip saying 'to'.
  • The Raspberry Pi does not communicate back to Alexa. Alexa thinks your device is always connected since the Amazon Lambda function always returns that your device is connected so Alexa will always say 'Okay' if you give her a correct command.

This Instructable aims to try not include too much technical jargon. Please pardon if I skip over some technical stuff (like omitting that flow diagram of user voice to Alexa then arrows all over the place going in and out of the Amazon cloud). My goal is to get you to control you TV or cable box as quick as possible without too much fuss. I suggest you follow the instructions as is first and then change things around to suit your needs after.

Also, if you follow this project as is, you can add on the website portion from my previous project seamlessly so you can have both web and voice control over your IR devices.

Change Log:

3/02/2018: Corrected GPIO references.

2/11/2018: Added Troubleshooting Section.

Step 1: Bill of Materials

Bill Of Materials

  • Alexa Device (Echo, Dot, Show, etc.)
  • Raspberry Pi Zero W
  • 5V Power Supply (1.2A minimum)
  • Micro USB Cable
  • Micro SD Card
  • IR LED 5mm (940nm) - TSAL6200
  • IR Receiver Module (3.3V type) - TSOP38238
  • 2N2222 NPN transistor
  • 36 Ohm 1/4W Resistor
  • 680 Ohm 1/4W Resistor
  • 10K Ohm 1/4W Resistor
  • Perfboard
  • 4-40 3/8" countersunk screws (if using the case I modeled)
  • Wire (stranded 24AWG works well)

Tools

  • Computer
  • SD card reader
  • Soldering Iron and solder
  • Hot glue gun and hot glue (or super glue)
  • Wire cutter
  • Wire stripper
  • Screw driver
  • 4-40 bottom tap
  • Helping hands or some sort of hobby vise
  • 3D printer (not necessary but you can print up a case)

Online Accounts

Notes

You will need a minimum size of 4GB micro SD according to the Raspberry Pi foundation documentation. I would just get a 16GB or 32GB because seems like 4GB and 8GB are hard to come by now and tend to cost more. Also the larger capacity allows you to multipurpose the Pi as a small file share, but that is beyond the scope of the Instructable, but something to consider after you complete the remote.

Make sure the IR LED is specified for wavelength of 940nm and get them from a reputable seller. I bought some cheapy ones off eBay and they only work when close to the television, like about 5-6 feet away. I ended up using a TSAL6200 IR LED from DigiKey which can control the television from the very back of my living room (15+ feet).

Make sure to us an IR Receiver Module that operates at 3.3V like a TSOP38238. This simplifies connecting the module to the Pi so you do not have to level shift the module's output down to 3.3V. I initially had a TSOP4838 that the datasheet says it operates from 2.5V to 5.5V, but I could only get it to work with 5V. That could also be the problem of going cheap off eBay. So yeah, save yourself some trouble of not having to add extra parts to convert the 5V output from the receiver down to 3.3V and just get a TSOP38238.

Buy components from a seller like DigiKey. As noted twice, I got bad components going cheap off eBay. I'm not saying all eBay sellers are bad, I'm just saying don't be surprised if you don't get exactly what you ordered. Save time and headache and buy from Adafruit, DigiKey, Mouser, etc. The bay is still good in my opinion if you keep track of good seller. Also ordering passive components such as resistors and capacitors through eBay are pretty safe.

Almost any jelly bean NPN transistor can be used as long as the transistor can handle a minimum of 150 or so milliamps. I happen to have a lot of 2N2222 transistors laying around so I just used that.

Step 2: Steps Overview

This is a quick overview of what needs to be done, not necessarily the number of steps. Looks like a lot but it really isn't. The longest part is probably the hardware portion of soldering up the IR components and boxing up the Raspberry Pi Zero.

  1. Setup Raspbian on the Raspberry Pi Zero W.
  2. Setup hardware on Raspberry Pi Zero W.
  3. Setup LIRC on Raspberry Pi Zero W.
  4. Test LIRC on your television or cable box.
  5. Sign up for Amazon AWS and Amazon Developer Services.
  6. Create AWS IoT Thing for our Raspberry Pi Zero W.
  7. Test our AWS IoT Thing with Amazon's MQTT client.
  8. Setup AlexaLirc application on Raspberry Pi Zero W.
  9. Test connection from Raspberry Pi to AWS IoT Thing.
  10. Create an Identity and Access Management Role.
  11. Create AWS Lambda function.
  12. Test Lambda function connection to our AWS IoT Thing.
  13. Create a Login with Amazon service.
  14. Create Alexa Skill.
  15. Link Lambda function.
  16. Link Login with Amazon service.
  17. Enable your Alexa Home Skill in your Alexa app.
  18. Discover new smart home devices in your Alexa app.
  19. Be lazy and control your TV and cable box from your couch or bed.

***NOTE***

If you completed the Raspbery Pi Zero Universal Remote project, you can skip the Instructable steps 3-26 as these are repeats of hardware setup and LIRC setup of that project. You don't need to do that project before this one. That project is a web interface and this project is an Alexa interface.

Step 3: Install & Setup Raspbian (YMMV)

Download Raspbian Lite from https://www.raspberrypi.org/downloads/raspbian/. Do not grab the desktop as you do not need the desktop. We will not be using the GUI. As of writing this, the latest Raspbian Lite image is 2017-11-29.

Follow their instructions on how to install Raspbian to your SD Card.

The Raspberry Pi Organization suggests using Etcher but it doesn't always works for me. I get validation errors. I think it has something to do with Windows 10 because when I use Linux (same machine, just swapped out the hard drives), Etcher works all the time.

Your mileage may vary on setting up Wi-Fi for the Pi Zero W. My router is a bit funky in that it will not allow computers to connect to other computers unless they have an assigned IP. So if you find that you cannot connect to your Pi, try assigning it a static IP.

After you flash the Raspian image to your SD card. Eject and reinsert your SD card into your computer. Create a text file named "wpa_supplicant.conf" and place in the /boot folder of the SD card. The following are contents of the wpa_supplicant.conf file (change country, ssid, psk, key_mgmt to your values):

ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev
update_config=1
country=US

network={
        ssid="Your Wi-Fi SSID"
        psk="Your Wi-Fi password"
        key_mgmt=WPA-PSK
}

Add a blank file named SSH to the /boot folder of the SD card. This will enable SSH as SSH is disabled by default now.

Hook up the Pi's power source to boot up the Pi. The wpa_supplicant.conf is automatically moved to /etc/wpa_supplicant/ if you ever need to edit the settings.

Test that you can connect to your Pi via SSH. The default user is "pi" with password "raspberry".

In my case, I had to hook up the Pi to a monitor and run ifconfig to get the MAC address of the Pi's Wi-Fi adapter so that I can assign a static IP to that MAC address.

If you can connect, great! First thing to do is change password. Then get the latest updates by the running the following two commands (don't copy the '$' sign, it denotes the terminal prompt):

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

Leave the SD card in the Pi and set aside the Pi for now while you work on the case and IR LED driver circuit.

Step 4: Print Enclosure

I modeled a case to hold the Pi Zero W, the IR LED driver circuit, IR LED and IR receiver module. You can download the model at https://www.thingiverse.com/thing:2742325. Having the case up front is handy so you can have the remote nicely boxed up while you configure LIRC.

If you do not have a 3d printer, try to find an enclosure that can fit the length of the Pi and width of the Pi plus the IR LED driver circuit (4 x 6 perfboard). An Altoid mint tin might do. Just make sure you insulate the inside so you don't short anything.

If you print up my enclosure, use a 4-40 bottom tap to cut screw threads in the corner screw holes. Make sure to use a bottom tap so you can get threads cut almost all the way to the bottom of the screw hole.

If you only have a regular tap, then you will need to drill out the holes all the way (or modify the model).

Step 5: IR LED Driver

The TSAL6200 IR LED can continuously handle 100mA of current. The max current you should pull from a Raspberry Pi GPIO pin is 16mA and no more than 51mA total from all pins (Raspberry Pi GPIO pin max current). We should not directly power the IR LED from a GPIO as 16mA may be to weak for the IR LED to be useful. We instead need to use a simple transistor amplifying circuit.

Follow the schematic to create the circuit to connect the IR LED to the Raspberry Pi. Not shown in the schematic is hooking up the IR LED to the 5V power pin. This will be shown in the upcoming steps and mentioned below as part of the calculations. The following steps detail putting the components on a perfboard.

If you are wondering about how I chose the resistor values, read on. If you just trust me and want to get on with the project, go to the next step.

R1 is a pull-down resistor to ensure the IR LED is off when the Raspberry Pi is in an unknown state. The value is a rule of thumb where 10K is good enough. This resistor is probably not needed since TV/DVD/etc. receivers receive encoded IR signals and the chances that your IR sends a valid signal when the Pi is off or booting to one of the devices are pretty slim. I personally leave the pull-down resistor because best practice is to always start/end in a known state.

R2 is the base current limiting resistor. You need to calculate the value of this resistor according to the transistor you use. The 2N2222 datasheet has a DC current gain from 35 to 100 depending on how much current and voltage you are using. I just went with worst case and used a gain of 35 for my calculation. I want the transistor base current to allow more than 100mA to flow from the collector to the emitter of the transistor. To calculate the base current we need to divide the desired current by the DC current gain, 100mA / 35 = 2.9mA. I rounded up to 4mA for some leeway which will allow up to 140mA to flow.

The GPIO pins output 3.3V. We also have to take into consideration the voltage drop from the base to emitter of the transistor. The voltage base emitter drop is 0.6V according to the datasheet. So to calculate the resistor required to limit the GPIO current to 4mA, use Ohm's law V / I = R, (3.3V - 0.6V) / 4mA = 675 Ohms. The nearest E24 resistor value is 680 Ohm (using this value rounds to 4mA).

We need to check what power rating to use for R2. Power formula is P = V * I. The power that R2 needs to dissipate is (3.3V - 0.6V) * 4mA = 0.011 Watts. I went with 1/4 Watt because that's the smallest wattage resistors my local electronics store carry.

R3 limits the current passing through the IR LED. The LED will be powered from the 5V GPIO pin which is directly connected to the USB 5V power. This means the max current you can draw from the 5V pin is the max the power supply supports minus the current the Pi draws.

The forward voltage of the TSAL6200 is 1.35V and there is a tiny 0.3V voltage drop across the transistor from collector to emitter (according to their respective datasheets). The value for R3 is then (5V - 1.35V - 0.3V) / 100mA = 33.5 Ohms. The nearest E24 value is 36 Ohms, which calculate to 93mA, which is still good enough for our purposes.

Finally we need to check how much power R3 needs to dissipate. Power formula, P = VI, calculates to (5V - 1.35V - 0.3V) * 93mA = 0.312 Watts. That means we need a 1/2 W resistor for R3. Well not quite. Thanks to B MW for pointing out that 0.312W is the instantaneous power usage and really only a concern if you are continuously powering the LED. IR codes are really short (usually in the milliseconds) sets of ~38KHz pulses. So you are not continuously powering the led. You can use a 1/4 Watt resistor for R3 instead of a 1/2 Watt resistor.

Step 6: Building the LED Circuit - R1

You will need to cut a perfboard to 4 x 6. I arrange the perfboard with 4 holes vertically and 6 holes horizontally (4 rows by 6 columns).

Start with R1, 10K Ohm resistor, and place it into the lower leftmost corner (bottom row, first column) of the perfboard with the leads spaced apart so there is two empty holes between them.

Bend the lead in the leftmost corner vertically and the opposite leg horizontally. We will use the legs as a trace to connect to the other components.

Step 7: Building the LED Circuit - R2

Insert R2, 680 Ohm resistor into the row above the R1 resistor.

Bend leftmost leg horizontally outward from the board and the other leg horizontally like how you did for R1.

Step 8: Building the LED Circuit - Q1

Insert the transistor Q1 to the right of R1 and R2 (bottom 3 rows of the 5th column)

Make sure Q1's emitter lead is through the bottom hole that is in line with R1.

Q1's base lead needs to go through the row that connects to R2.

Bend the emitter leg downward away from the board and the collector upward to hold Q1 in place.

Step 9: Building the LED Circuit - Solder First Set of Components

Now is a good time to solder some of the leads to hold the parts in place.

Solder Q1's base to the board which connects it to R2.

Solder Q1's emitter to the board which connects it to R1.

Solder R2's leftmost leg to the board connecting it to R1.

Trim the Q1 leads and R2 lead that were soldered.

Trim R1's lead one row up from the connection to R2. This will connect to a wire to the GPIO 22 pin of the Pi.

Trim R1's lead one column to the right from the connection to the Q1's emitter. This will connect to a wire to a ground pin on the Pi.

Trim Q1's collector lead one row up. This will connect to R3.

Step 10: Soldering IR LED Circuit - R3

Place R3, 36 Ohm resistor, in the topmost row all with the first lead in the first column and the other lead in the last column. The resistor should span the whole board.

Bend the leftmost leg horizontally inward toward the board. Trim the lead when it intersects Q1's collector lead at the 5th column. Solder the connection of R3 and Q1 together.

Bend the rightmost leg down and trim one row down. This will connect to the cathode of the IR LED.

Step 11: Building the LED Circuit - Wire Leads

Use colored wire to differentiate which wire connects to what. I used yellow for signal from the Pi, white for the IR LED cathode, and black as ground. Use lengths of about 3 to 4 inches so that you have some wiggle room when wiring up the board to the Pi in the case.

Strip and tin one end of the wires.

Insert the tinned end into the perfboard at their respective hole and solder in place.

Yellow wire in the 2nd row left most column.

White wire to 2nd row rightmost column.

Black wire bottom row rightmost column.

Make sure you trim any excess.

Step 12: Component Test Fit

Layout your components to somewhat match the case layout. The holes of the case are self-explanatory.

The top of the Pi should be facing the top of the case. The HDMI and usb ports will line up with the case cutouts.

Place the IR LED and IR receiver module in their respective holes.

Step 13: Trim LED Driver Wires to Length

Now you know how far the circuit board will be from the Pi you can cut the wires to length.

I removed the components from the case to easier work with the two. Space the Pi and LED driver circuit to how they would be in the case.

Leave a bit of length of the wire so that you can move the circuit board around if needed, but not leave too much wire where it takes up too much space. I made the wires do like a 'U' turn to the GPIO they are connected to instead of straight shot from the board to the Pi. This way you have some wiggle room.

Step 14: Solder Ground Wire

Trim the end of the wires and tin the ends.

Start with the black ground wire and poke the end through pin 6 (ground). Make sure you go from the top of the Pi board so that you are soldering the end of the wire on the back of the board.

Solder into place.

Note: I say pin but its really a hole since there are no preinstalled headers on a regular Pi Zero.

Step 15: Solder IR Signal Wire

Take the yellow signal wire and place through pin 15 (GPIO 22). Make sure to go from the top of the Pi like how you did for the ground wire.

Solder into place.

Place the board in the case to test fit to make sure your wires are not too long that they interfere with the other components. If they are, trim off some excess.

Step 16: Cut More Wires to Length

Cut 4 more wires for connecting the components together. Cut the wires to about the same length as you did for the ground and signal.

Use different colors of wire to easily differentiate what they connect to it.

Colors I used are:

  • Orange - 3.3V
  • Red - 5V
  • Black - Ground
  • Green - IR receiver signal

Trim the ends and tin.

Step 17: Solder Wires Into Place

Solder the orange wire to pin 1 (3.3V) of the GPIO header. Go from the top down so that you are soldering the wire from the back.

Solder the red wire to pin 2 (5V).

Solder the black wire to pin 14 (ground).

Solder the green wire to pin 16 (GPIO 23).

Step 18: Trim IR Component Leads

Place the IR components into their respective openings.

Bend the IR LED legs toward where the driver board will go.

Bend the legs of the IR receiver module up and then bend again toward the IR LED.

Trim the leads short like show in the picture.

Step 19: Glue IR Components

Glue the IR LED and IR receiver module to hold them in place. Use a good amount glue so the components do not move when you place the Pi and driver circuit wires in.

You can either use hot glue or super glue. I just went with hot glue because my little tube of super glue dried up.

Step 20: Tin IR Component Leads

Tin the ends of the leads of the IR LED and IR receiver module. This will make connecting wires easier in the upcoming steps.

Trim the cathode of the IR LED a tad bit shorter so that you can easily identify the cathode lead. There is a cutaway on the LED to tell you which is the anode or cathode but that cutaway may be covered by the hot glue so easier to just shorten up a lead.

Step 21: Test Fit

Test fit the Pi and LED driver board.

Make sure your wires are the right length, not too long and not too short, but just right.

Step 22: Solder IR Wires

Remove the Pi and driver circuit from the case.

Strip the end of the wires and tin them.

Solder the wires to the correct leads.

  • Red wire - IR LED anode
  • White wire - IR LED Cathode
  • Orange wire - IR receiver module lead 3
  • Black Wire - IR receiver module lead 2
  • Green Wire - IR receiver module lead 1

Use the picture of the pinout for the TSOP38238 to help solder the correct wires to the correct leads.

Eyeball your solder joints on the Pi to make sure they are not shorting to other pins.

Step 23: Screw Enclosure Cover

Make sure the SD card is still in the Pi before you screw on the back of the enclosure.

Place the back cover on the case.

Use four 4-40 countersunk screws on the corners of the case. Make sure you tapped the screw holes to prevent the plastic from splitting. Also, do not overtighten where you strip out the threads.

Slap some decals and labels on to pretty up the enclose and help you tell which micro USB port is the power port.

Step 24: LIRC Install

Power up the Pi and SSH into it.

Enter the following in the terminal to download and install LIRC. Answer 'Yes' to any questions when prompted. Note: Do not copy the '$' sign as that denotes the terminal prompt. This is to help differentiate what is a command and what are contents of a file.

$ sudo apt-get install lirc

Next we need to add two lines to '/etc/modules', but first make a backup of the modules file.

$ cd /etc/
$ sudo cp modules  modules.bak

Then using your favorite Linux editor of choice (nano, vim, or even emacs), add the follow two lines to the bottom of the /etc/modules file.

lirc_dev
lirc_rpi gpio_in_pin=23 gpio_out_pin=22

We also need to update boot configuration file 'boot/config.txt'. As we did for modules, we should make a back up first.

$ cd /boot
$ sudo cp config.txt config.txt.bak

Then change line 51 of config.txt from

#dtoverlay=lirc-rpi

to

dtoverlay=lirc-rpi,gpio_in_pin=23,gpio_out_pin=22

A fresh install of LIRC does not contain a hardware configuration file so you have to create it. User your editor of choice and create the file '/etc/lirc/hardware.conf' with the following contents:

########################################################
# /etc/lirc/hardware.conf
#
# Arguments which will be used when launching lircd
LIRCD_ARGS="--uinput"
# Don't start lircmd even if there seems to be a good config file
# START_LIRCMD=false
# Don't start irexec, even if a good config file seems to exist.
# START_IREXEC=false
# Try to load appropriate kernel modules
LOAD_MODULES=true
# Run "lircd --driver=help" for a list of supported drivers.
DRIVER="default"
# usually /dev/lirc0 is the correct setting for systems using udev
DEVICE="/dev/lirc0"
MODULES="lirc_rpi"
# Default configuration files for your hardware if any
LIRCD_CONF=""
LIRCMD_CONF=""
######################################################## 

Next we need to update the '/etc/lirc/lirc_options.conf' file, but as always, make a backup first just incase.

$ cd /etc/lirc
$ sudo cp lirc_options.conf lirc_options.conf.bak

Update line 11 of lirc_options.conf from

driver = devinput

to

driver=default

Reboot the Pi by entering the following. You will lose connection so SSH back in when the Pi is done booting up.

$ sudo shutdown -r now

Step 25: LIRC Install Quick Test

After the Pi has rebooted and you have SSH'ed back in from the previous step, we can quickly test if LIRC was installed correctly and if you connected your LED driver circuit correctly.

You will need to download a valid remote configuration file to correctly test installation and hookup. Run the following to download a remote configuration file into the LIRC configuration directory, '/etc/lirc/lircd.conf.d/'. Note, the sudo wget line is one long continuously line.

$ cd /etc/lirc/lircd.conf.d/
$ sudo wget -O test.conf https://sourceforge.net/p/lirc-remotes/code/ci/master/tree/remotes/samsung/00056A.lircd.conf?format=raw

LIRC will load any configuration file with extension '.conf' that is in the '/etc/lirc/lircd.conf.d' directory. The command above downloaded a Samsung remote configuration file and named it test.conf. We need to first restart LIRC to load the newly added configuration file. Ignore the warning about lircd.service can still be activated.

$ sudo systemctl stop lircd
$ sudo systemctl start lircd

We will manually send an IR code with the irrsend command. The following tells LIRC to send the power button IR code from the Samsung_00056A remote configuration file.

$ irsend SEND_ONCE Samsung_00056A KEY_POWER

You may be wondering where did the Samsung_00056A come from since we named the configuration file test.conf when we downloaded it. The name comes from the name setting in the test.conf at line 14. Keep this in mind since the name of the file is not necessarily the name of the device.

When you run the command there will be no output. You should just see the next command prompt. If there is an error of some sort, double check to make sure you followed the instructions in the previous step.

Test that your IR LED is correctly connected by using a digital camera. We cannot directly see the IR LED flash unless you are some sort of super human. Use a digital camera such as a smart phone camera and focus on the IR LED. Run the irsend command again and you should see the LED flash.

If the LED did not flash, double check your wiring and driver circuit. If everything is in working order, you may remove the test.conf file since we don't really need it anymore.

Step 26: LIRC Remote Configuration

You should still be SSH'ed into the Pi from the last step. If not, SSH back in.

Use the LIRC irrecord command to start the program that records your remote controller's IR codes. Follow my button naming convention so that the web interface structure I made will seamlessly integrate with LIRC. We need to pass the '--disable-namespace' parameter else we will not be able to name the buttons the way we want to.

$ irrecord --disable-namespace

When you run the command you should get a description of the program.

A proper config file for lircd is maybe the most vital part of this
package, so you should invest some time to create a working config
file. Although I put a good deal of effort in this program it is often
not possible to automatically recognize all features of a remote
control. Often short-comings of the receiver hardware make it nearly
impossible. If you have problems to create a config file READ THE
DOCUMENTATION at <a href="https://sf.net/p/lirc-remotes/wiki"> https://sf.net/p/lirc-remotes/wiki
</a>

If there already is a remote control of the same brand available at
<a href="http://sf.net/p/lirc-remotes"> https://sf.net/p/lirc-remotes/wiki
</a> you might want to try using such a
remote as a template. The config files already contains all
parameters of the protocol used by remotes of a certain brand and
knowing these parameters makes the job of this program much
easier. There are also template files for the most common protocols
available. Templates can be downloaded using irdb-get(1). You use a
template file by providing the path of the file as a command line
parameter.

Please take the time to finish the file as described in
<a href="https://sourceforge.net/p/lirc-remotes/wiki/Checklist/"> https://sf.net/p/lirc-remotes/wiki
</a> an send it
to  <lirc@bartelmus.de> so it can be made available to others.

Press RETURN to continue.

Press the return (enter) key. The program tests the ambient light for noise which will take a few seconds. As long as there is not too much noise, the program will then ask for the name of the remote.

Checking for ambient light  creating too much disturbances.
Please don't press any buttons, just wait a few seconds...

No significant noise (received 0 bytes)

Enter name of remote (only ascii, no spaces) :

Enter the name of the remote you will record. Keep the name simple because you will be using it later to setup the web interface. For this example, I entered 'LivingRoomTv' and then pressed return.

Using LivingRoomTv.lircd.conf as output filename

Now start pressing buttons on your remote control.

It is very important that you press many different buttons randomly
and hold them down for approximately one second. Each button should
generate at least one dot but never more than ten dots of output.
Don't stop pressing buttons until two lines of dots (2x80) have
been generated.

Press RETURN now to start recording.

The program will tell you that your configuration file is named 'name_used.lircd.conf', in this example the file is 'LivingRoomTv.lircd.conf'. The program says to press many differnent buttons randomly and hold down the button for about a second. I think the randomness is not really important but the amount of different buttons you press is.

Point your remote toward the IR receiver module. Press the return key on your keyboard. Start pressing and holding buttons on your remote for about a second. You will see dots appear on screen when you press and hold a button on your remote. If you do not see any dots, check your wiring on the IR receiver module and start the recording process over.

Keep pressing buttons till you get two rows of dots. The program will tell you when to stop. One of my remotes I ended up going three rows for whatever reason. If you run out of buttons to press, just repeat previously pressed buttons.

................................................................................
Got gap (109933 us)}

Please keep on pressing buttons like described above.
...............................................................................

Please enter the name for the next button (press <ENTER> to finish recording)

Eventually the program will have enough information it needs to decode your remotes IR codes. You will then enter the name of the button you want to record. I suggest you prefix all your buttons with 'Key_' as my previous project's web interface relies on this prefix. By doing so, you can add a web interface later on seamlessly. For example, name your buttons KEY_POWER, KEY_SOURCE, KEY_1, KEY_2, etc.

After you enter the button name, press enter. The program will ask you to press and hold your remote button down. If the program was successful, it will ask for another key. Example as follows:

Please enter the name for the next button (press <ENTER> to finish recording)
KEY_POWER

Now hold down button "KEY_POWER".

Please enter the name for the next button (press <ENTER> to finish recording)

Repeat for all your buttons. When you have no more buttons to record, leave the button name blank and press enter.

The program will now check if there are special bits to set. You will need to press just one button, any button, just make sure you use the same button, as fast as you can. Make sure that you are actually pressing the button fast and not holding it down. So when you are ready, press enter and press your button as fast as you can.

Checking for toggle bit mask.
Please press an arbitrary button repeatedly as fast as possible.
Make sure you keep pressing the SAME button and that you DON'T HOLD
the button down!.
If you can't see any dots appear, wait a bit between button presses.

Press RETURN to continue.

After the program is done checking for special bits, it will tell you that it wrote out the file. In this example the file is 'LivingRoomTv.lircd.conf'.

You will need to copy the newly created configuration file to '/etc/lirc/lircd.conf.d/'.

$ sudo cp LivingRoomTv.lircd.conf /etc/lirc/lircd.conf.d/

Repeat the process above for all other remotes you want to record.

Restart LIRC to load all your new remote configuration files. Ignore the warning when you stop lircd.

$ sudo systemctl stop lircd
$ sudo systemctl start lircd

Run the following to make sure your new remotes are loaded into LIRC.

$ irsend LIST '' ''

You should see a list of the remote names you made configuration files for.

Your univeral remote is ready to use by using irsend command. Test by pointing the IR LED towards the device you recorded the remote for. Enter an irsend command and the device should respond as if you pressed the button on the original remote. For example entering the following command will turn on my TV.

$ irsend SEND_ONCE LivingRooomTv POWER_KEY

If your device responds, great! The Pi is a working universal remote. Do not move on till you can get your Pi to respond to your LIRC irsend commands.

Step 27: Sign Up for Amazon AWS and Amazon Devloper Services

You will need to sign up for an Amazon Web Services (AWS) account and a separate Amazon Developer Services account. You will need to provide a credit card when you sign up for AWS.

AWS is Amazon's cloud service platform that does a whole lot of cool cloud stuff; way more than what we will be using. We will be using their Identity and Access Management, Lambda, and AWS IoT services.

  • Identity and Access Management (IAM) - Think of this as security area for creating users, roles, and policies.
  • Lambda - Think of this as a place where you can run code without having to worry about all the server setup.
  • AWS IoT - Think of this as the place where your physical device sends and receives information from the cloud (but not process it).

Amazon Developer Services is where you go to make Amazon apps. We will use Amazon Developer to create the Alexa application and use the Login with Amazon service.

Step 28: Create an AWS IoT Thing - Management Page

Login to your Amazon AWS account.

You should be on the AWS Services home page after logging in.

Get to the AWS IoT Device Management hub by either:

  • Typing in the search box 'IoT Device' and clicking on 'IoT Device Management' from the drop-down.

or

  • Searching near the bottom of the page and clicking on 'IoT Device Management' link in the Internet of Things section.

You should end up on the AWS IoT Things Management Hub page.

Step 29: Create an AWS IoT Thing - Create Page

From the AWS IoT Management Things hub page, click on 'Create' to open up the Creating AWS IoT things page.

Click on 'Create a single thing' which will open up the Add your device to the thing registry page.

Enter UniversalRasPiRemote for the name and you can leave the rest of the fields alone.

Click 'Next' to get to the certificates step of creating an AWS IoT thing.

Step 30: Create an AWS IoT Thing - Certificates

You should be on the Add a certificate for your thing step.

Click on 'Create certificate' to get to the certificate page. You should see a big green banner with "Certificate created!".

Make sure you download all the certificates now and the root CA for AWS IoT. I'm unsure how to download the private key after moving on from this page, so make sure you download the keys now and store them in a safe place.

The keys will have some weird hexadecimal prefix name. Rename you keys by stripping the hexadecimal hyphen prefix to make setup easier later on. The name of the files should be:

  • A certificate for this thing: certificate.pem.crt
  • A public key: public.pem.key
  • A private key: private.pem.key
  • root CA: root-ca.pem

Click on 'Activate' to activate the certificates and you should see a message flash "Successfully activated certificate."

Click 'Done' and you should be back at the Things hub page. You should also see your new thing 'UniveralRasPiRemote' listed.

Step 31: Create an AWS IoT Thing - Policies

You should be on the Things hub page.

Click on 'Secure' in the left pane to show the Secure sub sections.

Click on 'Policies' to get to the Policies hub page.

Click on 'Create' at the top right to get to the create a policy page.

Step 32: Create an AWS IoT Thing - Create Policy

You should be on the create a policy page.

Fill out the form as follows:

  • Name: UniversalRasPiRemotePolicy

Add Statements Section:

  • Action: iot:*
  • Resource ARN: *
  • Effect: Check Allow

Right now, we are just trying to get things to work. You should, after completing the Instructable, tweak the policy statements to suit your needs to only allow the necessary permissions instead of just allowing everything as we did here.

Click on 'Create' towards the bottom right of the page to create the policy. You should be back at the Policy hub page with a notification that your policy was created and you should see your UniversalRasPiRemotePolicy tile in the hub.

Step 33: Create an AWS IoT Thing - Attach Policy to Certificate

The Secure sub menus should still be visible.

Click on 'Certificates' to get back to the Certificates hub page.

Click on the 3 dots on the top right of the certificate tile that we created earlier.

Click on 'Attach policy' from the drop-down to bring up the Attach policies to certificate(s) dialog.

Check the UniversalRasPiRemotePolicy that we created earlier and click 'Attach'.

You should be back at the Certificate hub with a notification that the policy has been attached to the certificate.

Step 34: Create an AWS IoT Thing - Attach Thing to Certificate

You should still be on the Certificates hub.

Click on the 3 dots on the top right of the certificate we attached the policy to in the previous step.

Click on 'Attach thing' from the drop-down to bring up the Attach things to certificate(s) dialog.

Check the UniversalRasPiRemote that we created earlier and click 'Attach'.

You should be back at the Certificate hub with a notification that the thing has been attached to the certificate.

Step 35: Create an AWS IoT Thing - MQTT Client

Before we move on, we should get familiar with Amazon's MQTT client as this will help us test the connection between our Raspberry Pi and AWS IoT.

Click on 'Test' in the left pane to get to the MQTT client page.

In the Subscription topic textbox enter 'remote/+'. This means listen to all remote subtopics.

Click on 'Subscribe' (sorry my window was small and shortened the 'Subcribe' button) and you should be taken to I guess their publishing widget and your topic listed towards the left.

You can specify the topic to publish a message to. The textbox is where you enter the topic to publish to. The darkened text area is the message you want to publish.

Enter 'remote/tv' for topic and "hello world" in the text area and press 'Publish'.

You should see below the text area, the topic and message you published.

Let's do one more just for kicks. Enter 'remote/cable' for topic and "TurnOn" in the text area and press 'Publish'.

You should see that the message "TurnOn" was published to the topic 'remote/cable'.

Step 36: Install Node.js

Install Node.js on your Raspberry Pi Zero W with audstanley's scripts at NodeJs-Raspberry-Pi to install the latest Node.js. Follow the README.md for instructions on using his script.

I prefer using audstanley's scripts as it installs the latest Node.js without much hassle as opposed to using apt-get as that installs an old version of Node.js.

Step 37: Setup AlexaLirc - Download & Initialize

We will setup our Raspberry Pi as an MQTT client to listen to the 'remote/' subtopics from our AWS IoT service.

First we need to setup a directory to store the AlexaLirc Node.js project. I suggest you place into a direcotry named nodejs in your home directory.

SSH into your Raspberry Pi and run the following commands (skip making the directory if you already have it from previous projects):

$ cd ~ 
$ mkdir nodejs 
$ cd nodejs/ 
$ git clone https://github.com/bbtinkerer/AlexaLirc.git

That should copy the project from GitHub into a directory named AlexaLirc.

Next, you will need to download the project dependencies as they are not committed to GitHub with the project. Run the following commands:

$ cd AlexaLirc/
$ npm install

The download may take a few minutes.

Step 38: Setup AlexaLirc - Certificates

Copy your certificates that you downloaded earlier when you created the UniversalRasPiRemote AWS IoT thing into the certs/ directory of the AlexaLirc project.

Use your choice of file transfer for copying over the certificates to the Pi, USB thumb drive, scp from a Mac or Linux terminal, or pscp.exe for Windows users.

Step 39: Setup AlexaLirc - AWS IoT Configuration

We will need to update the configuration files. The project comes with example files that we can copy and edit to get started.

Run the following commands:

$ cd ~/nodejs/AlexaLirc/config/
$ cp default.example.json default.json
$ cp production.example.json production.json

That should copy the example files. We only need to edit default.json but need production.json when running in production mode.

Edit default.json with your favorite Linux text editor.

First we need to update the awsIotDevice section. If you followed the suggestion earlier about renaming your certificates, you only need to update host and region. The host value is your AWS IoT endpoint address. To get the host value, go back to your AWS IoT Thing page and click on Interact in the left pane. The host address is in the HTTP section of the page. The address is in the form "xxxxxxxxxxxxxx.iot.region.amazonaws.com". The sample configuration as follows:

...
  "awsIotDevice": {
    "host": "xxxxxxxxxxxxxx.iot.us-east-1.amazonaws.com",
    "port": 8883,
    "keyPath": "./certs/private.pem.key",
    "certPath": "./certs/certificate.pem.crt",
    "caPath": "./certs/root-ca.pem",
    "clientId": "UniversalRasPiRemote",
    "thingName": "UniversalRasPiRemote",
    "region": "us-east-1"
  },
...

Step 40: Setup AlexaLirc - Device Configuration

If you followed my advice earlier and prefixed your LIRC buttons with KEY_ there shouldn't be much to update for the remoteDevice section of the default.json configuration file.

The remoteDevice section is where you define your device and the buttons that are pressed when receiving a published message. Hopefully the format is self-explanatory but I will try my best to explain in writing.

Here is the sample that comes with the project:

...
  "remoteDevice":{
    "RasPi-TV-001": {
      "device": "SamsungTv",
      "keyMap": {
        "TurnOn": "KEY_POWER",
        "TurnOff": "KEY_POWER",
        "ChangeChannel": "KEY_",
        "SkipChannels UP": "KEY_CHANNEL_UP",
        "SkipChannels DOWN": "KEY_CHANNEL_DOWN",
        "SelectInput": "KEY_SOURCE",
        "AdjustVolume DOWN": "KEY_VOLUME_DOWN",
        "AdjustVolume UP": "KEY_VOLUME_UP",
        "SetMute": "KEY_MUTE"
      }
    },
...

"remoteDevice" is the start of the section and contains like a list of devices.

"RasPi-TV-001" is purposefully convoluted looking because this is the unique ID Alexa uses to identify your smart home device. This also the subtopic the Raspberry Pi will subscribe to.

"device" is the name of the device you defined in your LIRC remote configuration file. So I named mine SamsungTv to differentiate from my Vizio television. Change to what you used.

"keyMap" is the mapping of messages we receive to the key names you used in your LIRC remote configuration file. One exception is the ChangeChannel message as that is just the prefix to the number buttons.

Hopefully that makes sense. You just repeat for other devices and remove anything not applicable like how "RasPi-Cable-001" is defined. A cable box doesn't have volume controls so no need for it.

...
    "RasPi-Cable-001": {
      "device": "CableBox",
      "keyMap": {
        "TurnOn": "KEY_POWER",
        "TurnOff": "KEY_POWER",
        "ChangeChannel": "KEY_",
        "SkipChannels UP": "KEY_CHANNEL_UP",
        "SkipChannels DOWN": "KEY_CHANNEL_DOWN"
      }
    }
...

Step 41: Setup AlexaLirc - Test Run

After you have updated the configuration files, go back to the root directory of the project and run the following commands to start the application:

$ cd ~/nodejs/AlexaLirc/ 
$ node app.js

You should see the following if your configurations are correct (certificates named correctly/in the right place and host/region correct):

subscribed to remote/RasPi-TV-001
subscribed to remote/RasPi-Cable-001

That means the Pi will receive messages when they are published to either of those two topics.

Hop back to the Test MQTT client area of AWS IoT and subscribe to 'remote/+' again. This time in the topic textbox, enter "remote/RasPi-TV-001" and "TurnOn" in the text area (the program is case-sensitive, so please follow capitalizations) and press 'Publish'.

You should see in the AWS IoT MQTT client your message and you should see the "TurnOn" message in your Raspberry Pi terminal.

subscribed to remote/RasPi-TV-001
subscribed to remote/RasPi-Cable-001
topic: remote/RasPi-TV-001  message: TurnOn
success executing: irsend SEND_ONCE SamsungTv KEY_POWER

If you had your Raspberry Pi's IR LED pointed at your television and the buttons mapped correctly in the configuration file, your television should have responded as if you had press the power button.

Before moving on, make sure everything works. You should be able to control your TV or cable box from the AWS MQTT client. Try entering the commands from the config file like TurnOff, 'SkipChannels UP', 'SkipChannels DOWN', etc. For changing channels, append a space and the channel # to ChangeChannel (eg. 'ChangeChannel 35' or 'ChangeChannel 1440').

Now is the time to make sure you have the proper button/key mapping before moving on.


Step 42: Setup AlexaLirc Automatic Startup on Boot

These instructions are for Raspbian Stretch on the Pi Zero W with Node.js installed using audstanley's scripts. These instructions should be good for awhile until Raspbian changes how services startup. If you installed Node.js another way, you will need to update the location of the node executable.

You will need to create a systemd service file in '/etc/systemd/system/'. Change directory to the system directory.

$ cd /etc/systemd/system

Then create a file named alexaLirc.service with the following contents (don't forget to use sudo when starting your editor):

[Service]
WorkingDirectory=/home/pi/nodejs/AlexaLirc 
ExecStart=/opt/nodejs/bin/node app.js
Restart=always
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=alexaLirc
User=root
Group=root
Environment=NODE_ENV=production

[Install]
WantedBy=multi-user.target

Test that you have correctly made the service file by issuing the following command and then checking the syslog for alexaLirc entries. Don't forget to stop the app first if it is currently running.

$ sudo systemctl start alexaLirc

In a separate console window you can run the following to watch the tail end of syslog.

$ tail -f /var/log/syslog

Publish a few MQTT messages and you should see log entries by alexaLirc. After you have verified the AlexaLirc works, we need to enable the alexaLirc service so that it automatically starts after the Pi boots. Run the following command:

$ sudo systemctl enable alexaLirc

You should see the following output:

Created symlink /etc/systemd/system/multi-user.target.wants/alexaLirc.service → /etc/systemd/system/alexaLirc.service.

Reboot and check in the syslog that alexaLirc automatically started. Give the Pi a minute or so to startup before publishing another MQTT message.

$ sudo shutdown -r now

Step 43: Create IAM Role - IAM/Role Dashboard

We will need an IAM Role to assign to a Lambda function that we will create.

Head back to the AWS home page.

Search for IAM in the search bar and click on IAM from the dropdown to get to the Identity and Management dashboard (ignore that I didn't do 5 security steps).

Click on Roles in the left pane to get to the Roles dashboard.

Click on Create Role to get to the Create role page.

Step 44: Create IAM Role - Create Role

You should be on the Create role Page.

Scroll down if necessary, find and click on 'Lambda' to highlight it. You should see a message at the bottom after clicking on the link.

Click 'Next: Permissions' to move onto the Attach permission policies page.

Step 45: Create IAM Role - Attach Permissions Policies

You should be on the Attach permissions policies page.

Enter 'AWSLambdaBasicExecutionRole' in the Policy type Filter textbox. The list should now just show 'AWSLambdaBasicExecutionRole'. Click on the checkbox to highlight it.

Next, enter 'AWSIoTFullAccess' in the Policy type Filter textbox. The list should now just show 'AWSIoTFullAccess'. Click on the checkbox to highlight it.

Click 'Next: Review' at the bottom to get to the Review page.

Double check on the Review page that the two policies we checked are attached the role.

Step 46: Create IAM Role - Create Role Completion

You should be on the Create Role Review page.

Enter the following:

  • Role name: AlexaUniversalRasPiRemote
  • Role description: (anything you want that makes sense)

Double check that the polices are listed in the Policies section:

  • AWSLambdaBasicExecutionRole
  • AWSIoTFullAccess

Click on 'Create Role' at the bottom right and you will be back at the Roles dashboard and there should be a message that the Role has been created.

Step 47: Create Lambda Function - Create Function

Head back again to the AWS homepage and enter Lambda in the search box. Click on Lambda from the dropdown and you should be taken to the AWS Lambda Functions dashboard.

Click on 'Create function' to get to the Create function page.

Enter the following on the Create function page:

  • Select Author from scratch
  • Name: AlexaUniversalRasPiRemote
  • Runtime: Node.js 6.10
  • Role: Choose an existing role
  • Existing role: AlexaUniversalRasPiRemoteRole

Click on 'Create function' and you should be taken to your new Lambda function's dashboard.

Step 48: Create Lambda Function - Upload & Update Code

We need to upload the Lambda code contained in a zip file in the AlexaLirc project. Copy the file from '~/nodejs/AlexaLirc/awsLambdaSrc/lambdaSrc/AlexaUniversalRasPiRemote.zip' from the Raspberry Pi to your computer.

You should be on the AlexaUniversalRasPiRemote Lambda Configuration page.

Scroll down to the Function code section.

Click on the Code entry type dropdown and select 'Upload a .ZIP file'.

Click on 'Upload' and select the AlexaUniversalRasPiRemote.zip file.

You should see the name of the zip file next to the 'Upload' button.

Click on 'Save' at the top right to complete the file upload process.

Click on the Code entry type dropdown again and select 'Edit code inline'. You should see that the code from the zip file had been uploaded.

You will need to update iotEndpoint address in the MyDevices.js file to your AWS IoT endpoint. This is the same value you used for host in the AlexaLirc default.json configuration file.

Click on the little triangle next to the lib folder in the left pane of the coding area to show the files in the folder.

Double-click on 'MyDevices.js' to open the file in the editor.

Update line 8 and replace 'xxxxxxxxxxxxxx.iot.us-east-1.amazonaws.com' with your IoT endpoint address.


Step 49: Create Lambda Function - Test Setup

We will create test events that mimic what Alexa would send to our Lambda function. This way we can test without having the Alexa Skill setup yet.

In the "awsLambdaSrc/testEvents/" directory of the AlexaLirc project are a bunch JSON files that contain what would be sent by Alexa to the Lambda function. You will need to copy the contents of the files to the test setup of the Lambda function and make an update to the iotEndpoint value to point to your AWS IoT endpoint.

You should be on the Lambda Configuration page. At the top, to right of the Lambda functions name is the test event dropdown selection. Click on the dropdown and select "Configure test events" to open the Configure test event dialog.

Enter the following:

Select 'Create new test event'

Event template: leave as is

Event name: AlexaPowerOn

Text area: (copy the contents from AlexaPowerOn.js from the AlexaLirc project in the awsLambdaSrc/testEvents/ directory). Update iotEndpoint to your AWS IoT endpoint.

Click on 'Save' to save the event and return back to the Lambda Configuration page.

Step 50: Create Lambda Function - Test

You should be on the Lambda function configuration page and there is "AlexaPowerOn" in the test event dropdown.

Click on 'Test' and you should see a green tinted message box appear toward the top that has the execution results if everything went okay. If you had your Raspberry Pi IR LED pointed at your television, the TV would have responded accordingly.

Open the AWS IoT Test MQTT client and subscribe to 'remote/+' again. Press the 'Test' button from the Lambda page and you should see a 'TurnOn' message in the MQTT client. If your Pi was pointed to the television, the television should have turned on or off. And if you do this a few times, your significant other will get mad at you.

Repeat the previous step and this step for the rest of the test events found in the AlexaLirc project. The only exception is the AlexaDiscovery as that will not publish anything. That is to help debug if your devices are not discovered by Alexa.

Step 51: Create Login With Amazon Security Profile

We need to create a Login with Amazon service for our Alexa Skills app. Account linking is required when using the Alexa Home Skill API skill type.

Login to your Amazon Developer Console at https://developer.amazon.com/. Click on Developer Console link if you are not directly taken to the console.

Click on 'APPS & SERVICES' in the menu bar to display the apps and services sub menus.

Click on 'Login with Amazon' to get to the Login with Amazon page.

Click on 'Create a New Security Profile' to get to the Security Profile Management page.

Enter the following values:

Click on 'Save' at the bottom and you will return to the Login with Amazon page and there should be a message that your Security profile had been created.

Click on the 'Show Client ID and Client Secret' link to display the ID and password used for the AlexaUniversalRasPiRemote profile. Take note of the two values as you will need these when setting up the Alexa Home Skill.

Step 52: Create Alexa Home Skill - Create a New Skill

You should still be logged into Amazon Developer. Click on 'ALEXA' in the top menu to bring up the Get Started with Alexa page.

Click on 'Get Started >' in the Alexa Skills Kit tile to get to the Building Alexa Skills with Alexa Skills Kit page.

Click on 'Add a New Skill' towards the top right to get to the Create a New Alexa Skill Page.

Step 53: Create Alexa Home Skill - Skill Information

You should be on the Skill Information step of creating a new Alexa skill.

Enter the following:

  • Skill Type: Smart Home Skill API
  • Language: (your language)
  • Name: RaspPiRemote
  • Payload Version: v3 (preferred)

Click 'Save' at the bottom and you should notice that both Skill Information and Interaction Model are both complete (have green circle with check mark). The Skill Information page should now show the Application Id for your skill and also at the top under your skill name (the two lines I blanked out in the image). Take note of this Id as we will need to give it to the Lambda function we created earlier.

Click 'Next' and you will be taken to the Interaction model which tells you its covered by the Smart Home Skill API. This means that we don't have to write all possible utterances (things we say to Alexa) for our skill to work.

Click on 'Next' to get to the Configuration page.

Step 54: Create Alexa Home Skill - Configure Lambda Trigger

Before we can complete the Alexa Skill configuration, we need to add an Alexa Smart Home trigger to our Lambda function.

Open another browser window or tab to the AlexaUniversalRasPiRemote Lambda function configuration page.

In the Designer area towards the top, Click on 'Alexa Smart Home' in the Add triggers pane to attach a trigger to the Lambda function. You should see a Configure triggers section appear below the Designer section.

Enter the Application Id of the Alexa Skill we just created and ensure Enable trigger is checked. The application Id can be found under the Alexa Skill name in the Alexa Skill information page or by clicking on 'View Skill Id' from Alexa Skills dashboard.

Click 'Add' in the Configure triggers section and then 'Save' at the top right. You should see the Alexa Smart Home tile in the Designer says saved and the Configure trigger section now says Alexa Smart Home with the application Id you entered.

We are done with the Lambda function setup but take note of the Lambda's ARN at the top as we will need to enter that value as the service endpoint for our Alexa Skill.

Step 55: Create Alexa Home Skill - Configuration

Before completing the configuration page, open another browser tab or window to your LWA service as we will need the LWA client Id and secret. Also we will need to give our LWA service our Alexa redirect URLs.

Jump back to the tab or browser window that has your Alexa Skill Configuration page.

Enter the following values.

  • Service Endpoint Type
    • Default: (the ARN to the UniversalRasPiRemote Lambda function)
    • Provide geographical region endpoints: Choose yes and pick location nearest to and enter the Lambda ARN again).
  • Account Linking
    • Authorization URL: https://www.amazon.com/ap/oa
    • Client Id: Your LWA client Id
    • Domain List: (leave alone)
    • Scope: Click 'Add scope' and enter "profile" in the textbox
    • Redirect URLs: take note of these
    • Authorization Grant Type: Auth Code Grant
    • Access Token URI: https://api.amazon.com/auth/o2/token
    • Client Secret: Your LWA client secret
    • Client Authentication Scheme: HTTP Basic
  • Permissions
    • Request users to access resources and capabilities: Leave unchecked

Privacy Policy URL: (supposed to be your policy but I just put Amazon's again) https://www.amazon.com/gp/help/customer/display.html?nodeId=468496

Click on 'Save' and the page should refresh and show that it saved.

Click 'Next' to move onto the Test section

Ensure that Start testing this skill is switched to "Yes". You can try out the Test Simulator but as of writing this, the simulator has not been working properly. Maybe Amazon will have it fixed by the time you read this.

We are done with the Alexa Skill setup in the developer console.

Step 56: Create Alexa Home Skill - LWA Configuration

Jump to your browser window or tab that has the Login with Amazon page.

Click on the little gear next to the AlexaUniversalRasPiRemote security profile and select 'Web Settings' from the dropdown.

You should be on the Web Settings section of the security profile. Click 'Edit' to make the fields editable.

Leave Allowed Origins alone.

Enter the Redirect URLs from the Alexa Skill Configuration page into the Allowed Return URLs. Click on 'Save' when you have entered all the Redirect URLs.

We are done setting up our Login with Amazon service.

Step 57: Enable RasPiRemote Alexa Skill

Login to your Alexa application either from a browser or the Alexa phone app. These instructions are for the browser version of the Alexa app but should be similar to the phone app.

Click on 'Skills' on the left side bar menu to display the All Skills page.

Click on 'Your Skills' at the top right to display only your skills and then click on the 'DEV SKILLS' tab.

You should see the RasPiRemote skill with a notice that says 'Account linking required'.

Click on the RasPiRemote skill and then click on 'Enable' when the skill loads.

A new browser window or tab with the Login with Amazon page will open.

Enter your credentials and sign in.

You will be asked to give permission to access to your profile. Click 'Allow' and you will see a that the skill has successfully linked to your account.

Close that tab or window and go back to the Alexa app.

Step 58: Discover Devices

The Lambda function is setup to discover a TV and cable box device by default. Those devices are defined in the MyDevices.js file in the Lambda function project.

We will need to discover the two devices in the Alexa app.

Jump back to the browser window/tab that has the Alexa app open. After linking the skill, there should be a prompt to ask if you want to discover devices, go ahead and click on 'DISCOVER DEVICES'. You can then skip some the steps below which is just another way of discovering new devices.

Click on 'Smart Home' in the left side bar menu to display the Smart Home page.

Click on 'Devices' to get to the devices page.

Click on 'Discover' near the bottom to start scanning for new devices.

After the scanning process, there should be two new devices named "Television" and "Cable".

Step 59: Ask Alexa to ... Your Television

As long as you have tested at each test point, everything should just work. You can open up the Amazon MQTT test client to make sure the correct messages are published.

Try speaking:

  • "Alexa, turn on television"
  • "Alexa, channel up on television"
  • "Alexa, channel up" (should remember the last thing you channeled up on was the Television.

and so forth (well for the commands that we defined in the AlexaLirc default.json configuration file).

Keep in mind the limitations of the Smart Home Skill API and what Alexa interfaces were implemented in the AlexaLirc project. This project is for simple control of entertainment devices (on/off, volume, and channel controls).

The main purpose of this Instructable is to get you up and running an Alexa controlled television/cable box as fast as possible without all the nuances of coding and figuring out where things go. I figured, just get the project working first then figure out how services interact with each other is easier than trying to explain every little detail to the user.

Thank you for reading this really long Instructable. I hope you enjoy bossing Alexa around to control your TV/cable.

Step 60: Troubleshooting

AlexaLirc program no output to the terminal, check your AWS IoT thing's policy for a misconfiguration. Thanks to user JamesG368 for informing me of this.

AlexaLirc program unresponsive after awhile when running multiple RasPi's to one AWS IoT thing using the same certificates across all Pi's. Seemed like the last one wins when using multiple Pi's to one AWS IoT thing, the last Pi to connect would be the working Pi. Made separate AWS IoT things for separate Pi's to resolve this issue.

Share

    Recommendations

    • Creative Misuse Contest

      Creative Misuse Contest
    • Tiny Home Contest

      Tiny Home Contest
    • Water Contest

      Water Contest

    12 Discussions

    The best tutorial of all i can find in the internet.

    How should the MyDevices.js be updated to add other items (e.g. stereo etc.), also what controls how you refer to the item when speaking to Alexa?

    3 more answers

    Could be either Alexa Skill not communicating with the Lambda function or the Lambda function is sending back an incorrect response.

    In AWS, open a window to the Cloudwatch service. Go to the Logs sections and you should see a log group for your lambda function. Click on your Lambda's log group. I would clear all log streams to not get confused with old stuff for now.

    Perform the discovery and wait a minute or so and keep refreshing the log group. You should see a stream appear. If no stream appears after several minutes, then there is a configuration error connecting the Lambda with the Alexa Skill. If a stream appears, click on the stream to check what was sent by Alexa and what was sent back from the Lambda function.

    I just realized I forgot to stringify the response so the cloudwatch log doesn't show what was sent back to Alexa. You could either change line 42 of index.js for the Lambda function to console.log( JSON.stringify(response)); or setup the test events for an Alexa Discovery event (there is a sample in the AlexaLirc project's awsLambaSrc/testEvents folder that you can copy and paste into the test event then run the test and the response will be displayed in that green execution results at the top.

    Double check the response from the Lambda function is correct. The problem I came across while creating the project was sending back an incorrect response. https://developer.amazon.com/docs/device-apis/alexa-discovery.html#discoverresponse has an example of what a response could look like.

    Hope that helps.

    Thanks. I think I've set that all up properly now.

    When I try to discover devices my devices are not showing. I've been back through the steps and think that I've done everything required.

    Any idea what the problem could be? Everything working in Lambda, MQTT, the skill is installed etc, just don't have the devices showing up when I try to discover.

    Thank you. I totally forgot to add that in the project's readme. I will add it to the readme in more detail when I get the chance, but I can try to give a quick overview here.
    Create a new array that contains the AlexaInterfaces you want the device to have (eg. lines 13-18). The interfaces I coded for are in AlexaInterfacesUtil.js.
    Create a new Endpoint, for the capabilities parameter, choose from https://developer.amazon.com/docs/device-apis/alexa-discovery.html#display-categories (eg. lines 20-27)
    Then add the endpoint to DevicesUtil (eg. line 52)

    The friendlyName parameter is what you refer to when talking to alexa. So default setup is 'Television' and 'Cable'. I added a third one for my second tv and gave it a friendlyName of 'Samsung'. Just be aware on naming as Alexa doesn't always get it right. We have a Vizio television, I tried to use that as the friendlyName but Alexa kept thinking I said Video.

    When I run node app.js I don't get the subscribed lines you discussed in the instructions.
    Is there a log I can check or anything I can triple check to see if I missed something?
    I've looked at the default.json and cut and pasted the IOT host from the Amazon IOT so that is correct.
    I've purposefully inserted an error in default.json to see if app.js is reading it, and app.js quits and give me an error, so I know its reading the json file.
    Any help I can get would be greatly appreciated

    Thanks for a really good instructable. I've built the remote and have it working with Openhab (which allows Alexa control) so haven't tried the Alexa skill aspect yet, but it's a useful addition.

    Do you know if there's a way of updating the web interface to allow control of remotes in different rooms? I have built 3 or 4 remotes to control devices in different rooms, and can currently access them all through their own IP addresses. I just wondered if there's a way of having a single interface that can run commands on the different remotes? Any ideas?

    This would be a really useful addition, as it would allow a single remote solution for all around the house. Something that the Logitech Harmony solution fails to do.

    1 more answer

    I thought about this for a long time and maybe the easiest solution is to create a header row that just links to all the different rooms.

    If you want a big monolithic page controlling everything, then that will require some change to accept GET requests in the web servers. Then on the clientside, you would need to update the javascript from POST to GET to the IP with the correct URL call. So instead of posting back /devices/tv/SEND_ONCE/KEY_POWER, would need to GET with the absolute URL http://room/devices/tv/SEND_ONCE/KEY_POWER.

    0
    None
    fenyvesi

    Question 6 months ago

    Dear bbtinkerer,

    This is an iinstructable with epic details. My question is the following:
    Alexa can control TV/STB-s in other ways also. My problem is to control an A/V receiver. If I setup LIRC with the A/V receiver codes then does Alexa discover this service also? How can I control the input channel for example through voice command?
    Thanks in advance.
    George


    1 more answer

    Sorry for the late reply. You will have to add a new device for your A/V receiver in the MyDevices.js for the Lambda function. I did a quick outline in a comment above this one on how to do it. I'll get more detailed instructions in the project readme when I get the chance.

    The input part is the not so great part. Since our devices are not smart, we can't go directly to the input, we would have to utter the input command till the device changes to correct input, basically we are just mimicking pressing the input button. This is a pain to do. Well, assuming there is just that one input button you press to cycle through the inputs.

    If there are IR codes that could go direct to the input of choice, would need to update the Lambda code to publish the input name and update the AlexaLirc application to map that input name to the correct IR Code/key/button. This sounds like a feature that I should and will probably work on in the future.

    You did an amazing job on this project. I like your detailed step-by-step directions and a person can learn a lot from building your project. You got my vote, but I didn't build your project, because I already have an Alexa voice controlled remote that's based on the ESP8266 WiFi module combined with an IR receiver and transmitter. The system I have works perfectly in a quiet room, but I find that Alexa has a hard time hearing my voice commands over the sound from the TV set. I trained Alexa to recognize my voice, but that didn't help. I can't even command the TV to turn down the sound in order to change channels, unless the TV sound is already tuned down very low to start with. The TV sound has to be turned down so low for Alexa to understand my commands that I have to strain to hear the TV dialog and that's very annoying. Moving the Echo away from the TV and closer to me helps, but it doesn't solve the problem unless I shout, or sit next to the Echo and speak almost directly into it. The Echo doesn't have this problem when audio originates from the speaker that's built into the Echo. That's probably due to a local sound cancelling circuit built into the Echo. The problem is only caused by sound that originates from an outside source in the same room, such as a TV. The TV dialog appears to be in conflict with my voice and that prevents my commands from being understood by Alexa. Or maybe, the TV sound causes an automatic gain control circuit in the Echo to decrease the sensitivity of the Echo's built-in microphone. Whatever causes the problem, I couldn't find a solution, so I eventually had to stop using my voice command remote control. Your hardware and software is different, but it also depends on Alexa and the Echo, so I wonder if you've had this same problem and found a solution to it? It's disappointing to build a voice control device that's really cool and then find out that it doesn't work worth a damn due to a limitation of Alexa and Echo. Other than using wireless headphones, a possible solution to this problem might be to have the TV sound come out of the Echo via a Bluetooth link. This would take advantage of the Echo's internal sound cancellation circuitry, but the TV sound quality wouldn't be as good, because it would eliminate stereo surround sound and the sub-woofer. In any case, I haven't figured out how to make that idea work, so I can't test it.

    0
    None
    MinhN117

    Question 6 months ago

    Great work! I have almost the same setup but use LIRC with LIRC_web and a HA bridge to connect to the Echo. All connections are local and does not have to go out to the web. LIRC_Web uses GET commands that HA bridge does the rest. The only problem is that your have to say "Turn on volume UP".

    Screen Shot 2018-01-30 at 9.05.13 PM.png