当前位置: 首页 > news >正文

不用外部JAR包,自己实现JSP文件上传!

奋斗看书上(JSP应用与开发技术)使用JSP文件上传,写了个真无语,压根就有很多问题,上传500KB的文件传过去后只剩350KB,而且编码必须是GBK、GB2312,否则传过去的文件都数据截取不正确。

琢磨了许久,发现问题出在

int startPos = ((file.substring(0,pos)).getBytes()).length;
//取得文件数据的结束的位置
int endPos =((file.substring(0,boundaryLocation)).getBytes()).length;


这里,问题就是根据字符串获取的字节数,然后从字节数组里截取根本就不正确。而后自己实现了个,不用字符串字节,而是自己以字节找字节。如下:

UploadTelRecord.jsp

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%@page import="java.io.DataInputStream"%>
<%@page import="java.io.FileOutputStream"%>
<%@page import="java.io.File"%>
<%@page import="java.net.URLEncoder" %>
<!-- 上传通话录音文件 -->
<%!
 //在字节数组里查找某个字节数组,找到返回>=0,未找到返回-1
 private int byteIndexOf(byte[] data,byte[] search,int start)
 {
  int index=-1;
  int len=search.length;
  for(int i=start,j=0;i<data.length;i++)
  {  
  
   int temp=i;
   j=0;
   while(data[temp]==search[j])
   {
    System.out.println((j+1)+",值:"+data[temp]+","+search[j]);

    //计数
    j++;
    temp++;
    if(j==len)
    {
     index=i;
     return index;
    }
    
   }
   
     
  }
  return index;
 }
%>
<%
String getAction=request.getParameter("action");
if(getAction!=null&&(getAction.equals("upload"))) //上传文件
{
 //定义上传的最大文件字节数1M
 int MAX_SIZE=1024000;
 String rootPath;
 DataInputStream in=null;
 FileOutputStream fileOut=null;
 
 String remoteAddr=request.getRemoteAddr();
 String serverName=request.getServerName();
 String realPath=request.getRealPath("/");
 realPath=realPath.substring(0,realPath.lastIndexOf("\\"));
 //设置保存文件的目录
 rootPath=realPath+ "\\upload\\telRecord\\";
 //取得客户端上传的数据类型
 String contentType=request.getContentType();
 try{
  if(contentType.indexOf("multipart/form-data")>=0){
   in=new DataInputStream(request.getInputStream());
   int formDataLength=request.getContentLength();
   if(formDataLength>MAX_SIZE)
   {
    out.println("0,文件大小超过系统限制!");
    out.flush();
    return;
   } 
   //保存上传的文件数据
   byte dateBytes[]=new byte[formDataLength];
   int byteRead=0;
   int totalRead=0;
   while(totalRead<formDataLength)
   {
    byteRead=in.read(dateBytes,totalRead,formDataLength);
    totalRead+=byteRead;
   }
   String data=new String(dateBytes,"UTF-8");
   //取得上传的文件名
   String saveFile=data.substring(data.indexOf("filename=\"")+10);
   saveFile=saveFile.substring(0,saveFile.indexOf("\n"));
   saveFile=saveFile.substring(saveFile.lastIndexOf("\\")+1,saveFile.indexOf("\""));
   //取得数据分割字符串
   int lastIndex=contentType.lastIndexOf("="); //数据分割线开始位置boundary=---------------------------
   String boundary=contentType.substring(lastIndex+1,contentType.length());//---------------------------257261863525035
  
   //计算开头数据头占用的长度
  int startPos;
   startPos=byteIndexOf(dateBytes,"filename=\"".getBytes(),0);
   startPos=byteIndexOf(dateBytes,"\n".getBytes(),startPos)+1; //遍历掉3个换行符到数据块
   startPos=byteIndexOf(dateBytes,"\n".getBytes(),startPos)+1;
   startPos=byteIndexOf(dateBytes,"\n".getBytes(),startPos)+1;
   
   //边界位置
   int endPos=byteIndexOf(dateBytes,boundary.getBytes(),(dateBytes.length- startPos))-4;
   
   //创建文件
   String fileName=rootPath+saveFile;
   File checkFile=new File(fileName);
   if(checkFile.exists()){
    out.println("0,文件已经存在!");
    out.flush();
    return;
   }
   File fileDir=new File(rootPath);
   if(!fileDir.exists())
    fileDir.mkdirs();
   //写入文件
   fileOut=new FileOutputStream(fileName);     
   fileOut.write(dateBytes,startPos,(endPos-startPos));
   fileOut.flush();
   out.println("文件上传成功!保存在:"+fileName);
     
  }
  else
  {
   out.println("0,未找到上传文件!");
   out.flush();
   return;
  }
 }catch(Exception error)
 {
 
   out.println("发生异常:"+error.getMessage());
 }
 finally
 {
  try
  {
   if(in!=null)
   in.close();
   if(fileOut!=null)
   fileOut.close();
  }catch(Exception e ){}
  
 }
 out.println("<br><br>");
 out.println("<a href='UploadTelRecord.jsp'>继续上传</a>");
 return;
}
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
 <head>
 <title>上传通话记录</title>
 </head>
 
 <body style="margin:50px;">
 <p>请选择您要上传的通话录音文件,文件命名格式为:通话时间_手机号_联系人姓名.后缀,没有联系人姓名请置空,如:
 111213123123_10086_中国移动.amr,没有姓名则为111213123123_10086_.amr</p>
 <form method="POST" action="UploadTelRecord.jsp?action=upload" ENCTYPE="multipart/form-data">
 <input type="file" name="file1" size="30"><br/>
 <input type="submit" value="开始上传">
 </form>
 </body>
