WiFiESp library, server example - I don't 'get' how the while loop is working

This is the loop from the server example that services http requests:

void loop()
{
  // listen for incoming clients
  WiFiEspClient client = server.available();
  if (client) 
  {
    Serial.println("New client");
    // an http request ends with a blank line
    boolean currentLineIsBlank = true;
    while (client.connected()) 
    {
      if (client.available()) 
      {
        char c = client.read();
        Serial.write(c);
        // if you've gotten to the end of the line (received a newline
        // character) and the line is blank, the http request has ended,
        // so you can send a reply
        if (c == '\n' && currentLineIsBlank) 
        {
          Serial.println("Sending response");
          
          // end a standard http response header
          // use \r\n instead of many println statements to speedup data send
          client.print("HTTP/1.1 200 OK\r\nContent-Type: text/html\r\nConnection: close\r\n"  // the connection will be closed after completion of the response
            "Refresh: 20\r\n"        // refresh the page automatically every 20 sec
            "\r\n");
          client.print("<!DOCTYPE HTML>\r\n");
          client.print("<html>\r\n");
          client.print("<h1>Hello World!</h1>\r\n");
          client.print("Requests received: ");
          client.print(++reqCount);
          client.print("
\r\n");
          client.print("Analog input A0: ");
          client.print(analogRead(0));
          client.print("
\r\n");
          client.print("</html>\r\n");
          break;
        }
        if (c == '\n') 
        {
          // you're starting a new line
          currentLineIsBlank = true;
        }
        else if (c != '\r') 
        {
          // you've gotten a character on the current line
          currentLineIsBlank = false;
        }
      }
    }
    // give the web browser time to receive the data
    delay(10);

    // close the connection:
    client.stop();
    Serial.println("Client disconnected");
  }
}

I don’t understand why it won’t work if I separate the read and print parts of the loop something like this:

void loop()
{
  // listen for incoming clients
  WiFiEspClient client = server.available();
  if (client) 
  {
    Serial.println("New client");
    // an http request ends with a blank line
    boolean currentLineIsBlank = true;
    String strReq;
    
    while (client.connected()) 
    {
      if (client.available()) 
      {
        char c = client.read();
        strReq += (String(c));
        
        // if you've gotten to the end of the line (received a newline
        // character) and the line is blank, the http request has ended,
        // so you can send a reply
        if (c == '\n' && currentLineIsBlank) 
        {
          break;
        }
        if (c == '\n') 
        {
          // you're starting a new line
          currentLineIsBlank = true;
        }
        else if (c != '\r') 
        {
          // you've gotten a character on the current line
          currentLineIsBlank = false;
        }
      }
    }
    if (client.connected())
    {
      if (strReq == "GET / HTTP/1.1")
      {
        Serial.println("Sending response");
        
        // end a standard http response header
        // use \r\n instead of many println statements to speedup data send
        client.print("HTTP/1.1 200 OK\r\nContent-Type: text/html\r\nConnection: close\r\n"  // the connection will be closed after completion of the response
          "Refresh: 20\r\n"        // refresh the page automatically every 20 sec
          "\r\n");
        client.print("<!DOCTYPE HTML>\r\n");
        client.print("<html>\r\n");
        client.print("<h1>Hello World!</h1>\r\n");
        client.print("Requests received: ");
        client.print(++reqCount);
        client.print("
\r\n");
        client.print("Analog input A0: ");
        client.print(analogRead(0));
        client.print("
\r\n");
        client.print("</html>\r\n");
      }
      else if (strReq == "something else")
      {
      }
      }
    }
    // give the web browser time to receive the data
    delay(10);

    // close the connection:
    client.stop();
    Serial.println("Client disconnected");
  }
}

How is the ‘client’ interacting with that while loop such that my preferred code, just above, won’t work, i.e. the web browser just sits there waiting forever for the arduino client to send the http data.

boylesg:
This is the loop from the server example that services http requests:

void loop()

{
 // listen for incoming clients
 WiFiEspClient client = server.available();
 if (client)
 {
   Serial.println(“New client”);
   // an http request ends with a blank line
   boolean currentLineIsBlank = true;
   while (client.connected())
   {
     if (client.available())
     {
       char c = client.read();
       Serial.write(c);
       // if you’ve gotten to the end of the line (received a newline
       // character) and the line is blank, the http request has ended,
       // so you can send a reply
       if (c == ‘\n’ && currentLineIsBlank)
       {
         Serial.println(“Sending response”);
         
         // end a standard http response header
         // use \r\n instead of many println statements to speedup data send
         client.print(“HTTP/1.1 200 OK\r\nContent-Type: text/html\r\nConnection: close\r\n”  // the connection will be closed after completion of the response
           “Refresh: 20\r\n”        // refresh the page automatically every 20 sec
           “\r\n”);
         client.print("\r\n");
         client.print("\r\n");
         client.print(“

Hello World!

\r\n”);
         client.print(“Requests received: “);
         client.print(++reqCount);
         client.print(”
\r\n”);
         client.print(“Analog input A0: “);
         client.print(analogRead(0));
         client.print(”
\r\n”);
         client.print("\r\n");
         break;
       }
       if (c == ‘\n’)
       {
         // you’re starting a new line
         currentLineIsBlank = true;
       }
       else if (c != ‘\r’)
       {
         // you’ve gotten a character on the current line
         currentLineIsBlank = false;
       }
     }
   }
   // give the web browser time to receive the data
   delay(10);

// close the connection:
   client.stop();
   Serial.println(“Client disconnected”);
 }
}




I don't understand why it won't work if I separate the read and print parts of the loop something like this:



void loop()
{
 // listen for incoming clients
 WiFiEspClient client = server.available();
 if (client)
 {
   Serial.println(“New client”);
   // an http request ends with a blank line
   boolean currentLineIsBlank = true;
   String strReq;
   
   while (client.connected())
   {
     if (client.available())
     {
       char c = client.read();
       strReq += (String(c));
       
       // if you’ve gotten to the end of the line (received a newline
       // character) and the line is blank, the http request has ended,
       // so you can send a reply
       if (c == ‘\n’ && currentLineIsBlank)
       {
         break;
       }
       if (c == ‘\n’)
       {
         // you’re starting a new line
         currentLineIsBlank = true;
       }
       else if (c != ‘\r’)
       {
         // you’ve gotten a character on the current line
         currentLineIsBlank = false;
       }
     }
   }
   if (client.connected())
   {
     if (strReq == “GET / HTTP/1.1”)
     {
       Serial.println(“Sending response”);
       
       // end a standard http response header
       // use \r\n instead of many println statements to speedup data send
       client.print(“HTTP/1.1 200 OK\r\nContent-Type: text/html\r\nConnection: close\r\n”  // the connection will be closed after completion of the response
         “Refresh: 20\r\n”        // refresh the page automatically every 20 sec
         “\r\n”);
       client.print("\r\n");
       client.print("\r\n");
       client.print(“

Hello World!

\r\n”);
       client.print(“Requests received: “);
       client.print(++reqCount);
       client.print(”
\r\n”);
       client.print(“Analog input A0: “);
       client.print(analogRead(0));
       client.print(”
\r\n”);
       client.print("\r\n");
     }
     else if (strReq == “something else”)
     {
     }
     }
   }
   // give the web browser time to receive the data
   delay(10);

// close the connection:
   client.stop();
   Serial.println(“Client disconnected”);
 }
}



How is the 'client' interacting with that while loop such that my preferred code, just above, won't work, i.e. the web browser just sits there waiting forever for the arduino client to send the http data.

Ok,
Personally I hate the String() Class, It is inefficient, and tends to fillup RAM and cause overwrite problems.
Second, you code won’t work. After you append all of the incoming text to your String object, you do a comparison to a char*, and the comparison will never match because your String object also contains the EOL characters. Maybe if to use the SubString method it might have a chance.

This is from the String.subString() example:

 String stringOne = "Content-Type: text/html";

  // substring(index) looks for the substring from the index position to the end:
  if (stringOne.substring(19) == "html") {
   }

Chuck.

Originally I added all the chars to strHTMLReq but did nothing with it, i.e. that comparison was not there and I immediately started writing to the Wifi sever.

Regardless it seems to be something about my loop structure that hangs the web browser up.

boylesg:
Originally I added all the chars to strHTMLReq but did nothing with it, i.e. that comparison was not there and I immediately started writing to the Wifi sever.

Regardless it seems to be something about my loop structure that hangs the web browser up.

I modified your code to use a cstring instead of the String() object.

#define BUFLEN 100
char buf[BUFLEN+1]; // room for null at end.

void loop(){
// listen for incoming clients
WiFiEspClient client = server.available();
if (client){
  Serial.println("New client");
  // an http request ends with a blank line
  boolean currentLineIsBlank = true;
  byte a=0;
  while (client.connected()){
    if (client.available()){
      char c = client.read();
      if(a<BUFLEN){ // add to buffer
        buf[a++]=c; // store current character, increment pointer to next position
        }
        // if you've gotten to the end of the line (received a newline
        // character) and the line is blank, the http request has ended,
        // so you can send a reply
      if (c == '\n' && currentLineIsBlank){
        break;
        }
      if (c == '\n'){
          // you're starting a new line
        currentLineIsBlank = true;
        }
      else if (c != '\r') {
          // you've gotten a character on the current line
        currentLineIsBlank = false;
        }
      }
   }
 buf[a]= '\0'; // terminate cstring buffer.
 if (client.connected()){
   // if (strReq.substr(1) == "GET / HTTP/1.1"){
   if(strcmp("GET / HTTP/1.1",buf)==-14){ // buf contains "GET / HTTP/1.1".
      // the -14 also says that the character at position buf[14] has a larger lexical value than
      // the value at the end of "GET / HTTP/1.1", the null terminating the cstring. 
 Serial.println("Sending response");
 
 // end a standard http response header
 // use \r\n instead of many println statements to speedup data send
 client.print("HTTP/1.1 200 OK\r\nContent-Type: text/html\r\nConnection: close\r\n"  // the connection will be closed after completion of the response
 "Refresh: 20\r\n"        // refresh the page automatically every 20 sec
 "\r\n");
 client.print("<!DOCTYPE HTML>\r\n");
 client.print("<html>\r\n");
 client.print("<h1>Hello World!</h1>\r\n");
 client.print("Requests received: ");
 client.print(++reqCount);
 client.print("
\r\n");
 client.print("Analog input A0: ");
 client.print(analogRead(0));
 client.print("
\r\n");
 client.print("</html>\r\n"); // add blank line to terminat block
 }
//    else if (strReq == "something else"){}
    }
  }
    // give the web browser time to receive the data
delay(10);

    // close the connection:
client.stop();
Serial.println("Client disconnected");
}

See if it doesn’t work.

Chuck.