Apertura porta con rfid e da remoto

Buongiorno a tutti, è un po di tempo che non entro sul forum, ho bei ricordi legati a questo forum. Sono tornato perché ho bisogno di un aiuto. Ho la necessita di aprire una porta dotata di elettroserratura, sia tramite un rfid sia da remoto tramite internet. Sono riuscito a fare lo sketch per fare aprire la porta con rfid e adesso vorrei integra la possibilità di farlo anche da remoto. chi mi aiuta? posto lo script funzionante per quanto riguarda l'apertura con rfid. grazie

#include <SPI.h>
#include <RFID.h>
/* Vengono definiti PIN del RFID reader*/
#define SDA_DIO 4  // Pin 53 per Arduino Mega
#define RESET_DIO 5
#define delayRead 1000 // Tempo 
#define delayLed 2000 
#define ledVerde 3
#define ledRosso 4
#define rele 0
/* Viene creata una istanza della RFID libreria */
RFID RC522(SDA_DIO, RESET_DIO); 
  // inserire tutti i codici esadecimali delle schede magnetiche riconosciute 
String codiceAutorizzato1 = "CHIAVEVALIDA1";
String codiceAutorizzato2 = "CHIAVEVALIDA2";
String codiceAutorizzato3 = "CHIAVEVALIDA3";
 
void setup()
{ 
  Serial.begin(9600);
  /* Abilita SPI*/
  SPI.begin(); 
  /* Viene inizilizzato RFID reader */
  RC522.init();
  Serial.println("Setup");
  pinMode(ledVerde,OUTPUT);
  pinMode(ledRosso,OUTPUT);
  pinMode(rele,OUTPUT);
}
  
void loop()
{
  /* Temporary loop counter */
  byte i;
  // Se viene letta una tessera
  if (RC522.isCard())
  {
    // Viene letto il suo codice 
    RC522.readCardSerial();
    String codiceLetto ="";
    Serial.println("Codice delle tessera letto:");
  
    // Viene caricato il codice della tessera, all'interno di una Stringa
    for(i = 0; i <= 4; i++)
    {
      codiceLetto+= String (RC522.serNum[i],HEX);
      codiceLetto.toUpperCase();
    }
    Serial.println(codiceLetto);
    if(verificaCodice(codiceLetto,codiceAutorizzato1)||verificaCodice(codiceLetto,codiceAutorizzato2)
    ||verificaCodice(codiceLetto,codiceAutorizzato3)){
      Serial.println("Tessera autorizzata");
      accendiLed(ledVerde);
      digitalWrite (rele, HIGH);
      delay (1000);     // Tempo relè in stato ON
      digitalWrite (rele, LOW);
    }else{
      Serial.println("Tessera non autorizzata");
      accendiLed(ledRosso);
    }
  delay(delayRead);  
  }
}
// Questa funzione verifica se il codice Letto è autorizzato
boolean verificaCodice(String codiceLetto, String codiceAutorizzato){
  if(codiceLetto.equals(codiceAutorizzato)){
    return true;
  }else{
    return false;
  }  
}    
// Questa funzione permette di accendere un LED per un determinato periodo
void accendiLed(int ledPin){
  digitalWrite(ledPin,HIGH);
  delay(delayLed);
  digitalWrite(ledPin,LOW);
}

Di internet e del suo utilizzo non è capisco una mazza ma ti do qualche consiglio e guardo al tuo codice attuale.
vedo che fai uso di molte String. Per evitare possibili problemi di memoria, specialmente su lungo utilizzo, o dopo aver aggiunto nuove parti al codice, ti consiglio di sostituirle completamente con stringhe di C, alias array di char. Questo richiede la modifica di molte parti del codice Ma ti garantisce di non avere problemi di memoria in futuro perché le stringhe di ci non si espandono mentre le usi, a differenza di quelle che stai utilizzando.

Inoltre la richiesta di poter aprire la porta da internet mi sembra eccessivamente generica. Sai già cosa vuoi utilizzare, vuoi una applicazione già fatta, come telegram o altri sistemi di messaggi, o vuoi farlo con applicazione tua.
sei totalmente neofita dell'uso di internet o sai utilizzare qualcosa? E se sì cosa?

mi potresti consigliare come migliorare il codice? non ho esperienza in questo

