develooper Front page | perl.perl5.porters | Postings from January 2008

Re: MM_Win32.t failures (caused by PathTools upgrade)

Thread Previous | Thread Next
From:
Michael G Schwern
Date:
January 31, 2008 10:57
Subject:
Re: MM_Win32.t failures (caused by PathTools upgrade)
Message ID:
47A21A09.4080203@pobox.com
Steve Hay wrote:
>> Can you check what File::Spec->canonpath("C:trick\dir\now_OK") does?
> 
> Ick. You didn't mean that: you meant check what
> File::Spec->canonpath('C:trick\dir\now_OK') does, and the answer is
> nothing:
> 
> C:\p5p\bleadperl>.\perl -MFile::Spec -e "print
> File::Spec->canonpath('C:trick\dir\now_OK')"
> C:trick\dir\now_OK

Oh, I was thinking wrong.  MakeMaker is doing the right thing, meaning it's 
just doing what File::Spec does.  MakeMaker can be removed from consideration 
as part of the bug.  MakeMaker's test is wrong and should be using catpath().


>> Probably use a blank directory to represent root.  That's what Unix
>> does.  Try: 
>>
>> catdir( 'c:', '', 'trick', 'dir' );
> 
> No good either:
> 
> C:\p5p\bleadperl>.\perl -MFile::Spec -e "print File::Spec->catdir('C:',
> '', 'trick', 'dir')"
> C:trick\dir

Thinking more about this, it probably shouldn't work given that catdir() is 
treating C: as a directory so you're asking for a root directory in the middle 
of the path which doesn't make any sense.

catpath() is the correct thing to use.


>> Actually the correct answer is "none of the above" because catdir()
>> uses directories, not volumes.  In reality the correct thing to use
>> is catpath(). 
> 
> It's still confusing:
> 
> C:\p5p\bleadperl>.\perl -MFile::Spec -e "print File::Spec->catpath('C:',
> 'trick', 'file')"
> C:trick\file
> 
> C:\p5p\bleadperl>.\perl -MFile::Spec -e "print
> File::Spec->catpath('C:\\', 'trick', 'file')"
> C:\trick\file
 >
> In other words catpath() expects the $volume to be something like C:\
> rather than just C:, which is at odds with splitpath() which returns the
> $volume as just C:
>
> C:\p5p\bleadperl>.\perl -MFile::Spec -e "print
> +(File::Spec->splitpath('C:\trick\file'))[0]"
> C:

This is all correct.  splitpath() returns ($volume, $directories, $file) so 
the return value should be:

("C:", "\trick\", "file")

It's arguable whether the volume name should be "C" or "C:".  Depends on 
whether or not : is considered part of the volume name or just the volume 
separator.

Try this:

print join "\n", File::Spec->splitpath('C:\trick\file');
print File::Spec->catpath("C:", File::Spec->catdir("", "trick"), "file");

It should say:
C:
\trick\
file
C:\trick\file

That invocation of catpath/catdir is how you're supposed to do it.  I will 
admit that getting File::Spec to work correctly with volumes and root dir is 
confusing.  Path::Class is supposed to make this easier, but it doesn't appear 
to have any method for getting the volume at all.


>>> my @path_eg = qw( c: / trick dir/now_OK );
>>> print catdir(@path_eg);
>> That doesn't work?  Now that is odd.  Have you tried using backwhacks?
> 
> That definitely doesn't work with either forward- or back-slashes:
> 
> C:\p5p\bleadperl>.\perl -MFile::Spec -e "print File::Spec->catdir(qw(C:
> / trick dir/now_OK))
> C:trick\dir\now_OK
> 
> C:\p5p\bleadperl>.\perl -MFile::Spec -e "print File::Spec->catdir(qw(C:
> \ trick dir\now_OK))
> C:trick\dir\now_OK

Ok, that all makes sense now once you realize that catdir() does not 
understand the concept of a volume.  If you think about it in terms of Unix 
you have just asked for:

	catdir(qw(a / b c));

which is like a//b/c and it just threw out the duplicate slash.


-- 
Ahh email, my old friend.  Do you know that revenge is a dish that is best
served cold?  And it is very cold on the Internet!

Thread Previous | Thread Next


nntp.perl.org: Perl Programming lists via nntp and http.
Comments to Ask Bjørn Hansen at ask@perl.org | Group listing | About