核心代码:

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Author : suk
import struct
from io import BytesIO # 支持文件类型
# 用16进制字符串的目的是可以知道文件头是多少字节
# 各种文件头的长度不一样,少则2字符,长则8字符
def typeList(types):
type_dict = {'jpg': ['FFD8FFE000104A464946'],
'png': ['89504E470D0A1A0A0000'],
'gif': ['47494638396126026F01'],
'tif': ['49492A00227105008037'],
'bmp': ['424D8E1B030000000000'],
'dwg': [''],
'html': ['3C21444F435459504520'],
'htm': ['3C21646F637479706520'],
'css': ['48544D4C207B0D0A0942'],
'js': ['696B2E71623D696B2E71'],
'rtf': ['7B5C727466315C616E73'],
'psd': [''],
'eml': ['46726F6D3A203D3F6762'],
'wps': ['D0CF11E0A1B11AE10000'],
'mdb': ['5374616E64617264204A'],
'ps': '[252150532D41646F6265]',
'pdf': ['255044462D312E'],
'rmvb': ['2E524D46000000120001'],
'flv': ['464C5601050000000900'],
'mp4': ['00000020667479706D70'],
'mp3': [''],
'mpg': ['000001BA210001000180'],
'wmv': ['3026B2758E66CF11A6D9'],
'wav': ['52494646E27807005741'],
'avi': ['52494646D07D60074156'],
'mid': ['4D546864000000060001'],
'zip': ['504B0304140000000800', '504B0304140000080800', '504B03040A0000080000'],
'rar': ['526172211A0700CF9073'],
'ini': ['235468697320636F6E66'],
'jar': ['504B03040A0000000000'],
'exe': ['4D5A9000030000000400'],
'jsp': ['3C25402070616765206C'],
'mf': ['4D616E69666573742D56'],
'xml': ['3C3F786D6C2076657273'],
'sql': ['494E5345525420494E54'],
'java': ['7061636B616765207765'],
'bat': ['406563686F206F66660D'],
'gz': ['1F8B0800000000000000'],
'properties': ['6C6F67346A2E726F6F74'],
'class': ['CAFEBABE0000002E0041'],
'chm': [''],
'mxp': [''],
'docx': ['504B0304140006000800', '504B03040A0000000000'],
'torrent': ['6431303A637265617465'],
'mov': ['6D6F6F76'],
'wpd': ['FF575043'],
'dbx': ['CFAD12FEC5FD746F'],
'pst': ['2142444E'],
'qdf': ['AC9EBD8F'],
'pwl': ['E3828596'],
'ram': ['2E7261FD']
}
ret = {}
for k_hex, v_prefix in type_dict.items():
if k_hex in types:
ret[k_hex] = v_prefix
return ret # 字节码转16进制字符串
def bytes2hex(bytes):
num = len(bytes)
hexstr = u""
for i in range(num):
t = u"%x" % bytes[i]
if len(t) % 2:
hexstr += u""
hexstr += t
return hexstr.upper() # 获取文件类型
def file_type(filename):
binfile = open(filename, 'rb') # 必需二制字读取
tl = typeList(types=["jpg", "zip", "docx"])
ftype = None
for type_name, hcode_list in tl.items():
flag = False
for hcode in hcode_list:
numOfBytes = int(len(hcode) / 2) # 需要读多少字节
binfile.seek(0) # 每次读取都要回到文件头,不然会一直往后读取
hbytes = struct.unpack_from("B" * numOfBytes, binfile.read(numOfBytes)) # 一个 "B"表示一个字节
f_hcode = bytes2hex(hbytes) # 如果判断不出来,打印出这个值,往字典增加即可
# print("上传数据流hex", s_hcode, '=', "代码字典hex", hcode) # 如果判断不出来,打印出这个值,往字典增加即可
if f_hcode == hcode:
flag = True
break
if flag:
ftype = type_name
break
binfile.close()
return ftype # 获取字节流类型
def stream_type(stream, types):
"""
:param stream:流数据
:param types:需要判断文件类型,格式:["jpg","jpn"]
:return:
"""
tl = typeList(types=types)
ftype = None
for type_name, hcode_list in tl.items():
flag = False
for hcode in hcode_list:
numOfBytes = int(len(hcode) / 2) # 需要读多少字节
hbytes = struct.unpack_from("B" * numOfBytes, stream[0:numOfBytes]) # 一个 "B"表示一个字节
s_hcode = bytes2hex(hbytes)
# print("上传数据流hex", s_hcode, '=', "代码字典hex", hcode) # 如果判断不出来,打印出这个值,往字典增加即可
if s_hcode == hcode:
flag = True
break
if flag:
ftype = type_name
break
return ftype def stream_split(stream, count=3):
"""
主要处理流是分段获取的数据
:param stream: 块流
:param count: 取多少段合成来判断类型,默认三段
:return:
"""
block_stream = BytesIO()
temp = 1
for block in stream:
block_stream.write(block)
if temp == count:
break
temp += 1
return block_stream.getvalue()

is_file_type.py

type_dict字典,根据自己上传的文件,来填写,数据来自互联网。

基于Flask的上传示例

@index.route('/upload', methods=['GET', 'POST'])
def upload(): if request.method == 'GET':
return render_template('upload.html') upload_obj = request.files.get('code_file') if not upload_obj:
return '没有选择文件上传' ret = stream_type(stream_split(upload_obj.stream), ["jpg", "png", "pdf"]) if not ret:
return '上传失败,文件类型不匹配,类型必须 "jpg" or "png" or "pdf"' file_name = upload_obj.filename
upload_obj.save(os.path.join('files', file_name)) return '上传文件成功'

