假设您想要在某个地方保存一堆文件,例如在blob中。假设您希望通过网页分发这些文件,并让客户端自动打开正确的应用程序/查看器。
假设:浏览器通过HTTP响应中的mime-type (content-type?)报头确定要使用哪个应用程序/查看器。
基于这个假设,除了文件的字节外,还需要保存MIME类型。
如何找到文件的MIME类型?我现在用的是Mac,但这应该也适用于Windows。
浏览器是否在将文件发布到网页时添加此信息?
是否有一个简洁的python库来查找这些信息?WebService还是(更好的)一个可下载的数据库?
@toivotuo的方法在python3下工作得最好,最可靠。我的目标是识别那些没有可靠的.gz扩展名的gzip文件。我安装了python3-magic。
import magic
filename = "./datasets/test"
def file_mime_type(filename):
m = magic.open(magic.MAGIC_MIME)
m.load()
return(m.file(filename))
print(file_mime_type(filename))
对于一个gzip文件,它返回:
应用程序/ gzip;charset =二进制
对于解压缩的TXT文件(iostat数据):
文本/平原;charset = us - ascii
对于tar文件:
应用程序/ x-tar;charset =二进制
对于bz2文件:
应用程序/ x-bzip2;charset =二进制
最后但并非最不重要的一个。zip文件:
应用程序/邮政编码;charset =二进制
在Python 3中。X和webapp的url文件不能有扩展名或假扩展名。您应该安装python-magic,使用
pip3 install python-magic
对于Mac OS X,你也应该使用libmagic
brew install libmagic
代码片段
import urllib
import magic
from urllib.request import urlopen
url = "http://...url to the file ..."
request = urllib.request.Request(url)
response = urlopen(request)
mime_type = magic.from_buffer(response.readline())
print(mime_type)
或者,您可以在read中输入一个大小
import urllib
import magic
from urllib.request import urlopen
url = "http://...url to the file ..."
request = urllib.request.Request(url)
response = urlopen(request)
mime_type = magic.from_buffer(response.read(128))
print(mime_type)
libmagic的Python绑定
关于这个主题的所有不同答案都非常令人困惑,所以我希望通过概述libmagic的不同绑定来更清楚地说明问题。以前mammadori给出了一个简短的回答,列出了可用的选项。
libmagic
模块名称:魔术
pypi: file-magic
来源:https://github.com/file/file/tree/master/python
在确定文件mime类型时,所选择的工具简单地称为file,其后端称为libmagic。(请参阅项目主页。)该项目是在一个私有cvs存储库中开发的,但在github上有一个只读的git镜像。
现在,如果你想在python中使用任何libmagic绑定,你将需要这个工具,它已经自带名为file-magic的python绑定。关于它们没有太多专门的文档,但是您可以查看c库的手册页:man libmagic。基本用法在自述文件中描述:
import magic
detected = magic.detect_from_filename('magic.py')
print 'Detected MIME type: {}'.format(detected.mime_type)
print 'Detected encoding: {}'.format(detected.encoding)
print 'Detected file type name: {}'.format(detected.name)
除此之外,您还可以使用示例文件中所示的Magic .open(flags)创建Magic对象来使用这个库。
toivotuo和ewr2san都使用文件工具中包含的这些文件魔术绑定。他们错误地认为,他们使用的是python魔法包。这似乎表明,如果同时安装了file和python-magic,则python模块magic指的是前者。
python-magic
模块名称:魔术
pypi: python-magic
来源:https://github.com/ahupp/python-magic
这是Simon Zimmermann在他的回答中提到的图书馆,Claude COULOMBE和Gringo Suave也使用了这个图书馆。
filemagic
模块名称:魔术
pypi: filemagic
来源:https://github.com/aliles/filemagic
注:本项目最后一次更新是在2013年!
由于基于相同的c-api,这个库与libmagic中包含的file-magic有一些相似之处。只有mammadori提到过,没有其他答案使用它。
我首先尝试mimetypes库。如果它不起作用,我就使用python-magic库。
import mimetypes
def guess_type(filename, buffer=None):
mimetype, encoding = mimetypes.guess_type(filename)
if mimetype is None:
try:
import magic
if buffer:
mimetype = magic.from_buffer(buffer, mime=True)
else:
mimetype = magic.from_file(filename, mime=True)
except ImportError:
pass
return mimetype
Python 3参考:https://docs.python.org/3.2/library/mimetypes.html
mimetypes.guess_type(url, strict=True) Guess the type of a file based
on its filename or URL, given by url. The return value is a tuple
(type, encoding) where type is None if the type can’t be guessed
(missing or unknown suffix) or a string of the form 'type/subtype',
usable for a MIME content-type header.
encoding is None for no encoding or the name of the program used to
encode (e.g. compress or gzip). The encoding is suitable for use as a
Content-Encoding header, not as a Content-Transfer-Encoding header.
The mappings are table driven. Encoding suffixes are case sensitive;
type suffixes are first tried case sensitively, then case
insensitively.
The optional strict argument is a flag specifying whether the list of
known MIME types is limited to only the official types registered with
IANA. When strict is True (the default), only the IANA types are
supported; when strict is False, some additional non-standard but
commonly used MIME types are also recognized.
import mimetypes
print(mimetypes.guess_type("sample.html"))
我很惊讶没有人提到它,但是pyments能够对mime类型做出有根据的猜测,特别是文本文档。
pyuments实际上是一个Python语法高亮显示库,但它有一个方法,可以根据您的文档是500种受支持的文档类型中的哪一种进行有根据的猜测。
即c++ vs c# vs Python vs等等
import inspect
def _test(text: str):
from pygments.lexers import guess_lexer
lexer = guess_lexer(text)
mimetype = lexer.mimetypes[0] if lexer.mimetypes else None
print(mimetype)
if __name__ == "__main__":
# Set the text to the actual defintion of _test(...) above
text = inspect.getsource(_test)
print('Text:')
print(text)
print()
print('Result:')
_test(text)
输出:
Text:
def _test(text: str):
from pygments.lexers import guess_lexer
lexer = guess_lexer(text)
mimetype = lexer.mimetypes[0] if lexer.mimetypes else None
print(mimetype)
Result:
text/x-python
现在,它不是完美的,但如果您需要能够分辨出500种文档格式中正在使用的是哪一种,这是非常有用的。
13年后……
本页上关于python3的大多数答案不是过时就是不完整。
要获得我使用的文件的mime类型:
import mimetypes
mt = mimetypes.guess_type("https://www.w3.org/WAI/ER/tests/xhtml/testfiles/resources/pdf/dummy.pdf")
if mt:
print("Mime Type:", mt[0])
else:
print("Cannot determine Mime Type")
# Mime Type: application/pdf
现场演示
来自Python文档:
mimetype。guess_type (url,严格= True)
根据文件的文件名、路径或URL (URL)来猜测文件的类型。URL可以是字符串或类似路径的对象。
返回值是一个元组(type, encoding),如果无法猜到类型(缺少或未知后缀),则type为None,或者是一个'type/subtype'形式的字符串,可用于MIME内容类型头。
encoding为None,表示没有编码或用于编码的程序名称(例如compress或gzip)。该编码适合作为Content-Encoding标头使用,而不是Content-Transfer-Encoding标头。映射是表驱动的。编码后缀区分大小写;类型后缀首先区分大小写,然后不区分大小写。
可选的strict参数是一个标志,指定已知MIME类型列表是否仅限于在IANA注册的正式类型。当strict为True(默认值)时,只支持IANA类型;当strict为False时,一些额外的非标准但常用的MIME类型也会被识别出来。
在3.8版更改:增加了对url是类路径对象的支持。