Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Webserver.on calls wrong Callback #11074

Open
1 task done
ams-hh opened this issue Mar 11, 2025 · 8 comments
Open
1 task done

Webserver.on calls wrong Callback #11074

ams-hh opened this issue Mar 11, 2025 · 8 comments

Comments

@ams-hh
Copy link

ams-hh commented Mar 11, 2025

Board

ESP32-S3 on custom PCB

Device Description

Described issue is device independant

Hardware Configuration

Independant

Version

v2.0.17

IDE Name

platformio

Operating System

Windows 11

Flash frequency

?

PSRAM enabled

no

Upload speed

921600

Description

After several years of "works as expected" I now have crashes inside the Webserver.
(WebServer.h. "Now" means: Change from framework-arduinoespressif32 @ 3.20014 to framework-arduinoespressif32 @ 3.20017)

WbServer.h offers the method

void on(const Uri &uri, HTTPMethod method, THandlerFunction fn, THandlerFunction ufn); //ufn handles file uploads

to define two callbacks "Function" and "Uploads Function".

As said, until V 3.20014 everything worked as expected. From 3.20017 on, when exceuting a POST to the fn, THE UFN is called. NOT THE FN. (And my system then crashes because of wrong handling ...)

To demonstrate I provide:

  1. Demo-Program
  2. platformio.ini
  3. HTML Test-File

DEMO PROGRAM
(see below)

PLATFORMIO.INI
(I use a custom board file. Substitude it by an own board for ESP32-S3)

[platformio]
default_envs = esp32S3-with-6-10-0


[env]
framework = arduino
monitor_speed = 115200
upload_speed = 921600
monitor_filters = time, default

[env:esp32S3-with-6-10-0]
build_flags = 
  -D CORE_DEBUG_LEVEL=0

platform = espressif32@6.10.0
board = esp32s3_4MB_NOPSRAM_CDC

[env:esp32S3-with-6-6-0]
build_flags = 
  -D CORE_DEBUG_LEVEL=0
platform = espressif32@6.6.0
board = esp32s3_4MB_NOPSRAM_CDC

HTML FILE

<!DOCTYPE html>
<html>
	<head>
		<meta content="text/html;charset=ISO-8859-1" http-equiv="content-type">
		<title>CALL FN</title>
	</head>

	<body>
	</body>


	<script>
		alert("Now excecute FN Call");

	  	var xhttp = new XMLHttpRequest();

		//CAUTION: Change to your Webserver IP Address!!
		xhttp.open("POST", "http:/192.168.0.105/test", true); 
	  	xhttp.send();
	</script>
</html>

Why?

Can someone verify? Or provide a solution?

Thank you !

P.S.
There is a change in RequestHandlersImpl.h. in the class FunctionRequestHandler.
There appears two new methods canRaw and raw that do not exist in Version
3.20014. And they do something with the _ufn parameter. But I did not digg into deeper ...

Sketch

#include    <Arduino.h>
#include    <WiFi.h>
#include    <WebServer.h>

WebServer                   clWebServer(80);

// Change this!!
const char* ssid     = "???";   //  <----------- YOUR SSID
const char* password = "???";   //  <----------- YOUR PW

void    CB_FN()
{
    Serial.println("Hello! I am the FN-Callback");
}

void    CB_UFN()
{
    Serial.println("Hello! I am the UFN-Callback");
}

void    NotFound()
{
    Serial.println("Sorry ... did not found");
}


boolean connectWifi(){
  boolean state = true;
  int i = 0;
  
  WiFi.mode(WIFI_STA);
  WiFi.begin(ssid, password);
  Serial.println("");
  Serial.println("Connecting to WiFi");

  // Wait for connection
  Serial.print("Connecting...");
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
    if (i > 20){
      state = false; break;
    }
    i++;
  }
  Serial.println("");
  if (state){
    Serial.print("Connected to ");
    Serial.println(ssid);
    Serial.print("IP address: ");
    Serial.println(WiFi.localIP());
  }
  else {
    Serial.println("Connection failed.");
  }
  return state;
}

void setup()
{
    Serial.begin(115200);
    Serial.println("\n\nSTART");

    if (connectWifi())
    {
        clWebServer.on("/test"  , 
                       HTTP_POST,
                       CB_FN    ,
                       CB_UFN   );

        clWebServer.onNotFound(NotFound);  

        clWebServer.begin();
    }
    else
    {
        while(1)
        {
            Serial.print("?..");
            delay(1000);
        }
    }
}
 
void loop()
{
    clWebServer.handleClient();
}

Debug Message

No Debug messages.

Other Steps to Reproduce

0.) (Substitude SSID/PW in program for your needs!)
1.) Build the project with project environment esp32S3-with-6-6-0 (which comes with Version 2.14)
2.) Run and see the connected IP
3.) Substitude IP in HTML-File
4.) Open Brower and execute HTML-File
5.) See in PIO Terminal, that Function FN ist called
---> Works as expected

