[SOLVED] Sim800l 400 bad request

@fionasoon, I have found out a couple of things that I would like to point out that might help you correct this 400 Bad request error response code:

  1. Since you opened a TCP socket and connected to industrial.api.ubidots.com , keep the host the same when making the actual HTTP request, that is, instead of things.ubidots.com , use industrial.api.ubidots.com , so your line should look like mySerial.println("Host: industrial.api.ubidots.com \n");
  2. You declared the variable IDs variables, but never assigned them a value, that is, they are empty throughout the whole code, so the request you are making to Ubidots is rather inconclusive and hence, the API can’t resolve where to put that value in.

Last but not least, I’d recommend that instead of using the /variables endpoint ( /api/v1.6/variables/<variable-id> ), you could use the /devices endpoint ( /api/v1.6/devices/<device-label> ) for the specific Device you are aiming to send data to (remember that if the device doesn’t exist beforehand, Ubidots will create it automatically). The reason for this is that the variables endpoint requires variable IDs, whereas the devices endpoint requires device labels, and labels more friendly to handle than variable IDs.
Should you decide to follow this recommendation. you would have to declare the device label, and then just build a JSON formatted to send multiple variable values in one request. Please view our API Docs for additional information on that.

Best regards,
-Sebastián

Hi, Sebastian, thanks for your help. I have changed the codes according to the API Docs as you have advised.

However, I am still unable to see the device or variables in Ubidots although it is stated Send OK and Close OK. May i know how can i get it work? Thank you.

//Response from serial monitor

AT

OK
AT+CPIN?

+CPIN: READY

OK
AT+CREG?

+CREG: 0,5
AT+CSTT="my3g.com"

OK
AT+CIICR

OK
AT+CIFSR

21.14.57.205
AT+CIPSPRT=0

OK
AT+CIPSTART="tcp","industrial.api.ubidots.com","80"

OK

CONAT+CIPSEND
POST /api/v1.6/sim800l/values HTTP/1.1
Host:industrial.api.ubidots.com
X-Auth-Token: BBFF-BBFF-xxxxxxxxxxxxxxxxxxxxxxxxxxxx
Content-Type: application/json
Content-Length: 54
{"variable":1, "value":38}, {"variable":2, "value":28}


SEND OK

AT+CIPCLOSE

CLOSE OK

//The codes used are as follow:-

#include <SoftwareSerial.h>
#include <String.h>

//SoftwareSerial mySerial(7, 8);
SoftwareSerial mySerial(3, 2); //SIM800L Tx & Rx is connected to Arduino #3 & #2

int value1;
int value2;
int value3;


String token = "BBFF-BBFF-xxxxxxxxxxxxxxxxxxxxxxxxxxxxx";

String idvariable1 = "1";
String idvariable2 = "2";
String idvariable3 = "3";


void setup()
{

mySerial.begin(9600);
Serial.begin(9600);
delay(10000);
}

void loop()
{

value1 = random(36, 39);
value2 = random(24, 30);
value3 = random(65, 75);


comunication_start();

send_value(value1, idvariable1, value2, idvariable2);
//comunication_end();

if (mySerial.available())
Serial.write(mySerial.read());

}

void comunication_start()
{

  mySerial.println("AT");
  delay(1000);
 
  mySerial.println("AT+CPIN?");
  delay(1000);
 
  mySerial.println("AT+CREG?");
  delay(1000);
 
  mySerial.println("AT+CGATT?");
  delay(1000);
 
  mySerial.println("AT+CIPSHUT");
  delay(1000);
 
  mySerial.println("AT+CIPSTATUS");
  delay(2000);
 
  mySerial.println("AT+CIPMUX=0");
  delay(2000);
 
  ShowSerialData();
 
  mySerial.println("AT+CSTT=\"my3g.com\"");//start task and setting the APN,
  delay(1000);
 
  ShowSerialData();
 
  mySerial.println("AT+CIICR");//bring up wireless connection
  delay(3000);
 
  ShowSerialData();

  mySerial.println("AT+CIFSR"); // Get IP adress
  delay(2000);

  ShowSerialData();

  mySerial.println("AT+CIPSPRT=0");
  delay(3000);
  ShowSerialData();
  mySerial.println("AT+CIPSTART=\"tcp\",\"industrial.api.ubidots.com\",\"80\"");
  delay(6000);
  ShowSerialData();
 
}

void send_value(int value1, String idvariable1, int value2, String idvariable2)
{
int num;
String le;
String var;


var="{\"variable\":" + idvariable1 + ", \"value\":" + value1 + "}, {\"variable\":" + idvariable2 + ", \"value\":" + value2 + "}";
num=var.length();
le=String(num);

mySerial.println("AT+CIPSEND"); //begin send data to remote server
delay(3000);
ShowSerialData();
mySerial.print("POST /api/v1.6/sim800l");
delay(100);
ShowSerialData();
mySerial.println("/values HTTP/1.1");
delay(100);
ShowSerialData();
mySerial.println("Host:industrial.api.ubidots.com");
delay(100);
ShowSerialData();
mySerial.print("X-Auth-Token: ");
delay(100);
ShowSerialData();
mySerial.println(token);
delay(100);
ShowSerialData();
mySerial.println("Content-Type: application/json");
delay(100);
ShowSerialData();
mySerial.println("Content-Length: "+le);
delay(100);
ShowSerialData();
mySerial.println(var);// payload
delay(100);
ShowSerialData();
mySerial.println((char)26);
delay(7000);
mySerial.println();
ShowSerialData();
mySerial.println("AT+CIPCLOSE"); //close the communication
delay(1000);
ShowSerialData();


}

