I'm trying to test sending HTTP requests from my Arduino. I decided to use Free RESTful web service - http://services.groupkt.com. But something goes wrong and I don't understand what.
GET request:
GET /country/get/all HTTP/1.1
Host: 45.79.172.152
Connection: keep-alive
Serial Monitor:
AT+CIPMUX=0
OK
AT+CIPSTART="TCP","45.79.172.152",80
CONNECT
OK
AT+CIPSEND=74
OK
>
busy s...
Recv 74 bytes
SEND OK
+IPD,493:HTTP/1.1 408 Request Timeout
Date: Thu, 07 Jun 2018 16:10:59 GMT
Server: Apache/2.4.25 (Debian)
Content-Length: 307
Connection: close
Content-Type: text/html; charset=iso-8859-1
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>408 Request Timeout</title>
</head><body>
<h1>Request Timeout</h1>
<p>Server timeout waiting for the HTTP request from the client.</p>
<hr>
<address>Apache/2.4.25 (Debian) Server at services.groupkt.com Port 80</address>
</body></html>
CLOSED
What I'm doing wrong?
HTTP is not like Telnet. You can't enter a HTTP request line by line in Serial Monitor.
HTTP requests are meant to be sent by a program and the timeout to receive the
complete request on servers is one or two seconds. Write a sketch the sends the request.
Related
I am getting a 400 everytime I attempt a POST with the Telit ME910g1-WW
GET requests work great.
Here is my request:
//Check registration status
AT+CREG?
//Get the configuration of the sockets
AT#SCFG?
//Check if any socket has been activated
AT#SGACT?
//Activate the socket 1
AT#SGACT=1,1
//Wait for socket activation
WAIT=4
//Dial the socket. Port 80 is TCP connection.
AT#SD=1,0,80,"ptsv2.com"
//Wait for the CONNECT message
WAIT=4
POST /t/0ptzs-1659380654/post HTTP/1.1<cr><lf>Content-Type:application/json<cr><lf>Accept:*/*<cr><lf>Host:ptsv2.com<cr><lf>Content-Length:16<cr><lf>{"test":"test"}<cr><lf>
I am guessing it has something to do with the headers, attempted to URL encode the entire post request, but that seems to also fail.
Here is the response:
CONNECT
HTTP/1.0 400 Bad Request
Content-Type: text/html; charset=UTF-8
Referrer-Policy: no-referrer
Content-Length: 273
Date: Tue, 02 Aug 2022 12:28:36 GMT
<html><head>
<meta http-equiv="content-type" content="text/html;charset=utf-8">
<title>400 Bad Request</title>
</head>
<body text=#000000 bgcolor=#ffffff>
<h1>Error: Bad Request</h1>
<h2>Your client has issued a malformed or illegal request.</h2>
<h2></h2>
</body></html>
NO CARRIER
NO Carrier: Call dis-connected
Thanks all!
I'm trying to obtain the HTML dump of some RFC's from IETF website, via a simple GET request. However, it responds with status code 301. I'm making use of netcat to simulate the HTTP GET request with the following command :
$ printf 'GET /html/rfc3986 HTTP/1.1\r\nHost: tools.ietf.org\r\nConnection: close\r\n\r\n' | nc tools.ietf.org 80
The following reply is obtained as a result of the above command :
HTTP/1.1 301 Moved Permanently
Date: Wed, 09 Sep 2020 15:36:36 GMT
Server: Apache/2.2.22 (Debian)
Location: https://tools.ietf.org/html/rfc3986
Vary: Accept-Encoding
Content-Length: 323
Connection: close
Content-Type: text/html; charset=iso-8859-1
X-Pad: avoid browser bug
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>301 Moved Permanently</title>
</head><body>
<h1>Moved Permanently</h1>
<p>The document has moved here.</p>
<hr>
<address>Apache/2.2.22 (Debian) Server at tools.ietf.org Port 80</address>
</body></html>
However, if I try to send a HTTP/1.0 based HEAD request to the Location value determined in the above reply, I get status 404 in reply. I made use of HEAD method just to check the status code of the reply.
Command :
printf 'HEAD https://tools.ietf.org/html/rfc3986 HTTP/1.0\r\n\r\n' | nc tools.ietf.org 80
Reply:
HTTP/1.1 404 Not Found
Date: Wed, 09 Sep 2020 16:32:18 GMT
Server: Apache/2.2.22 (Debian)
Vary: accept-language,accept-charset,Accept-Encoding
Accept-Ranges: bytes
Connection: close
Content-Type: text/html; charset=iso-8859-1
Content-Language: en
Expires: Wed, 09 Sep 2020 16:32:18 GMT
Is there a mistake in the way I'm making use of GET method to obtain the results?
You are sending a plain text request to port 80, so the URL you are trying is effectively http://tools.ietf.org/html/rfc3986
The response is telling you to instead request https://tools.ietf.org/html/rfc3986. That's not a different path on the same server, but a full URL.
The difference is that it begins https meaning you need to make a TLS-secured connection on port 443.
That's not going to be possible with a trivial use of netcat, so you're better off using an HTTP client like curl or wget
I am sending the following HTTP request:
POST /input/8dZ8bgapvjfYzmwWno6W.txt HTTP/1.1
Host: data.sparkfun.com
Phant-Private-Key: pz5ga4pkydHgpEb8v608
Connection: close
Content-Type: application/x-www-form-urlencoded
Content-Length: 7
temp=44
In my code, I am sending it using UART tx requests to the xbee module, for which the translates to:
POST /input/8dZ8bgapvjfYzmwWno6Wr.txt HTTP/1.1\r\n
Host: data.sparkfun.com\r\n
Phant-Private-Key: pz5ga4pkydHgpEb8v608\r\n
Connection: close\r\n
Content-Type: application/x-www-form-urlencoded\r\n
Content-Length: 7\r\n
\r\n
temp=44
This is to communicate to the phant dataserver at data.sparkfun.com, and it responds with the following data:
HTTP/1.0 400 Bad request
Cache-Control: no-cache
Connection: close
Content-Type: text/html
<html><body><h1>400 Bad request</h1>
Your browser sent an invalid request.
</body></html>
I found the answer:
The packet is correct.
While configuring the Xbee Wifi module using XCTU, I had to give the correct port numbers of the server and client Xbee, which were wrong.
Server was 80, client was any port I think.
My client is sending:
POST /xxx/yyy HTTP/1.1
Host: localhost:9009
User-Agent: gSOAP/2.8
Content-Type: text/xml; charset=utf-8
Content-Length: 2442
Connection: keep-alive
SOAPAction: ""
But the server replies:
HTTP/1.1 200 OK
Content-Type: text/xml;charset=UTF-8
Content-Length: 11182
Server: Jetty(8.1.14.v20131031)
Isn't the server supposed to return "Connection: keep-alive" too?
I see that afterwards the client closes the connection although it is configure to keep the connection open.
I assumed it is because the server didn't provide the keep-alive in the reply (Is that the RFC?).
In my case the reason gSoap closed the connection wasn't related to the HTTP headers returned from server, but to the fact you need to specify the keep-alive flags on both directions by calling:
soap_set_imode(this, SOAP_IO_KEEPALIVE);
soap_set_omode(this, SOAP_IO_KEEPALIVE);
From what I've read in HTTP 1.1 persistent connections are the default so if the server didn't return "Connection: close" the connection can be used for next request too.
I'd like to get the whole page using telnet:
telnet
o test.bugs3.com 80
GET / HTTP/1.0
Actually I can get almost any website but this one. The same problem occurs with other free servers. I just want to know what exactly causes some restriction like that.
The request is as following:
Connected.
HTTP/1.1 200 OK
Server:
Date: Mon, 11 Nov 2013 04:11:47 GMT
Content-Type: text/html
Content-Length: 328
Last-Modified: Thu, 16 May 2013 12:17:53 GMT
Connection: close
Accept-Ranges: bytes
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>Account unavailable</title>
</head><body>
<h1>Account unavailable</h1>
<p>Maybe account have been moved, deleted, suspended or not activated yet.
<p>The requested resource could not be found but may be available again in
the future.
<hr>
</body></html>
It's because you aren't sending a Host: test.bugs3.com\r\n header. RFC 2616 #14.23: "A client MUST include a Host header field in all HTTP/1.1 request messages."