Я работаю над регистратором доступа RFID на основе Arduino, но у меня возникают некоторые проблемы при чтении ответов сервера.
Моя установка следующая:
-Arduino Mega, подключенный к кард-ридеру MFRC522 и сетевому модулю ENC28J60 (контакты SS и RST на MFRC522 изменены, чтобы избежать конфликтов внутри шины SPI).
-Локальный хост-сервер (на порту 100), который содержит базу данных MySQL и необходимые файлы php.
В настоящее время карты читаются правильно, и Arduino успешно обновляет переменные в базе данных, однако я не могу получить эхо из файла php для отображения через последовательный монитор. Чтобы проверить, все ли в порядке со стороны сервера, я создал небольшую HTML-форму, и, если я отправлю ее, я получу необходимое эхо, отображаемое в моем браузере.
Я печатаю значение, которое возвращает client.available (), и всегда получаю false, хотя client.connected () возвращает true. Сравнивая мой код с другими, найденными в сети, особой разницы нет. На данный момент я не знаю, что попробовать, я надеюсь, вы могли бы помочь мне с этим!
Я прилагаю коды ниже:
Arduino:
#include <SPI.h>
#include <MFRC522.h>
#include <UIPEthernet.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
//----RFID----/
MFRC522 rfid(8, 9); //(SS pin, RST pin)
byte nuidPICC[4];
//----ETHERNET----/
#define DEBUG
EthernetClient client;
char server[] = "192.168.xxx.xxx"; //<-Localhost
byte mac[] = { 0x54, 0x34, 0x41, 0x30, 0x30, 0x40 };
//----LCD----/
LiquidCrystal_I2C lcd(0x3F, 16, 2);
//----VARIABLES----/
int userid=0;
void setup() {
Serial.begin(9600);
SPI.begin(); // Init SPI bus
lcd.begin();
pinMode(2,OUTPUT);
//----RFID----/
rfid.PCD_Init(); // Init MFRC522
//----ETHERNET----/
Ethernet.begin(mac);
#ifdef DEBUG
Serial.println("-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-\n");
Serial.print("IP Address : ");
Serial.println(Ethernet.localIP());
Serial.print("Subnet Mask : ");
Serial.println(Ethernet.subnetMask());
Serial.print("Default Gateway IP: ");
Serial.println(Ethernet.gatewayIP());
Serial.print("DNS Server IP : ");
Serial.println(Ethernet.dnsServerIP());
lcd.print("IP Address");
lcd.setCursor(0,1);
lcd.print(Ethernet.localIP());
delay(2000);
lcd.clear();
lcd.noBacklight();
#endif
}
void sender(){
/*lcd.clear();
lcd.backlight();
lcd.setCursor(0,0);
lcd.print("identifying");
tone(2,900,400);*/
if(client.connect(server, 100)){
Serial.println("Conected");
}
//String query = "GET /uploader.php?userid=";
//query=query+String(userid);
//Serial.println(query);
//client.print(query);
client.print( "GET /uploader.php?userid=");
client.print(12345);
client.println(" HTTP/1.1");
client.print("HOST: ");
client.println(server);
client.println();
client.println();
Serial.println("Data sent");
delay(1000);
Serial.println(client.connected());
Serial.println(client.available());
if(client.available())
{
Serial.println("ARDUINO: HTTP message received");
Serial.println("ARDUINO: printing received headers and script response...\n");
while(client.available())
{
char c = client.read();
Serial.print(c);
}
//Code to display info through the serial monitor and the LCD
}
else
{
Serial.println("ARDUINO: no response received / no response received in time");
}
client.stop();
}
void reader(){
userid=0;
// Look for new cards
if ( ! rfid.PICC_IsNewCardPresent())
return;
// Verify if the NUID has been readed
if ( ! rfid.PICC_ReadCardSerial())
return;
// Store NUID into nuidPICC array
for (byte i = 0; i < 4; i++) {
nuidPICC[i] = rfid.uid.uidByte[i];
userid=userid+nuidPICC[i];
}
rfid.PICC_HaltA();
rfid.PCD_StopCrypto1();
sender();
}
void loop(){
reader();
}
Uploader.php
<?php
$conexion = mysql_connect("localhost", "user", "pass");
mysql_select_db("db_name", $conexion);
mysql_query("SET NAMES 'utf8'");
$userid = $_GET ['userid'];
$sql1 = "SELECT nombre, ultima_entrada, ultimo_pago, dentro FROM usuarios WHERE id = '$userid'";
$retval = mysql_query( $sql1, $conexion );
if(! $retval ) {
die('Could not get data: ' . mysql_error());
echo "return error";
}
$row = mysql_fetch_array($retval, MYSQL_ASSOC);
$month = date('n',strtotime($row['ultimo_pago']));
$date = date('n');
if($month < $date){
echo "El usuario:{$row['nombre']} es moroso <br> ";
}else{
if($row['dentro']==0){
echo "Usuario:{$row['nombre']} accediendo al lab <br>";
$sql2 = "UPDATE usuarios SET dentro='1', ultima_entrada = CURRENT_TIMESTAMP WHERE id = '$userid'";
mysql_query($sql2);
}elseif($row['dentro']==1){
echo "Usuario:{$row['nombre']} saliendo del lab <br>";
$sql3 = "UPDATE usuarios SET dentro='0', ultima_salida = CURRENT_TIMESTAMP WHERE id = '$userid'";
mysql_query($sql3);
}
}
mysql_close();
?>
Таблица SQL
CREATE TABLE `usuarios` (
`id` varchar(11) NOT NULL,
`nombre` tinytext NOT NULL,
`admin` tinyint(1) NOT NULL DEFAULT '0',
`ultima_entrada` timestamp NULL DEFAULT NULL,
`ultima_salida` timestamp NULL DEFAULT NULL,
`tiempo_total` time DEFAULT NULL,
`ultimo_pago` date DEFAULT NULL,
`dentro` tinyint(1) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`),
UNIQUE KEY `id` (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
INSERT INTO `usuarios` (`id`, `nombre`, `admin`, `ultima_entrada`, `ultima_salida`, `tiempo_total`, `ultimo_pago`, `dentro`) VALUES
('12345', 'John', 0, '2018-03-06 16:41:44', '2018-03-06 16:41:36', '00:00:00', '2018-03-01', 1);
ПРИМЕЧАНИЕ: я использую фиктивный идентификатор пользователя, в будущем это изменится, теперь я хочу только получить ответ от сервера.
Заранее спасибо!
Дурак я! Я нашел решение моей проблемы в разделе комментариев этого блога (от автора самой библиотеки UIPEthernet!):
https://www.tweaking4all.com/hardware/arduino/arduino-ethernet-data-push/#comment-21572
Если вы читаете комментарий, Норберт говорит, что следует избегать задержек, и я ошибался. В моем коде у меня прекрасная задержка в 1 секунду после запроса GET. Удаление это решило проблему. Я основал свой код на этом: http://www.smartsustainability.org/CIS508/?page_id=2203 но он сделан для разных экранов WIFI / Ethernet, а не для ENC28J60, вот откуда возникла проблема. (Не говоря, что это плохой код, хотя).
В заключение, решение было заменить эту строку:
delay(1000);
с этим циклом, который ждет, пока клиент не станет доступен:
while(!client.available()){}
Надеюсь, это поможет избежать головной боли в будущем!
Других решений пока нет …