Zapewne widzieliście już poradnik Jakuba Furmana o własnym internetowym termometrze. Do jego wykonania potrzebowaliśmy jednak mieć nieco wiedzy o bazach danych, cron tabie i tym podobnych. Dla przeciętnego człowieka – nie geeka, było to dość ciężkie do zrozumienia i zastosowania. Na szczęście można to zrobić to łatwiej za pomocą strony Xively.com (dawny Pachube). Umożliwia ona wstawianie pewnych wartości, a następnie za pomocą żądania HTTP odczytanie ich.
Zastosowanie Xively ma pewne zalety np.:
– odczyty będzie można zobaczyć z każdego miejsca, nie dotyczy nas wtedy ograniczenie przez niepubliczny adres IP i zakładanie serwera w sieci lokalnej,
– umożliwia automatyczne tworzenie prawie dowolnie konfigurowalnych wykresów,
– jest bardzo prosty w obsłudze.
Koniec opowiadania, zabierzmy się do pracy.
Potrzebne elementy:
– Arduino,
– Ethernet Shield,
– cyfrowy czujnik temperatury, w tym przypadku DS18B20,
– rezystor 4,7 KΩ
– płytka stykowa + kabelki.
Schemat podłączenia, choć prosty, dla formalności podaje obrazek z Fritzinga. Należy pamiętać, że rezystor umieszczony poniżej powinien mieć wartość 4,7 KΩ.
Powinniśmy także założyć konto na stronie Xively.com i stworzyć projekt:
Po założeniu należy znaleźć odpowiednie numery, kody i nazwy:
Teraz możemy przejść do pisania programu. Jako podstawę użyłem ćwiczenie z podstawowej biblioteki Ethernet Shield – Pachube Client.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 |
#include <SPI.h> #include <Ethernet.h> #include <OneWire.h> #include <OneWire.h> #include <DallasTemperature.h> #define ONE_WIRE_BUS 3 OneWire oneWire(ONE_WIRE_BUS); DallasTemperature sensors(&oneWire); #define APIKEY "API_KEY" //wpisz tutaj swój API Key #define FEEDID FEED_ID // wpisz tutaj swój feed ID #define USERAGENT "TYTUŁ" // wpisz tutaj nazwę projektu byte mac[] = { 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED}; IPAddress ip(10,10,10,100); // zastąp ten numer IP ze swojego zakresu sieci, będzie on używany, gdy Ethernet Shield nie będzie mógł uzyskać IP od routera za pomocą DHCP EthernetClient client; IPAddress server(216,52,233,122); // to zostaw //char server[] = "api.pachube.com"; unsigned long lastConnectionTime = 0; boolean lastConnected = false; const unsigned long postingInterval = 10*1000; //tutaj możesz zmienić częstotliwość wysyłania danych do Xively void setup() { Serial.begin(9600); if (Ethernet.begin(mac) == 0) { Serial.println("Failed to configure Ethernet using DHCP"); // DHCP failed, so use a fixed IP address: Ethernet.begin(mac, ip); } } void loop() { if (client.available()) { char c = client.read(); Serial.print(c); } if (!client.connected() && lastConnected) { Serial.println(); Serial.println("disconnecting."); client.stop(); } if(!client.connected() && (millis() - lastConnectionTime > postingInterval)) { sensors.requestTemperatures(); //odczyt temperatury float sensorReading = sensors.getTempCByIndex(0); //zapis temperatury do zmiennej sendData(sensorReading); //"wysłanie" odczytu } lastConnected = client.connected(); } void sendData(float thisData) { // if there's a successful connection: if (client.connect(server, 80)) { Serial.println("connecting..."); // send the HTTP PUT request: client.print("PUT /v2/feeds/"); client.print(FEEDID); client.println(".csv HTTP/1.1"); client.println("Host: api.pachube.com"); client.print("X-PachubeApiKey: "); client.println(APIKEY); client.print("User-Agent: "); client.println(USERAGENT); client.print("Content-Length: "); int thisLength = 8 + getLength(thisData); client.println(thisLength); client.println("Content-Type: text/csv"); client.println("Connection: close"); client.println(); client.print("Temp,"); //w tym miejscu możesz zmienic nazwę wysyłanych wartości client.println(thisData); } else { Serial.println("connection failed"); Serial.println(); Serial.println("disconnecting."); client.stop(); } lastConnectionTime = millis(); } int getLength(int someValue) { int digits = 1; int dividend = someValue /10; while (dividend > 0) { dividend = dividend /10; digits++; } return digits; } |
Jako, że niestety przy tej bibliotece i czujniku pierwszy odczyt jest zazwyczaj niepoprawny, w moim przypadku to 85 st. C lub -127 st.C, w tym miejscu:
1 2 3 4 5 6 7 8 9 |
if(!client.connected() && (millis() - lastConnectionTime > postingInterval)) { sensors.requestTemperatures(); //odczyt temperatury float sensorReading = sensors.getTempCByIndex(0); //zapis temperatury do zmiennej sendData(sensorReading); //"wysłanie" odczytu } |
możemy dodać kolejny warunek i w przypadku odczytu np. wartości wyższej niż 35 st. C żądać ponownego odczytania temperatury.
Po uzupełnieniu wedle uznania kodu, możemy wgrać go na Arduino, a jeżeli wszystko poprawnie podłączyłeś i wpisałeś, powinna się pojawić taka odpowiedź w monitorze portu COM:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
connecting... HTTP/1.1 200 OK Date: Sat, 01 Feb 2014 08:06:28 GMT Content-Type: text/plain; charset=utf-8 Content-Length: 0 Connection: close X-Request-Id: cfeb5cdf64f424f8de8bac701e9a303a8a6ffa2a Cache-Control: max-age=0 Vary: Accept-Encoding disconnecting. |
Możemy teraz na stronie projektu podglądać temperaturę. Ale co jeżeli chcemy ją wyświetlić na własnej stronie? Z pomocą przychodzi nam PHP i żądanie HTTP metodą GET. Przedstawię tu jak przedstawić odebrane wartości.
Najpierw szukamy na stronie projektu czegoś takiego jak API Endpoint i kopiujemy go.
Następnie tworzymy plik *.php. Uwaga: Aby móc wyświetlić stronę php, nie wystarcza zwykła przeglądarka jak w przypadku html, ale serwer. Można zrobić sobie domowy w programie Xammp lub wykupić jakiś tani hosting.
Do pliku wpisujemy to:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
<html> <head> <meta http-equiv="Refresh" content="10" /> </head> <title> Arduino Termometr </title> <body> <?php $json = file_get_contents('https://login:haslo@EndPoint.json'); //echo $json; //jeżeli chcesz zaobaczyc wynik usun // echo 'Wynik zapytania<br><br><br>'; $obj = json_decode($json); print $obj->{'title'}; echo '<br>'; echo 'Temperatura: '; print $obj->datastreams[0]->{'current_value'}; echo ' C<br>'; echo 'Zaktualizowane: '; print $obj->datastreams[0]->{'at'}; echo '<br>'; ?> </body> </html> |
Jak widać w tym przypadku żądanie wykonałem za pomocą file_get_contents, a odkodowanie za pomocą json_decode, oczywiście metod jest mnóstwo, ja przedstawiłem jedną z łatwiejszych.
Dodatkowo, jak na wstępie wspomniałem, Xively daje nam do dyspozycji generowanie wykresów jak to zrobić? Z pomocą przychodzi tutaj strona z dokumentacji: https://xively.com/dev/docs/api/data/read/single_datastream/.
Wykres zwyczajnie wklejamy za pomocą <img src=”url”>.
Efekt można zobaczyć na mojej stronie: serwer.xaa.pl/temp.php graf jest nieco dziwny, gdyż dawno akurat w tym projekcie nie wysyłałem danych.
Dziękuję za uwagę i mam nadzieję, że dzięki temu poradnikowi uda Wam się stworzyć własny, internetowy termometr. W razie pytań proszę pisać je w komentarzach, postaram się odpowiedzieć na każde z nich.
Dobry projekt. Do wizualizacji danych wystarczy przeglądarka. Dane pobrać AJAXem i sformatować w JavaScript. Wykresy rysować w Canvas HTML5.
Ew. dało by się chyba wykorzystać Highcharts.
Do wizualizacji. A ja swoim komentarzem chciałem zwrócić uwagę na to że nie trzeba stawiać serwera aby móc pobierać, parsować i wizualizować dane :).
żaden link w artykule nie jest linkiem :( …a przy okazji możnaby podlinkować jeszcze artykuł wspomnianego Jakuba
Nie ma linków, gdyż są one blokowane dla “nowych” użytkowników. Tutaj masz ten poradnik: https://majsterkowo.pl/wlasny-internetowy-termometr/
Czy koniecznie musi być rezystor 4.7KΩ? Gdzieś czytałem, że może być w przedziale od 4.7-10KΩ, i sam mam do DS18B20 podpięte 10KΩ i działa dobrze.
Ja zrobiłem taki projekt z użyciem Node na Linuxie i po stronie serwera. Napisałem taki prosty analizator z użyciem biblioteki SerialPort
[code]
var serialport = require(“serialport”);
var SerialPort = serialport.SerialPort;
http = require(“http”);
var port = new SerialPort(“/dev/ttyUSB0”, {
baudrate: 9600,
parser : serialport.parsers.readline (“n”)
});
port.on (“data”, function (d) {var odpowiedz = “Odpowiedz z serwera z res.send: “;
http.get(“http://*.pl/?temperatura=”+d, function(res){
console.log (“n Temperatura odczytana z Arduino: “+d);
console.log(“Kod odpowiedzi serwera: “+res.statusCode);
res.on (“data”, function(kawalek){odpowiedz += kawalek;});
res.on (“end”, function(){console.log(odpowiedz);});
});
});
[/code]
Ścieżka będąca pierwszym elementem konstruktora zostaje wcześniej odczytana z komunikatu bufora warstwy jądra z polecenia dmesg.
Po stronie serwera użyłem Nodowego Expressa i napisałem taką trasę:
[code]
app.get(‘/’, function(req, res) {
if (req.url == “/” && t===undefined) {
res.render (“brakdanych”);
}
else if (req.url == “/” && (t || t==0)) {
res.render(“termometr”,{temperatura : t});
}
else {
t = req.query.temperatura;
res.send (“Hej klient-parser, to ja serwer, wysylam ci odpowiedz: “+t);
}
});
[/code]
(to jest kluczowa część skryptu)
Jak widać w trasie wykorzystywane są dwa pliki Jade , brakdanych oraz termometr.
Termometr w Jade wygląda następująco:
[code]
doctype html
html
head
title Wizualizacja
script(src=”javascripts/termometrCanvas.js”)
link(rel=”stylesheet”, href=”stylesheets/styl.css”)
body
canvas#plotno
p#nie #{temperatura}
[/code]
i po wyrenderowaniu strony uruchamia napisany przezemnie z użyciem Canvas API kod w JavaScripcie wizualizujący dane w postaci termometru.
Paragrafu p o identyfikatorze #nie(wyswietlaj) uzyłem do przekaźnika temperatury t z server.js do pliku w JavaScripcie, nie miałem lepszej koncepcji jak to zrobić.
Przepraszam jeśli coś się tu źle sformatowało, wiadomo, że Jade wymaga bardzo rygorystycznego podejścia do formatowania.
Polecam Kolegom Majsterkowiczom spróbować Node i Arduino, miłego dnia.
U mnie jest chyba coś nie halo z tym odwołaniem w pliku PHP do strony Xively.
Na stronie na moim serwerze wyskakuje warning o nieautoryzowanym dostępie.
Czy ten API Endpoint to ma być wklejony w linii 11 ?
Jak przesłać tam login i hasło?
Czy jest możliwe takie przerobienie kodu aby obsługiwał (wysyłał dane) z paru czujników DS18b20?
Możliwe, kwestia lekkiego zmodyfikowania kodu. We wszystkie pola jak API_KEY, FEED ID, login, password należy wpisać własne dane
Witam czy zna ktoś jakiś dobry tutorial o wysyłaniu tego typu zapytań/poleceń przez arduino. Zaprezentowanu tu kod odpalił się bez najmniejszych problemów na module enc28j60, natomiast próbuję zrobić coś podobnego, ale dla serwera domoticz i nie chce działać. Korzystam, z przykładu dla ethernet shielda, i działa, natomiast po wpisaniu wartości dla domoticz’a mam błąd 400 i koniec.
The unnecessary files stored on pc occupy an oversized amount of your disk space and thereby slows down your computer system. You must delete such files using a third-party disk cleaner software package program.
computer startup manager http://seecofneeq.com/wp-content/PC-Cleaner/
Strona świadczy o nuetypowych wydarzeniach, namawiam ddo dysusji Plac zabaw producent