ESP32 WebServer Library – header()

Home / References / ESP32 Library / WebServer Library

Description

The header() method is used to retrieve HTTP request header values that have been previously collected by the ESP32 WebServer. This method allows you to access specific header information sent by clients in their HTTP requests. The headers must first be configured for collection using the collectHeaders() or collectAllHeaders() methods before they can be accessed with header(). This method is essential for implementing authentication, content negotiation, and other HTTP protocol features that rely on header information.



Syntax and Usage

The header() method can be used in two different ways:

  • By header name: server.header(headerName) – Retrieves the value of a specific header by its name (case-insensitive). Returns an empty string if the header doesn’t exist.
  • By header index: server.header(index) – Retrieves the value of a header at a specific index position. Useful for iterating through all collected headers.


Arguments

  • headerName (String) – The name of the HTTP header to retrieve. This is case-insensitive, so “Content-Type”, “content-type”, and “CONTENT-TYPE” will all match the same header.
  • index (int) – The zero-based index of the header to retrieve. Use with headers() method to determine the total number of available headers.


Return Value

The header() method returns a String containing the value of the requested header. If the header is not found (when using header name) or if the index is out of range, the method returns an empty string (“”).



Example Codes

Example 1: Accessing Headers by Name

This example demonstrates how to access specific headers by their names, which is the most common usage pattern for header processing.

How to use this example: Upload this code to your ESP32 and replace the WiFi credentials. After connecting, test with curl commands like: curl -H "User-Agent: MyCustomAgent" -H "Accept: application/json" http://ESP32_IP. The server will display the specific header values in a formatted response.

/*
 * Author: Avant Maker
 * Date: June 16, 2025
 * Version: 1.0
 * License: MIT 
 * 
 * Description: 
 * This example demonstrates how to access specific headers by their names,
 * which is the most common usage pattern for header processing.
 * 
 * How to use this example: 
 * Upload this code to your ESP32 and replace the WiFi credentials. 
 * After connecting, test with curl commands like: 
 * curl -H "User-Agent: MyCustomAgent" -H "Accept: application/json" http://ESP32_IP.
 * The server will display the specific header values in a formatted response.
 *
 * Code Source:
 * This example code is sourced from the Comprehensive Guide
 * to the ESP32 Arduino Core Library, accessible on AvantMaker.com.
 * For additional code examples and in-depth documentation related to
 * the ESP32 Arduino Core Library, please visit:
 *
 * https://avantmaker.com/home/all-about-esp32-arduino-core-library/
 *
 * AvantMaker.com, your premier destination for all things
 * DIY, AI, IoT, Smart Home, and STEM projects. We are dedicated
 * to empowering makers, learners, and enthusiasts with
 * the resources they need to bring their nnovative ideas to life.
 */
 
#include <WiFi.h>
#include <WebServer.h>

const char* ssid = "your_wifi_ssid";
const char* password = "your_wifi_password";

WebServer server(80);

// Headers we want to collect and access
const char* headerKeys[] = {"User-Agent", "Accept", "Content-Type", "Authorization"};
const size_t headerKeysCount = sizeof(headerKeys) / sizeof(headerKeys[0]);

void handleRoot() {
  String message = "ESP32 Header Information\n\n";
  
  // Access headers by name
  String userAgent = server.header("User-Agent");
  if (userAgent.length() > 0) {
    message += "Browser/Client: " + userAgent + "\n";
  } else {
    message += "User-Agent: Not provided\n";
  }
  
  String acceptHeader = server.header("Accept");
  if (acceptHeader.length() > 0) {
    message += "Accepts: " + acceptHeader + "\n";
  }
  
  String contentType = server.header("Content-Type");
  if (contentType.length() > 0) {
    message += "Content-Type: " + contentType + "\n";
  }
  
  String authorization = server.header("Authorization");
  if (authorization.length() > 0) {
    message += "Authorization: " + authorization + "\n";
  } else {
    message += "Authorization: Not provided\n";
  }
  
  message += "\nRequest Method: " + String((server.method() == HTTP_GET) ? "GET" : 
                                           (server.method() == HTTP_POST) ? "POST" : "OTHER");
  message += "\nURI: " + server.uri();
  
  server.send(200, "text/plain", message);
}

void setup() {
  Serial.begin(115200);
  
  // Connect to WiFi
  WiFi.begin(ssid, password);
  while (WiFi.status() != WL_CONNECTED) {
    delay(1000);
    Serial.println("Connecting to WiFi...");
  }
  
  // Configure headers to collect
  server.collectHeaders(headerKeys, headerKeysCount);
  
  // Set up route handler
  server.on("/", handleRoot);
  
  // Start server
  server.begin();
  Serial.println("HTTP server started");
  Serial.print("IP address: ");
  Serial.println(WiFi.localIP());
}

