⬆️ ⬇️

The interaction history of the “teapot” and DS18B20 through the Raspberry Pi with sending data to narodmon.ru

Good time of day, dear habrasoobschestvo!

A week ago, I finally waited for my Malinka. This post is about how to fill the bumps in such a simple task as working with temperature sensors.

Who cares - welcome under cat.



So, having become the owner of Crimson Happiness with 512 MB of RAM on board, I began to re-examine many posts, including on Habré, about the possible options for creating a Smart Home. But since my education is far from IT, I decided not to immediately make Alice , but I began with a simple one - temperature control.

I will omit the installation of the system on Malinka, this topic is described in sufficient detail here and here . I will go straight to setting up Malinki to automate temperature control with storing and displaying results via the web.

I was guided by a bunch of 1-wire, ds18b20 and rrdtool , as the easiest and most affordable option.



1. Installing software


Core patch for 1-wire
cd / boot

wget www.frank-buss.de/raspberrypi/kernel-rpi-w1.tgz

tar -xzf kernel-rpi-w1.tgz

rm -f kernel-rpi-w1.tgz

cd / lib / modules

wget www.frank-buss.de/raspberrypi/modules-rpi-w1.tgz

tar -xzf modules-rpi-w1.tgz

rm -f modules-rpi-w1.tgz

sync

reboot



Installing libwww-perl and rrdtool
sudo apt-get install libwww-perl rrdtool



2. Creating the necessary scripts


Create_db.sh database creation script
#! / bin / bash

rrdtool create multirPItemp.rrd --step 300 \

DS: in_temp: GAUGE: 600: 0: 50 \

DS: out_temp: GAUGE: 600: -30: 50 \

RRA: AVERAGE: 0.5: 1: 12 \

RRA: AVERAGE: 0.5: 1: 288 \

RRA: AVERAGE: 0.5: 12: 168 \

RRA: AVERAGE: 0.5: 12: 720 \

RRA: AVERAGE: 0.5: 288: 365


A little remark to the database creation script. In the script, I set the temperature ranges for the sensor on the street and in the apartment. --step 300 - temperature data storage interval - 300 seconds (5 minutes). 600 is a parameter in seconds, in the absence of which temperature values ​​become its value “UNKNOWN”.



Script for obtaining temperature from sensors get_temp.pl
#! / usr / bin / perl

use warnings;

& check_modules;

& get_device_IDs;

')

foreach $ device (@deviceIDs)

{

$ reading = & read_device ($ device);

if ($ reading! = "9999")

{

push (@ temp_readings, $ reading);

}

}



#update the database

`/ usr / bin / rrdtool update /home/pi/temperature/multirPItemp.rrd N: $ temp_readings [0]: $ temp_readings [1]`;



print "Temp 1 = $ temp_readings [0] Temp 2 = $ temp_readings [1] \ n";



################################################## #####################

Additions for narodmon.ru. Based on habrahabr.ru/post/166373

open (FILE, "> / home / pi / temperature / temp_out");

print FILE "$ temp_readings [0]";

close (FILE);

open (FILE, "> / home / pi / temperature / temp_in");

print FILE "$ temp_readings [1]";

close (FILE);

################################################## #####################



sub check_modules

{

$ mods = `cat / proc / modules`;

if ($ mods = ~ / w1_gpio / && $ mods = ~ / w1_therm /)

{

print "w1 modules already loaded \ n";

}

else

{

print "loading w1 modules \ n";

`sudo modprobe w1-gpio`;

`sudo modprobe w1-therm`;

}

}



sub get_device_IDs

{

# The Hex IDs off all detected

# "W1_master_slaves"



# open file

open (FILE, "/ sys / bus / w1 / devices / w1_bus_master1 / w1_master_slaves") or die ("Unable to open file");



# read file into an array

@deviceIDs =;



# close file

close (FILE);

}



sub read_device

