in reply to Problem with Renaming script

It looks like you may be trying to "rename" the file to a new directory. Are you sure that the new directory has been created at the point where the "rename" is being done?

Apart from that, it might make more sense to set this process up as a "filter" that will create a new set of files, rather than as an "in-place edit" that will relocate and then modify the files.

(The filter approach just seems safer -- if you find problems with what the program does, just fix it and run it again, because the original files that it used as input the first time are still where they used to be, and will still have the same contents they originally had, when you run it again.)

To summarize (in pseudo-perl):

locate the source directory and get the list of files there establish the name of the destination directory, and create it if nec +essary if $source_dir has subdirectories { create them as needed in the $dest_dir } for $infile ( @sourc_files ) { $outfile = $infile; $outfile =~ s{$source}{$dest}; # might be unnecessary? open(IN,"<","$source_dir/$infile"); open(OUT, ">","$dest_dir/$outfile"); while (<IN>) { s/$source/$dest/g; print OUT; } close IN; close OUT; }
It shouldn't need to be any more complicated than that (except maybe the initial part of finding the files and subdirectories, but I gather you already solved that part).

Replies are listed 'Best First'.
Re: Re: Problem with Renaming script
by kirk123 (Beadle) on May 22, 2003 at 15:49 UTC
    Hi, I am not creating a new directory.
      Oh -- sorry, I must have misunderstood. Well, I wonder if there might be some problem about a file being "open" in some sense when you're trying to rename it, and MSWindows not letting you do that... though the code you showed makes this seem unlikely.

      Still, it might be worthwhile to try a different different approach to the problem. Something like:

      my $oldhostname = "whatever"; my $newhostname = shift || "somethingnew"; die "Nothing to do\n" if ( $oldhostname eq $newhostname ); print "changing $oldhostname to $newhostname\n"; open( FLIST, "<file_containing_list_of_filenames" ) or die "Unable to get list of file names to personalize\n"; my @oldfiles = <FLIST>; chomp @oldfiles; my @renamefiles = grep /$oldhostname/i, @oldfiles; s/$oldhostname/$newhostname/gi for @renamefiles; for my $file ( @oldfiles ) { my $newfile = ( $file =~ /$oldhostname/i ) ? shift @renamefiles : "$file.tmp"; open(IN, "<$file") or die "Unable to read $file: $!\n"; open(OUT, ">$newfile) or die "Can't write $newfile:$!\n; while (<IN>) { s/$oldhostname/$newhostname/gi; print OUT; } close OUT; close IN; unlink $file; rename $newfile, $file if ( $newfile eq "$file.tmp" ); }
      Things to note: (1) if you're going to declare lexically scoped variables with "my", declare each variable as you need it, in the block where it will be used, not globally (which kind of defeats some of the value of lexical scoping).

      (2) This approach uses a different strategy than your original -- since it knows it will need to rewrite every file anyway, it'll use a standard filtering approach, using "newhostname" to set the name of the output file where appropriate, then deleting the old file, and renaming the new one back to the original name if that wasn't supposed to change.

      That's not tested, of course, but assuming that you have already taken care of creating the appropriate list of file names for input to the process, and have the host names the way you want, this should take care of the rest of the task.

      (Personally, if it were my machine, I'd probably want to write all the output files to some separate directory, or at least keep the originals intact somehow, so I could confirm that worked okay before blowing away the originals...)