Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems.. It's 100% free, no registration required.

In Script to change current directory (cd, pwd) it is shown how to run a bash script that changes terminal directory.

But how do i run a perl script that runs a bash script that changes terminal directory?

share|improve this question
5  
Have you also read changing current working dir with a script? –  manatwork Jul 17 '12 at 12:59
    
yeah and its not really answering the question. I need to run a perl script which changes directory on the terminal. –  Hermann Ingjaldsson Jul 17 '12 at 13:20
2  
No, is not answering your question. But points out an important detail: when the process which changed the work directory terminates, the parent will continue its job with its own unchanged environment. So if you chdir in a perl script, that will have no effect in the bash which started it. Are you sure this is fine for you? –  manatwork Jul 17 '12 at 13:35
2  
@HermannIngjaldsson Yes, both an answer and the comments are answering your question: "you can't". Perl, shell, whatever: you cannot change the working directory of your process parent shell. –  Matteo Jul 17 '12 at 14:05
2  
What are you really trying to do? –  jw013 Jul 17 '12 at 19:30

5 Answers 5

up vote 9 down vote accepted

You can't.

The Perl script runs in a process which is a child of your shell session. This child process can change its own working directory all it likes, but it cannot change it's parent's working directory. When the Perl script exits, control is returned to the parent process (the shell session), which will have remained in the same working directory the whole time, regardless of what the child process did while it was running.

share|improve this answer

There are multiple ways (TIMTOWTDI) of executing external commands from Perl. Like using exec(), using backticks (``) etc. If you can run the external commands right from your Perl script then I think there is no need to call another Bash script (but you can do that too). Follow the link below to learn more. Also note, any changes made within the program affects only the subshell and remains effective throughout the program only, which is always a good thing, but there are ways that you can make the changes permanent i.e. it would affect the parent shell as well.

http://www.perlhowto.com/executing_external_commands

UPDATE-

Some questions on "How to do it in other ways". For unusual requirements there ought to be unusual solutions (that work). But the question is why would you use Perl to change parent shell directory? Here's how you'd do it anyways

$cat test.pl
 print "Hello world\n";
 print "cd ..";
$pwd
 /home/user/perlcode
$eval `perl test.pl|tee -a test.pl.log|grep cd`
$pwd
 /home/user
share|improve this answer
1  
And what are those ways to affect the parent shell? –  Hermann Ingjaldsson Jul 17 '12 at 14:01

You can only do that indirectly, e.g. using aliases. Have your bash script, instead of changing to the desired directory, just print the desired directory to stdout. Perl should then capture this output and also print the desired directory to stdout. A shell alias or shell function can then take that output and change the directory inside the running shell.

An example:

a.sh:

#!/bin/bash
mkdir /tmp/$$
echo /tmp/$$

b.pl:

#!/usr/bin/perl
my $something = do_somestuff();
print `./a.sh $something`;

sub do_somestuff{
     #do some processing here
     return "";
}

Use this shell function and test it:

daku@server:/home/daku $ b() { DIR=`./b.pl`; if test -n "$DIR"; then cd "$DIR"; fi }
daku@server:/home/daku $ b
daku@server:/tmp/14397 $
share|improve this answer
    
Your b.pl script would be more simply written as system './a.sh' -- and it's not particularly useful, since you might as well just invoke a.sh directly. –  Keith Thompson Jul 17 '12 at 18:56
    
Well, it was just for demonstration. The OP wanted to have a Perl script that runs a shell script that changes the current directory of the shell running the perl script. –  daniel kullmann Jul 17 '12 at 19:26
    
Ah, I missed the "that runs a shell script" part. Which leaves an open question: Why?? –  Keith Thompson Jul 17 '12 at 19:49

You can't do this directly. The only way for a shell to change its current directory is for the shell itself to execute a cd command (or pushd, popd, etc.).

But you can do it indirectly. Here's a simple example that change the current directory to /tmp:

cd-tmp.pl:

#!/usr/bin/perl

print "cd /tmp\n";

In your .bashrc or .bash_profile:

cd-tmp() { eval $(cd-tmp.pl); }

This assumes that cd-tmp.pl is in a directory in your $PATH -- or you can specify the full path in the function.

When you type cd-tmp at your shell prompt, it invokes cd-tmp.pl, captures its output, and executes that output as a shell command.

A Perl script can't cause a calling shell to change directories, but it can provide it with a command that the shell can then execute itself.

Of course you can use a directory other than /tmp, including one that's determined based on other information or created on the fly.

One point of clarification: the current directory is a property of the current shell process, not of the terminal.

UPDATE :

I just realized that I missed part of your question; you want "a perl script that runs a bash script". It's easy enough to modify my example to do that, but I have no idea why you need the Perl script to run a bash script. You haven't told us nearly enough about what you're actually trying to accomplish.

share|improve this answer

One more solution is to first save the directory you want to visit in a string variable :
Eg :

$cd_path = "/var/tmp";
$cmd_to_run = "cd $cd_path ; ls -lrt";
system($cmd_to_run);
share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.