Comincia a andare sul Reference a cercare Cosa sono gli Array e le stringhe. Guardati qualche programma di esempio su come si utilizzano, credo che se cerchi sul Santo ne trovi tanti, e fai un po' di pratica, che non è mai tempo sprecato

tototer:
Buongiorno a tutti, è un po di tempo che non entro sul forum, ho bei ricordi legati a questo forum. Sono tornato perché ho bisogno di un aiuto. Ho la necessita di aprire una porta dotata di elettroserratura, sia tramite un rfid sia da remoto tramite internet. Sono riuscito a fare lo sketch per fare aprire la porta con rfid e adesso vorrei integra la possibilità di farlo anche da remoto. chi mi aiuta? posto lo script funzionante per quanto riguarda l'apertura con rfid. grazie

delay(delayLed);

digitalWrite(ledPin,LOW);
}

e beh... qui ti devi "spiegare" meglio..... :confused: via internet vuol dire "molte cose"
vuoi aprirla tramite un browser web qualsiasi da qualsiasi computer ?
vuoi aprirla tramite il tuo cellulare personale con un semplice tap sul display?
aprire una porta tramite internet o peggio tramite sempliceradiocomando mi pare un errore in partenza,
forse meglio prevedere degli "if meccanici" tipo un rilevatore di presenza/movimento o meglio un pulsante da premere comunque,
spero di far comprendere.....

Buongiorno a tutti ho appena scritto questo sketch unendone 2 che separatamente funzionano. Ho integrato allo sketch precedente il controllo di un relay tramite url da browser. Caricando tale sketch, il controllo del relay tramite url del browser avviene in modo corretto nel seguente modo:

URL http://ip//gpio/0 spento
URL http://ip//gpio/1 acceso

ma la restante parte di controllo relay tramite rfid non funziona più anche se inserito nel codice.
credo ci sia un problema nel loop. qualcuno mi aiuta? sono un pò arrugginito. a me serve fare funzionare entrambe le cose insieme. grazie a tutti

#include <ESP8266WiFi.h>

const char* ssid = "TP-LINK";
const char* password = "pass";

WiFiServer server(80);

#include <SPI.h>
#include <RFID.h>
/* Vengono definiti PIN del RFID reader*/
#define SDA_DIO 4  // Pin 53 per Arduino Mega
#define RESET_DIO 5
#define delayRead 1000 // Tempo 
#define delayLed 2000 
#define ledVerde 3
#define ledRosso 4
#define rele 0
/* Viene creata una istanza della RFID libreria */
RFID RC522(SDA_DIO, RESET_DIO); 
  // inserire tutti i codici esadecimali delle schede magnetiche riconosciute 
String codiceAutorizzato1 = "30774CD3D8";
String codiceAutorizzato2 = "ESEMPIO479";
String codiceAutorizzato3 = "ESEMPIO480";
 
void setup()
{ 
  Serial.begin(9600);
  /* Abilita SPI*/
  SPI.begin(); 
  /* Viene inizilizzato RFID reader */
  RC522.init();
  Serial.println("Setup");
  pinMode(ledVerde,OUTPUT);
  pinMode(ledRosso,OUTPUT);
  pinMode(rele,OUTPUT);

  // Connect to WiFi network
  Serial.println();
  Serial.println();
  Serial.print("Connecting to ");
  Serial.println(ssid);

  WiFi.mode(WIFI_STA);
  WiFi.begin(ssid, password);

  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.println("WiFi connected");

  // Start the server
  server.begin();
  Serial.println("Server started");

  // Print the IP address
  Serial.println(WiFi.localIP());
}
  
void loop() {

  // Check if a client has connected
  WiFiClient client = server.available();
  if (!client) {
    return;
  }

  // Wait until the client sends some data
  Serial.println("new client");
  while (!client.available()) {
    delay(1);
  }

  // Read the first line of the request
  String req = client.readStringUntil('\r');
  Serial.println(req);
  client.flush();

  // Match the request
  int val;
  if (req.indexOf("/gpio/0") != -1) {
    val = 0;
  } else if (req.indexOf("/gpio/1") != -1) {
    val = 1;
  } else {
    Serial.println("invalid request");
    client.stop();
    return;
  }

  // Set GPIO2 according to the request
  digitalWrite(rele, val);

  client.flush();

  // Prepare the response
  String s = "HTTP/1.1 200 OK\r\nContent-Type: text/html\r\n\r\n<!DOCTYPE HTML>\r\n<html>\r\nGPIO is now ";
  s += (val) ? "high" : "low";
  s += "</html>\n";

  // Send the response to the client
  client.print(s);
  delay(1);
  Serial.println("Client disonnected");

  
  /* Temporary loop counter */
  byte i;
  // Se viene letta una tessera
  if (RC522.isCard())
  {
    // Viene letto il suo codice 
    RC522.readCardSerial();
    String codiceLetto ="";
    Serial.println("Codice delle tessera letto:");
  
    // Viene caricato il codice della tessera, all'interno di una Stringa
    for(i = 0; i <= 4; i++)
    {
      codiceLetto+= String (RC522.serNum[i],HEX);
      codiceLetto.toUpperCase();
    }
    Serial.println(codiceLetto);
    if(verificaCodice(codiceLetto,codiceAutorizzato1)||verificaCodice(codiceLetto,codiceAutorizzato2)
    ||verificaCodice(codiceLetto,codiceAutorizzato3)){
      Serial.println("Tessera autorizzata");
      accendiLed(ledVerde);
      digitalWrite (rele, HIGH);
      delay (1000);     // Tempo relè in stato ON
      digitalWrite (rele, LOW);
    }else{
      Serial.println("Tessera non autorizzata");
      accendiLed(ledRosso);
    }
  delay(delayRead);  
  }
}
// Questa funzione verifica se il codice Letto è autorizzato
boolean verificaCodice(String codiceLetto, String codiceAutorizzato){
  if(codiceLetto.equals(codiceAutorizzato)){
    return true;
  }else{
    return false;
  }  
}    
// Questa funzione permette di accendere un LED per un determinato periodo
void accendiLed(int ledPin){
  digitalWrite(ledPin,HIGH);
  delay(delayLed);
  digitalWrite(ledPin,LOW);
}

ci hai pensato a...... :o :confused: a come hai configurato il "tutto" e per tutto intendo
il router in caso di riavvio assegnerà sempre lo stesso ip all'arduino?
e fuori dalla tua rete locale funzionerà sempre e comunque? se non hai un ip statico pubblico,

si ho già chiarito tutti questi aspetti. vorrei solo capire come far funzionare entrambi i programmi

#include <ESP8266WiFi.h>

const char* ssid = "tplink";
const char* password = "pass";

#include <SPI.h>
#include <RFID.h>
/* Vengono definiti PIN del RFID reader*/
#define SDA_DIO 4  // Pin 53 per Arduino Mega
#define RESET_DIO 5
#define delayRead 1000 // Tempo 
#define delayLed 2000 
#define ledVerde 3
#define ledRosso 4
#define rele 0
/* Viene creata una istanza della RFID libreria */
RFID RC522(SDA_DIO, RESET_DIO); 
  // inserire tutti i codici esadecimali delle schede magnetiche riconosciute 
String codiceAutorizzato1 = "1234567890";
String codiceAutorizzato2 = "ESEMPIO479";
String codiceAutorizzato3 = "ESEMPIO480";

WiFiServer server(80);
 
void setup()
{ 
  Serial.begin(9600);
  /* Abilita SPI*/
  SPI.begin(); 
  /* Viene inizilizzato RFID reader */
  RC522.init();
  Serial.println("Setup");
  pinMode(ledVerde,OUTPUT);
  pinMode(ledRosso,OUTPUT);
  pinMode(rele,OUTPUT);

  // Connect to WiFi network
  Serial.println();
  Serial.println();
  Serial.print("Connecting to ");
  Serial.println(ssid);

  WiFi.mode(WIFI_STA);
  WiFi.begin(ssid, password);

  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.println("WiFi connected");

  // Start the server
  server.begin();
  Serial.println("Server started");

  // Print the IP address
  Serial.println(WiFi.localIP());
  
}
  
