Beefy Boxes and Bandwidth Generously Provided by pair Networks
P is for Practical
 
PerlMonks  

Re: Find the full path of the script at run time

by mojotoad (Monsignor)
on Mar 13, 2003 at 00:01 UTC ( [id://242543]=note: print w/replies, xml ) Need Help??


in reply to Find the full path of the script at run time

Merely using Cwd and get_cwd() isn't going to cut the mustard -- mainly because you can invoke a script from directories other than your current working directory. Use abs_path() instead (or fast_abs_path()):

#!/usr/bin/perl -w use Cwd qw(abs_path); print "I am ", abs_path($0), "\n";

Note that abs_path() will also resolve chains of soft links, so if that's not what you want you might use rel2abs($0) from File::Spec, or you will have to back up a bit and manipulate $0 directly, possibly with get_cwd() and File::Spec for generating the cannonical path.

And in any of these cases, use File::Spec for slicing and dicing pathnames.

You can also just simply use FindBin, except that certain people might fuss at you for reasons such as these.

You might also find these nodes of interest, from Q&A:

Matt

Replies are listed 'Best First'.
Re: Re: Find the full path of the script at run time
by ibanix (Hermit) on Mar 13, 2003 at 00:12 UTC
    Thanks mojotoad.

    I'm not sure the abs_path method will work for me. I'm trying to share a set of scripts and associated files via a Windows network share. Here's what happens if I run
    use Cwd qw(abs_path); print "I am ", abs_path($0), "\n";
    via a script located on the network share:
    C:\>path_test.pl Cannot chdir to \\flash\it\NOC-TO~1\PATH_T~1.PL:No such file or direct +ory at \\flash\it\NOC-TO~1\PATH_T~1.PL line 2
    I'm guessing Cwd has issues with UNC paths.

    Perhaps I'll have to use $0 and hope for the best.

    $ echo '$0 & $0 &' > foo; chmod a+x foo; foo;
      Note my update above regarding rel2abs() from File::Spec.

      In this case, however, you are bumping into the difference between abs_path() and fast_abs_path(): both generate cannonical paths, but the first relies on the OS by repeatedly issuing chdir() on path fragments in order to verify that Cwd and the OS are in agreement. This will cause problems if the path in question is hypothetical or if you do not have permission to traverse the path tree.

      fast_abs_path(), on the other hand, does this "visually" without checking with the OS -- as a consequence it's much faster, but potentially more risky.

      99% of the time this is not a problem for most paths. If your paths have a tendency to utilize soft links that cross volumes and mount points (therefore potentially different filesystem types), then it can be a problem. Since Windows doesn't have soft links (shortcuts aren't soft links) then you shouldn't have a problem using fast_abs_path().

      Wrote a song about it once. Like to see it? Here it is.

      Matt

        Welp, I tried
        use File::Spec::Functions qw(rel2abs); print "I am ", rel2abs($0), "\n";
        and it works. It returns the exact same thing, in this one specific case, as plain $0.

        First, thanks for all the help! :-)

        Second, the decision. I have a bunch of scripts to convert. They will all be shared on a network drive and our team will run them over the network. I need the path so I can determine where the config files for the scripts are, on the fly, even if the whole set of scripts move to another location. This setup will let us always stay in-sync and share scripts, etc.

        Is it going to be worthwhile for me to put in the full-blown  use File::Spec::Functions qw(rel2abs);, or can I get away with just $0? This is a judgement call, but I want your judgements! :-)

        Update:

        After some experimentation, I've decided to go with the following for finding the directory my scripts are running in.
        use File::Spec::Functions qw(rel2abs splitpath catpath); (my $vol, my $dirs, undef) = splitpath( rel2abs($0) ); my $path = catpath( $vol, $dirs, undef ); print "I am ", $path, "\n";
        Thanks!
        ibanix

        $ echo '$0 & $0 &' > foo; chmod a+x foo; foo;

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://242543]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others scrutinizing the Monastery: (7)
As of 2024-04-19 09:31 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found