如何在 Perl 中查找用户的主目录?

发布于 2024-08-05 16:34:46 字数 301 浏览 12 评论 0原文

我需要检查用户主目录中的文件是否存在,因此使用文件检查:

if ( -e "~/foo.txt" ) {
   print "yes, it exists!" ;
}

即使用户主目录下有一个名为 foo.txt 的文件,Perl 总是 抱怨没有这样的文件或目录。当我用 /home/jimmy 替换“~”时(假设用户是 jimmy),Perl 会给出正确的判断。

你能解释一下为什么“~”在 Perl 中不起作用并告诉我 Perl 的方法是什么吗 找到用户的主目录?

I need to check whether a file in a user's home directory exists so use file check:

if ( -e "~/foo.txt" ) {
   print "yes, it exists!" ;
}

Even though there is a file called foo.txt under the user's home directory, Perl always
complains that there is no such file or directory. When I replace "~" with /home/jimmy (let's say the user is jimmy) then Perl give the right verdict.

Could you explain why "~" dosen't work in Perl and tell me what is Perl's way to
find a user's home directory?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(6

瞄了个咪的 2024-08-12 16:34:46

~ 是一个 bash-ism 而不是 perl-ism,这就是它不起作用的原因。鉴于您似乎使用的是 UNIX 类型的系统,可能最简单的解决方案是使用 $HOME 环境变量,例如:

if ( -e $ENV{"HOME"} . "/foo.txt" ) {
    print "yes ,it exists!" ;
}

是的,我知道用户可以更改他们的 $HOME 环境变量,但我会假设他们知道他们在做什么。如果没有,他们应得的一切:-)

如果你想以正确的方式做到这一点,你可以查看File::HomeDir,它更懂平台。您可以在以下脚本 chkfile.pl

use File::HomeDir;
$fileSpec = File::HomeDir->my_home . "/foo.txt";
if ( -e $fileSpec ) {
    print "Yes, it exists!\n";
} else {
    print "No, it doesn't!\n";
}

和脚本中看到它的运行情况:

pax$ touch ~/foo.txt ; perl chkfile.pl
Yes, it exists!

pax$ rm -rf ~/foo.txt ; perl chkfile.pl
No, it doesn't!

~ is a bash-ism rather than a perl-ism, which is why it's not working. Given that you seem to be on a UNIX-type system, probably the easiest solution is to use the $HOME environment variable, such as:

if ( -e $ENV{"HOME"} . "/foo.txt" ) {
    print "yes ,it exists!" ;
}

And yes, I know the user can change their $HOME environment variable but then I would assume they know what they're doing. If not, they deserve everything they get :-)

If you want to do it the right way, you can look into File::HomeDir, which is a lot more platform-savvy. You can see it in action in the following script chkfile.pl:

use File::HomeDir;
$fileSpec = File::HomeDir->my_home . "/foo.txt";
if ( -e $fileSpec ) {
    print "Yes, it exists!\n";
} else {
    print "No, it doesn't!\n";
}

and transcript:

pax$ touch ~/foo.txt ; perl chkfile.pl
Yes, it exists!

pax$ rm -rf ~/foo.txt ; perl chkfile.pl
No, it doesn't!
梦醒时光 2024-08-12 16:34:46

我不确定每个人是如何错过 File::HomeDir 的。这是听起来很容易的艰巨任务之一,因为没有人知道你必须考虑的所有愚蠢的例外情况。它没有附带 Perl,因此您需要自己安装。

知道主目录后,使用 File::Spec 构建所需的路径:

 use File::HomeDir qw(home);
 use File::Spec::Functions qw(catfile);

 print "The path is ", catfile( home(), 'foo.txt' ), "\n";

I'm not sure how everyone missed File::HomeDir. It's one of those hard tasks that sound easy because no one knows about all of the goofy exceptions you have to think about. It doesn't come with Perl, so you need to install it yourself.

Once you know the home directory, construct the path that you need with File::Spec:

 use File::HomeDir qw(home);
 use File::Spec::Functions qw(catfile);

 print "The path is ", catfile( home(), 'foo.txt' ), "\n";
笑红尘 2024-08-12 16:34:46

您可以glob波浪号,glob('~/foo.txt') 应该可以工作。或者您可以使用 File::Save::Home 模块还要照顾其他系统。

You can glob the tilde, glob('~/foo.txt') should work. Or you can use the File::Save::Home module that should also take care of other systems.

我不在是我 2024-08-12 16:34:46

用户的主目录存储在/etc/passwd中。获取信息的最佳方式是 getpw* 函数

#!/usr/bin/perl 

use strict;
use warnings;

print "uid:", (getpwuid 501)[7], "\n",
    "name:", (getpwnam "cowens")[7], "\n";

要解决您的具体问题,请尝试以下代码:

if ( -e (getpwuid 
gt;)[7] . "/foo.txt" ) {
   print "yes ,it exists!";
}

The home directory for a user is stored in /etc/passwd. The best way to get at the information is the getpw* functions:

#!/usr/bin/perl 

use strict;
use warnings;

print "uid:", (getpwuid 501)[7], "\n",
    "name:", (getpwnam "cowens")[7], "\n";

To address your specific problem, try this code:

if ( -e (getpwuid 
gt;)[7] . "/foo.txt" ) {
   print "yes ,it exists!";
}
难得心□动 2024-08-12 16:34:46

快进到 2020 年,从版本 5.31.10 开始,perl 中现在有一个名为 File 的模块: :Glob 解析波浪号,例如:

perl -MFile::Glob=":bsd_glob" -lE 'say File::Glob::bsd_glob( "~john" )'

会产生: /home/john

perl -MFile::Glob=":bsd_glob" -lE 'say File::Glob::bsd_glob( "~/some/folder" )'

会产生: /home/jack/some/folder

文件: :Glob 模块自 perl v5.6 起就存在,但仅与已弃用的 glob 子例程一起使用。

Fast forward to 2020 and there is now in perl since version 5.31.10 at its core a module called File::Glob which resolves the tilde, such as:

perl -MFile::Glob=":bsd_glob" -lE 'say File::Glob::bsd_glob( "~john" )'

would produce: /home/john

or

perl -MFile::Glob=":bsd_glob" -lE 'say File::Glob::bsd_glob( "~/some/folder" )'

would produce: /home/jack/some/folder

The File::Glob module exist since perl v5.6, but only with the glob subroutine which has been deprecated.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文