6.) Change to project environment esp32S3-with-6-10-0 (which comes with Version 2.17) and build
... rest the same as before

---> See in PIO Terminal, that Function UFN ist called. (... and than FN...?)

I have checked existing issues, online documentation and the Troubleshooting Guide

  • I confirm I have checked existing issues, online documentation and Troubleshooting guide.
@ams-hh ams-hh added the Status: Awaiting triage Issue is waiting for triage label Mar 11, 2025
@Jason2866
Copy link
Collaborator

Arduino Core 2.0.17 is out of support.

@ams-hh
Copy link
Author

ams-hh commented Mar 12, 2025

Yes .... but that's what is delivered in platformio with the newest Platform Espressif32, V6.10.0 ....

No way,... Then please take another, not "out of support" Version to see if there is as well a wrong called Callback.
If this what I've seen is really an issue, it maybe exists in newer versions as well...?

@Jason2866
Copy link
Collaborator

Jason2866 commented Mar 12, 2025

It is the other way around it works. In github issues people provide an example for the actual version where an error occurs.
Platformio company is in no way related to espressif. If the provide outdated stuff that's there problem.

@ams-hh
Copy link
Author

ams-hh commented Mar 12, 2025

Hello Jason2866,

I agree in principal.
So now I've made a new test with pioArduino and platform Espressif32 53.3.13 which comes with
framework-arduinoespressif32 @ 3.1.3 (There is no newer one, as far as I can see ...?)

Processing esp32S3-with-V3 (platform: https://github.com/pioarduino/platform-espressif32/releases/download/stable/platform-espressif32.zip; board: esp32s3_4MB_NOPSRAM_CDC; framework: arduino)
--------------------------------------------------------------------------------------------------------------Verbose mode can be enabled via `-v, --verbose` option
CONFIGURATION: https://docs.platformio.org/page/boards/espressif32/esp32s3_4MB_NOPSRAM_CDC.html
PLATFORM: Espressif 32 (53.3.13) > ESP32-S3 4MB No PSRAM
HARDWARE: ESP32S3 240MHz, 320KB RAM, 4MB Flash
DEBUG: Current (cmsis-dap) External (cmsis-dap, esp-bridge, esp-builtin, esp-prog, iot-bus-jtag, jlink, minimodule, olimex-arm-usb-ocd, olimex-arm-usb-ocd-h, olimex-arm-usb-tiny-h, olimex-jtag-tiny, tumpa)
PACKAGES:
 - framework-arduinoespressif32 @ 3.1.3
 - framework-arduinoespressif32-libs @ 5.3.0+sha.489d7a2b3a
.....

The result is the same. It calls the ufn function and not (as expected and correctly until 2.0.14) the fn function.
So the question remains ...

@Jason2866 Jason2866 removed the Status: Awaiting triage Issue is waiting for triage label Mar 13, 2025
@felmue
Copy link

felmue commented Apr 12, 2025

Hello @ams-hh

as you already mentioned there is a new method canRaw() which seem to be used in a new raw mode.

I did some digging and it looks like upload and raw mode both use the same two callback functions (fn and ufn).

A HTTP_POST w/ file upload triggers the ufn via the upload functionality - same as before.

A HTTP_POST w/o file upload triggers the ufn via the raw functionality - new behavior.

I think a possible way to mimic the previous behavior is to subclass RequestHandler and then to return false in its canRaw() member function (or not define a canRaw() member function at all). Similar as it is done in this example.

So in your code you could do the following:

  • copy the FunctionRequestHandler class from here.
  • modify the canRaw() member functions to always return false.
  • replace clWebServer.on() with clWebServer.addHandler(new FunctionRequestHandler(CB_FN, CB_UFN, "/test", HTTP_POST));

Thanks
Felix

@ams-hh
Copy link
Author

ams-hh commented Apr 12, 2025

Hello Felix,

thanks for the effort you made!

I am not a friend of manipulating core functions or libraries. It's quickly forgotten and after the next update the issue is probably (no ... for sure) back and the correction made is presumably overwritten ....

I made the following:
I split my request. There are two overloaded methods for weberser.on. One is the mentioned above with the two entries for the two functions fn and ufn. The second one takes only the fn function.

This second function works correctly. I use it for the fn function.
The first function I call with my ufn function and a dummy (empty) fn function.

So the combination in general works ok. Not nice ... but I do not have to change anything in the core.

Best regards
Andree

@ams-hh
Copy link
Author

ams-hh commented Apr 12, 2025

.... but beside of the workaround .... is this an error or not?

@felmue
Copy link

felmue commented Apr 12, 2025

Hello @ams-hh

thank you for sharing your workaround. As whether this is an error or wanted behavior I cannot say, sorry.

Well, actually my proposal wouldn't require modifying the core or libraries - it would all be in your own code. That said, I agree, it still could break with the next update.

Thanks
Felix

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants