1
votes

I am trying to control a LED from Thingspeak server by using the GSM module. The data received is successfully being printed on serial monitor(which is '1' as last updated) but when I am trying to assign that data to a variable so as to control the inbuilt LED of Arduino, nothing happens.

#include <SoftwareSerial.h>
SoftwareSerial SIM900A(10, 11);
void setup()
{
  pinMode(LED_BUILTIN, OUTPUT);
  SIM900A.begin(9600);
  Serial.begin(9600);
  while (!Serial)
    ;
  Serial.println("Arduino is ready");
  SIM900A.begin(9600);
  Serial.println("SIM900A started at 9600");
  delay(1000);
  Serial.println("Setup Complete");
}

void loop()
{
  SIM900A.println("AT");
  delay(1000);
  ShowSerialData();

  SIM900A.println("AT+CIPSHUT");
  delay(2000);
  ShowSerialData();

  SIM900A.println("AT+CIPMUX=0");
  delay(2000);
  ShowSerialData();

  SIM900A.println("AT+CGATT=1");
  delay(5000);

  SIM900A.println("AT+CSTT=\"INTERNET\",\"\",\"\"");
  delay(4000);

  SIM900A.println("AT+CIICR");
  delay(3000);
  ShowSerialData();

  SIM900A.println("AT+CIFSR");
  delay(5000);
  ShowSerialData();

  SIM900A.println("AT+CIPSTART=\"TCP\",\"184.106.153.149\",\"80\"");
  delay(4000);
  ShowSerialData();

  SIM900A.println("AT+CIPSEND");
  delay(4000);

  SIM900A.print("GET /channels/798173/fields/1/last");
  SIM900A.print("\r\n\x1A");
  ShowSerialData();

  char led = SIM900A.read();
  Serial.print(led);

  if (led == '1')
  {
    digitalWrite(LED_BUILTIN, HIGH);
  }

  else if (led == '0')
  {
    digitalWrite(LED_BUILTIN, LOW);
  }

  delay(8000);
}

void ShowSerialData()
{
  while (SIM900A.available() != 0)
    Serial.print(char(SIM900A.read()));
}

Last portion of the output from the serial monitor:

CONNECT OK
AT+CIPSEND

> ⸮GET /channels/798173/fields/1/last

SEND OK
1
3
You are receiving the data in variable led ?Saurabh P Bhandari
No, the output i.e. '1' is being printed from ShowSerialData(). If I remove it, no data is printed by Serial.print(led).Ankit Sharma
Ok, try commenting the ShowSerialData() function just before this char led = SIM900A.read();Saurabh P Bhandari
AT+CIPSEND > GET /channels/798173/fields/1/last SEND OKAnkit Sharma
This is the new output. (no data is printed)Ankit Sharma

3 Answers

1
votes

From what I have understood so far, in this snippet

SIM900A.print("GET /channels/798173/fields/1/last");  
SIM900A.print("\r\n\x1A");
ShowSerialData(); 

ShowSerialData() is printing the output which is '1'. Then immediately your are reading data into the variable led. Since, the actual data received is being printed already from ShowSerialData(), the next time you call SIM900A.read() will return either nothing or next set of data being sent by your module.

1
votes

As pointed out by @Saurabh P Bhandari, you cannot read the same data from the serial twice, thus you'd need to read the data in a variable in the first place if you wish to use it.

String getSerialData(){
      String buffer="";
      while (SIM900A.available() ){
        char c = SIM900A.read();
        buffer+=c;    
      }
      return buffer;
     }

Then you can use String led = getSerialData() to populate led with the buffer.
Here, you need to beware that the function getSerialData would return anything present on the buffer and would look something like:

GET /channels/798173/fields/1/last
SEND

HTTP RESPONSE

It appears that you're only interested in HTTP RESPONSE, thus you can update your conditionals to be

if(led.endsWith("1"))
...
else if(led.endsWith("0"))
1
votes

You are likely getting rate limited because you are hitting ThingSpeak servers too frequently. You can only update a channel once every 15s with a free account. Obviously, it makes no sense to ask for a value faster than it can be updated, i.e., once every 15s with a free account.

Consider putting some required delays in your code to ensure your device is not blacklisted for abuse of terms.