dudydude has asked for the wisdom of the Perl Monks concerning the following question:

Hey fellow monks, I have a quick question:

Where can I find a good tutorial on how to write a Perl code for a server and client?

I need the Unix machine to send some files to Windows and after some process Windows send back the answer to Unix (of course over the Internet). Is it possible?

If possible a server that can handle several connections at a time!

  • Comment on Quick Question about Server and Clients!

Replies are listed 'Best First'.
Re: Quick Question about Server and Clients!
by Marshall (Canon) on Jul 14, 2011 at 16:51 UTC
    I think it would help if you explained a bit more about the application that you'd like to implement. It is not clear to me that you even need a traditional client/server.

    Many file processing schemes are implemented with an input "drop-off directory" and an output "pick-up directory". An Acrobat setup might be like that. Drop a .doc file into directory IN and wait and the same file appears as a .pdf in the OUT directory.

    To get something like this going, you would need FTP or SFTP running on your Windows machine.

    Anyway, before sending you off in some very complicated and maybe wrong directions, please explain a bit more how you envision this thing working.

Re: Quick Question about Server and Clients!
by zentara (Cardinal) on Jul 14, 2011 at 19:51 UTC
    See the perl socket examples at UNO perl examples. They explain it from the very basic level, and you should move up to using higher level perl moules like IO::Socket and IO::Select. However, it is useful to know how to do it the hard way :-)

    Here is one tip that gets most beginners, your client should fork or thread itself off, so it can handle bi-directional socket flow seamlessly, without having to use the send and recv modes of IO::Socket. Here is the basic client to get you started, the $name thing is there for no essential reason except to identify clients, you don't need it. :-)

    A basic client:

    #!/usr/bin/perl -w use strict; use IO::Socket; my ( $host, $port, $kidpid, $handle, $line ); ( $host, $port ) = ('localhost',1200); my $name = shift || ''; if($name eq ''){print "What's your name?\n"} chomp ($name = <>); # create a tcp connection to the specified host and port $handle = IO::Socket::INET->new( Proto => "tcp", PeerAddr => $host, PeerPort => $port ) or die "can't connect to port $port on $host: $!"; $handle->autoflush(1); # so output gets there right away print STDERR "[Connected to $host:$port]\n"; # split the program into two processes, identical twins die "can't fork: $!" unless defined( $kidpid = fork() ); # the if{} block runs only in the parent process if ($kidpid) { # copy the socket to standard output while ( defined( $line = <$handle> ) ) { print STDOUT $line; } kill( "TERM", $kidpid ); # send SIGTERM to child } # the else{} block runs only in the child process else { # copy standard input to the socket while ( defined( $line = <STDIN> ) ) { print $handle "$name->$line"; } }

    I'm not really a human, but I play one on earth.
    Old Perl Programmer Haiku ................... flash japh
Re: Quick Question about Server and Clients!
by xhudik (Initiate) on Jul 14, 2011 at 16:18 UTC
    well, probably not the best, but you can read:
    http://perldoc.perl.org/perlipc.html#TCP-Clients-with-IO%3a%3aSocket
    Suppose you'd need some higher level literature though.
    Tomas
Re: Quick Question about Server and Clients!
by believer (Sexton) on Jul 15, 2011 at 09:09 UTC
    Yes, this is possible. But chances are high that a client / server setup is not the best solution to your problem (the XY problem).

    So I strongly advise you to explain the underlying problem,

Re: Quick Question about Server and Clients!
by zentara (Cardinal) on Jul 15, 2011 at 12:41 UTC
    I need the Unix machine to send some files to Windows and after some process Windows send back the answer to Unix (of course over the Internet). Is it possible?

    I havn't tested these recently, but you might get a head start with Sockets-File-Upload with Net::EasyTCP and File Transfer via Sockets and Indirect file transfer. Also don't forget netcat , you can google for it's usage.

    Just to demonstrate the base simplicity of the concept, here is a rudimentary server & client set

    Server

    #!/usr/bin/perl -w use strict; use IO::Socket::INET; #-- #-- server.pl #-- my $server = IO::Socket::INET->new(Listen => 5, LocalAddr => 'localhost', LocalPort => 5050, Proto => 'tcp') || die $!; #-- have we receive the filename from the client yet? my $file = undef; while(my $client = $server->accept){ #-- #-- in your code, you have while(<$client>){...} #-- which is very dangeous because <> will hang if #-- client and server use a different newline encoding #-- so please avoid using <$client> in your networking code #-- #-- 1024 is also a hack which assume your filename will not #-- be longer than 1K. #-- while(sysread($client,$_,1024)){ #-- #-- look for a filename before the first newline #-- if(/(.+?)\n(.*)/ && !$file){ #-- #-- for demo, i will create a filename (sent i +n by client) #-- appending with .by_server. this helps you #-- to run this demo code without worrying ove +rwriting #-- the original file in the same machine #-- $file = $1 . '.by_server'; open(FILE,">$file") || last; print FILE $2; }else{ print FILE if($file); } } close(FILE) if($file); close($client); $file = undef; } __END__

    Client

    #!/usr/bin/perl -w use strict; use IO::Socket::INET; #-- #-- client.pl #-- my $server = IO::Socket::INET->new(PeerAddr => 'localhost', PeerPort => 5050, Proto => 'tcp') || die $!; my $file = 'tmp.txt'; #-- #-- send the file name to server.pl #-- print $server "$file\n"; #-- #-- and then the content #-- open(FILE,$file) || die $!; print $server $_ while(<FILE>); close(FILE); close($server); __END__

    I'm not really a human, but I play one on earth.
    Old Perl Programmer Haiku ................... flash japh