void loop(){ 


  
  /* Temporary loop counter */
  byte i;
  // Se viene letta una tessera
  if (RC522.isCard())
  {
    // Viene letto il suo codice 
    RC522.readCardSerial();
    String codiceLetto ="";
   
    Serial.println("Codice delle tessera letto:");
 
    // Viene caricato il codice della tessera, all'interno di una Stringa
    for(i = 0; i <= 4; i++)
    {
      codiceLetto+= String (RC522.serNum[i],HEX);
      codiceLetto.toUpperCase();
    }
    Serial.println(codiceLetto);
    if(verificaCodice(codiceLetto,codiceAutorizzato1)||verificaCodice(codiceLetto,codiceAutorizzato2)
    ||verificaCodice(codiceLetto,codiceAutorizzato3)){
      Serial.println("Tessera autorizzata");
      accendiLed(ledVerde);
      digitalWrite (rele, HIGH);
      delay (1000);     // Tempo relè in stato ON
      digitalWrite (rele, LOW);
    }else{
      Serial.println("Tessera non autorizzata");
      accendiLed(ledRosso);
    }
  delay(delayRead);  
  }
}
// Questa funzione verifica se il codice Letto è autorizzato
boolean verificaCodice(String codiceLetto, String codiceAutorizzato){
  if(codiceLetto.equals(codiceAutorizzato)){
    return true;
  }else{
    return false;
  }  
}    
// Questa funzione permette di accendere un LED per un determinato periodo
void accendiLed(int ledPin){
  digitalWrite(ledPin,HIGH);
  delay(delayLed);
  digitalWrite(ledPin,LOW);
}

con questa prima parte di codice si avvia il web server e mi permette di leggere una chiave rfid, se la chiavetta è inserita tra quelle abilitate, attiva il relay per 1 secondo.

ora vorrei aggiungere sul void loop anche questa parte

WiFiClient client = server.available();
if (!client) {
    return;
  }

  // Wait until the client sends some data
  Serial.println("new client");
  while (!client.available()) {
    delay(1);
  }

  // Read the first line of the request
  String req = client.readStringUntil('\r');
  Serial.println(req);
  client.flush();

  // Match the request
  int val;
 if (req.indexOf("/gpio/0") != -1) {
    val = 0;
  } else if (req.indexOf("/gpio/1") != -1) {
    val = 1;
  } else {
    Serial.println("invalid request");
    client.stop();
    return;
  }

   // Set GPIO2 according to the request
  digitalWrite(rele, val);

  client.flush();

che permette di attivare il relay tramite url.
il problema sta che se metto tutto insieme nel void loop funziona una sola funzione.

come risolvo? grazie

E perché

if (!client)
{return;}

?
Così facendo fino a che non ricevu dati da client il loop sucessivo non viene eseguito. E se dopo ci mettessi la parte RFID non la farebbe mai.
O peggio, perché la

while (!client.available())
{delay (1);}

Fino a che non si trasmette qualcosa...aspetta li.
Non sarebbe possibile, che so, toglierli o sostituirli con una logica a if senza return?

tu cosa mi consigli di fare Silente? io non sono più ferrato. vorrei solo fare funzionare tutto al meglio. se hai qualche idee per come integrare le 2 parti tra di loro mi dici? cosi faccio una prova

La mia idea é questa:
Innanzitutto eliminare semplicemente cancellando le parti segnalate
Inoltre penso si dovrebbe inserire l'intero testo presente dopo la fine della seconda parte segnalata all'interno delle graffe di una if(client && client.available()).
Chiedo a te abbastanza chiaro? E agli altri abbastanza corretto?

Il suggerimento di Silente mi sembra corretto...
Il secondo programma, considerato da solo, ha senso attendere che ci siano dati sul client! Deve fare solo quello e quindi se si mette in attesa non è un problema.
Nel tuo caso col suggerimento di Silente, se non ci sono dati esegue il restante codice :slight_smile:

Buonasera Ragazzi, non capisco cosa intendete potete mandarmi il codice con le modifiche da voi pensate?

Nel codice che hai postato esegui le seguenti azioni:

  1. identifica l'ultima riga del codice
  2. scrivi '}'
  3. identifica il seguente pezzo
while (!client.available())
{delay (1);}
  1. seleziona dal punto finale del pezzo identificato fino all'inizio del codice
  2. cancella la parte selezionata
  3. vai sopra la riga "//read the first line of the request"
  4. scrivi "if (client.available()){"

Più chiaro?

#include <ESP8266WiFi.h>

const char* ssid = "TP-LINK";
const char* password = "pass";

WiFiServer server(80);

#include <SPI.h>
#include <RFID.h>
/* Vengono definiti PIN del RFID reader*/
#define SDA_DIO 4  // Pin 53 per Arduino Mega
#define RESET_DIO 5
#define delayRead 1000 // Tempo 
#define delayLed 2000 
#define ledVerde 3
#define ledRosso 4
#define rele 0
/* Viene creata una istanza della RFID libreria */
RFID RC522(SDA_DIO, RESET_DIO); 
  // inserire tutti i codici esadecimali delle schede magnetiche riconosciute 
