Quick explain of online tutorial line of code

Hi all,

I'm looking at this tutorial:

And I've moreorless got it working, except I seem to be getting an issue somewhere between the board and the thingspeak api - I can manually post into the url and it works, just the get command isn't working within the code.

This is the part it seems to be failing - can anyone explain what the Serial.find(">") is actually doing as I don't understand it. I'm not sure where that bracket would come from in the code??

//Use AT commands to send data
Serial.print("AT+CIPSEND=");
Serial.println(cmd.length());
** if(Serial.find(">")){**
//send through command to update values
Serial.print(cmd);
}else{
Serial.println("AT+CIPCLOSE");
}

if(Serial.find("OK")){
//success! Your most recent values should be online.
return true;
}else{
return false;
}
}

alphabeta279:
I'm not sure where that bracket would come from in the code??

The ESP-01 sends it, it's an AT command acknowledgement.

Hmm ok, scratching my head then - the API string is being generated as per the tutorial, it just doesn’t seem to return this “>” so it fails.

So this is the area I guess it’s failing:
cmd += “\r\n”;
Serial.println(cmd);
//Use AT commands to send data
Serial.print(“AT+CIPSEND=”);
Serial.println(cmd.length());
if (Serial.find(">")) {
//send through command to update values
Serial.print(cmd);
} else {
Serial.println(“AT+CIPCLOSE”);
}

Which in Serial Monitor is generating:
AT+CIPSEND=60
AT+CIPCLOSE

Any ideas how to debug this??

I think your problem happens earlier on in the code that you should have shown us, and didn’t. The symptoms suggest that you have failed to make a wifi connection.

#include<stdlib.h>
#include "DHT.h"

#define SSID ""//your network name
#define PASS ""//your network password
#define IP "" // thingspeak.com
#define DHTPIN 7     // what pin the DHT sensor is connected to
#define DHTTYPE DHT11   // Change to DHT22 if that's what you have
#define Baud_Rate 115200 //Another common value is 9600
#define GREEN_LED 3 //optional LED's for debugging
#define RED_LED 4 //optional LED's for debugging
#define DELAY_TIME 60000 //time in ms between posting data to ThingSpeak

//Can use a post also
String GET = "GET /update?key=N7BMROH65LC8OBH8&field1=";
String FIELD2 = "&field2=";

//if you want to add more fields this is how
//String FIELD3 = "&field3=";

bool updated;

DHT dht(DHTPIN, DHTTYPE);

//this runs once
void setup()
{
  Serial.begin(Baud_Rate);
  Serial.println("AT");
  
  delay(5000);
  
  if(Serial.find("OK")){
    //connect to your wifi netowork
    bool connected = connectWiFi();
    if(!connected){
      //failure, need to check your values and try again
      Error();
    }
  }else{
    Error();
  }
  
  //initalize DHT sensor
  dht.begin();
}

//this runs over and over
void loop(){
  float h = dht.readHumidity();
  // Read temperature as Fahrenheit (isFahrenheit = true)
  float f = dht.readTemperature(true);

  // Check if any reads failed and exit early (to try again).
  if (isnan(h) || isnan(f)) {
    LightRed();
    return;
  }
  
  //update ThingSpeak channel with new values
  updated = updateTemp(String(f), String(h));
  
  //if update succeeded light up green LED, else light up red LED
  if(updated){
    LightGreen();
  }else{
    LightRed();
  }
  
  //wait for delay time before attempting to post again
  delay(DELAY_TIME);
}

bool updateTemp(String tenmpF, String humid){
  //initialize your AT command string
  String cmd = "AT+CIPSTART=\"TCP\",\"";
  
  //add IP address and port
  cmd += IP;
  cmd += "\",80";
  
  //connect
  Serial.println(cmd);
  delay(2000);
  if(Serial.find("Error")){
    return false;
  }
  
  //build GET command, ThingSpeak takes Post or Get commands for updates, I use a Get
  cmd = GET;
  cmd += tenmpF;
  cmd += FIELD2;
  cmd += humid;
  
  //continue to add data here if you have more fields such as a light sensor
  //cmd += FIELD3;
  //cmd += <field 3 value>
  
  cmd += "\r\n";
  
  //Use AT commands to send data
  Serial.print("AT+CIPSEND=");
  Serial.println(cmd.length());
  if(Serial.find(">")){
    //send through command to update values
    Serial.print(cmd);
  }else{
    Serial.println("AT+CIPCLOSE");
  }
  
  if(Serial.find("OK")){
    //success! Your most recent values should be online.
    return true;
  }else{
    return false;
  }
}
 
boolean connectWiFi(){
  //set ESP8266 mode with AT commands
  Serial.println("AT+CWMODE=1");
  delay(2000);

  //build connection command
  String cmd="AT+CWJAP=\"";
  cmd+=SSID;
  cmd+="\",\"";
  cmd+=PASS;
  cmd+="\"";
  
  //connect to WiFi network and wait 5 seconds
  Serial.println(cmd);
  delay(5000);
  
  //if connected return true, else false
  if(Serial.find("OK")){
    return true;
  }else{
    return false;
  }
}

void LightGreen(){
  digitalWrite(RED_LED, LOW);
  digitalWrite(GREEN_LED, HIGH);  
}

void LightRed(){
  digitalWrite(GREEN_LED, LOW);
  digitalWrite(RED_LED, HIGH);
}