</html>




相关文章:

  • 计算机技术不是吓唬大众的工具!
  • Windows程序设计学习笔记--第一个Windows程序以及宽字符集(了解)
  • 云计算和大数据入门
  • Windows Azure使用必读
  • Windows Azure新功能:Hadoop和Web版的移动服务
  • 云计算的理解
  • 微软云存储SkyDrive API:将你的数据连接到任何应用、任何平台,及任何设备上...
  • 在 Windows Azure 上部署预配置 Oracle VM
  • 对于Visual Studio 2013中 Blend的HTML开发人员来说什么是新的
  • 微软云服务获政府认证 云服务或将迎来黄金期
  • SAE 搭建 WordPress
  • 自定义 WordPress 样式
  • 比较了一下基于PhoneGAP/JQ Mobile 等基于HTML5的Phone 开发框架
  • (poj1.2.1)1970(筛选法模拟)
  • 关于nmap的几个技巧
  • 深入了解以太坊
  • [js高手之路]搞清楚面向对象,必须要理解对象在创建过程中的内存表示
  • ComponentOne 2017 V2版本正式发布
  • CSS魔法堂:Absolute Positioning就这个样
  • Docker下部署自己的LNMP工作环境
  • ES6 学习笔记(一)let,const和解构赋值
  • iOS筛选菜单、分段选择器、导航栏、悬浮窗、转场动画、启动视频等源码
  • Javascript 原型链
  • Java多态
  • linux安装openssl、swoole等扩展的具体步骤
  • Linux各目录及每个目录的详细介绍
  • WebSocket使用
  • 浏览器缓存机制分析
  • 爬虫模拟登陆 SegmentFault
  • 前端学习笔记之观察者模式
  • 如何解决微信端直接跳WAP端
  • 算法系列——算法入门之递归分而治之思想的实现
  • 一、python与pycharm的安装
  • No resource identifier found for attribute,RxJava之zip操作符
  • #include到底该写在哪
  • (超简单)构建高可用网络应用:使用Nginx进行负载均衡与健康检查
  • (附源码)springboot 个人网页的网站 毕业设计031623
  • (机器学习的矩阵)(向量、矩阵与多元线性回归)
  • (十六)串口UART
  • (万字长文)Spring的核心知识尽揽其中
  • (原創) 人會胖會瘦,都是自我要求的結果 (日記)
  • (转)程序员疫苗:代码注入
  • (转)项目管理杂谈-我所期望的新人
  • (转载)Google Chrome调试JS
  • ***检测工具之RKHunter AIDE
  • .apk 成为历史!
  • .NET 6 Mysql Canal (CDC 增量同步,捕获变更数据) 案例版
  • .NET Standard / dotnet-core / net472 —— .NET 究竟应该如何大小写?
  • .NET 设计模式—简单工厂(Simple Factory Pattern)
  • @GlobalLock注解作用与原理解析
  • @value 静态变量_Python彻底搞懂:变量、对象、赋值、引用、拷贝
  • [ vulhub漏洞复现篇 ] ECShop 2.x / 3.x SQL注入/远程执行代码漏洞 xianzhi-2017-02-82239600
  • [].slice.call()将类数组转化为真正的数组
  • [【JSON2WEB】 13 基于REST2SQL 和 Amis 的 SQL 查询分析器
  • [04] Android逐帧动画(一)