refactor WebServer methods

and const specifiers for immutable returns
make &String arg overloads over const char*
+ some minor cleanups
This commit is contained in:
Emil Muratov
2024-06-28 00:45:05 +09:00
committed by Mathieu Carbou
parent 9e93f03525
commit c79f2d05f0
6 changed files with 176 additions and 100 deletions

View File

@@ -1145,7 +1145,6 @@ size_t AsyncWebSocket::printf_P(uint32_t id, PGM_P formatP, ...){
} }
return 0; return 0;
} }
#endif
size_t AsyncWebSocket::printfAll_P(PGM_P formatP, ...) size_t AsyncWebSocket::printfAll_P(PGM_P formatP, ...)
{ {
@@ -1168,6 +1167,7 @@ size_t AsyncWebSocket::printfAll_P(PGM_P formatP, ...)
textAll(buffer); textAll(buffer);
return len; return len;
} }
#endif
const char __WS_STR_CONNECTION[] PROGMEM = { "Connection" }; const char __WS_STR_CONNECTION[] PROGMEM = { "Connection" };
const char __WS_STR_UPGRADE[] PROGMEM = { "Upgrade" }; const char __WS_STR_UPGRADE[] PROGMEM = { "Upgrade" };
@@ -1225,7 +1225,7 @@ void AsyncWebSocket::handleRequest(AsyncWebServerRequest *request)
return; return;
} }
} }
AsyncWebHeader* version = request->getHeader(WS_STR_VERSION); const AsyncWebHeader* version = request->getHeader(WS_STR_VERSION);
if (version->value().toInt() != 13) if (version->value().toInt() != 13)
{ {
AsyncWebServerResponse *response = request->beginResponse(400); AsyncWebServerResponse *response = request->beginResponse(400);
@@ -1233,11 +1233,11 @@ void AsyncWebSocket::handleRequest(AsyncWebServerRequest *request)
request->send(response); request->send(response);
return; return;
} }
AsyncWebHeader* key = request->getHeader(WS_STR_KEY); const AsyncWebHeader* key = request->getHeader(WS_STR_KEY);
AsyncWebServerResponse *response = new AsyncWebSocketResponse(key->value(), this); AsyncWebServerResponse *response = new AsyncWebSocketResponse(key->value(), this);
if (request->hasHeader(WS_STR_PROTOCOL)) if (request->hasHeader(WS_STR_PROTOCOL))
{ {
AsyncWebHeader* protocol = request->getHeader(WS_STR_PROTOCOL); const AsyncWebHeader* protocol = request->getHeader(WS_STR_PROTOCOL);
//ToDo: check protocol //ToDo: check protocol
response->addHeader(WS_STR_PROTOCOL, protocol->value()); response->addHeader(WS_STR_PROTOCOL, protocol->value());
} }

View File

