![]() |
|
![]() | ||
|
Subject:
Need a Perl or shell (bash) script, or Netatalk tweak
Category: Computers > Programming Asked by: haversian-ga List Price: $14.50 |
Posted:
06 Oct 2002 02:28 PDT
Expires: 15 Oct 2002 02:27 PDT Question ID: 73157 |
I have a linux box running netatalk, which is letting Macintosh clients violate the Macintosh (OS9.2, 8.x, 7.5.x) naming conventions. Specifically, since ext3 is case sensitive, netatalk allows filenames differing only by case, but when the Mac tries to make use of these files simultaneously (for example, by copying a folder containing both foo and FOO from the server to the desktop), it complains that they're the same file. So, I need a way to configure Netatalk to disallow Mac clients from creating files differing only by case. OR A Perl or bash script to clean up. Specifically I want a script with the following characteristics: Will accept one or more directory names as command line arguments Will resursively search through all files in the directories given When it locates two or more files in the same directory whose filenames differ only by case, it will truncate the filenames of all but the first duplicate file to 23 characters and append the following string: "DUP#nnnn" where nnnn is a zero-extended integer in the range 0-9999. This number should be stored in a file (can be hard-coded in the script - I'll change it to be where I want it), and should increment by one each time a file renaming is performed. The script should operate efficiently. I have a directory which may contain 100,000+ files spanning 15GB, and it needs to be checked daily - this is not an operation that can take 6 hours. The files will not be changing while the script is running - reading a directory worth of filenames into an array for sorting may be a good way to start. When the file containing nnnn reaches 9999, it should wrap over to 0000. The order in which directories are scanned is unimportant. |
![]() | ||
|
There is no answer at this time. |
![]() | ||
|
Subject:
Re: Need a Perl or shell (bash) script, or Netatalk tweak
From: gmuslera-ga on 07 Oct 2002 14:24 PDT |
Why not make case insensitive the directory where the files are stored? A way that this can be done is in example configuring samba to export the "real" tree as case-insensitive, mount that share, and put it as the netatalk exported dir, so the clients will be not worried about duplicates filenames. |
Subject:
Re: Need a Perl or shell (bash) script, or Netatalk tweak
From: kyleha-ga on 08 Oct 2002 13:47 PDT |
#!/usr/bin/perl # # This seems to work. I just wrote it and tested it quickly. # use strict; use File::Find; use IO::File; use IO::Dir; my $counter_file = 'counter_file'; my $counter; my $fh = new IO::File $counter_file; if ( ! $fh ) { warn "can't read $counter_file: $!"; $counter = 0; } else { $counter = <$fh>; $fh->close; } foreach my $dir ( @ARGV ) { check_dir( $dir ); } $fh = new IO::File ">$counter_file"; if ( ! $fh ) { die "can't write $counter_file: $!"; } print $fh "$counter\n"; $fh->close; exit; sub check_dir { my ( $dir ) = @_; print "check_dir( $dir );\n"; my @dirs = (); my $dh = new IO::Dir $dir; my $fn; my %collide = (); my @tmp = (); while ( defined( $fn = $dh->read ) ) { push( @tmp, $fn ); } undef $dh; foreach my $fn ( @tmp ) { my $file = "$dir/$fn"; if ( -f $file ) { $fn =~ tr/A-Z/a-z/; if ( $collide{ $fn }++ ) { my $ending = next_counter(); $fn = substr( $fn, 0, 23 ) if ( length( $fn ) > 23 ); my $newname = "$fn\#$ending"; rename( $file, "$dir/$newname" ) || die "can't rename '$dir/$fn' to '$dir/$newname': $!"; } } elsif ( -d $file ) { next if ( $file =~ m:(/\.\.?$|^\.\.?$): ); push( @dirs, $fn ); } } foreach my $subdir ( @dirs ) { check_dir( "$dir/$subdir" ); } } sub next_counter { my $out = $counter++; $counter %= 10000; $out = "0$out" while ( length( $out ) < 4 ); return $out; } |
Subject:
Re: Need a Perl or shell (bash) script, or Netatalk tweak
From: haversian-ga on 09 Oct 2002 13:03 PDT |
Thanks much for the script! There's a bug somewhere that causes the first renamed file (each time the script is run) to be named incorrectly - rather than get 0001 added, it's getting 001? - I think the question mark is actually \n, but I'm not positive. Only happens to the first file, only happens when reading counter_file as opposed to generating a new one because it's missing. This doesn't happen to later renamings, so I've inelegantly fixed it using $counter++; $counter--; which does the trick. If I weren't a Perl newbie maybe I could do better than a cosmetic solution. *shrug* Again, thanks - it seems to be working just fine on my test cases as well. This afternoon I'll run it on (a copy of) the real data. |
If you feel that you have found inappropriate content, please let us know by emailing us at answers-support@google.com with the question ID listed above. Thank you. |
Search Google Answers for |
Google Home - Answers FAQ - Terms of Service - Privacy Policy |