概要:
前段时间,要做这样一个校验:当不符合要求的文件,通过修改文件后缀名后,仍然不允许上传。
我想这是大家经常会遇到的一个校验问题。我才用的办法是:用16进制读取文件头部(不妨成为head),比较head和常见文件头部16进制编码,进行判断。
我个人认为,这个校验方法有弊端,例如当两中不同的文件的文件头编码一样时,一种符合上传要求,一种不符合上传要求,起不到校验功能,例如office 2007和zip。
但是这个方法还是很实用的,毕竟文件头一样的不同文件总是不多的,而且在网站上传是碰到的就更少了,对图片校验还是非常有效的,目前没发现常见图片文件头相同的现象。
注明:office 2007和zip,一般都是允许的上传文件格式,“你可以上传ppt/pptx, doc/docx, ... ,多个文件可以压缩成zip,rar上传”,所以不用担心这个情况了。同文件头编码总是不多的!
ZIP Archive (zip),文件头:504B0304 MS Word/Excel (xlsx pptx docx),文件头: 504B0304 当 docx 没有内容时,没有找到文件头;当它有内容时,它有文件头:504B0304
文章顺序:
1.常见文件后缀名
2.我的代码
3.参考的资料
1.常见文件后缀名
参见:http://www.cnblogs.com/xxchao/p/3965005.html
2.我的代码
代码有什么改进的方法,求高手指教一二,谢谢。
。。。。InputStream in = fileItem.getInputStream(); String head = readOriginal2Hex(in, 4).toUpperCase(); if(null == head || "".equals(head)){ msgBean.setMsg("请上传.jpg/.jpeg/.png/.gif/.bmp的格式").setMsgCode(MsgBean.MsgCode.FAILURE); return msgBean; } /* 文件开头的标志字符 JPEG (jpg),文件头:FFD8FF PNG (png),文件头:89504E47 GIF (gif),文件头:47494638 Windows Bitmap (bmp),文件头:424D */ if("47494638".equals(head) || "89504E47".equals(head) || "FFD8FF".equals(head.substring(0, 6)) || "424D".equals(head.substring(0, 4))){。。。。 //做你要的业务} 。。。。。/** * 读取文件开头n个字节,为16进制String * @param InputStream * @param int * @return String * @throws IOException */ public String readOriginal2Hex(InputStream in, int n) throws IOException{ //FileInputStream fin = new FileInputStream(new File(RO_HOME + BAK_FILE)); StringWriter sw = new StringWriter(); int len = 1; byte[] temp = new byte[len]; //字节,字节(Byte)是计算机信息技术用于计量存储容量和传输容量的一种计量单位,1个字节等于8位二进制。 //16进制转化模块 for(int i = 0; (in.read(temp, 0, len)!=-1) && (i < n); i++){ if(temp[0] > 0xf && temp[0] <= 0xff){ // 10~ff sw.write(Integer.toHexString(temp[0])); }else if(temp[0] >= 0x0 && temp[0] <= 0xf){ // 0~f //对于只有一位的16进制数前面补“0” sw.write("0" + Integer.toHexString(temp[0])); }else{ //对于int<0的位转化为16进制的特殊处理,因为Java没有Unsigned int,所以这个int可能为负数 sw.write(Integer.toHexString(temp[0]).substring(6)); /* 对于为什么是从6开始截,这涉及内存溢出的知识,我的解释是:java调试跟踪查到 -1 ffffffff,-40 ffffffd8,-31 ffffffe1 ,一个字节8位二进制,最大255 = ff,一个16进制数由4位二进制数转化得来,这里无符号数才能到达255,下次在说理由。。 有知道的说下。。 */ } } return sw.toString(); }
3.参考的资料
http://blog.csdn.net/cdtdx/article/details/1529804