Updated fcgi engine for multi process external support
Sebastian Riedel [Mon, 31 Oct 2005 14:08:16 +0000 (14:08 +0000)]
Build.PL
Changes
lib/Catalyst/Engine/FastCGI.pm
lib/Catalyst/Helper.pm

index bc9e77f..471b1b6 100644 (file)
--- a/Build.PL
+++ b/Build.PL
@@ -29,7 +29,8 @@ my $build = Module::Build->new(
         'Tree::Simple::Visitor::FindByPath' => 0,
         'URI'                               => 1.35,
     },
-    recommends         => { 'Catalyst::Engine::Apache' => 0 },
+    recommends =>
+      { 'Catalyst::Engine::Apache' => 0, FCGI => 0, 'FCGI::ProcManager' => 0 },
     create_makefile_pl => 'passthrough',
     create_readme      => 1,
     script_files       => [ glob('script/*') ],
@@ -52,7 +53,15 @@ print(
 print( '*' x 80, "\n" );
 
 eval "use FCGI";
-print qq/Install "FCGI" for FastCGI support.\n/ if $@;
+if ($@) {
+    print qq/Install "FCGI" for FastCGI support.\n/;
+}
+else {
+    eval "use FCGI::ProcManager";
+    print
+qq/Install "FCGI::ProcManager" for multiprocess FastCGI external support.\n/
+      if ($@);
+}
 
 print qq/
 *** IMPORTANT NOTE: ***
diff --git a/Changes b/Changes
index 7ec9a4f..b27a67c 100644 (file)
--- a/Changes
+++ b/Changes
@@ -1,6 +1,7 @@
 Tis file documents the revision history for Perl extension Catalyst.
 
 5.50
+        - Added multi process external FCGI support
         - Restarter process in HTTP engine now properly exits when the
           parent app is shut down.  
         - Improved performance of restarter loop while watching for
index ecbfc20..d1fd5f3 100644 (file)
@@ -18,17 +18,68 @@ This class overloads some methods from C<Catalyst::Engine::CGI>.
 
 =over 4
 
-=item $self->run($c)
+=item $self->run($c, $listen, { option => value, ... })
+Starts the FastCGI server.  If C<$listen> is set, then it specifies a
+location to listen for FastCGI requests;
+
+  Form            Meaning
+  /path           listen via Unix sockets on /path
+  :port           listen via TCP on port on all interfaces
+  hostname:port   listen via TCP on port bound to hostname
+
+Options may also be specified;
+
+  Option          Meaning
+  leave_umask     Set to 1 to disable setting umask to 0
+                  for socket open
+  nointr          Do not allow the listener to be
+                  interrupted by Ctrl+C
+  nproc           Specify a number of processes for
+                  FCGI::ProcManager
 
 =cut
 
 sub run {
-    my ( $self, $class ) = @_;
+    my ( $self, $class, $listen, $options ) = @_;
+
+    my $sock;
+    if ($listen) {
+        my $old_umask = umask;
+        unless ( $options->{leave_umask} ) {
+            umask(0);
+        }
+        $sock = FCGI::OpenSocket( $listen, 100 )
+          or die "failed to open FastCGI socket; $!";
+        unless ( $options->{leave_umask} ) {
+            umask($old_umask);
+        }
+    }
+    else {
+        -S STDIN
+          or die "STDIN is not a socket; specify a listen location";
+    }
+
+    $options ||= {};
 
-    my $request = FCGI::Request();
+    my $request =
+      FCGI::Request( \*STDIN, \*STDOUT, \*STDERR, \%ENV, $sock,
+        ( $options->{nointr} ? 0 : &FCGI::FAIL_ACCEPT_ON_INTR ),
+      );
+
+    my $proc_manager;
+
+    if ( $listen and ( $options->{nproc} || 1 ) > 1 ) {
+        require FCGI::ProcManager;
+        $proc_manager =
+          FCGI::ProcManager->new( { n_processes => $options->{nproc} } );
+        $proc_manager->pm_manage();
+    }
 
     while ( $request->Accept >= 0 ) {
+        $proc_manager && $proc_manager->pm_pre_dispatch();
         $class->handle_request;
+        $proc_manager && $proc_manager->pm_pre_dispatch();
     }
 }
 
index e3c2895..ccdf5b7 100644 (file)
@@ -644,11 +644,24 @@ __fastcgi__
 BEGIN { $ENV{CATALYST_ENGINE} ||= 'FastCGI' }
 
 use strict;
+use Getopt::Long;
+use Pod::Usage;
 use FindBin;
 use lib "$FindBin::Bin/../lib";
 use [% name %];
 
-[% name %]->run;
+my $help = 0;
+my ( $listen, $nproc );
+GetOptions(
+    'help|?'     => \$help,
+    'listen|l=s' => \$listen,
+    'nproc|n=i'  => \$nproc,
+);
+
+pod2usage(1) if $help;
+
+[% name %]->run( $listen, { nproc => $nproc } );
 
 1;
 
@@ -658,7 +671,16 @@ use [% name %];
 
 =head1 SYNOPSIS
 
-See L<Catalyst::Manual>
+[% appprefix %]_server.pl [options]
+ Options:
+   -? -help      display this help and exits
+   -l -listen    Socket path to listen on
+                 (defaults to standard input)
+                 can be HOST:PORT, :PORT or a
+                 filesystem path
+   -n -nproc     specify number of processes to keep
+                 to serve requests (defaults to 1)
 
 =head1 DESCRIPTION