Prosty sposób na przetwarzanie formularza wysłanego metodą post z poziomu arduino.
Używa biblioteki UIPEthernet dla kompatybilności z ENC28J60.
#include <UIPEthernet.h>
byte mac[] = { 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED };
IPAddress ip( 19,135,197,202 );
IPAddress gateway( 19,135,197,193 );
IPAddress subnet( 255, 255, 255, 224 );
EthernetServer server(80);
const String code = "1234";
String Post;
void setup()
{
Serial.begin(57600);
pinMode(8, OUTPUT); //relay
Ethernet.begin(mac, ip, dns, gateway, subnet);
delay(2000);
server.begin();
Serial.println("setup finished");
}
void loop()
{
// listen for incoming clients
EthernetClient client = server.available();
if (client) {
boolean currentLineIsBlank = true;
while (client.connected()) {
while (client.available()) {
char c = client.read();
if (c == '\n' && currentLineIsBlank) {
// Obsługa HTTP POST - Pobranie danych
while (client.available())
{
c = client.read();
Post += c;
}
// Analiza HTTP POST
Serial.println(Post);
Serial.println(Post.indexOf(code));
if (Post.indexOf(code) > -1) {
digitalWrite(8, HIGH);
delay(1000);
digitalWrite(8, LOW);
}
// Kasowanie Zmiennej POST i wysłanie danych do klienta
Post="";
client.println("HTTP/1.0 200 OK");
client.println("Content-Type: text/html");
client.println();
client.println("<HTML><BODY>");
client.println("<FORM METHOD=\"post\">");
client.println("Access Code: <INPUT TYPE=\"TEXT\" NAME=\"Code\">");
client.println("<INPUT TYPE=\"SUBMIT\" NAME=\"submit\">");
client.println("</FORM>");
client.stop();
}
else if (c == '\n') {
// you're starting a new line
currentLineIsBlank = true;
}
else if (c != '\r') {
// you've gotten a character on the current line
currentLineIsBlank = false;
}
}
}
Serial.println("Disconnected");
}
}
Dlaczego?
Miałem trochę problemów z obsługą metody POST, praktycznie każdy projekt opiera się na metodzie GET. Dla mojego projektu krytyczne było użycie POST z dwóch powodów:- Walidacja ponownego przesłania danych (komunikat z potwierdzeniem)
- Możliwość wysłania różnych kodów za pomocą pola INPUT
Opis projektu
Projekt ma robić bardzo prostą rzecz, a możliwe że będzie rozbudowany. Mianowicie jego zadaniem jest wciśniecie przycisku reset w serwerze w przypadku braku fizycznego dostępu.
Aby zabezpieczyć przed przypadkowym resetem (lub resetem w trakcie indeksowania przez roboty) dodałem pole input i walidację danych.
Jeżeli wpisany kod zgadza się z kodem zapisanym na sztywno w kontrolerze następuje uruchomienie przekaźnika.
Jak?
Poniżej kod umożliwiający obsługę Formularza HTML wysłanego metodą POST:Używa biblioteki UIPEthernet dla kompatybilności z ENC28J60.
#include <UIPEthernet.h>
byte mac[] = { 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED };
IPAddress ip( 19,135,197,202 );
IPAddress gateway( 19,135,197,193 );
IPAddress subnet( 255, 255, 255, 224 );
EthernetServer server(80);
const String code = "1234";
String Post;
void setup()
{
Serial.begin(57600);
pinMode(8, OUTPUT); //relay
Ethernet.begin(mac, ip, dns, gateway, subnet);
delay(2000);
server.begin();
Serial.println("setup finished");
}
void loop()
{
// listen for incoming clients
EthernetClient client = server.available();
if (client) {
boolean currentLineIsBlank = true;
while (client.connected()) {
while (client.available()) {
char c = client.read();
if (c == '\n' && currentLineIsBlank) {
// Obsługa HTTP POST - Pobranie danych
while (client.available())
{
c = client.read();
Post += c;
}
// Analiza HTTP POST
Serial.println(Post);
Serial.println(Post.indexOf(code));
if (Post.indexOf(code) > -1) {
digitalWrite(8, HIGH);
delay(1000);
digitalWrite(8, LOW);
}
// Kasowanie Zmiennej POST i wysłanie danych do klienta
Post="";
client.println("HTTP/1.0 200 OK");
client.println("Content-Type: text/html");
client.println();
client.println("<HTML><BODY>");
client.println("<FORM METHOD=\"post\">");
client.println("Access Code: <INPUT TYPE=\"TEXT\" NAME=\"Code\">");
client.println("<INPUT TYPE=\"SUBMIT\" NAME=\"submit\">");
client.println("</FORM>");
client.stop();
}
else if (c == '\n') {
// you're starting a new line
currentLineIsBlank = true;
}
else if (c != '\r') {
// you've gotten a character on the current line
currentLineIsBlank = false;
}
}
}
Serial.println("Disconnected");
}
}
Problemy
Podczas testów pojawił się problem z zawieszaniem się arduino, prawdopodobnie jest to problem z portem ethernet. Zostało to rozwiązane przez zastosowanie watchdoga.
Ten komentarz został usunięty przez autora.
OdpowiedzUsuń