bluethundr has asked for the wisdom of the Perl Monks concerning the following question:

Hey guys,

It's been a long and unwelcomed departure from the perl fold. Unfortunately, I had to take a break from Randal and Tom's _wonderful_ book to do some work mandated after work study. Wonder why no kid says "hey! I wanna be an IT guy when I grow up!"

Oh well, poor me. :) At least I have a job. But I have a passion for learning perl at this point. Took me a while to re-read through all the material a second time up to the point I left off ...chapter 13... and made sure I still understood all the exercises I did before and even tried re-writing most from scratch. I actually feel the second pass has helped me to get the material a bit deeper into my nueral pathways. After my work assignment was done I even took my dilapedated Llama copy with me onto a cruise ship to the Bahamas and did some perl whilst imbibing Bahama Mamas. Heaven! :D

But right at this point my brain seems like a frozen lump of clay and I was hoping for some help! For some godforesaken reason I seem to have forgotten how to do a simple pattern match!

Exercise 4 in chapter 13 of Llama asks the student to replicate the unix 'ln' function. The question implies that the File::Basename function can come in handy here, but I am going to try attacking that angle after I've had a good night's sleep. In the meantime, I simply can't for the _LIFFE_ of me figure out why the following code breaks at compile time!

=====================================
#!/usr/bin/perl use strict; use warnings; my @list; print "\nPlease enter the name of the file you would like to rename : +"; chomp (my $name = <STDIN>); print "\nPlease enter the name/location you would like the file change +d to: "; chomp (my $final = <STDIN>); print "\nThe name you entered is $name and the output desired is $fina +l."; if ($final =~ /(\-s*)/) { symlink $name, $final or die "\nCouldn't create symlink!"; @list = glob "$name, $final"; } else { link $name, $final or die "\nCouldn't create link!"; @list = glob "$name, $final"; } foreach (@list) { print "\nYou've succesfullly linked or symlinked $_ to"; } print "\nYou're Done\n\n";


=======================================

The error message I get back reads thus:
syntax error at ./ex4-13 line 14, near "$final ~" BEGIN not safe after errors--compilation aborted at ./ex4-13 line 16.


Once the light dawns on this one I will be able to un-lumpify my brain. And monkish un-lumpification will be appreciated.

Much Thanks to the Monkery!



As a side note, I've moved up in the world. Before I would only do perl under vi on init level 3 to be "hardcore" about my Unix use. These days? OS X and BBEdit, baby! Oohhh yeah! BALANCE them braces! I find I have a taste for luxury after that cruise and my hard fought for new Apple laptop!

Replies are listed 'Best First'.
Re: brain re-engaging perl mode
by pg (Canon) on Oct 24, 2004 at 03:53 UTC

    symlink is not implemented on all platforms, to make your code more portable, do something like this:

    if (eval { symlink("",""); 1 }) { symlink "a", "b"; } else { print "symlink is not implemented\n"; }
Re: brain re-engaging perl mode
by tilly (Archbishop) on Oct 24, 2004 at 02:17 UTC
    The code that you posted runs.

    Somehow you're looking at different code than you're running. Did you, for instance, forget to hit "save" in your editor before trying to run the script?

      Boy, I must really be brain dead and tired! Yup that code ran though not quite exactly as I predicted. The symlink portion seems still to be broken. I think I will try working with it some more tomorrow. Thanks for your input. Any other suggestestions anyone would like to make are always welcome, of course.

      Thanks!
Re: brain re-engaging perl mode
by graff (Chancellor) on Oct 24, 2004 at 09:54 UTC
    Save yourself a lot of typing and frustration: start using ARGV instead of prompting the user and fetching values for variables via responses from STDIN.

    I don't get why you're using glob here... Could you explain what  @list = glob "$name, $final"; is supposed to do?

    Also, the basis for your decision between symlink and hard link seems cryptic, and possibly at odds with your probable intention. (But even given your reply to tilly, it's not clear what your intention is, or what might still be going wrong with the symlink part.)

    Based on the regex in your "if" statement, any of the following values for $final would trigger creation of a symlink having this value as its name: "-", "foo-", "-s", "foo-s", "-ss", "foo-ss", "foo-bar", "pre-sorted", and many more. Basically, any value that contains a hyphen, whether or not the hyphen is followed by any number of s's.

    Just guessing now... Do you want all the symlinks you create to have "-s" at the end of their names? Then:

    use strict; my $Usage = <<ENDUSE; Usage: $0 file_name link_name if link_name ends with "-s", it will be a symbolic link. otherwise, it will be created as a hard link. ENDUSE die $Usage unless ( @ARGV == 2 and -e $ARGV[0] ); if ( $ARGV[1] =~ /-s$/ ) { symlink $ARGV[0], $ARGV[1] or die "symlink failed: $!\n"; } else { link $ARGV[0], $ARGV[1] or die "link failed: $!\n"; } print "$ARGV[1] is now installed as a link to $ARGV[0]\n";
    Now, if your intention is to allow any string as a symlink name (including any that does not end with "-s"), you could accept an optional third argument in the command line usage -- something like "-s file_name link_name" -- i.e.:
    my $Usage = <<ENDUSE; Usage: $0 [-s] file_name link_name blah blah... ENDUSE my $ltype = ( @ARGV and $ARGV[0] eq '-s' ) ? shift : ''; die $Usage unless ( @ARGV == 2 and -e $ARGV[0] ); if ( $ltype eq '-s' ) { symlink ... } else { link ... }
    (this is, of course, just how the unix "ln" command works)
Re: brain re-engaging perl mode
by Zaxo (Archbishop) on Oct 24, 2004 at 06:13 UTC

    Since you're doing your job, you'll probably get a little time to relax in the corporate mudbath. Use the moment to jail your imagination in a fertile but remote part of your head. Hide the symptoms if they threaten to become obvious to the headhunters and beancounters.

    After Compline,
    Zaxo