Solved

cgi script:  background process keeping my script from finishing?

Posted on 2001-08-31
9
467 Views
Last Modified: 2008-03-17
Hi all

I'm writing a "web power switch" for a set of applications, such that authorized users can visit a web page, and start or stop the application without having to log in to the server.  

However, the application takes a long time to start up, (so long, in fact, that a web query will time out if you wait for process to finish) so I tried to run it in the background:

system("mybigslowapp 2>&1 >/tmp/logfile  &");

This appears to allow my script to continue, but the page never seems to "finish" (The browser seems to be "waiting" for something, then eventually spits out an error message, saying the request timed out.  (The app _does_ start up correctly, its just the web page I'm having trouble with)  I also have this same script kill the app, and it works fine.

Am I correct in assuming that, in my current config,  "bigslowapp" will have to finish before my perl script will finish up?  How can I do this so it just spawns bigslowapp, and doesn't wait?

...If the points seem low for this question, speak up, I've got more :)
0
Comment
Question by:gmancuso
9 Comments
 

Author Comment

by:gmancuso
ID: 6446748
other potentially relevant info:

I'm using CGI::standard for most of the html on the page
On submit, the script calls itself, and performs actions based on the existence of parameters
running on a solaris server, 2.6
0
 
LVL 5

Accepted Solution

by:
Droby10 earned 100 total points
ID: 6447537
have you tried forking the script instead of running the process in the background...?
0
 

Author Comment

by:gmancuso
ID: 6454073
OK.. that's closer.. I changed the call to:

    unless(fork) {
      $SIG{INT} = 'IGNORE';  # c 'turn undead' zombies
       exec(" mybigslowapp 2>&1 > /tmp/log.web ");
       exit;  # This block only executes if we're the child, so exit when we're done.
    }

This works great from the command line, but the web page still won't finish.  I guess that means my problem may  not be with the background process, but with the buffers, maybe?  

Previously, the script (when called from command line) would wait until the system call was finished, then exit.  Now, the script returns immediately (this is good).  However, I'm still getting the same behavior from my web page (it's a little better, but still takes a minute or more to return.  I have tried changing $| =1; still the same results.  The script is actually making it to the end of the html page (I put a print() directly before the print end_html; line and it gets printed).  Why would I get different behavior from the web?  I test-run these scripts in the same environment, as the "web server user"
0
 

Author Comment

by:gmancuso
ID: 6464795
I figured it out... a combination of cgi technicalities, and a typing mistake had me stumped.  The correct calling sequence is as follows:

    $SIG{INT} = 'IGNORE';  # c 'turn undead' zombies
    unless(fork) {
       open STDIN,  "</dev/null";
       open STDOUT, ">/dev/null";
       exec(" $startcmd > /tmp/log.web &");
       exit;  # This block only executes if we're the child, so exit when we're done.
    }


Points of interest:  

Not setting stdin & stdout to /dev/null caused most of my problems, as that actually created an error when the browser got tired of waiting for input it would never receive.   (Thanks to a Randal Swartz article in Web Techniques for pointing this out to me:   http://www.stonehenge.com/merlyn/WebTechniques/col20.html)

Even though I'm forking off a second process, I had to run the start command in the background (note the added &).  

I was incorrectly setting the SIGINT handler to ignore only in the child process.

Also during my search for answers I found that I'm probably using exec insecurely, and I should pass the parameters in separately (as a list? I can't remember now).  But that's a journey for another day.

Thanks to Droby10 for pointing me in the right direction...  I'm giving you a B for having the right answer, but leaving out a lot of details.

Thanks -G
0
Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

 
LVL 5

Expert Comment

by:Droby10
ID: 6466789
thanks, glad you got it all working...
0
 

Expert Comment

by:bitsrfr
ID: 6997313
Needed the same functionality and it worked for me too...
0
 

Expert Comment

by:Brimstar
ID: 8766104
It looks like this thread has helped at least three people.  Was just trying to implement the same thing and it's working quite nicely.  Thanks for the help!
0
 

Expert Comment

by:enan0
ID: 8998595
Ok... I tryed but id didn't work for me. Anyway I make it work so I'm posting just if someone happen the same as me.
This was my code according to this article:

$::SIG{INT} = 'IGNORE';
unless(fork) {
  open STDIN,  "</dev/null";
  open STDOUT, ">/dev/null";
  exec("$script $dynparameter 2 > /tmp/ouch.log &");
  exit;  # This block only executes if we're the child, so exit when we're done.
}

And it didn't work. Then I try to play and look around newsgroups and i found some otherguy code, which just one difference with the one you have.... It has one extra line to redirect STDERR output also to /dev/null

so after: OPEN STDOUT, ">/dev/null";
it should go: OPEN STDERR, ">/dev/null";

at least  for me... now it works as wanted. Otherwise cgi keeps waiting for child to finish.
I'm using perl 5.8.0 under Redhat Linux 9.0.

c ya!

enan0
P.d: Anyone in hamburg? I'm quite bored and I don't know the language!
0
 

Expert Comment

by:degao
ID: 9082039
i got it to work... heres what i have..



#####################################

      $SIG{INT} = 'IGNORE';  # c 'turn undead' zombies
 
      if( !defined( $kidpid =fork()))
      {
        die "can't fork";
     
      }
      elsif( $kidpid == 0 )
      {

print << "EOD";
        <table width="640" border="0" bgcolor="#FFFFFF">
          <tr align="center" bgcolor="#FFFFFF">
            <td colspan="3">
              <table width="100%" border="0" cellspacing="0" cellpadding="0">
                <tr>
                  <td align="center"><b><font face="Arial, Helvetica, sans-serif" size="5" color="#000000">Application
                    Listing by Registered Attorney</font><font face="Arial, Helvetica, sans-serif" size="4" color="#000000"><br>
                    Spreadsheet Generator</font></b></td>
                  <td width="150" align="right"><img src="ebc.gif" width="150" height="75"></td>
                </tr>
           
              </table> </td> </tr>
              <tr>
                <td>
                  Request is being Processed.  Please check your e-mail in few minutes.
                </td>
              </tr>
         </table>
EOD
 print $query->end_html;
   
    }
    else
    {
        open STDIN,  "</dev/null";
        open STDOUT, ">/dev/null";
        open STDERR, ">/dev/null";
        exec("perl $scriptName &");
        exit;  # This block only executes if we're the child, so exit when we're done.
       
   }


########################
0

Featured Post

Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
perl script 4 98
Move Function in Perl Script 2 65
batch script for automated email 12 101
PHP pack() : What exactly is meant by signed char and unsigned char? 7 96
On Microsoft Windows, if  when you click or type the name of a .pl file, you get an error "is not recognized as an internal or external command, operable program or batch file", then this means you do not have the .pl file extension associated with …
I have been pestered over the years to produce and distribute regular data extracts, and often the request have explicitly requested the data be emailed as an Excel attachement; specifically Excel, as it appears: CSV files confuse (no Red or Green h…
Explain concepts important to validation of email addresses with regular expressions. Applies to most languages/tools that uses regular expressions. Consider email address RFCs: Look at HTML5 form input element (with type=email) regex pattern: T…
This is used to tweak the memory usage for your computer, it is used for servers more so than workstations but just be careful editing registry settings as it may cause irreversible results. I hold no responsibility for anything you do to the regist…

861 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

23 Experts available now in Live!

Get 1:1 Help Now