@@ -327,10 +327,11 @@ class AsyncWebSocket: public AsyncWebHandler {
size_t printf(uint32_t id, const char *format, ...) __attribute__ ((format (printf, 3, 4))); size_t printf(uint32_t id, const char *format, ...) __attribute__ ((format (printf, 3, 4)));
size_t printfAll(const char *format, ...) __attribute__ ((format (printf, 2, 3))); size_t printfAll(const char *format, ...) __attribute__ ((format (printf, 2, 3)));
#ifndef ESP32 #ifndef ESP32
size_t printf_P(uint32_t id, PGM_P formatP, ...) __attribute__ ((format (printf, 3, 4))); size_t printf_P(uint32_t id, PGM_P formatP, ...) __attribute__ ((format (printf, 3, 4)));
#endif
size_t printfAll_P(PGM_P formatP, ...) __attribute__ ((format (printf, 2, 3))); size_t printfAll_P(PGM_P formatP, ...) __attribute__ ((format (printf, 2, 3)));
#endif
//event listener //event listener
void onEvent(AwsEventHandler handler){ void onEvent(AwsEventHandler handler){

View File

@@ -129,7 +129,7 @@ class AsyncWebHeader {
AsyncWebHeader(const AsyncWebHeader &) = default; AsyncWebHeader(const AsyncWebHeader &) = default;
AsyncWebHeader(const String& name, const String& value): _name(name), _value(value){} AsyncWebHeader(const String& name, const String& value): _name(name), _value(value){}
AsyncWebHeader(const String& data): _name(), _value(){ AsyncWebHeader(const String& data){
if(!data) return; if(!data) return;
int index = data.indexOf(':'); int index = data.indexOf(':');
if (index < 0) return; if (index < 0) return;
@@ -237,8 +237,15 @@ class AsyncWebServerRequest {
const String& contentType() const { return _contentType; } const String& contentType() const { return _contentType; }
size_t contentLength() const { return _contentLength; } size_t contentLength() const { return _contentLength; }
bool multipart() const { return _isMultipart; } bool multipart() const { return _isMultipart; }
#ifndef ESP8266
const char* methodToString() const;
const char* requestedConnTypeToString() const;
#else
const __FlashStringHelper *methodToString() const; const __FlashStringHelper *methodToString() const;
const __FlashStringHelper *requestedConnTypeToString() const; const __FlashStringHelper *requestedConnTypeToString() const;
#endif
RequestedConnectionType requestedConnType() const { return _reqconntype; } RequestedConnectionType requestedConnType() const { return _reqconntype; }
bool isExpectedRequestedConnType(RequestedConnectionType erct1, RequestedConnectionType erct2 = RCT_NOT_USED, RequestedConnectionType erct3 = RCT_NOT_USED); bool isExpectedRequestedConnType(RequestedConnectionType erct1, RequestedConnectionType erct2 = RCT_NOT_USED, RequestedConnectionType erct3 = RCT_NOT_USED);
void onDisconnect (ArDisconnectHandler fn); void onDisconnect (ArDisconnectHandler fn);
@@ -251,9 +258,22 @@ class AsyncWebServerRequest {
void requestAuthentication(const char * realm = NULL, bool isDigest = true); void requestAuthentication(const char * realm = NULL, bool isDigest = true);
void setHandler(AsyncWebHandler *handler){ _handler = handler; } void setHandler(AsyncWebHandler *handler){ _handler = handler; }
void addInterestingHeader(const String& name);
void redirect(const String& url); /**
* @brief add header to collect from a response
*
* @param name
*/
void addInterestingHeader(const char* name);
void addInterestingHeader(const String& name){ return addInterestingHeader(name.c_str()); };
/**
* @brief issue 302 redirect responce
*
* @param url
*/
void redirect(const char* url);
void redirect(const String& url){ return redirect(url.c_str()); };
void send(AsyncWebServerResponse *response); void send(AsyncWebServerResponse *response);
void send(int code, const String& contentType=String(), const String& content=String()); void send(int code, const String& contentType=String(), const String& content=String());
@@ -262,8 +282,10 @@ class AsyncWebServerRequest {
void send(Stream &stream, const String& contentType, size_t len, AwsTemplateProcessor callback=nullptr); void send(Stream &stream, const String& contentType, size_t len, AwsTemplateProcessor callback=nullptr);
void send(const String& contentType, size_t len, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr); void send(const String& contentType, size_t len, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr);
void sendChunked(const String& contentType, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr); void sendChunked(const String& contentType, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr);
#ifdef ESP8266
void send_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback=nullptr); void send_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback=nullptr);
void send_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback=nullptr); void send_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback=nullptr);
#endif
AsyncWebServerResponse *beginResponse(int code, const String& contentType=String(), const String& content=String()); AsyncWebServerResponse *beginResponse(int code, const String& contentType=String(), const String& content=String());
AsyncWebServerResponse *beginResponse(FS &fs, const String& path, const String& contentType=String(), bool download=false, AwsTemplateProcessor callback=nullptr); AsyncWebServerResponse *beginResponse(FS &fs, const String& path, const String& contentType=String(), bool download=false, AwsTemplateProcessor callback=nullptr);
@@ -272,44 +294,83 @@ class AsyncWebServerRequest {
AsyncWebServerResponse *beginResponse(const String& contentType, size_t len, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr); AsyncWebServerResponse *beginResponse(const String& contentType, size_t len, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr);
AsyncWebServerResponse *beginChunkedResponse(const String& contentType, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr); AsyncWebServerResponse *beginChunkedResponse(const String& contentType, AwsResponseFiller callback, AwsTemplateProcessor templateCallback=nullptr);
AsyncResponseStream *beginResponseStream(const String& contentType, size_t bufferSize=1460); AsyncResponseStream *beginResponseStream(const String& contentType, size_t bufferSize=1460);
#ifdef ESP8266
AsyncWebServerResponse *beginResponse_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback=nullptr); AsyncWebServerResponse *beginResponse_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback=nullptr);
AsyncWebServerResponse *beginResponse_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback=nullptr); AsyncWebServerResponse *beginResponse_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback=nullptr);
#endif
size_t headers() const; // get header count size_t headers() const; // get header count
bool hasHeader(const String& name) const; // check if header exists
bool hasHeader(const __FlashStringHelper * data) const; // check if header exists
AsyncWebHeader* getHeader(const String& name); // check if header exists
const AsyncWebHeader* getHeader(const String& name) const; bool hasHeader(const char* name) const;
AsyncWebHeader* getHeader(const __FlashStringHelper * data); bool hasHeader(const String& name) const { return hasHeader(name.c_str()); };
#ifdef ESP8266
bool hasHeader(const __FlashStringHelper * data) const; // check if header exists
#endif
const AsyncWebHeader* getHeader(const char* name) const;
const AsyncWebHeader* getHeader(const String& name) const { return getHeader(name.c_str()); };
#ifdef ESP8266
const AsyncWebHeader* getHeader(const __FlashStringHelper * data) const; const AsyncWebHeader* getHeader(const __FlashStringHelper * data) const;
AsyncWebHeader* getHeader(size_t num); #endif
const AsyncWebHeader* getHeader(size_t num) const; const AsyncWebHeader* getHeader(size_t num) const;
size_t params() const; // get arguments count size_t params() const; // get arguments count
bool hasParam(const String& name, bool post=false, bool file=false) const; bool hasParam(const String& name, bool post=false, bool file=false) const;
bool hasParam(const __FlashStringHelper * data, bool post=false, bool file=false) const; bool hasParam(const __FlashStringHelper * data, bool post=false, bool file=false) const;
const AsyncWebParameter* getParam(const String& name, bool post=false, bool file=false) const; /**
* @brief Get the Request parameter by name
*
* @param name
* @param post
* @param file
* @return const AsyncWebParameter*
*/
const AsyncWebParameter* getParam(const char* name, bool post=false, bool file=false) const;
const AsyncWebParameter* getParam(const String& name, bool post=false, bool file=false) const { return getParam(name.c_str()); };
#ifdef ESP8266 #ifdef ESP8266
const AsyncWebParameter* getParam(const __FlashStringHelper * data, bool post, bool file) const; const AsyncWebParameter* getParam(const __FlashStringHelper * data, bool post, bool file) const;
#endif #endif
/**
* @brief Get request parameter by number
* i.e., n-th parameter
* @param num
* @return const AsyncWebParameter*
*/
const AsyncWebParameter* getParam(size_t num) const; const AsyncWebParameter* getParam(size_t num) const;
size_t args() const { return params(); } // get arguments count size_t args() const { return params(); } // get arguments count
const String& arg(const String& name) const; // get request argument value by name
// get request argument value by name
const String& arg(const char* name) const;
// get request argument value by name
const String& arg(const String& name) const { return arg(name.c_str()); };
#ifdef ESP8266
const String& arg(const __FlashStringHelper * data) const; // get request argument value by F(name) const String& arg(const __FlashStringHelper * data) const; // get request argument value by F(name)
#endif
const String& arg(size_t i) const; // get request argument value by number const String& arg(size_t i) const; // get request argument value by number
const String& argName(size_t i) const; // get request argument name by number const String& argName(size_t i) const; // get request argument name by number
bool hasArg(const char* name) const; // check if argument exists bool hasArg(const char* name) const; // check if argument exists
#ifdef ESP8266
bool hasArg(const __FlashStringHelper * data) const; // check if F(argument) exists bool hasArg(const __FlashStringHelper * data) const; // check if F(argument) exists
#endif
const String& ASYNCWEBSERVER_REGEX_ATTRIBUTE pathArg(size_t i) const; const String& ASYNCWEBSERVER_REGEX_ATTRIBUTE pathArg(size_t i) const;
const String& header(const char* name) const;// get request header value by name // get request header value by name
const String& header(const char* name) const;
const String& header(const String& name) const { return header(name.c_str()); };
#ifdef ESP8266
const String& header(const __FlashStringHelper * data) const;// get request header value by F(name) const String& header(const __FlashStringHelper * data) const;// get request header value by F(name)
#endif
const String& header(size_t i) const; // get request header value by number const String& header(size_t i) const; // get request header value by number
const String& headerName(size_t i) const; // get request header name by number const String& headerName(size_t i) const; // get request header name by number
String urlDecode(const String& text) const; String urlDecode(const String& text) const;
}; };
@@ -362,8 +423,8 @@ class AsyncWebHandler {
public: public:
AsyncWebHandler(){} AsyncWebHandler(){}
AsyncWebHandler& setFilter(ArRequestFilterFunction fn) { _filter = fn; return *this; } AsyncWebHandler& setFilter(ArRequestFilterFunction fn) { _filter = fn; return *this; }
AsyncWebHandler& setAuthentication(const char *username, const char *password){ _username = String(username);_password = String(password); return *this; }; AsyncWebHandler& setAuthentication(const char *username, const char *password){ _username = username; _password = password; return *this; };
AsyncWebHandler& setAuthentication(const String& username, const String& password){ _username = username;_password = password; return *this; }; AsyncWebHandler& setAuthentication(const String& username, const String& password){ _username = username; _password = password; return *this; };
bool filter(AsyncWebServerRequest *request){ return _filter == NULL || _filter(request); } bool filter(AsyncWebServerRequest *request){ return _filter == NULL || _filter(request); }
virtual ~AsyncWebHandler(){} virtual ~AsyncWebHandler(){}
virtual bool canHandle(AsyncWebServerRequest *request __attribute__((unused))){ virtual bool canHandle(AsyncWebServerRequest *request __attribute__((unused))){

View File

@@ -147,31 +147,36 @@ String requestDigestAuthentication(const char * realm){
return header; return header;
} }
bool checkDigestAuthentication(const char * header, const __FlashStringHelper *method, const char * username, const char * password, const char * realm, bool passwordIsHash, const char * nonce, const char * opaque, const char * uri){ #ifndef ESP8266
bool checkDigestAuthentication(const char * header, const char* method, const char * username, const char * password, const char * realm, bool passwordIsHash, const char * nonce, const char * opaque, const char * uri)
#else
bool checkDigestAuthentication(const char * header, const __FlashStringHelper *method, const char * username, const char * password, const char * realm, bool passwordIsHash, const char * nonce, const char * opaque, const char * uri)
#endif
{
if(username == NULL || password == NULL || header == NULL || method == NULL){ if(username == NULL || password == NULL || header == NULL || method == NULL){
//os_printf("AUTH FAIL: missing requred fields\n"); //os_printf("AUTH FAIL: missing requred fields\n");
return false; return false;
} }
String myHeader = String(header); String myHeader(header);
int nextBreak = myHeader.indexOf(','); int nextBreak = myHeader.indexOf(',');
if(nextBreak < 0){ if(nextBreak < 0){
//os_printf("AUTH FAIL: no variables\n"); //os_printf("AUTH FAIL: no variables\n");
return false; return false;
} }
String myUsername = String(); String myUsername;
String myRealm = String(); String myRealm;
String myNonce = String(); String myNonce;
String myUri = String(); String myUri;
String myResponse = String(); String myResponse;
String myQop = String(); String myQop;
String myNc = String(); String myNc;
String myCnonce = String(); String myCnonce;
myHeader += F(", "); myHeader += F(", ");
do { do {
String avLine = myHeader.substring(0, nextBreak); String avLine(myHeader.substring(0, nextBreak));
avLine.trim(); avLine.trim();
myHeader = myHeader.substring(nextBreak+1); myHeader = myHeader.substring(nextBreak+1);
nextBreak = myHeader.indexOf(','); nextBreak = myHeader.indexOf(',');
@@ -181,7 +186,7 @@ bool checkDigestAuthentication(const char * header, const __FlashStringHelper *m
//os_printf("AUTH FAIL: no = sign\n"); //os_printf("AUTH FAIL: no = sign\n");
return false; return false;
} }
String varName = avLine.substring(0, eqSign); String varName(avLine.substring(0, eqSign));
avLine = avLine.substring(eqSign + 1); avLine = avLine.substring(eqSign + 1);
if(avLine.startsWith(String('"'))){ if(avLine.startsWith(String('"'))){
avLine = avLine.substring(1, avLine.length() - 1); avLine = avLine.substring(1, avLine.length() - 1);
@@ -227,7 +232,7 @@ bool checkDigestAuthentication(const char * header, const __FlashStringHelper *m
} }
} while(nextBreak > 0); } while(nextBreak > 0);
String ha1 = (passwordIsHash) ? String(password) : stringMD5(myUsername + ':' + myRealm + ':' + String(password)); String ha1 = (passwordIsHash) ? String(password) : stringMD5(myUsername + ':' + myRealm + ':' + password);
String ha2 = String(method) + ':' + myUri; String ha2 = String(method) + ':' + myUri;
String response = ha1 + ':' + myNonce + ':' + myNc + ':' + myCnonce + ':' + myQop + ':' + stringMD5(ha2); String response = ha1 + ':' + myNonce + ':' + myNc + ':' + myCnonce + ':' + myQop + ':' + stringMD5(ha2);

View File

@@ -26,7 +26,12 @@
bool checkBasicAuthentication(const char * header, const char * username, const char * password); bool checkBasicAuthentication(const char * header, const char * username, const char * password);
String requestDigestAuthentication(const char * realm); String requestDigestAuthentication(const char * realm);
bool checkDigestAuthentication(const char * header, const char* method, const char * username, const char * password, const char * realm, bool passwordIsHash, const char * nonce, const char * opaque, const char * uri);
#ifdef ESP8266
bool checkDigestAuthentication(const char * header, const __FlashStringHelper *method, const char * username, const char * password, const char * realm, bool passwordIsHash, const char * nonce, const char * opaque, const char * uri); bool checkDigestAuthentication(const char * header, const __FlashStringHelper *method, const char * username, const char * password, const char * realm, bool passwordIsHash, const char * nonce, const char * opaque, const char * uri);
#endif
//for storing hashed versions on the device that can be authenticated against //for storing hashed versions on the device that can be authenticated against
String generateDigestHash(const char * username, const char * password, const char * realm); String generateDigestHash(const char * username, const char * password, const char * realm);

View File

@@ -605,7 +605,7 @@ size_t AsyncWebServerRequest::headers() const{
return _headers.size(); return _headers.size();
} }
bool AsyncWebServerRequest::hasHeader(const String& name) const { bool AsyncWebServerRequest::hasHeader(const char* name) const {
for(const auto& h: _headers){ for(const auto& h: _headers){
if(h.name().equalsIgnoreCase(name)){ if(h.name().equalsIgnoreCase(name)){
return true; return true;
@@ -614,44 +614,20 @@ bool AsyncWebServerRequest::hasHeader(const String& name) const {
return false; return false;
} }
#ifdef ESP8266
bool AsyncWebServerRequest::hasHeader(const __FlashStringHelper * data) const { bool AsyncWebServerRequest::hasHeader(const __FlashStringHelper * data) const {
return hasHeader(String(data)); return hasHeader(String(data));
} }
#endif
AsyncWebHeader* AsyncWebServerRequest::getHeader(const String& name) { const AsyncWebHeader* AsyncWebServerRequest::getHeader(const char* name) const {
auto iter = std::find_if(std::begin(_headers), std::end(_headers), auto iter = std::find_if(std::begin(_headers), std::end(_headers),
[&name](const AsyncWebHeader &header){ return header.name().equalsIgnoreCase(name); }); [&name](const AsyncWebHeader &header){ return header.name().equalsIgnoreCase(name); });
if (iter == std::end(_headers)) return (iter == std::end(_headers)) ? nullptr : &(*iter);
return nullptr;
return &(*iter);
}
const AsyncWebHeader* AsyncWebServerRequest::getHeader(const String& name) const {
auto iter = std::find_if(std::begin(_headers), std::end(_headers),
[&name](const AsyncWebHeader &header){ return header.name().equalsIgnoreCase(name); });
if (iter == std::end(_headers))
return nullptr;
return &(*iter);
}
AsyncWebHeader* AsyncWebServerRequest::getHeader(const __FlashStringHelper * data) {
PGM_P p = reinterpret_cast<PGM_P>(data);
size_t n = strlen_P(p);
char * name = (char*) malloc(n+1);
if (name) {
strcpy_P(name, p);
AsyncWebHeader* result = getHeader( String(name));
free(name);
return result;
} else {
return nullptr;
}
} }
#ifdef ESP8266
const AsyncWebHeader* AsyncWebServerRequest::getHeader(const __FlashStringHelper * data) const { const AsyncWebHeader* AsyncWebServerRequest::getHeader(const __FlashStringHelper * data) const {
PGM_P p = reinterpret_cast<PGM_P>(data); PGM_P p = reinterpret_cast<PGM_P>(data);
size_t n = strlen_P(p); size_t n = strlen_P(p);
@@ -665,17 +641,12 @@ const AsyncWebHeader* AsyncWebServerRequest::getHeader(const __FlashStringHelper
return nullptr; return nullptr;
} }
} }
#endif
AsyncWebHeader* AsyncWebServerRequest::getHeader(size_t num) {
if (num >= _headers.size())
return nullptr;
return &(*std::next(std::begin(_headers), num));
}
const AsyncWebHeader* AsyncWebServerRequest::getHeader(size_t num) const { const AsyncWebHeader* AsyncWebServerRequest::getHeader(size_t num) const {
if (num >= _headers.size()) if (num >= _headers.size())
return nullptr; return nullptr;
return &(*std::next(std::begin(_headers), num)); return &(*std::next(_headers.cbegin(), num));
} }
size_t AsyncWebServerRequest::params() const { size_t AsyncWebServerRequest::params() const {
@@ -695,7 +666,7 @@ bool AsyncWebServerRequest::hasParam(const __FlashStringHelper * data, bool post
return hasParam(String(data).c_str(), post, file); return hasParam(String(data).c_str(), post, file);
} }
const AsyncWebParameter* AsyncWebServerRequest::getParam(const String& name, bool post, bool file) const { const AsyncWebParameter* AsyncWebServerRequest::getParam(const char* name, bool post, bool file) const {
for(const auto &p: _params){ for(const auto &p: _params){
if(p.name() == name && p.isPost() == post && p.isFile() == file){ if(p.name() == name && p.isPost() == post && p.isFile() == file){
return &p; return &p;
@@ -711,34 +682,15 @@ const AsyncWebParameter* AsyncWebServerRequest::getParam(const __FlashStringHelp
#endif #endif
const AsyncWebParameter* AsyncWebServerRequest::getParam(size_t num) const { const AsyncWebParameter* AsyncWebServerRequest::getParam(size_t num) const {
if (num >= _params.size()) return nullptr; if (num >= _params.size())
auto iter = _params.cbegin(); return nullptr;
std::advance(iter, num); return &(*std::next(_params.cbegin(), num));
return &(*iter);
} }
void AsyncWebServerRequest::addInterestingHeader(const String& name){ void AsyncWebServerRequest::addInterestingHeader(const char* name){
if(std::none_of(std::begin(_interestingHeaders), std::end(_interestingHeaders), if(std::none_of(std::begin(_interestingHeaders), std::end(_interestingHeaders),
[&name](const String &str){ return str.equalsIgnoreCase(name); })) [&name](const String &str){ return str.equalsIgnoreCase(name); }))
_interestingHeaders.push_back(name); _interestingHeaders.emplace_back(name);
}
void AsyncWebServerRequest::send(AsyncWebServerResponse *response){
_response = response;
if(_response == NULL){
_client->close(true);
_onDisconnect();
return;
}
if(!_response->_sourceValid()){
delete response;
_response = NULL;
send(500);
}
else {
_client->setRxTimeout(0);
_response->_respond(this);
}
} }
AsyncWebServerResponse * AsyncWebServerRequest::beginResponse(int code, const String& contentType, const String& content){ AsyncWebServerResponse * AsyncWebServerRequest::beginResponse(int code, const String& contentType, const String& content){
@@ -775,6 +727,7 @@ AsyncResponseStream * AsyncWebServerRequest::beginResponseStream(const String& c
return new AsyncResponseStream(contentType, bufferSize); return new AsyncResponseStream(contentType, bufferSize);
} }
#ifdef ESP8266
AsyncWebServerResponse * AsyncWebServerRequest::beginResponse_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback){ AsyncWebServerResponse * AsyncWebServerRequest::beginResponse_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback){
return new AsyncProgmemResponse(code, contentType, content, len, callback); return new AsyncProgmemResponse(code, contentType, content, len, callback);
} }
@@ -782,6 +735,25 @@ AsyncWebServerResponse * AsyncWebServerRequest::beginResponse_P(int code, const
AsyncWebServerResponse * AsyncWebServerRequest::beginResponse_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback){ AsyncWebServerResponse * AsyncWebServerRequest::beginResponse_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback){
return beginResponse_P(code, contentType, (const uint8_t *)content, strlen_P(content), callback); return beginResponse_P(code, contentType, (const uint8_t *)content, strlen_P(content), callback);
} }
#endif
void AsyncWebServerRequest::send(AsyncWebServerResponse *response){
_response = response;
if(_response == NULL){
_client->close(true);
_onDisconnect();
return;
}
if(!_response->_sourceValid()){
delete response;
_response = NULL;
send(500);
}
else {
_client->setRxTimeout(0);
_response->_respond(this);
}
}
void AsyncWebServerRequest::send(int code, const String& contentType, const String& content){ void AsyncWebServerRequest::send(int code, const String& contentType, const String& content){
send(beginResponse(code, contentType, content)); send(beginResponse(code, contentType, content));
@@ -811,6 +783,7 @@ void AsyncWebServerRequest::sendChunked(const String& contentType, AwsResponseFi
send(beginChunkedResponse(contentType, callback, templateCallback)); send(beginChunkedResponse(contentType, callback, templateCallback));
} }
#ifdef ESP8266
void AsyncWebServerRequest::send_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback){ void AsyncWebServerRequest::send_P(int code, const String& contentType, const uint8_t * content, size_t len, AwsTemplateProcessor callback){
send(beginResponse_P(code, contentType, content, len, callback)); send(beginResponse_P(code, contentType, content, len, callback));
} }
@@ -818,8 +791,9 @@ void AsyncWebServerRequest::send_P(int code, const String& contentType, const ui
void AsyncWebServerRequest::send_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback){ void AsyncWebServerRequest::send_P(int code, const String& contentType, PGM_P content, AwsTemplateProcessor callback){
send(beginResponse_P(code, contentType, content, callback)); send(beginResponse_P(code, contentType, content, callback));
} }
#endif
void AsyncWebServerRequest::redirect(const String& url){ void AsyncWebServerRequest::redirect(const char* url){
AsyncWebServerResponse * response = beginResponse(302); AsyncWebServerResponse * response = beginResponse(302);
response->addHeader(F("Location"), url); response->addHeader(F("Location"), url);
send(response); send(response);
@@ -885,12 +859,13 @@ bool AsyncWebServerRequest::hasArg(const char* name) const {
return false; return false;
} }
#ifdef ESP8266
bool AsyncWebServerRequest::hasArg(const __FlashStringHelper * data) const { bool AsyncWebServerRequest::hasArg(const __FlashStringHelper * data) const {
return hasArg(String(data).c_str()); return hasArg(String(data).c_str());
} }
#endif
const String& AsyncWebServerRequest::arg(const char* name) const {
const String& AsyncWebServerRequest::arg(const String& name) const {
for(const auto& arg: _params){ for(const auto& arg: _params){
if(arg.name() == name){ if(arg.name() == name){
return arg.value(); return arg.value();
@@ -899,9 +874,11 @@ const String& AsyncWebServerRequest::arg(const String& name) const {
return emptyString; return emptyString;
} }
#ifdef ESP8266
const String& AsyncWebServerRequest::arg(const __FlashStringHelper * data) const { const String& AsyncWebServerRequest::arg(const __FlashStringHelper * data) const {
return arg(String(data).c_str()); return arg(String(data).c_str());
} }
#endif
const String& AsyncWebServerRequest::arg(size_t i) const { const String& AsyncWebServerRequest::arg(size_t i) const {
return getParam(i)->value(); return getParam(i)->value();
@@ -916,14 +893,15 @@ const String& AsyncWebServerRequest::pathArg(size_t i) const {
} }
const String& AsyncWebServerRequest::header(const char* name) const { const String& AsyncWebServerRequest::header(const char* name) const {
const AsyncWebHeader* h = getHeader(String(name)); const AsyncWebHeader* h = getHeader(name);
return h ? h->value() : emptyString; return h ? h->value() : emptyString;
} }
#ifdef ESP8266
const String& AsyncWebServerRequest::header(const __FlashStringHelper * data) const { const String& AsyncWebServerRequest::header(const __FlashStringHelper * data) const {
return header(String(data).c_str()); return header(String(data).c_str());
}; };
#endif
const String& AsyncWebServerRequest::header(size_t i) const { const String& AsyncWebServerRequest::header(size_t i) const {
const AsyncWebHeader* h = getHeader(i); const AsyncWebHeader* h = getHeader(i);
@@ -939,7 +917,7 @@ String AsyncWebServerRequest::urlDecode(const String& text) const {
char temp[] = "0x00"; char temp[] = "0x00";
unsigned int len = text.length(); unsigned int len = text.length();
unsigned int i = 0; unsigned int i = 0;
String decoded = String(); String decoded;
decoded.reserve(len); // Allocate the string internal buffer - never longer from source text decoded.reserve(len); // Allocate the string internal buffer - never longer from source text
while (i < len){ while (i < len){
char decodedChar; char decodedChar;
@@ -958,7 +936,32 @@ String AsyncWebServerRequest::urlDecode(const String& text) const {
return decoded; return decoded;
} }
#ifndef ESP8266
const char* AsyncWebServerRequest::methodToString() const {
if(_method == HTTP_ANY) return "ANY";
if(_method & HTTP_GET) return "GET";
if(_method & HTTP_POST) return "POST";
if(_method & HTTP_DELETE) return "DELETE";
if(_method & HTTP_PUT) return "PUT";
if(_method & HTTP_PATCH) return "PATCH";
if(_method & HTTP_HEAD) return "HEAD";
if(_method & HTTP_OPTIONS) return "OPTIONS";
return "UNKNOWN";
}
const char* AsyncWebServerRequest::requestedConnTypeToString() const {
switch (_reqconntype) {
case RCT_NOT_USED: return "RCT_NOT_USED";
case RCT_DEFAULT: return "RCT_DEFAULT";
case RCT_HTTP: return "RCT_HTTP";
case RCT_WS: return "RCT_WS";
case RCT_EVENT: return "RCT_EVENT";
default: return "ERROR";
}
}
#endif
#ifdef ESP8266
const __FlashStringHelper *AsyncWebServerRequest::methodToString() const { const __FlashStringHelper *AsyncWebServerRequest::methodToString() const {
if(_method == HTTP_ANY) return F("ANY"); if(_method == HTTP_ANY) return F("ANY");
else if(_method & HTTP_GET) return F("GET"); else if(_method & HTTP_GET) return F("GET");
@@ -981,6 +984,7 @@ const __FlashStringHelper *AsyncWebServerRequest::requestedConnTypeToString() co
default: return F("ERROR"); default: return F("ERROR");
} }
} }
#endif
bool AsyncWebServerRequest::isExpectedRequestedConnType(RequestedConnectionType erct1, RequestedConnectionType erct2, RequestedConnectionType erct3) { bool AsyncWebServerRequest::isExpectedRequestedConnType(RequestedConnectionType erct1, RequestedConnectionType erct2, RequestedConnectionType erct3) {
bool res = false; bool res = false;