Differences

This shows you the differences between two versions of the page.

Link to this comparison view

iothings:proiecte:2025sric:rfidscanner [2025/04/10 08:37]
robert_ionut.alexa created
iothings:proiecte:2025sric:rfidscanner [2025/05/29 10:07] (current)
flaviu.ghena
Line 1: Line 1:
 ====== ESP32 RFID scanner ====== ====== ESP32 RFID scanner ======
 +Author: [[mailto:​ghena.flaviu@gmail.com|Ghena Flaviu]] \\
 +Master: SRIC
 +
 +===== Project Description =====
 +
 +This project implements a secure RFID-based access control system using an ESP32-WROOM-32 microcontroller and an RC522 RFID reader. The system grants or denies access based on scanned RFID cards, with visual feedback provided by green (access granted) and red (access denied) LEDs.
 +
 +===== Concept =====
 +
 +This project implements an IoT-based RFID access control system using an ESP32 microcontroller. It scans RFID cards, validates them against a predefined list, and provides visual feedback via LEDs. The system logs all access attempts to Firebase in real-time and sends Telegram notifications for unauthorized access. A web interface allows remote monitoring and manual control.
 +
 +Key features include:
 +Real-time access logging to Firebase Realtime Database [1]
 +Remote monitoring and control through a web interface
 +Instant Telegram notifications for unauthorized access attempts [2]
 +Manual access control via web interface buttons
 +Time-synchronized logging with NTP server
 +
 +The system validates scanned cards against a predefined list of authorized cards, providing immediate LED feedback and updating the cloud database. Unauthorized access attempts trigger Telegram alerts to the system administrator.
 +
 +===== Hardware Description =====
 +
 +{{:​iothings:​proiecte:​2025sric:​flaviu4.jpg?​600|}}
 +
 +**Parts List:**
 +  * ESP32-WROOM-32:​ Main microcontroller for processing and connectivity.
 +  * RFID-RC522 Module: Reads RFID card UIDs.
 +  * Green LED: Indicates authorized access.
 +  * Red LED: Indicates denied access.
 +  * Resistors (2x): Current-limiting resistors for LEDs
 +  * Breadboard/​Jumper Wires: For prototyping connections.
 +  * Power Supply: 3.3V for ESP32 and RC522.
 +
 +**ESP32-WROOM-32:​** \\
 +- Connects to WiFi for cloud communication.\\
 +- Interfaces with the RC522 via SPI (GPIO 5, 18, 19, 23).\\
 +- Controls LEDs via GPIO 25 (green) and 26 (red).\\
 +
 +**RFID-RC522:​** \\
 +- Communicates with ESP32 via SPI pins.\\
 +- Powered by 3.3V \\
 +- Antenna gain boosted for better sensitivity.\\
 +
 +**LEDs:** \\
 +- Green LED: Activated for valid cards or manual "​grant"​ commands.\\
 +- Red LED: Activated for invalid cards or manual "​deny"​ commands.\\
 +
 +{{:​iothings:​proiecte:​2025sric:​flaviu3.png?​600|}}
 +
 +===== Functionality Breakdown =====
 +
 +**Key Components**
 +
 +**RFID Handling:**
 +- The MFRC522 library interfaces with the RFID reader\\
 +- Cards are identified by their UID and converted to decimal format\\
 +- Reader automatically resets after periods of inactivity\\
 +
 +**Access Control Logic:**
 +- Compares scanned card IDs against authorized list\\
 +- Provides immediate visual feedback via LEDs\\
 +- Green LED for authorized access, red for denied\\
 +
 +**Firebase Integration:​**
 +- Stores all access events with timestamps\\
 +- Allows remote control via the ledControl path\\
 +- Uses anonymous authentication for security\\
 +
 +**Realtime Database rules**
 +<​code>​
 +{
 +  "​rules":​ {
 +    "​rfidSystem":​ {
 +      "​control":​ {
 +        "​.read":​ true,
 +        "​.write":​ true
 +      },
 +      "​logs":​ {
 +        "​.read":​ true,
 +        "​.write":​ true
 +      },
 +      "​ledControl":​ {
 +        "​.read":​ true,
 +        "​.write":​ true
 +      }
 +    }
 +  }
 +}
 +
 +</​code>​
 +
 +{{:​iothings:​proiecte:​2025sric:​flaviu6.png?​300|}}
 +
 +**Telegram Notifications:​**
 +- Sends instant alerts for all access attempts\\
 +- Differentiates between authorized and unauthorized access\\
 +- Includes system startup notification\\
 +
 +{{:​iothings:​proiecte:​2025sric:​flaviu2.jpeg?​250|}}
 +
 +
 +**Web Interface:​**
 +- Provides real-time access logs display\\
 +- Allows manual access control via buttons\\
 +- Shows system connection status\\
 +- The system combines local hardware control with cloud connectivity for a comprehensive access control solution with remote monitoring capabilities.\\
 +
 +**Error Handling:**
 +- Auto-resets RFID reader if inactive.\\
 +- Reconnects to WiFi/​Firebase if disconnected.\\
 +
 +^ RC522 Pin  ^ ESP32 Pin  ^
 +| SDA       | GPIO 5     |
 +| SCK       | GPIO 18    |
 +| MOSI      | GPIO 23    |
 +| MISO      | GPIO 19    |
 +| IRQ       | Not connected |
 +| GND       | GND        |
 +| RST       | GPIO 22    |
 +| 3.3V      | 3.3V       |
 +
 +^ LED Pin         ^ ESP32 Pin  ^
 +| GREEN LED PIN   | GPIO 25    |
 +| RED LED PIN     | GPIO 26    |
 +
 +{{:​iothings:​proiecte:​2025sric:​flaviu1.png?​600|}}
 +
 +
 +
 +
 +===== Code Breakdown =====
 +
 +<​code>​
 +#include <​SPI.h>​
 +#include <​MFRC522.h>​
 +#include <​WiFi.h>​
 +#include <​WiFiClientSecure.h>​
 +#include <​HTTPClient.h>​
 +#include <​Firebase_ESP_Client.h>​
 +#include "​addons/​TokenHelper.h"​
 +#include "​addons/​RTDBHelper.h"​
 +#include <​time.h>​
 +
 +// Configuration Section
 +#define WIFI_SSID "​DIGI-x39P"​
 +#define WIFI_PASSWORD "​xxxx"​
 +#define API_KEY "​xxxx"​
 +#define DATABASE_URL "​https://​iotproiectflaviu-default-rtdb.europe-west1.firebasedatabase.app"​
 +
 +// Telegram Bot Settings
 +#define BOT_TOKEN "​7635387808:​AAGwtP_Y6fJ0LEhLbCuXkeLQb5a-0iDDQgs"​
 +#define CHAT_ID "​2124464812"​
 +const char* TELEGRAM_HOST = "​api.telegram.org";​
 +
 +// Hardware Configuration
 +#define RST_PIN 22
 +#define SS_PIN 5
 +#define GREEN_LED_PIN 25
 +#define RED_LED_PIN 26
 +#define READ_TIMEOUT 300
 +#define LED_FEEDBACK_MS 1000
 +
 +// System Objects
 +MFRC522 mfrc522(SS_PIN,​ RST_PIN);
 +FirebaseData fbdo;
 +FirebaseData ledControlStream;​
 +FirebaseAuth auth;
 +FirebaseConfig config;
 +
 +// Database Paths
 +String databasePath = "​rfidSystem";​
 +String logsPath = "/​logs";​
 +String ledControlPath = "/​ledControl";​
 +
 +// Authorized Cards List
 +const unsigned long validCards[] = {2318660736,​ 240163822};
 +const int numValidCards = sizeof(validCards)/​sizeof(validCards[0]);​
 +
 +// NTP Configuration
 +const char* ntpServer = "​pool.ntp.org";​
 +const long gmtOffset_sec = 0;
 +const int daylightOffset_sec = 0;
 +
 +// Function to send Telegram alerts
 +void sendTelegramAlert(unsigned long cardID, bool isAuthorized) {
 +  WiFiClientSecure client;
 +  client.setInsecure();​ // Bypass SSL verification
 +  ​
 +  HTTPClient https;
 +  String url = "​https://"​ + String(TELEGRAM_HOST) + "/​bot"​ + String(BOT_TOKEN) + "/​sendMessage";​
 +  ​
 +  // Customize message based on access status
 +  String message = isAuthorized ? 
 +    "✅ Authorized access: Card " + String(cardID) :
 +    "🚨 Unauthorized access attempt: Card " + String(cardID);​
 +  ​
 +  String payload = "​chat_id="​ + String(CHAT_ID) + "&​text="​ + message;
 +
 +  if (https.begin(client,​ url)) {
 +    https.addHeader("​Content-Type",​ "​application/​x-www-form-urlencoded"​);​
 +    int httpCode = https.POST(payload);​
 +    if (httpCode == HTTP_CODE_OK) {
 +      Serial.println("​Telegram alert sent"​);​
 +    } else {
 +      Serial.printf("​Telegram error: %d\n", httpCode);
 +    }
 +    https.end();​
 +  } else {
 +    Serial.println("​Failed to connect to Telegram"​);​
 +  }
 +}
 +
 +// Initialize WiFi connection
 +void connectToWiFi() {
 +  Serial.print("​Connecting to WiFi"​);​
 +  WiFi.begin(WIFI_SSID,​ WIFI_PASSWORD);​
 +  ​
 +  while (WiFi.status() != WL_CONNECTED) {
 +    Serial.print('​.'​);​
 +    // Blink both LEDs while connecting
 +    digitalWrite(GREEN_LED_PIN,​ !digitalRead(GREEN_LED_PIN));​
 +    digitalWrite(RED_LED_PIN,​ !digitalRead(RED_LED_PIN));​
 +    delay(300);
 +  }
 +  ​
 +  Serial.println("​\nConnected with IP: " + WiFi.localIP().toString());​
 +  // Quick green LED confirmation
 +  digitalWrite(GREEN_LED_PIN,​ HIGH);
 +  delay(500);
 +  digitalWrite(GREEN_LED_PIN,​ LOW);
 +  digitalWrite(RED_LED_PIN,​ LOW);
 +}
 +
 +// Initialize time synchronization
 +void initTime() {
 +  configTime(gmtOffset_sec,​ daylightOffset_sec,​ ntpServer);
 +  Serial.println("​Waiting for NTP time sync..."​);​
 +  ​
 +  time_t now;
 +  while ((now = time(nullptr)) < 8 * 3600 * 2) {
 +    Serial.print("​."​);​
 +    delay(500);
 +  }
 +  ​
 +  Serial.println("​\nCurrent time: " + String(ctime(&​now)));​
 +}
 +
 +// Initialize Firebase connection
 +void initFirebase() {
 +  config.api_key = API_KEY;
 +  config.database_url = DATABASE_URL;​
 +  config.token_status_callback = tokenStatusCallback;​
 +  ​
 +  Firebase.reconnectWiFi(true);​
 +  fbdo.setResponseSize(4096);​
 +  ​
 +  // Anonymous authentication
 +  if (Firebase.signUp(&​config,​ &auth, "",​ ""​)) {
 +    Serial.println("​Anonymous signup successful"​);​
 +  } else {
 +    Serial.println("​Signup error: " + fbdo.errorReason());​
 +  }
 +  ​
 +  Firebase.begin(&​config,​ &auth);
 +  ​
 +  // Wait for Firebase connection
 +  unsigned long startTime = millis();
 +  while (!Firebase.ready() && millis() - startTime < 15000) {
 +    Serial.print("​."​);​
 +    delay(300);
 +  }
 +  ​
 +  if (Firebase.ready()) {
 +    Serial.println("​Firebase connected!"​);​
 +    // Start listening for LED control commands
 +    if (!Firebase.RTDB.beginStream(&​ledControlStream,​ (databasePath + ledControlPath).c_str())) {
 +      Serial.println("​Stream begin error: " + ledControlStream.errorReason());​
 +    }
 +  } else {
 +    Serial.println("​Failed to connect to Firebase"​);​
 +    // Blink red LED indefinitely on failure
 +    while(1) {
 +      digitalWrite(RED_LED_PIN,​ HIGH);
 +      delay(500);
 +      digitalWrite(RED_LED_PIN,​ LOW);
 +      delay(500);
 +    }
 +  }
 +}
 +
 +// Handle LED control commands from Firebase
 +void handleLEDControl() {
 +  if (Firebase.RTDB.readStream(&​ledControlStream)) {
 +    if (ledControlStream.streamAvailable()) {
 +      FirebaseJsonData jsonData;
 +      FirebaseJson *json = ledControlStream.jsonObjectPtr();​
 +      ​
 +      if (json->​get(jsonData,​ "​command"​)) {
 +        String command = jsonData.stringValue;​
 +        Serial.println("​Received LED command: " + command);
 +        ​
 +        if (command == "​grant"​) {
 +          digitalWrite(GREEN_LED_PIN,​ HIGH);
 +          digitalWrite(RED_LED_PIN,​ LOW);
 +          delay(LED_FEEDBACK_MS);​
 +          digitalWrite(GREEN_LED_PIN,​ LOW);
 +          sendToFirebase(0,​ true, true); // Manual grant
 +          sendTelegramAlert(0,​ true); ​   // Notify manual grant
 +        } else if (command == "​deny"​) {
 +          digitalWrite(RED_LED_PIN,​ HIGH);
 +          digitalWrite(GREEN_LED_PIN,​ LOW);
 +          delay(LED_FEEDBACK_MS);​
 +          digitalWrite(RED_LED_PIN,​ LOW);
 +          sendToFirebase(0,​ false, true); // Manual deny
 +          sendTelegramAlert(0,​ false); ​   // Notify manual deny
 +        }
 +      }
 +    }
 +  }
 +}
 +
 +// Send access event to Firebase
 +void sendToFirebase(unsigned long cardID, bool accessGranted,​ bool isManual) {
 +  if (Firebase.ready()) {
 +    time_t now;
 +    time(&​now);​
 +    ​
 +    String path = databasePath + logsPath + "/"​ + String(now);​
 +    FirebaseJson json;
 +    ​
 +    // Prepare JSON data
 +    json.set("​card_id",​ String(cardID));​
 +    json.set("​timestamp",​ now);
 +    json.set("​access_granted",​ accessGranted);​
 +    json.set("​is_manual",​ isManual);
 +    ​
 +    if (Firebase.RTDB.setJSON(&​fbdo,​ path.c_str(),​ &json)) {
 +      Serial.println("​Data sent to Firebase"​);​
 +    } else {
 +      Serial.println("​Firebase error: " + fbdo.errorReason());​
 +    }
 +  }
 +}
 +
 +// Check if card is authorized
 +bool isCardValid(unsigned long cardID) {
 +  for (int i = 0; i < numValidCards;​ i++) {
 +    if (cardID == validCards[i]) return true;
 +  }
 +  return false;
 +}
 +
 +// Reset RFID reader
 +void resetReader() {
 +  mfrc522.PCD_Reset();​
 +  mfrc522.PCD_Init();​
 +  mfrc522.PCD_SetAntennaGain(mfrc522.RxGain_48dB);​ // Increase sensitivity
 +  Serial.println("​Reader was reset"​);​
 +}
 +
 +// Setup function - runs once at startup
 +void setup() {
 +  Serial.begin(115200);​
 +  ​
 +  // Initialize hardware
 +  pinMode(GREEN_LED_PIN,​ OUTPUT);
 +  pinMode(RED_LED_PIN,​ OUTPUT);
 +  digitalWrite(GREEN_LED_PIN,​ LOW);
 +  digitalWrite(RED_LED_PIN,​ LOW);
 +  ​
 +  SPI.begin();​
 +  resetReader();​ // Initialize RFID reader
 +  ​
 +  // Connect to services
 +  connectToWiFi();​
 +  initTime();
 +  initFirebase();​
 +  ​
 +  // Send startup notification
 +  sendTelegramAlert(0,​ true); // System startup notification
 +  Serial.println("​System ready"​);​
 +}
 +
 +// Main program loop
 +void loop() {
 +  static bool readerEnabled = true;
 +  static unsigned long lastReadTime = 0;
 +  ​
 +  // Handle incoming Firebase commands
 +  handleLEDControl();​
 +  ​
 +  // Reset reader if inactive for too long
 +  if (millis() - lastReadTime > 3000 && readerEnabled) {
 +    readerEnabled = false;
 +    resetReader();​
 +    lastReadTime = millis();
 +    readerEnabled = true;
 +  }
 +  ​
 +  // Skip if not time to read yet or reader disabled
 +  if (millis() - lastReadTime < READ_TIMEOUT || !readerEnabled) return;
 +  ​
 +  // Check for new card
 +  if (!mfrc522.PICC_IsNewCardPresent()) return;
 +  if (!mfrc522.PICC_ReadCardSerial()) {
 +    Serial.println("​Failed to read card"​);​
 +    return;
 +  }
 +  ​
 +  lastReadTime = millis();
 +  readerEnabled = false;
 +  ​
 +  // Read card ID
 +  unsigned long cardID = 0;
 +  Serial.print("​Card UID:"​);​
 +  ​
 +  for (byte i = 0; i < mfrc522.uid.size;​ i++) {
 +    cardID = (cardID << 8) | mfrc522.uid.uidByte[i];​
 +    Serial.print(mfrc522.uid.uidByte[i] < 0x10 ? " 0" : " ");
 +    Serial.print(mfrc522.uid.uidByte[i],​ HEX);
 +  }
 +  ​
 +  Serial.print("​ | Decimal: ");
 +  Serial.println(cardID);​
 +  ​
 +  // Check access and provide feedback
 +  bool accessGranted = isCardValid(cardID);​
 +  digitalWrite(GREEN_LED_PIN,​ accessGranted ? HIGH : LOW);
 +  digitalWrite(RED_LED_PIN,​ accessGranted ? LOW : HIGH);
 +  ​
 +  // Log event and send notifications
 +  sendToFirebase(cardID,​ accessGranted,​ false);
 +  sendTelegramAlert(cardID,​ accessGranted);​
 +  ​
 +  // LED feedback duration
 +  delay(LED_FEEDBACK_MS);​
 +  digitalWrite(GREEN_LED_PIN,​ LOW);
 +  digitalWrite(RED_LED_PIN,​ LOW);
 +  ​
 +  // Clean up RFID communication
 +  mfrc522.PICC_HaltA();​
 +  mfrc522.PCD_StopCrypto1();​
 +  readerEnabled = true;
 +}
 +</​code>​
 +
 +
 +===== Webpage =====
 +
 +{{:​iothings:​proiecte:​2025sric:​flaviu5.png?​600|}}
 +
 +<​code>​
 +<​!DOCTYPE html>
 +<​html>​
 +<​head>​
 +  <​title>​RFID Access Control</​title>​
 +  <meta name="​viewport"​ content="​width=device-width,​ initial-scale=1">​
 +  <script src="​https://​www.gstatic.com/​firebasejs/​8.10.0/​firebase-app.js"></​script>​
 +  <script src="​https://​www.gstatic.com/​firebasejs/​8.10.0/​firebase-auth.js"></​script>​
 +  <script src="​https://​www.gstatic.com/​firebasejs/​8.10.0/​firebase-database.js"></​script>​
 +  <​style>​
 +    body { font-family:​ Arial, sans-serif; max-width: 800px; margin: 0 auto; padding: 20px; }
 +    .card { background: #f9f9f9; border-radius:​ 8px; padding: 20px; margin-bottom:​ 20px; box-shadow: 0 2px 4px rgba(0,​0,​0,​0.1);​ }
 +    button { padding: 10px 15px; margin: 5px; border: none; border-radius:​ 4px; cursor: pointer; }
 +    .grant-btn { background-color:​ #4CAF50; color: white; }
 +    .deny-btn { background-color:​ #f44336; color: white; }
 +    table { width: 100%; border-collapse:​ collapse; margin-top: 20px; }
 +    th, td { padding: 12px; text-align: left; border-bottom:​ 1px solid #ddd; }
 +    .access-granted { color: #4CAF50; }
 +    .access-denied { color: #f44336; }
 +    .manual-access { font-style: italic; }
 +  </​style>​
 +</​head>​
 +<​body>​
 +  <div class="​card">​
 +    <​h1>​RFID Access Control System</​h1>​
 +    <div id="​authStatus"></​div>​
 +    <div>
 +      <​h2>​Manual Control</​h2>​
 +      <button id="​grantBtn"​ class="​grant-btn">​Grant Access</​button>​
 +      <button id="​denyBtn"​ class="​deny-btn">​Deny Access</​button>​
 +    </​div>​
 +  </​div>​
 +
 +  <div class="​card">​
 +    <​h2>​Access Logs</​h2>​
 +    <div id="​connectionStatus"></​div>​
 +    <​table>​
 +      <​thead>​
 +        <tr>
 +          <​th>​Timestamp</​th>​
 +          <​th>​Card ID</​th>​
 +          <​th>​Access</​th>​
 +        </tr>
 +      </​thead>​
 +      <tbody id="​logsBody"></​tbody>​
 +    </​table>​
 +  </​div>​
 +
 +  <​script>​
 +    const firebaseConfig = {
 +      apiKey: "​AIzaSyAK0KP-a7qqbuoqp-qyPt1e-8xuktIrHVo",​
 +      authDomain: "​iotproiectflaviu.firebaseapp.com",​
 +      databaseURL:​ "​https://​iotproiectflaviu-default-rtdb.europe-west1.firebasedatabase.app"​
 +    };
 +
 +    firebase.initializeApp(firebaseConfig);​
 +    const database = firebase.database();​
 +    const ledControlRef = database.ref('​rfidSystem/​ledControl'​);​
 +    const logsRef = database.ref('​rfidSystem/​logs'​);​
 +
 +    // Auth state
 +    firebase.auth().signInAnonymously()
 +      .then(() => {
 +        document.getElementById('​authStatus'​).textContent = "​Authenticated";​
 +      })
 +      .catch(error => {
 +        document.getElementById('​authStatus'​).innerHTML = 
 +          `<span style="​color:​red">​Auth error: ${error.message}</​span>​`;​
 +      });
 +
 +    // Connection state
 +    database.ref('​.info/​connected'​).on('​value',​ (snapshot) => {
 +      const isConnected = snapshot.val();​
 +      document.getElementById('​connectionStatus'​).innerHTML = isConnected ? 
 +        '<​span style="​color:​green">​Connected to Firebase</​span>'​ : 
 +        '<​span style="​color:​red">​Disconnected</​span>';​
 +    });
 +
 +    // Button handlers
 +    document.getElementById('​grantBtn'​).addEventListener('​click',​ () => {
 +      ledControlRef.set({ command: "​grant",​ timestamp: Date.now() })
 +        .then(() => console.log("​Grant command sent"​))
 +        .catch(error => console.error("​Error:",​ error));
 +    });
 +
 +    document.getElementById('​denyBtn'​).addEventListener('​click',​ () => {
 +      ledControlRef.set({ command: "​deny",​ timestamp: Date.now() })
 +        .then(() => console.log("​Deny command sent"​))
 +        .catch(error => console.error("​Error:",​ error));
 +    });
 +
 +    // Logs display
 +    logsRef.limitToLast(20).on('​value',​ (snapshot) => {
 +      const logsBody = document.getElementById('​logsBody'​);​
 +      logsBody.innerHTML = '';​
 +      ​
 +      if (!snapshot.exists()) {
 +        logsBody.innerHTML = '<​tr><​td colspan="​3">​No logs found</​td></​tr>';​
 +        return;
 +      }
 +
 +      const logs = [];
 +      snapshot.forEach(child => {
 +        logs.push({
 +          key: child.key,
 +          ...child.val()
 +        });
 +      });
 +
 +      logs.sort((a,​ b) => b.timestamp - a.timestamp);​
 +      ​
 +      logs.forEach(log => {
 +        const row = document.createElement('​tr'​);​
 +        if (log.is_manual) row.classList.add('​manual-access'​);​
 +        ​
 +        const timeCell = document.createElement('​td'​);​
 +        timeCell.textContent = new Date(log.timestamp * 1000).toLocaleString();​
 +        row.appendChild(timeCell);​
 +        ​
 +        const idCell = document.createElement('​td'​);​
 +        idCell.textContent = log.card_id === "​0"​ ? "​MANUAL"​ : log.card_id;​
 +        row.appendChild(idCell);​
 +        ​
 +        const accessCell = document.createElement('​td'​);​
 +        accessCell.textContent = log.access_granted ? '​Granted'​ : '​Denied';​
 +        accessCell.className = log.access_granted ? '​access-granted'​ : '​access-denied';​
 +        row.appendChild(accessCell);​
 +        ​
 +        logsBody.appendChild(row);​
 +      });
 +    });
 +  </​script>​
 +</​body>​
 +</​html>​
 +</​code>​
 +
 +===== Libraries =====
 +
 +  * SPI.h: Enables SPI communication for the RC522.
 +  * MFRC522.h: Interfaces with the RFID reader.
 +  * WiFi.h: Manages WiFi connectivity.
 +  * Firebase_ESP_Client.h:​ Handles Firebase Realtime Database operations.
 +  * WiFiClientSecure.h/​HTTPClient.h:​ Sends Telegram alerts via HTTPS.
 +  * time.h: Syncs time via NTP for accurate timestamps.
 +
 +
 +===== Conclusions =====
 +This project demonstrates a scalable IoT access control system combining hardware (ESP32, RFID, LEDs) with cloud services (Firebase, Telegram). Key achievements:​
 +- Security: Real-time validation and alerts for unauthorized access.
 +- Remote Monitoring: Web interface and Telegram notifications.
 +- Reliability:​ Auto-reset functions and error handling.
 +- Future enhancements could include adding biometric verification or integrating with physical locks.
 +
 +===== Demo =====
 +
 +<​html><​iframe width="​456"​ height="​811"​ src="​https://​www.youtube.com/​embed/​BdYKw6g49gY"​ title="​RFID22"​ frameborder="​0"​ allow="​accelerometer;​ autoplay; clipboard-write;​ encrypted-media;​ gyroscope; picture-in-picture;​ web-share"​ allowfullscreen></​iframe></​html>​
 +
 +<​html><​iframe width="​456"​ height="​811"​ src="​https://​www.youtube.com/​embed/​UwR_TnAOcD8"​ title="​RFID11"​ frameborder="​0"​ allow="​accelerometer;​ autoplay; clipboard-write;​ encrypted-media;​ gyroscope; picture-in-picture;​ web-share"​ allowfullscreen></​iframe></​html>​
 +
 +===== References =====
 +[1] https://​randomnerdtutorials.com/​control-esp-gpios-firebase-web-app/​ \\
 +[2] https://​randomnerdtutorials.com/​esp32-door-status-telegram/​
iothings/proiecte/2025sric/rfidscanner.1744263452.txt.gz · Last modified: 2025/04/10 08:37 by robert_ionut.alexa
CC Attribution-Share Alike 3.0 Unported
www.chimeric.de Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0