For some reasons I can only use IO::Socket to build my small http server (not the other modules dedicated to that).
EDIT1: I edited my question, I want to know what I can put instead of the commented line "#last ..."
Here is my script:
use strict;
use IO::Socket;
my $server = IO::Socket::INET->new(LocalPort => 6800,
Type => SOCK_STREAM,
Reuse => 1,
Listen => 10) or die "$@\n";
my $client ;
while ( $client = $server->accept()) {
my $client_info;
while(<$client>) {
#last if /^\r\n$/;
print "received: '" . $_ . "'\n";
$client_info .= $_;
}
print $client "HTTP/1.0 200 OK\r\n";
print $client "Content-type: text/html\r\n\r\n";
print $client '<H1>Hello World(!), from a perl web server</H1>';
print $client '<br><br>you sent:<br><pre>' . $client_info . '</pre>';
close($client);
}
Now, when I send a POST request, it (the script) doesn't take into account the last line (the POST data):
wget -qO- --post-data='hello=ok' http://127.0.0.1:6800
<H1>Hello World(!), from a perl web server</H1><br><br>you sent:<br><pre>POST / HTTP/1.1
User-Agent: Wget/1.14 (linux-gnu)
Accept: */*
Host: 127.0.0.1:6800
Connection: Keep-Alive
Content-Type: application/x-www-form-urlencoded
Content-Length: 8
</pre>
The script output is:
perl server.pl
received: 'POST / HTTP/1.1
'
received: 'User-Agent: Wget/1.14 (linux-gnu)
'
received: 'Accept: */*
'
received: 'Host: 127.0.0.1:6800
'
received: 'Connection: Keep-Alive
'
received: 'Content-Type: application/x-www-form-urlencoded
'
received: 'Content-Length: 8
'
This is to be expected. A POST request looks like
You terminate processing after the end of the header, but the data is in the body!
If you really want to write your own HTTP server, then you should extract the HTTP method from the header. If it is
POST
, you can look at the value from theContent-length
header, and read that number of bytes:WRT the updated question:
If you want to build a production HTTP server, you are going to have a bad time. This stuff is difficult. Please read through
perlipc
which covers the topic of TCP servers. You can then implement a subset of HTTP on top of this.Also read through the modules on CPAN that implement servers. Even if you cannot compile modules on your system, you may be able to use pure-Perl modules, or may find parts of code that you can reuse. Large parts of CPAN can be used under a GPL license.
If you want to do this, do it right. Write yourself a subroutine that parses a HTTP request. Here is a sketch that doesn't handle encoded fields etc.:
Then in your
accept
loop: