What do you need to know to make this project:
You need to know about:
- Some electronics skills (soldering)
- Arduino IDE
(you will need to update additional boards in the IDE: http://arduino.esp8266.com/stable/package_esp8266...)
- updating/programming an ESP board via the Arduino IDE.
(there are some nice tutorials available on the web)
This can be done using an Arduino Uno or using a FTDI (usb to serial adapter).
I used my Uno because I did not have any serial port on my PC nor did I have an FTDI
Step 1: Go Shopping
What will you need to make this happen?
For the Digital Temperature and Humidity Sensor:
- Either a breadboard or an alternative like prototype pcb, solder, soldering iron ...
- Some wire
- two jumpers
- a 10k Ohm resistor
- an ESP12F (other models might work too...)
- a DHT22 (a bit more expensive than the DHT11 but more accurate)
- 3 AA rechargable batteries and a battery holder
- a little plastic box to put your project in
- In a later stage I plan to add a HT7333 with two 10uF capacitors between the battery pack and the ESP
to stabilize the input voltage (VCC) to the recommended 3.3V but also to protect the ESP from overvoltage.
For the Network part:
- Your home WiFi Network
For the Server part:
- Any Linux based system (always on!)
I used a Raspberry Pi (which I also use as server for my Outdoor IP cameras.)
- gcc compiler to compile your server code
- rrdtool package to store the data and generate graphs
- apache (or another webserver)
Your favorite PC or laptop with Arduino IDE on it.
Step 2: Setup and Background
In this version of a WiFi connected - not to say IOT - temperature and humidity sensor
I used an ESP12F, a DHT22 and a 3 AA battery holder with rechargable batteries.
Every 20 minutes the ESP takes a measurement from the DHT22 and sends it to a server (a Raspberry Pi) over UDP on my home WiFi network. After the measurments have been sent, the ESP goes into deepsleep. This means that only the Real Time Clock of the module remains powered, resulting in an incredibel power saving. For about 5 seconds, the module requires about 100mA, then during the 20 minutes deepsleep only 150uA.
I didn't want to use any Internet based service because I have my Raspberry Pi which is always on anyway and in this way I had the pleasure of writing the server part as well.
On the server (a Raspberry Pi running Raspbian) I have written a simple UDP listener (server) which stores the values into a simple RRD. (Round Robin Database using RRDtool by Tobias Oetiker.)
The advantage of RRDtool is that you create your database once and the size remains the same. Alse you don't need to have a database server (like mySQLd) running in the background. RRDtool gives you the tools to create the Database and generate the graphs.
My server creates the graphs on a periodic basis and displays everything in a very simple http page. I can consult my readings with a simple browser by connecting to the Apache2 webserver on the Raspberry Pi!
Finally, I didn't have an FTDI (USB to Serial) so I used my Arduino UNO.
You need to connect the TX's and the RX's and the GND of the ESP and the UNO. (I know, your instinct might tell you to cross RX's and TX's... tried it too, does not work.)
I didn't do a level conversion (UNO: High=5V but ESP is basically a 3.3V device... There are some nice FTDI's on the market where you can even select your High level to be 5 or 3.3V.
My circuit is powered by 3 AA rechargeable batteries - so in fact 3 X 1.2V. In a later phase I intend to put a HT7333 between the battery pack and the circuit for safety; newly charged batteries could have more than 1.2V and the ESP should be powered with min. 3V and max. 3.6V. Also if I decide - in a moment of weakness - to put in Alkaline batteries (3 X 1.5V = 4.5V) my ESP will not be fried!
I also considered using a 10cm x 10cm Solar panel, but it was just not worth the hassle. By doing 3 measurements per hour (basically 3x 5 seconds @ 100mA max. and the rest of the time @100uA) , I hope to power my circuit for 1 year on the same rechargeable batteries.
Step 3: The Arduino - ESP12 Part
I did this project in different steps.
There are several links that help you to import the ESP12 (aka. ESP8266) into the Arduino IDE. (I had to use the version 2.3.0 instead of the latest one because of a bug that might have been solved meanwhile...)
I started by hooking up the ESP, over my Arduino UNO (only used as a bridge between my PC via USB to the Serial) to the ESP serial interface. There are separate Instructables explaining this.
In my finished project I left the wires to connect to the Serial in case I ever need to troubleshoot.RX
Then you need to wire your ESP12 as follows:
GND --> UNO GND
RX --> UNO RX
TX --> UNO TX
EN --> VCC
GPIO15 --> GND
Initially I tried powering my ESP from the 3.3V on the UNO but I quicky moved to powering my ESP with a bench Power Supply but you can use your battery pack too.
GPIO0 --> I connected this one with a jumper to GND to enable flashing (= programming) the ESP.
First test: leave the jumper open and start a serial monitor in the Arduino IDE (at 115200 baud !).
Power cycle the ESP, you should see some rubbish characters and then a message like:
Ai-Thinker Technology Co. Ltd.
In this mode, the ESP acts a bit like an oldfashioned modem. You need to use AT commands.
Try the following commands:
and the following two commands
This should give you a list of all WiFi networks in the area.
If this is working you are ready for the next step.
Step 4: Testing the ESP As a Network Time Protocol (NTP) Client.
In the Arduino IDE, under File, Examples, ESP8266WiFi, load NTPClient.
Minor tweaks are needed to make it work; you need to put in your SSID and password of your WiFi network.
Now place the jumper, shorting GPIO0 to GND.
Power cycle the ESP and upload the sketch to the ESP.
After the compilation, the upload to the ESP should start. The blue LED on the ESP will be blinking rapidly as the code is being downloaded.
I noticed that I had to play around a bit with restarting the IDE, restarting the ESP before the upload would work.
Before you start compiling/uploading the sketch, be sure to close the serial console (=serial monitor) because this will prevent you from doing the upload.
Once the upload has succeeded, you can re-open the serial monitor to see the ESP effectively getting the time from the Internet.
Great, you have programmed your ESP, connected to your WiFi and got the time from the Internet.
Next step we will test the DHT22.
Step 5: Testing the DHT22 Sensor
Now some extra wiring is required.
Connect pin 1 (on the left) of the sensor to VCC (3.3V)
Connect pin 2 --> ESP GPIO5 (DHTPIN in the sketch)
Connect pin 4 (on the right) of the sensor to GROUND
Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor.
Similar to the NTP test, go find the DHTtester sketch, and tweak it in the following way:
#define DHTPIN 5 // we selected GPIO5 to connect to the sensor
#define DHTTYPE DHT22 // since we are using a DHT22 but this code/library is also suited for DHT11
Again, close the serial monitor, power cycle the ESP and compile and flash the ESP.
If all goes well you should see the measurements appear in the serial monitor.
You can play around a bit with the sensor. If you breathe on it, you will see the humidity going up.
If you have a (non LED) desk lamp, you can shine on the sensor to heat it up a bit.
Great! Two large parts of the sensor are now working.
In the next step I will comment on the final code.
Step 6: Putting It Together...
Again some extra wiring... this is to make the DeepSleep possible.
Remember, DeepSleep is an incredible function for IoT devices.
However if your sensor is hardwired for DeepSleep, it might be difficult to reprogram the ESP so we are going to make another jumper connection between
Yes it MUST be GPIO16, because that is the GPIO that is hardwired to wake up the device when the Real Time Clock goes off after the DeepSleep!
While you are testing, you can decide to do a 15 seconds DeepSleep.
When I was debugging, I would move the jumper to GPIO0 so I could flash my program.
Upon download complete, I would move the jumper to GPIO16 so that DeepSleep would work.
The code for the ESP is called TnHclient.c
You have to change your SSID, Password and the IP address of your server.
There are extra lines of code that you can use to troubleshoot or test your setup.
Step 7: The Server Side of Things.
It is a common misunderstanding that UDP is unreliable and TCP is...
That is just as silly as saying a hammer is more usefull than a screwdriver. They are simply different very usefull tools and they both have their uses.
By the way, without UDP the Internet would not work... DNS is based on UDP.
So, I chose UDP because it is very lightweight, easy and fast.
I tend to think that my WiFi is very reliable so the client will send at most 3 UDP packets if the acknowledgement "OK!" is not received.
The C-code for the TnHserver is in the TnHServer.c file.
There are several comments in the code explaining it.
We will need some extra tools on the server: rrdtool, apache and maybe tcpdump.
To install rrdtool on Raspbian you can simply install the package like this:
apt-get install rrdtool
If you need to debug the network traffic, tcpdump comes in handy apt-get install tcpdump
I needed a webserver to be able to use a browser in order to consult the graphs: apt-get install apache2
I used this tool: http://rrdwizard.appspot.com/index.php to get the command to create the Round Robin Database. You only need to run this once (if you get it right the first time).
rrdtool create TnHdatabase.rrd --start now-10s \
--step '1200' \
Finally, I use a crontab entry to restart my TnHserver every day at midnight. I run the TnHserver as a normal user (ie. NOT root) as a security precaution.
0 0 * * * /usr/bin/pkill TnHserver; /home/user/bin/TnHserver >/dev/null 2>&1
You can check that the TnHserver is running by doing
$ ps -elf | grep TnHserver
and you can verify it is listening for packets on port 7777 by doing
$ netstat -anu
Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address Foreign Address State
udp 0 0 0.0.0.0:7777 0.0.0.0:*
Finally CreateTnH_Graphs.sh.txt is an example script to generate the graphs. (I generate the scripts as root, you might not want to do this.)
Using a very simple webpage you can watch the graphs from any browser on your home network.