Geocache with esp32

I have build a letterbox to use for geocaching.
i have manged to get it to work properly except for OTA.
I am using an MH-ET Live ESP-WROOM-32.
and using SPIFFS for imaging.

rst:0x1 (POWERON_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0030,len:1288
load:0x40078000,len:13872
load:0x40080400,len:4
ho 8 tail 4 room 4
load:0x40080404,len:3048
entry 0x40080590
[     3][D][esp32-hal-cpu.c:264] setCpuFrequencyMhz(): PLL: 480 / 2 = 240 Mhz, APB: 80000000 Hz
=========== Before Setup Start ===========
Chip Info:
------------------------------------------
  Model             : ESP32
  Package           : D0WD-Q5
  Revision          : 1.44
  Cores             : 2
  Frequency         : 240 MHz
  Embedded Flash    : No
  Embedded PSRAM    : No
  2.4GHz WiFi       : Yes
  Classic BT        : Yes
  BT Low Energy     : Yes
  IEEE 802.15.4     : No
------------------------------------------
INTERNAL Memory Info:
------------------------------------------
  Total Size        :   343756 B ( 335.7 KB)
  Free Bytes        :   313464 B ( 306.1 KB)
  Allocated Bytes   :    23212 B (  22.7 KB)
  Minimum Free Bytes:   308084 B ( 300.9 KB)
  Largest Free Block:   110580 B ( 108.0 KB)
------------------------------------------
Flash Info:
------------------------------------------
  Chip Size         :  4194304 B (4 MB)
  Block Size        :    65536 B (  64.0 KB)
  Sector Size       :     4096 B (   4.0 KB)
  Page Size         :      256 B (   0.2 KB)
  Bus Speed         : 80 MHz
  Bus Mode          : DIO
------------------------------------------
Partitions Info:
------------------------------------------
                nvs : addr: 0x00009000, size:    20.0 KB, type: DATA, subtype: NVS
            otadata : addr: 0x0000E000, size:     8.0 KB, type: DATA, subtype: OTA
               app0 : addr: 0x00010000, size:  1920.0 KB, type:  APP, subtype: OTA_0
               app1 : addr: 0x001F0000, size:  1920.0 KB, type:  APP, subtype: OTA_1
             spiffs : addr: 0x003D0000, size:   128.0 KB, type: DATA, subtype: SPIFFS
           coredump : addr: 0x003F0000, size:    64.0 KB, type: DATA, subtype: COREDUMP
------------------------------------------
Software Info:
------------------------------------------
  Compile Date/Time : Jun  4 2024 20:24:43
  Compile Host OS   : windows
  ESP-IDF Version   : v5.1.4-51-g442a798083-dirty
  Arduino Version   : 3.0.0
------------------------------------------
Board Info:
------------------------------------------
  Arduino Board     : MH_ET_LIVE_ESP32MINIKIT
  Arduino Variant   : mhetesp32minikit
  Arduino FQBN      : esp32:esp32:mhetesp32minikit:FlashFreq=80,PartitionScheme=min_spiffs,UploadSpeed=921600,DebugLevel=debug,EraseFlash=all
============ Before Setup End ============
Setup started.
AP IP address: 192.168.4.1
[   621][D][AP.cpp:88] _onApArduinoEvent(): Arduino AP Event: 19 - AP_START
HTTP server started
=========== After Setup Start ============
INTERNAL Memory Info:
------------------------------------------
  Total Size        :   343756 B ( 335.7 KB)
  Free Bytes        :   256312 B ( 250.3 KB)
  Allocated Bytes   :    77172 B (  75.4 KB)
  Minimum Free Bytes:   255632 B ( 249.6 KB)
  Largest Free Block:   110580 B ( 108.0 KB)
------------------------------------------
GPIO Info:
------------------------------------------
  GPIO : BUS_TYPE[bus/unit][chan]
  --------------------------------------  
     1 : UART_TX[0]
     3 : UART_RX[0]
    14 : GPIO
    25 : GPIO
    26 : GPIO
    27 : GPIO
============ After Setup End =============

This is my sketch

#include <WiFi.h>
#include <WebServer.h>
#include <SPIFFS.h>
#include <Update.h>

const char* ssid = "Geocache_WiFi";
const char* password = "password";

WebServer server(80);

#define RED_PIN 14
#define GREEN_PIN 27
#define BLUE_PIN 26
#define COIL_PIN 25

const String correctCode = "313";

unsigned long coilActivatedTime = 0;
bool coilActivated = false;
bool shouldRestart = false;
unsigned long restartTimer = 0;

void handleRoot() {
  String page = "<html><head><style>";
  page += "body { font-size: 24px; }";
  page += "h1 { font-size: 36px; }";
  page += "p { font-size: 24px; }";
  page += "</style></head><body>";
  page += "<h1>Geocache Access Point</h1>";
  page += "<p>Voer het kenteken in van de auto van Donald Duck om de cache te openen:</p>";
  page += "<form action='/check' method='POST'><input name='code' type='text'><input type='submit'></form>";
  page += "<br><img src='/image.jpg' alt='Geocache Image'>";
  page += "<script>";
  page += "if(window.location.hostname !== '192.168.4.1') { window.location.href = 'http://192.168.4.1'; }";
  page += "</script>";
  page += "</body></html>";
  server.send(200, "text/html", page);
}

void handleImage() {
  File file = SPIFFS.open("/image.jpg", "r");
  if (!file) {
    server.send(404, "text/plain", "File not found");
    return;
  }

  server.streamFile(file, "image/jpeg");
  file.close();
}

void handleSuccessImage() {
  File file = SPIFFS.open("/success.jpg", "r");
  if (!file) {
    server.send(404, "text/plain", "File not found");
    return;
  }

  server.streamFile(file, "image/jpeg");
  file.close();
}

void handleOopsImage() {
  File file = SPIFFS.open("/oops.jpg", "r");
  if (!file) {
    server.send(404, "text/plain", "File not found");
    return;
  }

  server.streamFile(file, "image/jpeg");
  file.close();
}

void handleCheck() {
  if (server.hasArg("code") && server.arg("code") == correctCode) {
    digitalWrite(GREEN_PIN, HIGH);
    digitalWrite(RED_PIN, LOW);
    digitalWrite(BLUE_PIN, LOW);
    digitalWrite(COIL_PIN, HIGH);
    coilActivatedTime = millis();
    coilActivated = true;

    String page = "<html><body style='font-size:24px;'>";
    page += "<h1>Correct code!</h1>";
    page += "<p>Gefeliciteerd!<br>De cache is nu geopend en wordt gereset na 30 seconden.<br>Zou u de klep voorzichtig willen sluiten.</p>";
    page += "<img src='/success.jpg' alt='Success Image'>";
    page += "<br><br><a href='/'>Terug</a>";
    page += "</body></html>";

    server.send(200, "text/html", page);
  } else {
    String page = "<html><body style='font-size:24px;'>";
    page += "<h1>Incorrect code!</h1>";
    page += "<p>Probeer het opnieuw.</p>";
    page += "<form action='/check' method='POST'><input name='code' type='text'><input type='submit'></form>";
    page += "<img src='/oops.jpg' alt='Oops Image'>";
    page += "<br><br><a href='/'>Terug</a>";
    page += "</body></html>";

    server.send(200, "text/html", page);
  }
}

void handleOTAUpdate() {
  String page = "<html><body style='font-size:24px;'>";
  page += "<h1>OTA Update</h1>";
  page += "<form method='POST' action='/update' enctype='multipart/form-data'>";
  page += "<input type='file' name='update'>";
  page += "<input type='submit' value='Update'>";
  page += "</form>";
  page += "</body></html>";
  server.send(200, "text/html", page);
}

void handleUpdate() {
  HTTPUpload& upload = server.upload();
  if (upload.status == UPLOAD_FILE_START) {
    if (!Update.begin(UPDATE_SIZE_UNKNOWN)) { // start with max available size
      Update.printError(Serial);
    }
  } else if (upload.status == UPLOAD_FILE_WRITE) {
    if (Update.write(upload.buf, upload.currentSize) != upload.currentSize) {
      Update.printError(Serial);
    }
  } else if (upload.status == UPLOAD_FILE_END) {
    if (Update.end(true)) { // true to set the size to the current progress
      server.sendHeader("Connection", "close");
      server.send(200, "text/plain", (Update.hasError()) ? "FAIL" : "OK");
      shouldRestart = true;
      restartTimer = millis();
    } else {
      Update.printError(Serial);
    }
  } else {
    Update.printError(Serial);
    server.sendHeader("Connection", "close");
    server.send(200, "text/plain", "FAIL");
  }
}

void setup() {
  pinMode(RED_PIN, OUTPUT);
  pinMode(GREEN_PIN, OUTPUT);
  pinMode(BLUE_PIN, OUTPUT);
  pinMode(COIL_PIN, OUTPUT);

  Serial.begin(115200);

  if (!SPIFFS.begin(true)) {
    return;
  }

  WiFi.softAP(ssid, password);

  IPAddress IP = WiFi.softAPIP();

  server.on("/", handleRoot);
  server.on("/image.jpg", handleImage); // Serve the image from SPIFFS
  server.on("/success.jpg", handleSuccessImage); // Serve the success image from SPIFFS
  server.on("/oops.jpg", handleOopsImage); // Serve the oops image from SPIFFS
  server.on("/check", HTTP_POST, handleCheck);
  server.on("/ota-update", handleOTAUpdate);
  server.on("/update", HTTP_POST, handleUpdate);
  server.begin();
}

void loop() {
  static unsigned long lastBlink = 0;
  static bool ledState = false;
  unsigned long currentMillis = millis();

  // Check if any devices are connected
  if (WiFi.softAPgetStationNum() > 0) {
    if (!coilActivated) {
      // Blink the blue LED if a device is connected and the coil is not activated
      if (currentMillis - lastBlink >= 250) {
        lastBlink = currentMillis;
        ledState = !ledState;
        digitalWrite(BLUE_PIN, ledState ? HIGH : LOW);
        digitalWrite(RED_PIN, LOW);
        digitalWrite(GREEN_PIN, LOW);
      }
    }
  } else {
    // Blink the red LED if no devices are connected
    if (currentMillis - lastBlink >= 500) {
      lastBlink = currentMillis;
      ledState = !ledState;
      digitalWrite(RED_PIN, ledState ? HIGH : LOW);
      digitalWrite(BLUE_PIN, LOW);
      digitalWrite(GREEN_PIN, LOW);
    }
  }

  // Check if the coil has been activated for more than 30 seconds
  if (coilActivated && (currentMillis - coilActivatedTime >= 30000)) {
    digitalWrite(COIL_PIN, LOW);
    digitalWrite(GREEN_PIN, LOW);
    coilActivated = false;
  }

  // Handle OTA restart after blinking LEDs
  if (shouldRestart) {
    if (currentMillis - restartTimer >= 10000) {
      ESP.restart();
    } else {
      // Blink blue and green LEDs alternately to indicate successful OTA update
      if (currentMillis - lastBlink >= 250) {
        lastBlink = currentMillis;
        ledState = !ledState;
        digitalWrite(GREEN_PIN, ledState ? HIGH : LOW);
        digitalWrite(BLUE_PIN, !ledState ? HIGH : LOW);
      }
    }
  }

  server.handleClient();
}

The page "192.168.4.1/ota-update" is working, i can select the *.bin file.
only when i press the button "update" the bin file dus not getting flashed.
Can some one of you can help mee with this??

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.