{

#takes one parameter - a device ID

#returns the temperature

#else we return "9999" for undefined



$ readcommand = "cat /sys/bus/w1/devices/"$$_[0001."/w1_slave 2> & 1";

$ readcommand = ~ s / \ R // g;

$ sensor_temp = `$ readcommand`;



if ($ sensor_temp! ~ / No such file or directory /)

{

if ($ sensor_temp! ~ / NO /)

{

$ sensor_temp = ~ / t = (\ d +) / i;

$ temperature = (($ 1/1000));

}

else

{

$ ret = "9999";

}

}

else

{

$ ret = "9999"

}

}


This is the original form of the script, such as I found it on the Internet . The connected sensors in the room showed adequate results, but when I brought one sensor out to the street for permanent residence, I was disappointed that the temperature showed exactly 0 degrees Celsius, whatever I did (and we now have -5 outside. ..-ten).

As it turned out, the whole thing in this line:

$:sensor_temp =~ /t=(\d+)/i;

which involves getting the temperature from the sensor without negative temperatures. Due to the lack of relevant knowledge, I spent half an hour and a couple of cups of coffee to bring the line to the form:

$:sensor_temp =~ /t=(\D*\d+)/i;

which allowed to normally bring in the database and negative temperatures.



Script to create graphs create_graphs.sh
 #!/bin/bash RRDPATH="/home/pi/temperature/" INCOLOUR="#990000" OUTCOLOUR="#009900" TRENDCOLOUR1="#FF0000" TRENDCOLOUR2="#00FF00" #hour rrdtool graph $RRDPATH/mhour_in.png --start -6h --alt-autoscale \ DEF:intemp=$RRDPATH/multirPItemp.rrd:in_temp:AVERAGE \ DEF:outtemp=$RRDPATH/multirPItemp.rrd:out_temp:AVERAGE \ CDEF:intrend=intemp,1200,TREND \ CDEF:outtrend=outtemp,1200,TREND \ LINE2:intemp$INCOLOUR:"Inside" \ LINE1:intrend$TRENDCOLOUR1:"20 min AVG" \ #LINE2:outtemp$OUTCOLOUR:"Outside" \ #LINE1:outtrend$TRENDCOLOUR2:"20 min AVG" #hour outside rrdtool graph $RRDPATH/mhour_out.png --start -6h --alt-autoscale \ DEF:intemp=$RRDPATH/multirPItemp.rrd:in_temp:AVERAGE \ DEF:outtemp=$RRDPATH/multirPItemp.rrd:out_temp:AVERAGE \ CDEF:intrend=intemp,1200,TREND \ CDEF:outtrend=outtemp,1200,TREND \ LINE2:outtemp$OUTCOLOUR:"Outside" \ LINE1:outtrend$TRENDCOLOUR2:"20 min AVG" #day rrdtool graph $RRDPATH/mday.png --start -1d --alt-autoscale \ DEF:intemp=$RRDPATH/multirPItemp.rrd:in_temp:AVERAGE \ DEF:outtemp=$RRDPATH/multirPItemp.rrd:out_temp:AVERAGE \ CDEF:intrend=intemp,1800,TREND \ CDEF:outtrend=outtemp,1800,TREND \ LINE2:intemp$INCOLOUR:"Inside" \ LINE1:intrend$TRENDCOLOUR1:"1h min AVG" \ LINE2:outtemp$OUTCOLOUR:"Outside" \ LINE1:outtrend$TRENDCOLOUR2:"1h min AVG" #week rrdtool graph $RRDPATH/mweek.png --start -1w --alt-autoscale \ DEF:intemp=$RRDPATH/multirPItemp.rrd:in_temp:AVERAGE \ DEF:outtemp=$RRDPATH/multirPItemp.rrd:out_temp:AVERAGE \ LINE2:intemp$INCOLOUR:"Inside temperature" \ LINE2:outtemp$OUTCOLOUR:"Outside temperature" \ #month rrdtool graph $RRDPATH/mmonth.png --start -1m --alt-autoscale \ DEF:intemp=$RRDPATH/multirPItemp.rrd:in_temp:AVERAGE \ DEF:outtemp=$RRDPATH/multirPItemp.rrd:out_temp:AVERAGE \ LINE2:intemp$INCOLOUR:"Inside temperature" \ LINE2:outtemp$OUTCOLOUR:"Outside temperature" \ #year rrdtool graph $RRDPATH/myear.png --start -1y --alt-autoscale \ DEF:intemp=$RRDPATH/multirPItemp.rrd:in_temp:AVERAGE \ DEF:outtemp=$RRDPATH/multirPItemp.rrd:out_temp:AVERAGE \ LINE2:intemp$INCOLOUR:"Inside temperature" \ LINE2:outtemp$OUTCOLOUR:"Outside temperature" \ 


In this script, I posted hourly graphs of temperatures in the apartment and on the street, because the large variation in temperature makes the graphics not very readable. Also I corrected colors and captions for graphs.



After that, I created a script to launch the temperatures from the sensors and generate get.sh graphs

 #!/bin/bash /home/pi/temperature/get_temp.pl /home/pi/temperature/create_graphs.sh 


and added to the crontab -e line to launch it:

 */5 * * * * /home/pi/temperature/get.sh 


allowing you to run the script automatically every 5 minutes.

This is all displayed on a simple web page.



2.1. Connect to narodmon.ru


At the request of the workers, I add information about the connection of this entire farm for sending data to narodmon.ru. Made on materials from here .

So:

1. We make changes to the script for receiving data from the sensors in order to record the current results, each in its own file (added code to the script, see above).

2. Install (if not yet)

sudo apt-get install php5-cgi

3. Create a script to send data from files with readings to the site narodmon.ru

Script to send data to narodmon.ru - send.php
 #!/usr/bin/php-cgi -q <? $file_name="/home/pi/temperature/temp_out"; $file=fopen("$file_name", «r»); $gradus_out=fread($file, filesize($file_name)); echo "$gradus_out\n"; fclose($file); $file_name="/home/pi/temperature/temp_in"; $file=fopen("$file_name", «r»); $gradus_in=fread($file, filesize($file_name)); echo "$gradus_in\n"; fclose($file); $fp = @fsockopen(«tcp://narodmon.ru», 8283, $errno, $errstr); if(!$fp) exit(«ERROR(».$errno."): ".$errstr); fwrite($fp, "#01-23-45-67-89-AF\n#0123456789ABCDEF#$gradus_out\n#0123456789ABCDEF#$gradus_in\n##"); fclose($fp); ?> 


01-23-45-67-89-AF - MAC address of the Malinki network card, 0123456789ABCDEF - serial numbers of temperature sensors.

4. Add a line to crontab to regularly send information to narodmon.ru (there is a limit on the frequency of receiving information on the site - no more than once every 5 minutes, so I sent it every 10 minutes):

 */10 * * * * /home/pi/temperature/send.php 


5. We register on the project narodmon.ru and add the MAC address of Malinki. Now the statistics are kept and they :)



3. Now go to the gland


Rummaging in the bins of the storeroom, I found myself in a two-row connector of the type "mother" and a telephone extension cable. I bit off the connector 2x4 and soldered the 4k7 resistor between leg 1 and leg 7 (on leg 1 we have + 3V, leg 6 - ground, leg 7 - PIN4, which in Malinka allows you to communicate using 1-wire).



The first ds18b20 sensor was soldered into the extension cord, and I soldered the second sensor directly to the telephone cable, wrapped it with black (not blue) tape and through the former hole for the satellite antenna cable I brought it outside the apartment to the street.

In assembled form, taking into account the placement of Raspberry in the shipping case, the following picture was obtained:



As it turned out, using a microtunner is a very handy thing :)

And finally - a picture from the site.



The result on the project narodmon.ru .



Instead of an afterword


If you expected to see the connection of temperature sensors to the kettle - I apologize :) The “kettle” in this article is me. Little by little he understood the question to the best of his strength and knowledge, looking into Google and using the method of trial and error.

I have achieved my goal. I would be grateful to everyone for tips on improvement or the right approach to achieving local goals. Thanks for attention :)



ZY I will not give a link to the page with graphs - “Malinka” will “lie down”;)

Source: https://habr.com/ru/post/163575/



All Articles