void loop() {
  server.handleClient();
}

Example 2: Iterating Through All Headers by Index

This example shows how to access all collected headers using index-based iteration, which is useful for debugging or when you need to process all available headers.

How to use this example: After uploading and connecting to WiFi, visit the ESP32’s IP address in your browser. The /headers endpoint will display all collected headers with their index positions. Try accessing from different browsers or with different HTTP clients to see how header sets vary.

/*
 * Author: Avant Maker
 * Date: June 16, 2025
 * Version: 1.0
 * License: MIT 
 * 
 * Description: 
 * This example shows how to access all collected headers using index-based
 * iteration, which is useful for debugging or when you need to process
 * all available headers.
 * 
 * How to use this example: 
 * After uploading and connecting to WiFi, visit the ESP32's IP address
 * in your browser. The /headers endpoint will display all collected headers
 * with their index positions. Try accessing from different browsers
 * or with different HTTP clients to see how header sets vary.
 *
 * Code Source:
 * This example code is sourced from the Comprehensive Guide
 * to the ESP32 Arduino Core Library, accessible on AvantMaker.com.
 * For additional code examples and in-depth documentation related to
 * the ESP32 Arduino Core Library, please visit:
 *
 * https://avantmaker.com/home/all-about-esp32-arduino-core-library/
 *
 * AvantMaker.com, your premier destination for all things
 * DIY, AI, IoT, Smart Home, and STEM projects. We are dedicated
 * to empowering makers, learners, and enthusiasts with
 * the resources they need to bring their nnovative ideas to life.
 */
 
#include <WiFi.h>
#include <WebServer.h>

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

const char* ssid = "your_wifi_ssid";
const char* password = "your_wifi_password";

WebServer server(80);

void handleHeaders() {
  String message = "All Collected Headers\n";
  message += "=====================\n\n";
  
  int headerCount = server.headers();
  message += "Total headers collected: " + String(headerCount) + "\n\n";
  
  // Iterate through headers by index
  for (int i = 0; i < headerCount; i++) {
    String headerName = server.headerName(i);
    String headerValue = server.header(i);
    
    message += "Header[" + String(i) + "]: ";
    message += headerName + " = " + headerValue + "\n";
  }
  
  if (headerCount == 0) {
    message += "No headers were collected.\n";
    message += "Make sure to call collectHeaders() or collectAllHeaders()!\n";
  }
  
  server.send(200, "text/plain", message);
}

void handleRoot() {
  String html = "<html><body>";
  html += "<h1>ESP32 Header Inspector</h1>";
  html += "<p><a href='/headers'>View All Headers</a></p>";
  html += "<p><a href='/specific'>View Specific Headers</a></p>";
  html += "</body></html>";
  
  server.send(200, "text/html", html);
}

void handleSpecific() {
  String message = "Specific Header Values\n";
  message += "======================\n\n";
  
  // Check for common headers
  if (server.hasHeader("Host")) {
    message += "Host: " + server.header("Host") + "\n";
  }
  
  if (server.hasHeader("Connection")) {
    message += "Connection: " + server.header("Connection") + "\n";
  }
  
  if (server.hasHeader("Cache-Control")) {
    message += "Cache-Control: " + server.header("Cache-Control") + "\n";
  }
  
  server.send(200, "text/plain", message);
}

void setup() {
  Serial.begin(115200);
  
  // Connect to WiFi
  WiFi.begin(ssid, password);
  while (WiFi.status() != WL_CONNECTED) {
    delay(1000);
    Serial.println("Connecting to WiFi...");
  }
  
  // Collect all headers for comprehensive inspection
  server.collectAllHeaders();
  
  // Set up route handlers
  server.on("/", handleRoot);
  server.on("/headers", handleHeaders);
  server.on("/specific", handleSpecific);
  
  // Start server
  server.begin();
  Serial.println("HTTP server started");
  Serial.print("IP address: ");
  Serial.println(WiFi.localIP());
}

void loop() {
  server.handleClient();
}

Example 3: Header-Based Content Negotiation and Authentication

This example demonstrates practical usage of headers for implementing content negotiation and basic authentication, showing real-world applications of the header() method.

How to use this example: Test different scenarios: curl -H "Accept: application/json" http://ESP32_IP/api for JSON response, curl -H "Accept: text/xml" http://ESP32_IP/api for XML response, and curl -H "Authorization: Bearer validtoken123" http://ESP32_IP/secure for authenticated access. Default responses are in plain text.

