我们可以在perl脚本中找到一个shell脚本吗?
实施例: 计划1:
cat test1.sh
#!/bin/ksh
DATE=/bin/date
计划2:
cat test2.sh
#!/bin/ksh
. ./test1.sh
echo `$DATE`
计划3:
cat test3.pl
#!/usr/bin/perl
### here I need to source the test1.sh script
print `$DATE`'
如何在perl中获取shell以获取执行test3.pl
时打印的日期感谢 raghu
答案 0 :(得分:4)
你无法做到
system("source src.sh");
system()
启动一个新的子shell,你的环境变量不会传递给运行Perl脚本的shell。即使你的shell脚本导出变量,它也会将它们导出到子shell,不是你的实际外壳。
一种解决方案是编写一个包装脚本
答案 1 :(得分:1)
你可以做一些简单的事情,比如:
system "source /path/to/shell_env.sh &&"
. "/path/to/script.sh";
请注意,这与以下建议不同:
system "source /path/to/shell_env.sh &&"
. "/bin/sh /path/to/script.sh";
答案 2 :(得分:0)
你无法在Perl 5中获取shell文件.Sourcing实际上是在目标shell的shell文件中运行命令;但是,打开并阅读文件是微不足道的:
#!/usr/bin/perl
use strict;
use warnings;
use Carp;
sub source {
my $file = shift;
open my $fh, "<", $file
or croak "could not open $file: $!";
while (<$fh>) {
chomp;
#FIXME: this regex isn't quite good enough
next unless my ($var, $value) = /\s*(\w+)=([^#]+)/;
$ENV{$var} = $value;
}
}
source "./test1.sh";
print "$ENV{DATE}\n";
答案 3 :(得分:0)
嗯..是下面的作弊?
#!/bin/sh
. ./test1.sh # source the test script
echo Bash says $DATE
export DATE; # KEY to have the below Perl bit see $ENV{DATE}
perl <<'ENDPERL';
print "Perl says $ENV{DATE}\n";
ENDPERL
问题是,获取sh文件可能会做任何事情,而不只是将值X赋给变量Y ...
答案 4 :(得分:0)
我不知道这会有所帮助,但我觉得有必要想出一种在Perl中写这个的方法。我的目的是让Perl运行一个shell脚本,并将它设置的任何shell变量分配给Perl脚本中的命名变量。
其他的都是正确的,因为你“源”的任何shell脚本都将在子shell中。我想我可以使用“sh -x cmd”来至少让shell显示变量,因为它们已被设置。
这是我写的:
use strict; use warnings;
our $DATE;
my $sh_script = "./test1.sh";
my $fh;
open($fh, "sh -x '$sh_script' 2>&1 1>/dev/null |") or die "open: $!";
foreach my $line (<$fh>) {
my ($name, $val);
if ($line =~ /^\+ (\w+)='(.+)'$/) { # Parse "+ DATE='/bin/date;'
$name = $1;
($val = $2) =~ s{'\\''}{'}g; # handle escaped single-quotes (eg. "+ VAR='one'\''two'")
} elsif ($line =~ /^\+ (\w+)=(\S+)$/) { # Parse "+ DATE=/bin/date"
$name = $1;
$val = $2;
} else {
next;
}
print "Setting '$name' to '$val'\n" if (1);
# NOTE: It'd be better to use something like "$shell_vars{$name} = $val",
# but this does what was asked (ie. $DATE = "/bin/date")...
no strict 'refs';
${$name} = $val; # assign to like-named variable in Perl
}
close($fh) or die "close: ", $! ? $! : "Exit status $?";
print "DATE: ", `$DATE` if defined($DATE);
你肯定可以做更多的错误检查,但如果您想要捕获的只是shell变量,这对我来说就是诀窍。
答案 5 :(得分:0)
是的,您现在可以使用Env::Modify
module。
$result = file_get_contents($url);
答案 6 :(得分:0)
我在一个项目的OP中满足了一个紧迫的需求,在该项目中,我需要通过采购定义环境的shell脚本来配置Perl脚本(就此而言,可以是任何一种语言)。
除了配置和环境设置外,我个人很少将采购用于其他任何事情(我知道采购的唯一另一个好理由是在shell脚本中导入函数,但我可能缺少一些创造性的用法)。
我的解决方案是从启动器脚本(在外壳中)中获取配置脚本,然后在同一启动器脚本中 exec Perl脚本(用Perl脚本有效替换启动器脚本,因此避免创建子流程。
# configuration_script.sh
export MY_ENV_VAR1=value1
export MY_ENV_VAR2=value2
# launcher_script.sh
. configuration_script.sh # source the configuration
exec /path/to/main_script.pl "$@" # could be any other language here (Python, Tcl, Ruby, C, Java...)
“ $ @”允许将命令行参数从启动器脚本传递到主脚本。
然后由主要脚本作者来检索环境(例如,在Perl中使用$ ENV {MY_ENV_VAR1})。