
試圖幫助我的岳父解決一個奇怪的問題:突然間,他的新 MacBook Pro 上的 iCloud Drive 文件的很大一部分(可能是 20%)無法開啟。我查看過它,有問題的文件似乎是沒有文件擴展名的文件。它們顯示為“Unix 可執行檔”而不是 .doc 檔案。
如果我進入並將 .doc 新增為檔案副檔名,該檔案將立即下載並正確開啟。
有人以前看過這個嗎?除了實際手動重命名數百個文件(一次一個)之外,還有其他解決方案嗎?
答案1
在 Mac OS 9 及更早版本中,Mac 了解檔案類型的唯一方法是透過檔案「類型」和「創建者」程式碼。在 OS X 中,它切換到擴展,但這些代碼仍然存在(可能可以覆蓋一開始的設置,但現在我認為它們是識別文件的“備份”方式)。
我剛剛獲取了一個 DOC 檔案(擴展名為 .doc),將其重命名為“Foo”(無擴展名),Finder 識別了它。使用該xattr
命令,我可以看到原始文件中的程式碼已複製到新文件中,因此我的第一台 Mac 上的 Finder 可以打開。
檢查另一台 Mac 上的 Finder(透過 iCloud 同步),發現「Foo」檔案是 UNIX 檔案。因此,iCloud 不會從來源同步擴充屬性。如果沒有副檔名,您必須在目標端重新套用程式碼,或僅新增副檔名。
如果幸運的話,您已將 Word、Excel 等檔案保存在單獨的資料夾中,並且可以批次重新命名(請參閱下文)。如果沒有,您可以file
對每個檔案執行該命令以查看它是什麼,然後手動重新命名。
要批量重命名文件,我認為有很多工具可以做到這一點,或者您可以使用這個 Perl 腳本來做到這一點。我幾年前寫的,它很蹩腳,但它適用於我扔給它的所有東西。
#!/usr/bin/perl
use strict;
use File::Copy;
if (scalar(@ARGV) < 2) {
print "\nUSAGE: $0 <extension> <file(s)>\n\n";
exit 1;
}
my $ext = shift;
# Strip off leading period, since we'll add it later.
$ext =~ s/^\.//;
# Everytime I pass this script's @ARGV back out to a system call
# the whole argument arrary gets treated like a long string.
# If any individual $ARGV had spaces in it, that $ARGV ends up
# looking like multiple args to the system call.
# So, parse each $ARGV one at a time, in double-quotes.
foreach my $arg (@ARGV) {
if ($arg =~ m/\./) {
# This $arg already has an extension!
if ($arg =~ m/\.$ext$/) {
# This $arg already has this $ext. Skip it.
warn "WARNING! $arg already has that extension.\n";
next;
}
else {
# This $arg has an extension, but it's not the same as $ext.
warn "WARNING! $arg already had an extension.\n";
}
}
renameFile("\$", ".$ext", $arg);
}
sub renameFile {
my $searchString = shift;
my $replacementString = shift;
my $file = shift;
if (-e "$file") {
my $newName = $file;
if ($newName =~ s/$searchString/$replacementString/ge) {
if (-e "$newName") {
print "ERROR! Unable to move '$file' to '$newName' because\n";
print " a file named '$newName' already exists!\n";
}
else {
print "Moving '$file' to '$newName'.\n";
move("$file", "$newName") || die "Unable to rename '$file'.\nStopped";
}
}
}
else {
print "File '$file' does not exist.\n";
}
}