upload.html

{% extends 'layout.html' %}
{% block content %}
<h1>上传代码</h1>
<form action="" method="post" enctype="multipart/form-data">
<input type="file" name="code_file">
<input type="submit" value="上传"></input>
</form>
{% endblock %}

开始上传文件:

上传不在列表中的文件类型


上传在列表中的文件类型

Python之基于十六进制判断文件类型的更多相关文章

  1. Python使用filetype精确判断文件类型

    Python使用filetype精确判断文件类型 判断文件类型在开发中非常常见的需求,怎样才能准确的判断文件类型呢?首先大家想到的是文件的后缀,但是非常遗憾的是这种方法是非常不靠谱的,因为文件的后缀是 ...

  2. 【转】python通过文件头判断文件类型

    刚刚看到一个好玩的程序,拉过来.原文地址:https://www.ttlsa.com/python/determine-file-type-by-the-file-header/ 侵权删. ===== ...

  3. Python使用filetype精确判断文件类型 (文件类型获取)

    filetype.py Small and dependency free Python package to infer file type and MIME type checking the m ...

  4. python准确判断文件类型

    判断文件类型在开发中非常常见的需求,怎样才能准确的判断文件类型呢?首先大家想到的是文件的后缀,但是非常遗憾的是这种方法是非常不靠谱的,因为文件的后缀是可以随意更改的,而大家都知道后缀在linux系统下 ...

  5. JavaScript根据文件名判断文件类型

    //JavaScript根据文件名判断文件类型 var imgExt = new Array(".png",".jpg",".jpeg",& ...

  6. 利用PHP取二进制文件头判断文件类型

    <?php $files = array('D:\no.jpg', 'D:\no.png','D:\no2.JPEG','D:\no.BMP'); $fileTypes = array( 779 ...

  7. Linux中用st_mode判断文件类型

    Linux中用st_mode判断文件类型 2012-12-11 12:41 14214人阅读 评论(4) 收藏 举报  分类: Linux(8)  C/C++(20)  版权声明:本文为博主原创文章, ...

  8. php 读取文件头判断文件类型的实现代码

    php代码实现读取文件头判断文件类型,支持图片.rar.exe等后缀. 例子: <?php $filename = "11.jpg"; //为图片的路径可以用d:/uploa ...

  9. PHP取二进制文件头快速判断文件类型的实现代码

    通过读取文件头信息来识别文件的真实类型. 一般我们都是按照文件扩展名来判断文件类型,但是这个很不靠谱,轻易就通过修改扩展名来躲避了,一般必须要读取文件信息来识别,PHP扩展中提供了类似 exif_im ...

随机推荐

  1. Markdown用法说明(用此篇博客做示例)

    一份好的博客文档离不开一个优秀的编辑器.借此篇文章介绍一下编写该博客markdown的语法,后续再增加介绍其他语法,方便大家写出更好更漂亮的文档.点击左上角github,有主题源码哦 一份好的博客文档 ...

  2. 让mysql的id字段变成表的主键

    1.#已经加主键 desc szdj.sys_message_user;alter table sys_message_user add constraint pk_mess_user primary ...

  3. 第四周课程总结&实验报告(二)

    Java实验报告(二) 实验二 Java简单类与对象 一. 实验目的 (1) 掌握类的定义,熟悉属性.构造函数.方法的作用,掌握用类作为类型声明变量和方法返回值: (2) 理解类和对象的区别,掌握构造 ...

  4. adb工具介绍与安装

    一天笑嘻嘻是一名测试人员,想了解Android的测试方法,于是,就找到了小测试. 笑嘻嘻:身为一名测试人员需要了解ADB的哪些内容? 小测试:了解原理和简单的命令使用就可以了. 笑嘻嘻:你有毒啊,都了 ...

  5. 【Python】【基础知识】【内置函数】【input的使用方法】

    原英文帮助文档: input([prompt]) If the prompt argument is present, it is written to standard output without ...

  6. java-selenium上传

    一.sendkeys()上传 HTML源码 <td>sendkeys上传</td> <div id='pf'><input type='file' id='p ...

  7. .Net Core使用AutoMapper做对象关系映射

    我想很多后端开发者,纠结于如何在Dto及表实体中做属性关系映射,因为真的太繁琐了., ⒈如何使用? Mapper.Initialize(cfg => cfg.CreateMap<Users ...

  8. LOJ526「LibreOJ β Round #4」子集

    题目 算是比较裸的题吧. 首先我们把符合要求的\((i,j)\)建一条边,那么我们要求的就是最大团. 转化为补图的最小独立集. 然后我们来证明补图是一个二分图. \((u,v)\)有边\(\Leftr ...

  9. PermissionError: [Errno 13] Permission denied: '/run/user/0/jupyter'

    解决办法:需要给/run/user整个目录开放权限,不能单独给'/run/user/0/jupyter'这个文件,因为jupyter是需要往目录中添加文件,/run/user/0/jupyter,此时 ...

  10. linux centos 安装mongoDB

    1.下载mongoDB 例如下载3.2.19 64位版本 https://fastdl.mongodb.org/linux/mongodb-linux-x86_64-rhel70-3.2.19.tgz ...