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

Ufs serve fix - makes it work better on esp32cam (ai thinker style) #21486

Merged
merged 2 commits into from
May 24, 2024
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
76 changes: 65 additions & 11 deletions tasmota/tasmota_xdrv_driver/xdrv_50_filesystem.ino
Original file line number Diff line number Diff line change
Expand Up @@ -889,15 +889,20 @@ void UFSRename(void) {
*/
#include "detail/RequestHandlersImpl.h"

//#define SERVING_DEBUG

// class to allow us to request auth when required.
// StaticRequestHandler is in the above header
class StaticRequestHandlerAuth : public StaticRequestHandler {
public:
StaticRequestHandlerAuth(FS& fs, const char* path, const char* uri, const char* cache_header):
StaticRequestHandlerAuth(FS& fs, const char* path, const char* uri, const char* cache_header, bool requireAuth):
StaticRequestHandler(fs, path, uri, cache_header)
{
_requireAuth = requireAuth;
}

bool _requireAuth;

// we replace the handle method,
// and look for authentication only if we would serve the file.
// if we check earlier, then we will reject as unauth even though a later
Expand All @@ -906,8 +911,10 @@ public:
if (!canHandle(requestMethod, requestUri))
return false;

log_v("StaticRequestHandler::handle: request=%s _uri=%s\r\n", requestUri.c_str(), _uri.c_str());

//log_v("StaticRequestHandler::handle: request=%s _uri=%s\r\n", requestUri.c_str(), _uri.c_str());
#ifdef SERVING_DEBUG
AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handle: request=%s _uri=%s"), requestUri.c_str(), _uri.c_str());
#endif
String path(_path);

if (!_isFile) {
Expand All @@ -919,8 +926,9 @@ public:
// Append whatever follows this URI in request to get the file path.
path += requestUri.substring(_baseUriLength);
}
log_v("StaticRequestHandler::handle: path=%s, isFile=%d\r\n", path.c_str(), _isFile);

#ifdef SERVING_DEBUG
AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handle: path=%s, isFile=%d"), path.c_str(), _isFile);
#endif
String contentType = getContentType(path);

// look for gz file, only if the original specified path is not a gz. So part only works to send gzip via content encoding when a non compressed is asked for
Expand All @@ -932,19 +940,63 @@ public:
}

File f = _fs.open(path, "r");
if (!f || !f.available())
if (!f || !f.available()){
AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handler missing file?"));
return false;

if (!WebAuthenticate()) {
}
#ifdef SERVING_DEBUG
AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handler file open %d"), f.available());
#endif
if (_requireAuth && !WebAuthenticate()) {
#ifdef SERVING_DEBUG
AddLog(LOG_LEVEL_ERROR, PSTR("UFS: serv of %s denied"), requestUri.c_str());
#endif
server.requestAuthentication();
return true;
}

if (_cache_header.length() != 0)
server.sendHeader("Cache-Control", _cache_header);

server.streamFile(f, contentType);
#ifdef SERVING_DEBUG
AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handler sending"));
#endif
uint8_t buff[512];
uint32_t bread;
uint32_t flen = f.available();
WiFiClient download_Client = server.client();
server.setContentLength(flen);
server.send(200, contentType, "");

// transfer is about 150kb/s
uint32_t cnt = 0;
while (f.available()) {
bread = f.read(buff, sizeof(buff));
cnt += bread;
#ifdef SERVING_DEBUG
//AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handler sending %d/%d"), cnt, flen);
#endif
uint32_t bw = download_Client.write((const char*)buff, bread);
if (!bw) { break; }
yield();
}
#ifdef SERVING_DEBUG
AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handler sent %d/%d"), cnt, flen);
#endif

if (cnt != flen){
AddLog(LOG_LEVEL_ERROR, PSTR("UFS: ::handler incomplete file send: sent %d/%d"), cnt, flen);
}

// It does seem that on lesser ESP32, this causes a problem? A lockup...
//server.streamFile(f, contentType);

f.close();
download_Client.stop();

#ifdef SERVING_DEBUG
AddLog(LOG_LEVEL_DEBUG, PSTR("UFS: ::handler done"));
#endif
return true;
}
};
Expand All @@ -959,9 +1011,9 @@ void UFSServe(void) {
if (Webserver) { // fail if no Webserver yet.
StaticRequestHandlerAuth *staticHandler;
if (noauth && *noauth == '1'){
staticHandler = (StaticRequestHandlerAuth *) new StaticRequestHandler(*ffsp, fpath, url, (char *)nullptr);
staticHandler = new StaticRequestHandlerAuth(*ffsp, fpath, url, (char *)nullptr, false);
} else {
staticHandler = new StaticRequestHandlerAuth(*ffsp, fpath, url, (char *)nullptr);
staticHandler = new StaticRequestHandlerAuth(*ffsp, fpath, url, (char *)nullptr, true);
}
if (staticHandler) {
//Webserver->serveStatic(url, *ffsp, fpath);
Expand Down Expand Up @@ -1319,6 +1371,8 @@ void UfsListDir(char *path, uint8_t depth) {
HtmlEscape(name).c_str(), tstr.c_str(), entry.size(), delpath, editpath);
}
entry.close();

yield(); // trigger watchdog reset
}
}
dir.close();
Expand Down