void comunication_end()
{
mySerial.println("AT+CIPCLOSE"); // Close the connection
delay(1000);
ShowSerialData();
}

// This function is to show the response in your serial terminal

void ShowSerialData()
{
while(mySerial.available()!=0)
Serial.write(mySerial.read());


}

@fionasoon, a couple more things to change and you should be all set to send data successfully to Ubidots.

  1. The POST should be pointed towards /api/v1.6/devices/sim800l , assuming that you want your device to be labelled “sim800l”, note that you may place whatever label you would like to have your device assigned (any alphanumeric string without spaces or periods, for example “my new device” should go as “my-new-device”) .

  2. Your JSON isn’t following the expected format. The correct would be {"variable-label": 38}, where “variable-label” is an alphanumeric string, with no white-spaces and optional dashes ("-") and underscores ("_"). With this, instead of {"variable": 1,"value": 38} you’d have {"1": 38}.
    Here “1” would be taken as the variable-label

  3. Note that Ubidots API allows sending multiple variables in a single request so instead of {"1":38},{"2":28}, do {"1":38,"2":28}
    Here, “1” and “2” would be considered as the variable labels.

Best regards,
-Sebastián

Hi, Sebastian,

Thanks for your patience.
I did as you have suggested according to the JASON format. I changed the data format to {“Temperature” : 34, “Pressure” : 25}. But, I am still not able to post to the ubidots

The response from serial monitor is:-

AT

OK
AT+CPIN?

+CPIN: READY

OK
AT+CREG?

+CREG: 0,5
AT+CSTT="my3g.com"

OK
AT+CIICR

OK
AT+CIFSR

21.45.101.138
AT+CIPSPRT=0

OK
AT+CIPSTART="tcp","industrial.api.ubidots.com","80"

OK

CONAT+CIPSEND
POST /api/v1.6/sim800l/ HTTP/1.1
Host:industrial.api.ubidots.com
X-Auth-Token: BBFF-BBFF-Gxxxxxxxx
Content-Type: application/json
Content-Length: 32
{"Temperature":36,"Pressure":26}


SEND OK
AT+CIPCLOSE

CLOSE OK

The codes used:-

#include <SoftwareSerial.h>
#include <String.h>

//SoftwareSerial mySerial(7, 8);
SoftwareSerial mySerial(3, 2); //SIM800L Tx & Rx is connected to Arduino #3 & #2

int value1;
int value2;
int value3;


String token = "BBFF-BBFF-Gxxxxxxxxxxxxxxxxxxxxxxxxx";

void setup()
{

mySerial.begin(9600);
Serial.begin(9600);
delay(10000);
}

void loop()
{

value1 = random(36, 39);
value2 = random(24, 30);
value3 = random(65, 75);


comunication_start();

send_value(value1, value2);
//comunication_end();

if (mySerial.available())
Serial.write(mySerial.read());

}

void comunication_start()
{

  mySerial.println("AT");
  delay(1000);
 
  mySerial.println("AT+CPIN?");
  delay(1000);
 
  mySerial.println("AT+CREG?");
  delay(1000);
 
  mySerial.println("AT+CGATT?");
  delay(1000);
 
  mySerial.println("AT+CIPSHUT");
  delay(1000);
 
  mySerial.println("AT+CIPSTATUS");
  delay(2000);
 
  mySerial.println("AT+CIPMUX=0");
  delay(2000);
   ShowSerialData();
 
  mySerial.println("AT+CSTT=\"my3g.com\"");//start task and setting the APN,
  delay(1000);
   ShowSerialData();
 
  mySerial.println("AT+CIICR");//bring up wireless connection
  delay(3000);
   ShowSerialData();

  mySerial.println("AT+CIFSR"); // Get IP adress
  delay(2000);
  ShowSerialData();

  mySerial.println("AT+CIPSPRT=0");
  delay(3000);
  ShowSerialData();
  
  mySerial.println("AT+CIPSTART=\"tcp\",\"industrial.api.ubidots.com\",\"80\"");
  delay(7000);
  ShowSerialData();
 
}

//void send_value(int value1, String idvariable1, int value2, String idvariable2)
void send_value(int value1, int value2)
{
int num;
String le;
String var;


var="{\"Temperature\":" + String (value1) +",\"Pressure\":" + String (value2)+"}";

num=var.length();
le=String(num);



mySerial.println("AT+CIPSEND"); //begin send data to remote server
delay(5000);
ShowSerialData();

mySerial.print("POST /api/v1.6/sim800l");
delay(1000);
ShowSerialData();
mySerial.println("/ HTTP/1.1");
delay(1000);
ShowSerialData();
mySerial.println("Host:industrial.api.ubidots.com");
delay(1000);
ShowSerialData();
mySerial.print("X-Auth-Token: ");
delay(1000);
ShowSerialData();
mySerial.println(token);
delay(1000);
ShowSerialData();
mySerial.println("Content-Type: application/json");
delay(1000);
ShowSerialData();
mySerial.println("Content-Length: "+le);
delay(1000);
ShowSerialData();
mySerial.println(var);// Begin send payload to remote servr
delay(5000);
ShowSerialData();

mySerial.println((char)26);
delay(7000);
ShowSerialData();

mySerial.println("AT+CIPCLOSE"); //close the communication
delay(1000);
ShowSerialData();


}

void comunication_end()
{
mySerial.println("AT+CIPCLOSE"); // Close the connection
delay(1000);
ShowSerialData();
}

// This function is to show the response in your serial terminal

void ShowSerialData()
{
while(mySerial.available()!=0)
Serial.write(mySerial.read());


}

@fionasoon, I see that you got the JSON correct, that’s great.

I also see that your Token has the “BBFF-” twice, so it’s most likely a copy-paste error, as they usually have only one set of BBFF

Hi, Sebastian. I was really careless. Thanks. I have corrected the token and I am still not able to connect to the ubidots. I really hope to get it work. Please help ya…

The latest code:

#include <SoftwareSerial.h>
#include <String.h>

//SoftwareSerial mySerial(7, 8);
SoftwareSerial mySerial(3, 2); //SIM800L Tx & Rx is connected to Arduino #3 & #2

int value1;
int value2;
int value3;


String token = "BBFF-GvHtRUwUsH7587lLf3ylaWxv1uosxl";

void setup()
{

mySerial.begin(9600);
Serial.begin(9600);
delay(10000);
}

void loop()
{

value1 = random(36, 39);
value2 = random(24, 30);
value3 = random(65, 75);


comunication_start();
send_value(value1);



//comunication_end();

if (mySerial.available())
Serial.write(mySerial.read());

}

void comunication_start()
{

  mySerial.println("AT");
  delay(1000);
 
  mySerial.println("AT+CPIN?");
  delay(1000);
 
  mySerial.println("AT+CREG?");
  delay(1000);
 
  mySerial.println("AT+CGATT?");
  delay(1000);
 
  mySerial.println("AT+CIPSHUT");
  delay(1000);
 
  mySerial.println("AT+CIPSTATUS");
  delay(2000);
 
  mySerial.println("AT+CIPMUX=0");
  delay(2000);
   ShowSerialData();
 
  mySerial.println("AT+CSTT=\"my3g.com\"");//start task and setting the APN,
  delay(1000);
   ShowSerialData();
 
  mySerial.println("AT+CIICR");//bring up wireless connection
  delay(3000);
   ShowSerialData();

  mySerial.println("AT+CIFSR"); // Get IP adress
  delay(2000);
  ShowSerialData();

  mySerial.println("AT+CIPSPRT=0");
  delay(3000);
  ShowSerialData();
  
  mySerial.println("AT+CIPSTART=\"tcp\",\"industrial.api.ubidots.com\",\"80\"");
  delay(7000);
  ShowSerialData();
 
}

void send_value(int value1)
{
int num;
String le;
String var;

var="{\"Temperature\":"+ String(value1) + "}";
num=var.length();
le=String(num);



mySerial.println("AT+CIPSEND"); //begin send data to remote server
delay(5000);
ShowSerialData();

mySerial.print("POST /api/v1.6/sim800l");
delay(1000);
ShowSerialData();
mySerial.println("/ HTTP/1.1");
delay(1000);
ShowSerialData();
mySerial.println("Host:industrial.api.ubidots.com");
delay(1000);
ShowSerialData();
mySerial.println("User-Agent:arduino/1.0");
delay(1000);
ShowSerialData();
mySerial.print("X-Auth-Token: ");
delay(1000);
ShowSerialData();
mySerial.println(token);
delay(1000);
ShowSerialData();
mySerial.println("Content-Type: application/json");
delay(1000);
ShowSerialData();
mySerial.println("Content-Length: "+le);
delay(1000);
ShowSerialData();
mySerial.println(var);// Begin send payload to remote servr
delay(5000);
ShowSerialData();

mySerial.println((char)26);
delay(7000);
ShowSerialData();

mySerial.println("AT+CIPCLOSE"); //close the communication
delay(1000);
ShowSerialData();


}

void comunication_end()
{
mySerial.println("AT+CIPCLOSE"); // Close the connection
delay(1000);
ShowSerialData();
}

// This function is to show the response in your serial terminal

void ShowSerialData()
{
  delay(500);
while(mySerial.available()!=0)
Serial.write(mySerial.read());


}

Hi, Sebastian,

I was thinking if i should use the TCP/UDP protocol? https://ubidots.com/docs/hw/#send-data
What is your suggestion?

Thanks.

You are posting data to a wrong topic. Following our docs, you should make a POST request to:

api/v1.6/devices/{DEVICE_LABEL}

and you are posting to

api/v1.6/{DEVICE_LABEL}

Just add devices to your path and try again.

All the best

Thanks jotathebest. I added api/v1.6/devices/sim900 and i still can’t get the posting in ubidots. This really puzzles me…

The response from serial monitor:

AT

OK
AT+CPIN?

+CPIN: READY

OK
AT+CREG?

+CREG: 0,AT+CSTT=“my3g.com”

OK
AT+CIICR

OK
AT+CIFSR

21.154.62.125
AT+CIPSPRT=0

OK
AT+CIPSTART=“TCP”,“industrial.api.ubidots.com”,“80”

OK

COAT+CIPSEND
POST /api/v1.6/devices/sim900 HTTP/1.1
Host:industrial.api.ubidots.com
User-Agent:arduino/1.0
X-Auth-Token: BBFF-GvHtRUwUsH7587lLf3ylaWxv1uosxl
Content-Type:application/json
Content-Length: 18
{“Temperature”:36}

SEND OK
AT+CIPCLOSE

CLOSE OK

The code used:-

#include <SoftwareSerial.h>
#include <String.h>

SoftwareSerial mySerial(7, 8);
//SoftwareSerial mySerial(3, 2); //SIM900 Tx & Rx is connected to Arduino #3 & #2

int value1;
int value2;
int value3;

int num;
String le;
String var;
String token = "BBFF-GvHtRUwUsH7587lLf3ylaWxv1uosxl";



void setup()
{

mySerial.begin(9600);
Serial.begin(9600);
delay(10000);
}

void loop()
{


value1 = random(36, 39);
value2 = random(24, 30);
value3 = random(65, 75);


var="{\"Temperature\":"+ String(value1) + "}";
num=var.length();
le=String(num);

comunication_start();
send_value();
//comunication_end();

if (mySerial.available())
Serial.write(mySerial.read());

}

void comunication_start()
{

 
  mySerial.println("AT");
  delay(1000);
 
  mySerial.println("AT+CPIN?");
  delay(1000);
 
  mySerial.println("AT+CREG?");
  delay(1000);
 
  mySerial.println("AT+CGATT?");
  delay(1000);
 
  mySerial.println("AT+CIPSHUT");
  delay(1000);
 
  mySerial.println("AT+CIPSTATUS");
  delay(2000);
 
  mySerial.println("AT+CIPMUX=0");
  delay(2000);
 
  ShowSerialData();
 
  mySerial.println("AT+CSTT=\"my3g.com\"");//start task and setting the APN,
  delay(1000);
 
  ShowSerialData();
 
  mySerial.println("AT+CIICR");//bring up wireless connection
  delay(2000);
 
  ShowSerialData();
 
  mySerial.println("AT+CIFSR");//get local IP adress
  delay(2000);
 
  ShowSerialData();
 
  mySerial.println("AT+CIPSPRT=0");
  delay(3000);
  ShowSerialData();
  
  mySerial.println("AT+CIPSTART=\"TCP\",\"industrial.api.ubidots.com\",\"80\"");
  delay(8000);
  ShowSerialData();
 
}


void send_value()
{

mySerial.println("AT+CIPSEND"); //begin send data to remote server
delay(3000);
ShowSerialData();

mySerial.print("POST /api/v1.6/devices");
delay(1000);
ShowSerialData();
mySerial.println("/sim900 HTTP/1.1");
delay(1000);
ShowSerialData();
mySerial.println("Host:industrial.api.ubidots.com");
delay(1000);
ShowSerialData();
mySerial.println("User-Agent:arduino/1.0");
delay(1000);
ShowSerialData();
mySerial.print("X-Auth-Token: ");
delay(1000);
ShowSerialData();
mySerial.println(token);
delay(1000);
ShowSerialData();
mySerial.println("Content-Type:application/json");
delay(1000);
ShowSerialData();
mySerial.println("Content-Length: "+le);
delay(1000);
ShowSerialData();
mySerial.println(var);// Begin send payload to remote servr
delay(5000);
ShowSerialData();

mySerial.println((char)26);
delay(7000);
ShowSerialData();

mySerial.println("AT+CIPCLOSE"); //close the communication
delay(1000);
ShowSerialData();


}

void comunication_end()
{
mySerial.println("AT+CIPCLOSE"); // Close the connection
delay(1000);
ShowSerialData();
}

// This function is to show the response in your serial terminal

void ShowSerialData()
{
  delay(500);
while(mySerial.available()!=0)
Serial.write(mySerial.read());


}

please read closely my comment

Your actual path does not look like the one that I have just specified to you previously

image

You can find here the expected HTTP request, make sure that you are creating it properly. It should look like the one below:

POST /api/v1.6/devices/{DEVICE_LABEL} HTTP/1.1<CR><LN>
Host: {Host}<CR><LN>
User-Agent: {USER_AGENT}<CR><LN>
X-Auth-Token: {TOKEN}<CR><LN>
Content-Type: application/json<CR><LN>
Content-Length: {PAYLOAD_LENGTH}<CR><LN><CR><LN>
{PAYLOAD}
<CR><LN>

Additionally, there is not need to read the server answer in every step, you must send the whole request and after that to read the response coming from the Ubidots side.

image

All the best

Thanks Jotathebest. I have tried with and without the delay and ShowSerialData().

Without delay and ShowSerialData(), it gives error. With the delay, the send and close are ok.
Both can’t post to ubidots. Headache.

This is what i put in the structure requirement as suggested:-

void send_value()
{

mySerial.println(“AT+CIPSEND”); //begin send data to remote server
mySerial.print(“POST /api/v1.6/devices/SIM900/Temperature”);
mySerial.println("/ HTTP/1.1");
mySerial.println(“Host:industrial.api.ubidots.com”);
mySerial.println(“User-Agent:arduino/1.0”);
mySerial.print("X-Auth-Token: ");
mySerial.println(token);
mySerial.println(“Content-Type:application/json”);
mySerial.println("Content-Length: "+le);
mySerial.println(var);
mySerial.println();
mySerial.println((char)26);
delay(7000);
ShowSerialData();
mySerial.println(“AT+CIPCLOSE”); //close the communication
ShowSerialData();

}

The output looks like this:-

AT

OK
AT+CPIN?

+CPIN: READY

OK
AT+CREG?

+CREG: 0,AT+CSTT=“my3g.com”

OK
AT+CIICR

OK
AT+CIFSR

21.6.176.232
AT+CIPSPRT=0

OK
AT+CIPSTART=“TCP”,“industrial.api.ubidots.com”,“80”

OK

COAT+CIPSEND
POST /api/v1.6/devices/SIM900/Temperature/ HTTP/1.1AT+CIPCLOSE

Hello @fionasoon, after thoroughly inspecting your code again, I’ve found out that there was (An empty new line) after the line:

mySerial.println("Content-Length: "+le);

We’ve added a mySerial.println(""); to create the missing new line.

So please upload the following code, to see if it works now

#include <String.h>
SoftwareSerial mySerial(7, 8);
//SoftwareSerial mySerial(3, 2); //SIM900 Tx & Rx is connected to Arduino #3 & #2
int value1;
int value2;
int value3;
int num;
String le;
String var;
String token = "BBFF-xxxxxxxxxxxxxxx";
void setup()
{
    mySerial.begin(9600);
    Serial.begin(9600);
    delay(10000);
}
void loop()
{
    value1 = random(36, 39);
    value2 = random(24, 30);
    value3 = random(65, 75);
    var = "{\"temperature\":" + String(value1) + "}";
    num = var.length();
    le = String(num);
    comunication_start();
    send_value();
    //comunication_end();
    if (mySerial.available())
        Serial.write(mySerial.read());
}
void comunication_start()
{
    mySerial.println("AT");
    delay(1000);
    mySerial.println("AT+CPIN?");
    delay(1000);
    mySerial.println("AT+CREG?");
    delay(1000);
    mySerial.println("AT+CGATT?");
    delay(1000);
    mySerial.println("AT+CIPSHUT");
    delay(1000);
    mySerial.println("AT+CIPSTATUS");
    delay(2000);
    mySerial.println("AT+CIPMUX=0");
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CSTT=\"my3g.com\""); //start task and setting the APN,
    delay(1000);
    ShowSerialData();
    mySerial.println("AT+CIICR"); //bring up wireless connection
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CIFSR"); //get local IP adress
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CIPSPRT=0");
    delay(3000);
    ShowSerialData();
    mySerial.println("AT+CIPSTART=\"TCP\",\"industrial.api.ubidots.com\",\"80\"");
    delay(8000);
    ShowSerialData();
}
void send_value()
{
    mySerial.println("AT+CIPSEND"); //begin send data to remote server
    delay(3000);
    mySerial.print("POST /api/v1.6/devices/sim900 HTTP/1.1");
    mySerial.println("Host:industrial.api.ubidots.com");
    mySerial.println("User-Agent:arduino65437823/1.0");
    mySerial.print("X-Auth-Token: ");
    mySerial.println(token);
    mySerial.println("Content-Type:application/json");
    mySerial.println("Content-Length: " + le);
    mySerial.println("");
    mySerial.println(var); // Begin send payload to remote servr
    mySerial.println((char)26);
    delay(3000);
    ShowSerialData();
    mySerial.println("AT+CIPCLOSE"); //close the communication
    delay(1000);
}
void comunication_end()
{
    mySerial.println("AT+CIPCLOSE"); // Close the connection
    delay(1000);
    ShowSerialData();
}
// This function is to show the response in your serial terminal
void ShowSerialData()
{
    while (mySerial.available() != 0)
        Serial.write(mySerial.read());
}

Hi, @Sebastian, I appreciate your help in checking through the codes. I have copied and paste you codes in to arduino. It didn’t give error but it didn’t post to ubidots still.

I have also tried to put CR LN after the send payload as below. It didn’t work also.
mySerial.println(var); // Begin send payload to remote server
mySerial.println("");

This is the output from the serial monitor:-
AT

OK
AT+CPIN?

+CPIN: READY

OAT+CSTT=“my3g.com”

OK
AT+CIICR

OK
AT+CIFSR

22.3.211.246
AT+CIPSPRT=0

OK
AT+CIPSTART=“TCP”,“industrial.api.ubidots.com”,“80”

OK

COAT+CIPSEND
POST /api/v1.6/devices/sim900 HTTP/1.1Host:industriAT+CIPCLOSE

CLOSE OK


The codes is exactly copied and pasted:-

#include <String.h>
#include <SoftwareSerial.h>

SoftwareSerial mySerial(7, 8);

//SoftwareSerial mySerial(3, 2); //SIM900 Tx & Rx is connected to Arduino #3 & #2

int value1;

int value2;

int value3;

int num;

String le;

String var;

String token = “BBFF-GvHtRUwUsH7587lLf3ylaWxv1uosxl”;

void setup()

{

mySerial.begin(9600);

Serial.begin(9600);

delay(10000);

}

void loop()

{

value1 = random(36, 39);

value2 = random(24, 30);

value3 = random(65, 75);

var = "{\"temperature\":" + String(value1) + "}";

num = var.length();

le = String(num);

comunication_start();

send_value();

//comunication_end();

if (mySerial.available())

    Serial.write(mySerial.read());

}

void comunication_start()

{

mySerial.println("AT");

delay(1000);

mySerial.println("AT+CPIN?");

delay(1000);

mySerial.println("AT+CREG?");

delay(1000);

mySerial.println("AT+CGATT?");

delay(1000);

mySerial.println("AT+CIPSHUT");

delay(1000);

mySerial.println("AT+CIPSTATUS");

delay(2000);

mySerial.println("AT+CIPMUX=0");

delay(2000);

ShowSerialData();

mySerial.println("AT+CSTT=\"my3g.com\""); //start task and setting the APN,

delay(1000);

ShowSerialData();

mySerial.println("AT+CIICR"); //bring up wireless connection

delay(2000);

ShowSerialData();

mySerial.println("AT+CIFSR"); //get local IP adress

delay(2000);

ShowSerialData();

mySerial.println("AT+CIPSPRT=0");

delay(3000);

ShowSerialData();

mySerial.println("AT+CIPSTART=\"TCP\",\"industrial.api.ubidots.com\",\"80\"");

delay(8000);

ShowSerialData();

}

void send_value()

{

mySerial.println("AT+CIPSEND"); //begin send data to remote server

delay(3000);

mySerial.print("POST /api/v1.6/devices/sim900 HTTP/1.1");

mySerial.println("Host:industrial.api.ubidots.com");

mySerial.println("User-Agent:arduino65437823/1.0");

mySerial.print("X-Auth-Token: ");

mySerial.println(token);

mySerial.println("Content-Type:application/json");

mySerial.println("Content-Length: " + le);

mySerial.println("");

mySerial.println(var); // Begin send payload to remote servr

//mySerial.println("");

mySerial.println((char)26);

delay(5000);

ShowSerialData();

mySerial.println("AT+CIPCLOSE"); //close the communication

delay(1000);

}

void comunication_end()

{

mySerial.println("AT+CIPCLOSE"); // Close the connection

delay(1000);

ShowSerialData();

}

// This function is to show the response in your serial terminal

void ShowSerialData()

{

while (mySerial.available() != 0)

    Serial.write(mySerial.read());

}

Hello @fionasoon, please accept my apologies, I had one wrong line on the code above. I’m really hoping we can get this working as soon as possible.

SoftwareSerial mySerial(7, 8);
//SoftwareSerial mySerial(3, 2); //SIM900 Tx & Rx is connected to Arduino #3 & #2
int value1;
int value2;
int value3;
int num;
String le;
String var;
String token = "BBFF-xxxxxxxxxxxxxxx";
void setup()
{
    mySerial.begin(9600);
    Serial.begin(9600);
    delay(10000);
}
void loop()
{
    value1 = random(36, 39);
    value2 = random(24, 30);
    value3 = random(65, 75);
    var = "{\"temperature\":" + String(value1) + "}";
    num = var.length();
    le = String(num);
    comunication_start();
    send_value();
    //comunication_end();
    if (mySerial.available())
        Serial.write(mySerial.read());
}
void comunication_start()
{
    mySerial.println("AT");
    delay(1000);
    mySerial.println("AT+CPIN?");
    delay(1000);
    mySerial.println("AT+CREG?");
    delay(1000);
    mySerial.println("AT+CGATT?");
    delay(1000);
    mySerial.println("AT+CIPSHUT");
    delay(1000);
    mySerial.println("AT+CIPSTATUS");
    delay(2000);
    mySerial.println("AT+CIPMUX=0");
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CSTT=\"my3g.com\""); //start task and setting the APN,
    delay(1000);
    ShowSerialData();
    mySerial.println("AT+CIICR"); //bring up wireless connection
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CIFSR"); //get local IP adress
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CIPSPRT=0");
    delay(3000);
    ShowSerialData();
    mySerial.println("AT+CIPSTART=\"TCP\",\"industrial.api.ubidots.com\",\"80\"");
    delay(8000);
    ShowSerialData();
}
void send_value()
{
    mySerial.println("AT+CIPSEND"); //begin send data to remote server
    delay(3000);
    mySerial.println("POST /api/v1.6/devices/sim900 HTTP/1.1");
    mySerial.println("Host:industrial.api.ubidots.com");
    mySerial.println("User-Agent:arduino65437823/1.0");
    mySerial.print("X-Auth-Token: ");
    mySerial.println(token);
    mySerial.println("Content-Type:application/json");
    mySerial.println("Content-Length: " + le);
    mySerial.println("");
    mySerial.println(var); // Begin send payload to remote servr
    mySerial.println((char)26);
    delay(5000);
    ShowSerialData();
    mySerial.println("AT+CIPCLOSE"); //close the communication
    delay(1000);
}
void comunication_end()
{
    mySerial.println("AT+CIPCLOSE"); // Close the connection
    delay(1000);
    ShowSerialData();
}
// This function is to show the response in your serial terminal
void ShowSerialData()
{
    while (mySerial.available() != 0)
        Serial.write(mySerial.read());
}

I’ve also extended a little bit the time after the payload is added to the message, just to make sure the device has the time to add it completely before sending the message itself.

I’ll be attentive to your response.

Hello @Sebastian, don’t worry, I will try this code patiently. It is still not posting yet after changing by following the codes given. I have also tried to add serialprintln("") after sending the payload. It also could not post to ubidots.


void send_value()

{

mySerial.println("AT+CIPSEND"); //begin send data to remote server

delay(3000);

mySerial.print("POST /api/v1.6/devices/sim900 HTTP/1.1");

mySerial.println("Host:industrial.api.ubidots.com");

mySerial.println("User-Agent:arduino65437823/1.0");

mySerial.print("X-Auth-Token: ");

mySerial.println(token);

mySerial.println("Content-Type:application/json");

mySerial.println("Content-Length: " + le);

mySerial.println("");

mySerial.println(var); // Begin send payload to remote servr

//mySerial.println("");

mySerial.println((char)26);

delay(5000);

ShowSerialData();

mySerial.println("AT+CIPCLOSE"); //close the communication

delay(1000);

}

Output from Serial Monitor

AT

OK
AT+CPIN?

+CPIN: READY

OAT+CSTT=“my3g.com”

OK
AT+CIICR

OK
AT+CIFSR

21.118.35.100
AT+CIPSPRT=0

OK
AT+CIPSTART=“TCP”,“industrial.api.ubidots.com”,“80”

OK

COAT+CIPSEND
POST /api/v1.6/devices/sim900 HTTP/1.1Host:industriAT+CIPCLOSE

CLOSE OK

Hello @fionasoon, sorry for the late reply.

I think some of the delays were necessary for the AT commands to execute properly. It seems that after erasing them from the code, the request isn’t fully executed before the AT+CIPCLOSE comes in.

The request isn’t complete. Does it make sense?

Just to make sure, I would like to see if the delays might be the reason for the request not being sent complete. So I’ve added them back on.

//SoftwareSerial mySerial(3, 2); //SIM900 Tx & Rx is connected to Arduino #3 & #2
int value1;
int value2;
int value3;
int num;
String le;
String var;
String token = "BBFF-xxxxxxxxxxxxxxx";
void setup()
{
    mySerial.begin(9600);
    Serial.begin(9600);
    delay(10000);
}
void loop()
{
    value1 = random(36, 39);
    value2 = random(24, 30);
    value3 = random(65, 75);
    var = "{\"temperature\":" + String(value1) + "}";
    num = var.length();
    le = String(num);
    comunication_start();
    send_value();
    //comunication_end();
    if (mySerial.available())
        Serial.write(mySerial.read());
}
void comunication_start()
{
    mySerial.println("AT");
    delay(1000);
    mySerial.println("AT+CPIN?");
    delay(1000);
    mySerial.println("AT+CREG?");
    delay(1000);
    mySerial.println("AT+CGATT?");
    delay(1000);
    mySerial.println("AT+CIPSHUT");
    delay(1000);
    mySerial.println("AT+CIPSTATUS");
    delay(2000);
    mySerial.println("AT+CIPMUX=0");
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CSTT=\"my3g.com\""); //start task and setting the APN,
    delay(1000);
    ShowSerialData();
    mySerial.println("AT+CIICR"); //bring up wireless connection
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CIFSR"); //get local IP adress
    delay(2000);
    ShowSerialData();
    mySerial.println("AT+CIPSPRT=0");
    delay(3000);
    ShowSerialData();
    mySerial.println("AT+CIPSTART=\"TCP\",\"industrial.api.ubidots.com\",\"80\"");
    delay(8000);
    ShowSerialData();
}
void send_value()
{
    mySerial.println("AT+CIPSEND"); //begin send data to remote server
    delay(3000);
    mySerial.println("POST /api/v1.6/devices/sim900 HTTP/1.1");
    delay(1000);
    mySerial.println("Host:industrial.api.ubidots.com");
    delay(1000);
    mySerial.println("User-Agent:arduino65437823/1.0");
    delay(1000);
    mySerial.print("X-Auth-Token: ");
    delay(1000);
    mySerial.println(token);
    delay(1000);
    mySerial.println("Content-Type:application/json");
    delay(1000);
    mySerial.println("Content-Length: " + le);
    delay(1000);
    mySerial.println("");
    mySerial.println(var); // Begin send payload to remote servr
    delay(5000);
    mySerial.println((char)26);
    delay(5000);
    ShowSerialData();
    mySerial.println("AT+CIPCLOSE"); //close the communication
    delay(1000);
}
void comunication_end()
{
    mySerial.println("AT+CIPCLOSE"); // Close the connection
    delay(1000);
    ShowSerialData();
}
// This function is to show the response in your serial terminal
void ShowSerialData()
{
    while (mySerial.available() != 0)
        Serial.write(mySerial.read());
}

