Gaurav Pant
Gaurav Pant

Reputation: 4199

switch perl process to background after user input

Problem Statement --

I display a message to user using Perl and takes an input.On the basis of input I decide whether I need to do further processing or not.This processing takes a long time ( say 5 hour) and user run this process by logging into remote Unix/Linux system.Hence to make sure that network malfunctioning will not affect the process; I want to switch the process to background.

How can I switch such running Perl process to background?

or

Is it possible to take user input from current terminal( the terminal from where user run process as input need to be taken at very starting) if process is running into background?

OS - Linux variants

Upvotes: 2

Views: 852

Answers (3)

Jim Black
Jim Black

Reputation: 1482

Here is a very, very simple example for my comment above...

#!/usr/bin/perl
use strict;
use warnings;
my $lcnt = 0;
if( !$ARGV[0] ) {  # If no ARGS on the command line, get user input
    print "How many lines do you want to print?";
    chomp( $lcnt = <STDIN> );
    if( $lcnt > 0 ) {
        # when we are sure we have what we need
        # call myself.pl and put it in the background with '&'
        my $cmd = "./myself.pl ".$lcnt.' &';
        system($cmd);
        exit(0);
    } else { die "Invalid input!\n"; }
} else {  # Otherwise, lets do the processing
    $lcnt = $ARGV[0];
    for( my $x = 0; $x <= $lcnt; $x++ ) {
        my $cmd = "echo 'Printing line: $lcnt' >> /tmp/myself.txt";
        system($cmd);
        sleep(1);
    }
}
exit(0);

If you save this to a file called 'myself.pl' then run it. With no arguments on the command line, the script will ask you to input a number. Type in 20 and press enter. You'll see the script exit almost instantly. But if you quickly

tail -f /tmp/myself.txt

you'll see that the background process is still running, printing a new line to the file every second. Also, typing the 'ps' command on Linux systems, should show the spawned process running in the background:

jlb@linux-f7r2:~/test> ps
 PID TTY          TIME CMD
 1243 pts/1    00:00:00 bash
 4171 pts/1    00:00:00 myself.pl
 4176 pts/1    00:00:00 ps

Upvotes: 2

bks
bks

Reputation: 1360

Yup, you want to daemonize your program after it finishes its interaction with the user. I would encourage you to use a module like Proc::Daemon to do the work, though: there are a bunch of subtleties in doing it correctly. The POD for Proc::Daemon gives a good description of its usage, but a simple usage can be as basic as

use Proc::Daemon;

# ... finished the interactive stuff
my $pid = Proc::Daemon::Init( { work_dir => '/var/run/my_program' })
exit 0 if ($pid == 0);
die "Error daemonizing, cannot continue: $!\n" if ($! != 0);
# ... now do the background processing
# note that STDOUT and STDERR are no longer connected to the user's terminal!

Upvotes: 4

user1937198
user1937198

Reputation: 5348

Demonise the process if the correct input:

#test input
if($inputsuccess) {
    if(fork() = 0) {
        #child
        if(fork() = 0) {
            #child
            #background processing
        }
    } else {
       wait();
    }
}

Upvotes: 2

Related Questions