Interpolate perl variable in shell command

I want to accept the date as input from the user and pass that input to the shell command below.

eg.

$date = ARGV[0]; `cd xyz $date` 

will this variable be interpolated in perl?

+6
source share
4 answers

This is trivial to check:

Input:

 use v5.16; use strict; use warnings; my $foo = 123; say `echo $foo`; 

Output:

 123 

So yes.

Beware of variables containing characters with special meaning in the shell, though.

+7
source

You have a couple of problems; First of all, cd accepts only one parameter. Did you mean something like cd xyz$date ? Secondly, backticks start a shell that executes the command you give, which will execute the change catalog command, and then exit immediately without any effect. (The current directory of the parent perl process remains unchanged.) Perhaps you are looking for chdir .

But yes, interpolation will work; To turn off interpolation in backward measures, you either avoid special characters ( echo xyz \$date ) or use qx with single quote delimiters ( qx'echo xyz $date' ).

+10
source

Perldoc has the answers, as always.

In particular, http://perldoc.perl.org/perlop.html#Quote-and-Quote-like-Operators has a Yes in Interpolates? column (assuming you don't have to worry here), so yes, it is safe to assume that your variable will be interpolated.

You can get the same document, often using "perldoc perlop" on the local command line.

+6
source

Yes, it will interpolate the variable. However, I highly recommend two things:

  • Use qx/../ instead of back ticks.
  • Define the command that you run first in the Perl variable, and then interpolate this variable.

qx/../ is good because it makes more obvious what you are doing:

 my $variable = qx(ls $directory); 

For qx you can use a wide range of characters:

 my $variable = qx(ls $directory); my $variable = qx/ls $directory/; my $variable = qx^ls $directory^; my $variable = qx#ls $directory#; 

The character after qx will be used as quotation marks. If you use parentheses, square brackets or curly braces, you use them in pairs with opening and closing.

This means that you can avoid problems when a particular character in your team can confuse things.

Another thing is to create a command in a Perl variable, and then execute it when trying to interpolate. This gives you more control over what you are doing:

 my $HOME; my $command; $HOME = "bin"; $command = "ls $HOME"; print qx($command); #Lists the directory bin $command = 'ls $HOME'; print qx($command); #List user home directory 

In both of these examples, I am doing qx($command) . However, in the first example, I allow Perl to substitute the value of $HOME. In the second example, I use single quotes, so Perl doesn't substitute the value of $HOME. In the second example, I use single quotes, so Perl doesn't substitute the value of $ HOME . Instead, the string . Instead, the string $ HOME` is just part of my command that I use. I allow the shell to interpolate it.

I usually use any program that uses qx/.../ . In most cases, it was used to run a command that can be executed in Perl itself. For example, in early Perl programs you will see things like this:

  $date = `date +%M/%Y/%D` chop $date; #Yeah, I said EARLY Perl programs 

Because it was easier to just run the Unix command, rather than trying to do it in a clean Perl way. However, by doing this, Perl (i.e. the correct) way means that you are no longer dependent on OS behavior that is not completely under your control.

If you need the output of a command to use in your Perl script, you must use open to execute your command, and handle the output of the command as a file.

 my $command = "ls $HOME"; open my command_fh, "|-", $command or die qq(Couldn't execute "$command"); 

If you just need to execute the command, use the system command:

 my $command = "xyz $date"; my $error = system $command; if ( $error ) { #Something terrible happened... } 

Please note that if you send only one scalar argument to the system command, and it contains possible shell metacharacters, it will execute the command through the OS shell. If you send the system command the list to execute, or there are no shell metacharacters, Perl will invoke the command executor to execute the command directly without any shell interpolations:

 my @command = qw(ls $HOME); system @command; #Will print out "No such directory '$HOME' 
+5
source

Source: https://habr.com/ru/post/945685/


All Articles