Hello everybody, I am working with a SIM900A GSM module interfaced to Arduino MEGA(2560). I am sending an HTTP GET request to a server using AT commands, and storing the data retrieved by HTTPREAD in a String buffer. However, the complete data is not read by HTTPREAD (only the first 34 bytes are read and stored in the buffer). I tried increasing delay after HTTPACTION, but that didn't help. Hoping to find a solution here. The AT commands sent and the corresponding responses received are as follows:
AT+CREG?
+CREG: 0,1
OK
AT+SAPBR=1,1
OK
AT+HTTPINIT
OK
AT+HTTPPARA="URL","http://****"
OK
AT+HTTPPARA="CID",1
OK
AT+HTTPACTION=0
OK
+HTTPACTION:0,200,37
AT+HTTPREAD
AT+HTTPTERM
+HTTPREAD:37
Unnamed Road, Karnataka 570008, In // Only the initial 34 bytes are read and stored in the buffer
AT+CMGF=1
AT+CMGS="******"
As you can see, 37 bytes were received after HTTPACTION but only 34 bytes are read by HTTP read. The code snippet is as follows:
Serial.println("AT+HTTPREAD");
delay(200);
// This may be emptying the serial buffer before all the characters have arrived.
while(Serial.available()>0)
buf+=(char)Serial.read();
It really shouldn't need a delay. You should be waiting for all the characters to arrive.
edit: I presume buf is a String data type. The String type has never failed to disappoint me.
SurferTim:
Varying the delay isn't all there is to it.
Serial.println("AT+HTTPREAD");
delay(200);
// This may be emptying the serial buffer before all the characters have arrived.
while(Serial.available()>0)
buf+=(char)Serial.read();
It really shouldn't need a delay. You should be waiting for all the characters to arrive.
edit: I presume buf is a String data type. The String type has never failed to disappoint me.
SurferTim:
Varying the delay isn't all there is to it.
Serial.println("AT+HTTPREAD");
delay(200);
// This may be emptying the serial buffer before all the characters have arrived.
while(Serial.available()>0)
buf+=(char)Serial.read();
It really shouldn't need a delay. You should be waiting for all the characters to arrive.
edit: I presume buf is a String data type. The String type has never failed to disappoint me.
Yeah, buf is a String data type.
So what changes should I make to get all characters into the buffer?
The Serial buffer size was a restriction. The buffer size is of 64 bytes which resulted in just the initial 64 bytes being read, of which first 30 bytes was the response to the HTTPREAD command and the next 34 bytes was the actual data.
The Serial buffer size was a restriction. The buffer size is of 64 bytes which resulted in just the initial 64 bytes being read, of which first 30 bytes was the response to the HTTPREAD command and the next 34 bytes was the actual data.
No. The problem was you weren't reading from the serial port often enough. I've uploaded and downloaded thousands of characters through the serial port with that size buffer.
I had this same issue, and found a way to handle it on both a SIM800L (hackerboxes.com#0016) and SIM900 (SeedStudio GSM shield).
I call the SIM module "serialSIMx00" in the code below, as it applies to both module types.
The SIM module has a very small HTTP response-stream buffer. After that buffer fills up, you have to -
A) empty it (as you already are, in your code) and
B) ask the SIM module to go fetch the next buffer's-worth of data. (This is what appears to be missing in your code!)
You can do "B)" by adding parameters to your "AT+HTTPREAD" command.
Here is an example of how to do this -
int totCharsRead=0; // # chars read from the HTTP results stream - Absolute total
int newCharsRead=0; // # chars read in each loop, below (continually added to totCharsRead)
char outStr[199+1]; // Small buffer used to create commands to write out to the SIM device
//Turn off command-echo and response codes
serialSIMx00.println("ATE0Q1");
delay(1000);
readData(); // A user-provided function (SEE NOTES, BELOW)
totCharsRead = 0; // We haven't read anything from the HTTP response yet
newCharsRead = 1; // Set to non-zero to make the following loop work properly
// Ask the SIM device to retrieve "chunks" of data from the HTTP response (if any)
while (newCharsRead)
{
// Read next "chunk" of data from the HTTP response
sprintf(outStr, "AT+HTTPREAD=%d,64", totCharsRead); // NOTE: 64-byte device buffer is default
serialSIMx00.println(outStr);
// Give the SIM device a chance to go collect the HTTP data from the TCP stream
delay(15000); // 15 seconds. 10-20 seconds is probably long enough...
newCharsRead = readData(); // This function should read/clear the device buffer, and then return
// the number of characters read from the HTTP response stream.
// (NOTE: DO NOT count characters that are part of the SIM device
// responses - e.g. any "+HTTPREAD: 64" type messages.)
totCharsRead += newCharsRead; // Adjust the starting point of the next read-chunk request
// to be right after what we just read in the current loop
}
//Turn command-echo and response codes back on
serialSIMx00.println("ATE1Q0");
delay(1000);
readData();
====================================
I've gotten this code to work on both SIM800L and SIM900 modules.