文件在不同的作業系統上提供不同的 Mime 類型
所以我有一個 bash 腳本,它部分執行以下操作:
file -b --mime-type "$1"
然後我有邏輯來檢查它是否是預期的文件類型。
if [[ $type == "application/gzip" ]]; then <stuff> exit 0 fi # basically the else echo "File type $type not supported"
所以我在 Debian 系統上建構了這個腳本,所有的邏輯都很好。然而,當一位同事問他是否可以在他正在使用的某些系統(基於 CentOS)上使用它時,他不斷得到以下錯誤輸出:
File type application/x-gzip not supported
該腳本旨在可移植,因此使用 bash 和 file 等。我試圖在
/usr/share/magic
CentOS 系統上查看,它似乎是純文字。然而,在 Debian 上,它是二進制格式,並且更難與之互動。所以我的理解是,通過呼叫
---mime-type
這將在每個作業系統上每次顯示相同的 mime 類型。我知道我可以將 if 添加application/x-gzip
到 if 語句中,但是如果有辦法使輸出保持一致,我寧願將其作為一個選項。另外,如果我將來在這個腳本中添加其他部分,或者將它用作未來工作的模板,我希望有一種方法可以在作業系統之間獲得一致的輸出,這樣我就不必擔心很多邊緣案例。如果有辦法獲得一致的答案,我可以更改為文件以外的其他內容。
提前致謝。
編輯#00
我最初將 IANA 視為參考,但後來意識到 IANA 無法辨識許多類型。這當然會讓事情變得更糟。
至於您對版本差異的建議,我認為這可能是根本原因,因為 Debian 系統在附近:
redacted@redacted ~$ file -v file-5.35 magic file from /etc/magic:/usr/share/misc/magic
而 CentOS 系統位於:
redacted@redacted ~$ file -v file-5.11 magic file from /etc/magic:/usr/share/misc/magic
至於來自 strace 的測試,它確實出現(以及上面兩種環境的備份)正在讀取 /etc/magic 中的文件,而在 CentOS 的情況下,它是純文字的。strace 看起來像:
strace -e trace=stat,open,openat file -i bob.txt open("/usr/lib64/tls/x86_64/libmagic.so.1", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory) stat("/usr/lib64/tls/x86_64", 0x7fff0427d1d0) = -1 ENOENT (No such file or directory) open("/usr/lib64/tls/libmagic.so.1", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory) stat("/usr/lib64/tls", {st_mode=S_IFDIR|0555, st_size=4096, ...}) = 0 open("/usr/lib64/x86_64/libmagic.so.1", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory) stat("/usr/lib64/x86_64", 0x7fff0427d1d0) = -1 ENOENT (No such file or directory) open("/usr/lib64/libmagic.so.1", O_RDONLY|O_CLOEXEC) = 3 open("/usr/lib64/tls/libz.so.1", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory) open("/usr/lib64/libz.so.1", O_RDONLY|O_CLOEXEC) = 3 open("/usr/lib64/tls/libc.so.6", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory) open("/usr/lib64/libc.so.6", O_RDONLY|O_CLOEXEC) = 3 open("/usr/lib/locale/locale-archive", O_RDONLY|O_CLOEXEC) = 3 stat("/root/.magic.mgc", 0x7fff0427e750) = -1 ENOENT (No such file or directory) stat("/root/.magic", 0x7fff0427e750) = -1 ENOENT (No such file or directory) stat("/etc/sysconfig/64bit_strstr_via_64bit_strstr_sse2_unaligned", 0x7fff0427dcb0) = -1 ENOENT (No such file or directory) open("/etc/magic.mgc", O_RDONLY) = -1 ENOENT (No such file or directory) stat("/etc/magic", {st_mode=S_IFREG|0644, st_size=111, ...}) = 0 open("/etc/magic", O_RDONLY) = 3 open("/usr/share/misc/magic.mgc", O_RDONLY) = 3 open("/usr/lib64/gconv/gconv-modules.cache", O_RDONLY) = 3 stat("bob.txt", {st_mode=S_IFREG|0644, st_size=19, ...}) = 0 open("bob.txt", O_RDONLY) = 3 bob.txt: text/troff; charset=us-ascii +++ exited with 0 +++
不要介意 troff 和 .txt 不匹配,這是故意的。TROFF 被選中,所以它不僅僅是純文字……
我會看看我的同事是否可以在 CentOS 盒子上更新文件的版本,看看結果是否更好。
編輯#01
因此,查看另一個工具 xdg-mime,我發現在該程序中(至少),x-gzip 和 gzip 之間似乎沒有功能差異。
它似乎被認為是該程序中的別名(我正在研究是否會有獨立的魔法儲存來解決這個問題)。因此,魔術文件中的任何一種變體似乎都很常見。
IANA 已於
application/gzip
2012 年定義。但即對於 HTTP 有這個註釋:
$$ … $$或與以前的 HTTP 實現兼容,應用程序應該考慮 “x-gzip” 和 “x-compress” 分別等同於 “gzip” 和 “compress”。
但那是針對 HTTP/1.1 的,而且相當(非常)舊——而且是一種不同的遊戲,這完全取決於它的用途。
gzip 本身是從 90 年代初開始的,在那個時候,也有人說
x-
可以用於未註冊的子類型。一般來說,兩者都已經被使用。如果可以選擇,我會使用非
x-
變體。但是由於野獸的性質,像這樣的事情100%的*一致性是非常困難的。*就像file
隨著時代的變化而變化一樣,其他做同樣事情的工具也隨著時代的變化而變化。至於標準等,RFC 6838(2013 年 1 月) 強烈反對使用
x-
類型。如果看一下
file
命令本身,就會發現它在 2019 年x-gzip
被替換為(從外觀上看)。gzip
請注意,還有一個帶有 x-gzip的 BGZF(Blocked gzip) 。這是*“更”*可以理解的,因為它是 gzip 的變體,儘管與上面提到的 RFC 相衝突。再說一遍,這些事情需要很長時間才能到位。它用於,誰知道,有多少應用程序等。
確保它一致的唯一方法是確保跨系統使用相同的數據庫。
file
使用魔術模式文件 ,當然可以將其與腳本一起分發,*magic.mgc
*並說應該將其放入$HOME/.magic
或類似文件中-或使用-m
腳本中的選項(使用此/這些魔術文件)。如果使用不同版本的人可能會遇到問題file
- 但不確定是哪個版本等。魔術文件以文本形式編寫,然後編譯成 mgc。
file -C -m my-magic-file
但也可以將其用作純文字。也許 CentOS 系統上發生了什麼?A
strace
應該揭示發生了什麼,例如strace -e trace=stat,open,openat file -i foo.ext
抱歉,如果這變得非常不一致並且到處都是。