Could you try this to see if the delays are actually needed?

Hi, @Sebastian. Thank God that I finally got it working. I follow your advices and added also ShowSerialData() at after certain codes to get the delay. It was a bit tricky to set the right timing and the right format for the Json. Here, I would like to share the codes to whoever is trying hard.
Thank you so much Sebastian and your team for untiring and patience in helping me to troubleshoot the codes. You can close this case as [Solved]. :smiley:

void send_value()

{
mySerial.println(“AT+CIPSEND”); //begin send data to remote server
delay(1000);

mySerial.println("POST /api/v1.6/devices/sim900 HTTP/1.1");
delay(1000);
ShowSerialData();

mySerial.println("Host:industrial.api.ubidots.com");
delay(1000);

mySerial.println("User-Agent:arduino65437823/1.0");
delay(1000);
ShowSerialData();

mySerial.print("X-Auth-Token: ");
delay(1000);

mySerial.println(token);
delay(1000);

mySerial.println("Content-Type:application/json");
delay(1000);

mySerial.println("Content-Length: " + le); 
delay(1000);

mySerial.println("");

mySerial.println(var); // Begin send payload to remote servr
delay(2000);
  
mySerial.println((char)26);

delay(5000);

 delay(1000);

mySerial.println("AT+CIPCLOSE"); //close the communication

delay(1000);

}

The 400 (Bad Request) status code indicates that the server cannot or will not process the request because the received syntax is invalid, nonsensical, or exceeds some limitation on what the server is willing to process. It means that the request itself has somehow incorrect or corrupted and the server couldn’t understand it. The server is refusing to service the request because the entity of the request is in a format not supported by the requested resource for the requested method . Therefore, it prevents the website from being properly displayed. The main thing to understand is that the 400 Bad Request error is a client-side error.

The cause of a 400 error can be a wrongly written URL or a URL that contains unrecognizable characters. Another cause of the error might be an invalid or expired cookie. Also, if you try to upload a file that’s too large. If the server is programmed with a file size limit, then you might encounter a 400 error.

Hi, @Sebastian,

Thanks for your last help in getting my first SIM device (sim900) works with Ubidots.

Now, I am trying to use similar codes to connect to the second SIM (sim901) device. But, it gives error code for the POST code. Am I using the correct postcode and User Agent? Please kindly help. :pray: :pray: :pray:
The error message is as follows:-

Content-TypeAAT+CSTT=“my3g.com”

OK
AT+CIICR

OK
AT+CIFSR

21.226.218.83
AT+CIPSPRT=0

OK
AT+CIPSTART=“TCP”,“industrial.api.ubidots.com”,“80”

OK
AT+CIPSEND

ERROR
POST /api/v1.6/devices/sim901 HTTP/1.1
Host:industrial.api.ubidots.com

STATE: IP STATUS

CONNECT X

The send code that I used in arduino is:
void send_value()
{
mySerial.println(“AT+CIPSEND”); //begin send data to remote server
delay(1000);//if send error means data plan not updated
mySerial.println(“POST /api/v1.6/devices/sim901 HTTP/1.1”);
delay(1000);
ShowSerialData();
mySerial.println(“Host:industrial.api.ubidots.com”);
delay(1000);
mySerial.println(“User-Agent:arduino65437823/1.0”);
//mySerial.println(“User-Agent:arduino/1.0”);
delay(1000);
ShowSerialData();
mySerial.print("X-Auth-Token: “);
delay(1000);
mySerial.println(token);
delay(1000);
mySerial.println(“Content-Type:application/json”);
delay(1000);
mySerial.println(“Content-Length: " + le);
delay(1000);
mySerial.println(””);
mySerial.println(var); // Begin send payload to remote servr
delay(2000);
mySerial.println((char)26);
delay(5000);
mySerial.println(“AT+CIPCLOSE”); //close the communication
delay(1000);

}

Hello @fionasoon ,

We hope you have a great 2022.

Does the error message say anything else? Maybe a response code?

What I do see, is that your User-Agent is the same as for the SIM-900. This can sometimes cause these type of issues. Could you please change the User-Agent to another random string so that we don’t have any possible collisions on the request?

I’ll be attentive for when you try this out.

Best regards,
Sebastián