/*
 * Author: Avant Maker
 * Date: June 16, 2025
 * Version: 1.0
 * License: MIT 
 * 
 * Description: 
 * This example demonstrates practical usage of headers for implementing
 * content negotiation and basic authentication, showing real-world applications
 * of the header() method.
 * 
 * How to use this example: 
 * curl -H "Accept: application/json" http://ESP32_IP/api for JSON response,
 * curl -H "Accept: text/xml" http://ESP32_IP/api for XML response,
 * and curl -H "Authorization: Bearer validtoken123" http://ESP32_IP/secure
 * for authenticated access. Default responses are in plain text.
 *
 * Code Source:
 * This example code is sourced from the Comprehensive Guide
 * to the ESP32 Arduino Core Library, accessible on AvantMaker.com.
 * For additional code examples and in-depth documentation related to
 * the ESP32 Arduino Core Library, please visit:
 *
 * https://avantmaker.com/home/all-about-esp32-arduino-core-library/
 *
 * AvantMaker.com, your premier destination for all things
 * DIY, AI, IoT, Smart Home, and STEM projects. We are dedicated
 * to empowering makers, learners, and enthusiasts with
 * the resources they need to bring their nnovative ideas to life.
 */

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

const char* ssid = "your_wifi_ssid";
const char* password = "your_wifi_password";

WebServer server(80);

// Valid API token for demonstration
const String validToken = "validtoken123";

void handleAPI() {
  String acceptHeader = server.header("Accept");
  String response;
  String contentType;
  
  // Content negotiation based on Accept header
  if (acceptHeader.indexOf("application/json") != -1) {
    response = "{\"message\":\"Hello from AvantMaker ESP32 Example\",\"status\":\"success\",\"timestamp\":" + String(millis()) + "}";
    contentType = "application/json";
  } else if (acceptHeader.indexOf("text/xml") != -1 || acceptHeader.indexOf("application/xml") != -1) {
    response = "<?xml version=\"1.0\"?><response><message>Hello from ESP32</message><status>success</status><timestamp>" + String(millis()) + "</timestamp></response>";
    contentType = "application/xml";
  } else {
    response = "Hello from ESP32\nStatus: success\nTimestamp: " + String(millis());
    contentType = "text/plain";
  }
  
  server.send(200, contentType, response);
}

void handleSecure() {
  String authHeader = server.header("Authorization");
  
  if (authHeader.length() == 0) {
    server.send(401, "text/plain", "Authorization header required");
    return;
  }
  
  // Simple Bearer token authentication
  if (authHeader.startsWith("Bearer ")) {
    String token = authHeader.substring(7); // Remove "Bearer " prefix
    if (token == validToken) {
      String response = "Access granted!\n";
      response += "User-Agent: " + server.header("User-Agent") + "\n";
      response += "Client IP: " + server.client().remoteIP().toString() + "\n";
      response += "Request time: " + String(millis()) + " ms";
      
      server.send(200, "text/plain", response);
    } else {
      server.send(403, "text/plain", "Invalid token");
    }
  } else {
    server.send(400, "text/plain", "Invalid authorization format. Use 'Bearer <token>'");
  }
}

void handleRoot() {
  String userAgent = server.header("User-Agent");
  String html = "<html><body>";
  html += "<h1>ESP32 Advanced Header Processing</h1>";
  html += "<p>Your browser: " + userAgent + "</p>";
  html += "<h2>Available Endpoints:</h2>";
  html += "<ul>";
  html += "<li><a href='/api'>/api</a> - Content negotiation demo</li>";
  html += "<li>/secure - Authentication demo (requires Bearer token)</li>";
  html += "</ul>";
  html += "</body></html>";
  
  server.send(200, "text/html", html);
}

void setup() {
  Serial.begin(115200);
  
  // Connect to WiFi
  WiFi.begin(ssid, password);
  while (WiFi.status() != WL_CONNECTED) {
    delay(1000);
    Serial.println("Connecting to WiFi...");
  }
  
  // Collect headers needed for our functionality
  const char* requiredHeaders[] = {"Accept", "Authorization", "User-Agent", "Content-Type"};
  const size_t headerCount = sizeof(requiredHeaders) / sizeof(requiredHeaders[0]);
  
  server.collectHeaders(requiredHeaders, headerCount);
  
  // Set up route handlers
  server.on("/", handleRoot);
  server.on("/api", handleAPI);
  server.on("/secure", handleSecure);
  
  // Start server
  server.begin();
  Serial.println("HTTP server started");
  Serial.print("IP address: ");
  Serial.println(WiFi.localIP());
}

void loop() {
  server.handleClient();
}
error: Content is protected !!