I'm trying to create a simple server to transfer groups of large files - tye suggested pointed me in a direction where I found HTTP::Server::Simple as I could use the HTTP protocol to send multi-part data that would include both metadata and multiple files, just as a browser does. Since HTTP::Server::Simple supports Net::Server, I threw that in, because the files being sent are large (multiple GB) and it's perfectly reasonable that more than one upload will go on at a time, so Net::Server::PreFork seemed like a simple way to do this.
All this is working fine. As long as I use "http://" on the client. However, since there will be user IDs and passwords sent in the metadata, I really want to use SSL. The client side, using LWP, is simple enough - change http: to https:, and we're good. However, the server side is much more convoluted. Here is a boiled-down example:
use strict;
use warnings;
my $s = Server->new(@ARGV);
$s->background(
SSL_cert_file => '/etc/ssl/apache2/server.crt',
SSL_key_file => '/etc/ssl/apache2/server.key',
);
exit;
package Server;
use base 'HTTP::Server::Simple::CGI';
sub net_server { 'Net::Server::PreFork' }
If I run this with the param of "12345", all is good. I can point my browser at "http://localhost:12345" and get the default HTTP::Server::Simple::CGI page. However, if I kill that, then run it again with a parameter of "12345/ssleay", then I get:
2011/04/26-15:03:18 Server::NetServer0 (type Net::Server::PreFork) sta
+rting! pid(6116)
Using default listen value of 128
Binding to SSLEAY port 12345 on host *
SSLeay missing SSL_key_file.
And the process is not running in the background - it died. I've run this through the debugger a few times, without quite figuring out how these parameters are supposed to be passed in, nor why they are missing from $s->{server} where
Net::Server::Proto::SSLEAY is expecting them.
I must be overlooking something simple. Those files are readable by the current user - the debugger shows that the options are simply not getting all the way through, and I don't know why.
Update: With shmem's prodding, I finally got something to "work". It's ugly. I think I'll investigate james2vegas' CB suggestion and look at Net::Server::HTTP quickly, and see if I get something that doesn't need quite so much hacking. However, for posterity, here's what I have:
use strict;
use warnings;
our $real_stdout;
open $real_stdout, '>&', \*STDOUT or die "Can't write to stdout";
my $s = Server->new(@ARGV);
$s->background(
SSL_cert_file => '/etc/ssl/apache2/server.crt',
SSL_key_file => '/etc/ssl/apache2/server.key',
);
exit;
package Server;
use base 'HTTP::Server::Simple::CGI';
sub net_server { 'Net::Server::PreFork::SSL' }
package Net::Server::PreFork::SSL;
use base 'Net::Server::PreFork';
use Data::Dumper;
sub options
{
my $self = shift;
my $prop = $self->{server};
my $ref = shift;
$self->SUPER::options($ref);
foreach my $p (qw(SSL_cert_file SSL_key_file))
{
$prop->{$p} = undef unless exists $prop->{$p};
$ref->{$p} = \$prop->{$p};
}
}
sub Net::Server::TiedHandle::BINMODE { } #my $s = shift; $s->[1] ? $s-
+>[1]->($s->[0], 'binmode', @_) : $s->[0]->binmode(@_) }
It's incomplete since it only includes the SSL_{cert|key}_file keys, not all the keys that SSLEAY supports. But it's a start.