String codiceAutorizzato1 = "30774CD3D8";
String codiceAutorizzato2 = "ESEMPIO479";
String codiceAutorizzato3 = "ESEMPIO480";
 
void setup()
{ 
  Serial.begin(9600);
  /* Abilita SPI*/
  SPI.begin(); 
  /* Viene inizilizzato RFID reader */
  RC522.init();
  Serial.println("Setup");
  pinMode(ledVerde,OUTPUT);
  pinMode(ledRosso,OUTPUT);
  pinMode(rele,OUTPUT);

  // Connect to WiFi network
  Serial.println();
  Serial.println();
  Serial.print("Connecting to ");
  Serial.println(ssid);

  WiFi.mode(WIFI_STA);
  WiFi.begin(ssid, password);

  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.println("WiFi connected");

  // Start the server
  server.begin();
  Serial.println("Server started");

  // Print the IP address
  Serial.println(WiFi.localIP());
}
  
void loop() {

  // Check if a client has connected
  WiFiClient client = server.available();
  if (!client) {
    return;
  }

  // Wait until the client sends some data
  Serial.println("new client");
  
  if (client.available()){
    
  // Read the first line of the request
  String req = client.readStringUntil('\r');
  Serial.println(req);
  client.flush();

  // Match the request
  int val;
  if (req.indexOf("/gpio/0") != -1) {
    val = 0;
  } else if (req.indexOf("/gpio/1") != -1) {
    val = 1;
  } else {
    Serial.println("invalid request");
    client.stop();
    return;
  }

  // Set GPIO2 according to the request
  digitalWrite(rele, val);

  client.flush();

  // Prepare the response
  String s = "HTTP/1.1 200 OK\r\nContent-Type: text/html\r\n\r\n<!DOCTYPE HTML>\r\n<html>\r\nGPIO is now ";
  s += (val) ? "high" : "low";
  s += "</html>\n";

  // Send the response to the client
  client.print(s);
  delay(1);
  Serial.println("Client disonnected");

  
  /* Temporary loop counter */
  byte i;
  // Se viene letta una tessera
  if (RC522.isCard())
  {
    // Viene letto il suo codice 
    RC522.readCardSerial();
    String codiceLetto ="";
    Serial.println("Codice delle tessera letto:");
  
    // Viene caricato il codice della tessera, all'interno di una Stringa
    for(i = 0; i <= 4; i++)
    {
      codiceLetto+= String (RC522.serNum[i],HEX);
      codiceLetto.toUpperCase();
    }
    Serial.println(codiceLetto);
    if(verificaCodice(codiceLetto,codiceAutorizzato1)||verificaCodice(codiceLetto,codiceAutorizzato2)
    ||verificaCodice(codiceLetto,codiceAutorizzato3)){
      Serial.println("Tessera autorizzata");
      accendiLed(ledVerde);
      digitalWrite (rele, HIGH);
      delay (1000);     // Tempo relè in stato ON
      digitalWrite (rele, LOW);
    }else{
      Serial.println("Tessera non autorizzata");
      accendiLed(ledRosso);
    }
  delay(delayRead);  
  }
}
// Questa funzione verifica se il codice Letto è autorizzato
boolean verificaCodice(String codiceLetto, String codiceAutorizzato){
  if(codiceLetto.equals(codiceAutorizzato)){
    return true;
  }else{
    return false;
  }  
}    
// Questa funzione permette di accendere un LED per un determinato periodo
void accendiLed(int ledPin){
  digitalWrite(ledPin,HIGH);
  delay(delayLed);
  digitalWrite(ledPin,LOW);
}
}

seguendo le tue istruzioni viene cosi, ma non me lo fa compilare, mi da un errore. come mai?

Perchè non chiudi il loop() nel posto giusto,se formattassi il testo forse te ne accorgeresti

Poi mi togli una curiosita' ?
Perchè usi una libreria RFID.h che è absoleta già da diversi anni, visto che l'autore ne ha riproposta una più aggiornata link Rfid
E poi, sempre per discuterne, perchè usi lo stesso pin sia per il CS della scheda che per il led rosso ?