Question : how do i send a full request for POST?

Hi. I need to send a full request via POST to a host. unfortunately, the way my code works is that it does a while loop on the response and I print the responses per line... works fine with GET but POST needs a few more details like Content-Length. How do I "bunch" it up so that I send the whole message to the server?
Code Snippet:
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
if ($browser_line =~ /^\s*$/ and $method eq "POST") {
		   while (my $host_line = <$host>) {
			 #print $host_line;
	     print $browser $host_line;
       next;
       }
     }
 
     elsif ($browser_line =~ /^\s*$/ and $method ne 'POST') {
		   while (my $host_line = <$host>) {
			 #print $host_line;
	     print $browser $host_line;
       next;
       }
     }

Answer : how do i send a full request for POST?

Okay, we'll try that, then...theory with no code, but with an example you can follow to see the underlying methodology.

First thing...Content-Length.  You need to get a fully byte count of your message as it starts from the first character -after- the blank line that follows the headers, through the end of the content, inclusive.  In your example, you're throwing the data at the server line by line.  What I'd do is accumulate it by concatenating it into a single string, then use length() on that string.

As for encoding, there are a couple ways to go.  If you're using a SOAP type methodology, your data can stand as-is, and it's just posted with the appropriate length.  If you're intending the data for a CGI application, you need to encode with either application/x-www-form-urlencoded or multipart/form-data.  Those are the two MIME types.  Corresponding to those MIME types are two entirely different encapsulation techniques.  Essentially, the former is the same as GET; you URL-encode your data, and put it into fieldname=value pairs, separated by an & characters.  The multipart/form-data is more complex, and is essentially a MIME formatting with a small tweak here or there.  There is a solid example of this in RFC 1867:  http://www.ietf.org/rfc/rfc1867.txt

In any event, your content length should be calculated -after- all encoding, since any encoding changes the length of your data.

As for the actual posting itself...you know, I've never done it -programmatically- without a library of one kind or another--or at least the original NCSA C-based skeleton for query-post.c that was included as an example back in the day with NCSA 1.0 and 1.1 servers.  However, I've done it manually with telnet, debugging CGI by hand, and if you were to telnet to the server directly, it would go like this:

[shell1] [~] [3:26pm]: telnet www.somehost.com 80
Trying xxx.xxx.xxx.xx...
Connected to www.somehost.com.
Escape character is '^]'.
POST /cgi-bin/showenvplus HTTP/1.1
Content-Length: 9
Host: www.somehost.com

test=test


And that's it.  As soon as the server sees Content-Length bytes, you'd then get back headers, a blank separating line, and whatever information came from the responding application:

HTTP/1.1 200 OK
Date: Tue, 15 Sep 2009 19:26:44 GMT
Server: Apache/1.3.41 (Unix)
Transfer-Encoding: chunked
Content-Type: text/plain

[imagine actual data response here]
[...]


The only real pain to doing it with telnet is calculating your content length ahead of time, which is why I used a very short test=test 9-character string so that I knew what my length would be as I manually fed in the query.  This query was formatted for the old-school application/x-www-form-urlencoded CGI methodology, by the way.  Force of habit, plus I was throwing it at a CGI script so it made sense to do that.  :)

That's pretty much all you need to feed to the server as a bare minimum under HTTP 1.1--the POST with a location and HTTP version, the Host line, and the Content-Length line.  The Host header you send is supposed to be set to the value of the host from the URL you're POSTing to; it's to aid in disambiguation (and I suspect potentially NameVirtualHost resolution).  There are other things you can set (check RFC 2616 for the HTTP specification), but this is the bare minimum you need with HTTP 1.1.

Hope this helps you see what you need to send to the server, and when.  Just remember, headers, blank line, then data.  Have your data encoded and ready ahead of time, as well as the content length.  Send headers, blank line, then data.
Random Solutions  
 
programming4us programming4us