In this article I will describe a small hack that I put together a couple of days ago. I wanted some sort of Network enabled temperature sensor to measure the temperature in my storage basement. I was fascinated by the idea of having the measurements stored in a database in order to do some server side processing and generate charts of temperature over time.
I am going to describe the system and show the source code needed for such a task.
My system consists of the following parts
1. Arduino board. I used the Duemilanove wi
th the atme
ga328. But any arduino board will do as well.
2. An ethernet shield.
3. a temperature sensor (MCP9700) from microchip.
5. a server running Lighttpd, php, mysql. I used an
NSLU2 running Debian etch.
The system’s architecture is really sim
ple. The arduino board measures the temperature every minute. Everytime a measurement is taken, the adruino acts as a web client and calls a PHP file which is located on a small server (NSLU2). This file inserts the measurement in a mysql database.
Thats pretty well it.
A user can access the webserver at any time to see a temperature graph which is created with the help of the Google Chart API.
There are also some similar projects out there to
get you inspired:
http://www.youritronics.com/arduino-temperature-sensor/
The code running on arduino, connects to the webserver on NSLU2, and issues a “GET /script.php?…..” in order to submit the measurements to the database. When I started working on the code, I came across a strange bug that spoils the reliability of the webclient connection.
There is a relevant conversation here. Anyway, to rectify the problem I did two things.
1) Modified the Client.cpp file from the Ethernet library, so that the transmission includes the whole string and not one by one byte. Informat
ion about these modifications can be found here
In case the link break in the future,
I will show t
he modifications that I followed below.
Client.cpp , add the following code
void Client::print(const char c[]) {
send(_sock, (uint8_t *) c, strlen(c));
}
void Client::println(const char c[]) {
print(c);
print(“\r\n”);
}
Client.h, add the following code
friend class Server;
//new code
void print(const char c[]);
void println(const char c[]);
using Print::print;
using Print::println;
#endif
};
These modifications improve the transmission efficiency of the ethernet library.
2) The next thing I did was to prepare the ‘G
ET’ string before sending it to the server, and avoid breaking the transmission by calling client.print more than once.
The code of the arduino is shown below. Pay attention on how the string with the GET request is pre-formatted with sprintf() and sent at once to the server.
Once the Arduino was programmed, I did some performance tests, and confirmed that there was no connection failure ever through 24 hou
rs.
The next part was to create a new mysql database with 1 table for the measurements logging.
The table looks like this
mysql> describe measurements;
+—————-+———+——+—–+———+—————-+
| Field | Type | Null | Key | Default | Extra |
+—————-+———+——+—–+———+
—————-+
| ID | int(11) | NO | PRI | NULL | auto_increment |
| measurement_id | int(11) | YES | | NULL | |
| timeposted | int(11) | YES | | NULL | |
| temperature | int(11) | YES | | NULL | |
+—————-+———+——+—–+———+—————-+
4 rows in set (0.39 sec)
While the ‘ID’ is auto incremented, the ‘measu
rement_id’ is only a serial number
sent by the arduino for every measurement. Keep in mind that this serial starts from zero every time the arduino power up. The only reason to have this field is to look for power ups of the board, and for the fun of it.
As I already mentioned before, there are 2 .php files on the server.
enter.php – called from the arduino to insert the values in the database
index.php – called by the user to see the measurements over time
The code of the ‘enter.php” is shown below
When this file is called, it gets the two parameters (measurement_id and temperature) and together with the current system time, it inserts them in the database as a now row into the table.
The index.php does all the nice work. It reads a number of rows from the table and uses the google chart API to display a nice chart of th
e measurements.
To avoid pasting the code here and having problems with the blog editor, all the files can be found here