//if an error has occurred alternate green and red leds
void Error(){      
  while(true){      
    LightRed();      
    delay(2000);      
    LightGreen();
    delay(2000);
  }  }

Hmm pretty sure it gets that far - as have been logging throughout - full serial monitor code is printing out the wifi connection (ie my SSID/Pass etc) and progressing through.

I can paste the generated API string into thingspeak and it logs fine, so formatting appears ok

Full code is:

#include<stdlib.h>
#include "DHT.h"

#define SSID "<MY NETWORK NAME>"//your network name
#define PASS "<MY NETWORK PASS>"//your network password
#define IP "thingspeak.com" // thingspeak.com
#define DHTPIN 7     // what pin the DHT sensor is connected to
#define DHTTYPE DHT22   // Change to DHT22 if that's what you have
#define Baud_Rate 115200 //Another common value is 9600
#define GREEN_LED 3 //optional LED's for debugging
#define RED_LED 4 //optional LED's for debugging
#define DELAY_TIME 30000 //time in ms between posting data to ThingSpeak

//Can use a post also
String GET = "GET /update?key=<MY API STRING>&field1=";
String FIELD2 = "&field2=";

//if you want to add more fields this is how
//String FIELD3 = "&field3=";

bool updated;

DHT dht(DHTPIN, DHTTYPE);

//this runs once
void setup()
{
 Serial.begin(Baud_Rate);
 Serial.println("AT");

 delay(5000);
 if (Serial.find("OK")) {
   //connect to your wifi netowork
   bool connected = connectWiFi();
   if (!connected) {
     //failure, need to check your values and try again
     Error();
   }
 } else {
    Serial.println("Failed to connect to wifi");
   Error();
 }

 //initalize DHT sensor
 dht.begin();
}

//this runs over and over
void loop() {
 float h = dht.readHumidity();
 // Read temperature as Fahrenheit (isFahrenheit = true)
 float f = dht.readTemperature(true);

 // Check if any reads failed and exit early (to try again).
 if (isnan(h) || isnan(f)) {
   LightRed();
   return;
 }

 //update ThingSpeak channel with new values
 updated = updateTemp(String(f), String(h));

 //if update succeeded light up green LED, else light up red LED
 if (updated) {
   LightGreen();
 } else {
   LightRed();
 }

 //wait for delay time before attempting to post again
 delay(DELAY_TIME);
}

bool updateTemp(String tenmpF, String humid) {
 //initialize your AT command string
 String cmd = "AT+CIPSTART=\"TCP\",\"";

 //add IP address and port
 cmd += IP;
 cmd += "\",80";

 //connect
 Serial.println(cmd);
 delay(2000);
 if (Serial.find("Error")) {
   return false;
 }

 //build GET command, ThingSpeak takes Post or Get commands for updates, I use a Get
 cmd = GET;
 cmd += tenmpF;
 cmd += FIELD2;
 cmd += humid;

 //continue to add data here if you have more fields such as a light sensor
 //cmd += FIELD3;
 //cmd += <field 3 value>

 cmd += "\r\n";
 Serial.println(cmd);
 //Use AT commands to send data
 Serial.print("AT+CIPSEND=");
 Serial.println(cmd.length());
 if (Serial.find(">")) {
   //send through command to update values
   Serial.print(cmd);
 } else {
   Serial.println("AT+CIPCLOSE");
 }

 if (Serial.find("OK")) {
   //success! Your most recent values should be online.
   Serial.println("Data Sent!");
   return true;
 } else {
   Serial.println("Data Fail!");
   return false;
 }
}

boolean connectWiFi() {
 //set ESP8266 mode with AT commands
 Serial.println("AT+CWMODE=1");
 delay(2000);

 //build connection command
 String cmd = "AT+CWJAP=\"";
 cmd += SSID;
 cmd += "\",\"";
 cmd += PASS;
 cmd += "\"";

 //connect to WiFi network and wait 5 seconds
 Serial.println(cmd);
 delay(5000);

 //if connected return true, else false
 if (Serial.find("OK")) {
   return true;
 } else {
   return false;
 }
}

void LightGreen() {
 digitalWrite(RED_LED, LOW);
 digitalWrite(GREEN_LED, HIGH);
}

void LightRed() {
 digitalWrite(GREEN_LED, LOW);
 digitalWrite(RED_LED, HIGH);
}

//if an error has occurred alternate green and red leds
void Error() {
 while (true) {
   LightRed();
   delay(2000);
   LightGreen();
   delay(2000);
 }
}

Please go back and edit your post so that the code is placed inside code tags, to make it forum compatible. Also please post the actual serial debug message stream.

:confused: SORRY!! Slap taken! :wink:

I’ve pasted serial monitor code below (just redacted the sensitive bits)

AT+CWMODE=1
AT+CWJAP="<SSID>","<NETWORK PASS>"
AT+CIPSTART="TCP","api.thingspeak.com",80
GET /update?key=<API KEY>&field1=71.96&field2=35.90

AT+CIPSEND=60
AT+CIPCLOSE
Data Fail!

That can not be right - the second line in setup() just sends an "AT" with a newline. That does not show up in your output.

Yes, sorry that was cut off - had to reset because I was forgetting to disconnect the wires in the serial ports 1 & 2.

I don't think your configuration is useful for debugging - you can't see the responses from the ESP.

Yes, complete copy and paste from the tutorial - agree it's tricky to interpret, hence I'm asking!

Any suggestions how to view the responses from the ESP? Should I be printing out the responses at certain points?