我们在之前的文章

JavaWeb静态资源分离思路

中已经了解到要把文件上传到静态资源服务器有三种方式:

java上传文件到ftp服务器(这个方案需要在静态资源服务器安装ftp服务)

java使用HttpURLConnection上传文件到远程服务器  (分为客户端和服务端,客户端负责上传,服务端负责接收文件)

java使用HttpClient通过Post上传文件到远程服务器  (分为客户端和服务端,客户端负责上传,服务端负责接收文件)

本章我们就来尝试HttpURLConnection上传文件到远程服务器。

我们在之前的文章中已经在SpringMVC基础框架的基础上应用了BootStrap的后台框架,在此基础上记录HttpURLConnection上传文件到远程服务器。

应用bootstrap模板

基础项目源码下载地址为:

SpringMVC+Shiro+MongoDB+BootStrap基础框架

我们在基础项目中已经做好了首页index的访问。
现在就在index.jsp页面和index的路由Controller上做修改,HttpURLConnection上传文件到远程服务器。

客户端

客户端HttpURLConnection上传文件到远程服务器的原理是通过构造参数模仿form提交文件的http请求,把文件提交到远程服务器的接收路由中。

index.jsp的代码为:

<%@ include file="./include/header.jsp"%><div id="page-wrapper"><div id="page-inner"><div class="row"><div class="col-md-12"><h1 class="page-header">HttpURLConnection <small>HttpURLConnection</small></h1></div></div><!-- /. ROW  --><form class="form-horizontal" name="upform" action="upload" method="post" enctype="multipart/form-data"><div class="form-group"><label for="sourceModule" class="col-sm-2 control-label">上传文件:</label><div class="col-sm-10"><input type="file" name="filename"/><br/>  <input type="submit" value="提交" /><br/> </div></div></form>  <!-- /. ROW  --></div><!-- /. PAGE INNER  --></div><!-- /. PAGE WRAPPER  --><%@ include file="./include/footer.jsp"%><script type="text/javascript">$(document).ready(function () {});</script></body></html>

当提交表单里包含文件上传的时候,即Form的enctype属性值为multipart/form-data时,后台是无法像普通表单那样通过request.getParameter来获取用户提交的数据的。

这时候,当然可以通过解析提交到服务器的数据流来得到数据了,但是这样不但麻烦而且容易出错。

最好的方式是使用第三方的jar包获取数据,这方面有很多现成的成熟优秀的jar包。最常用的时以下三个:

apache的commons-fileupload : http://commons.apache.org/fileupload/

O'Reilly的cos: http://www.servlets.com/cos/index.html

jspsmart的SmartUpload:官方不提供下载了,google搜吧。

其中,据评测效率最高的是COS,最慢的是SmartUpload;最常用的是common-upload;文件太大时SmartUpland会崩溃。

我们这里使用commons-fileupload,需要引入两个jar包:commons-fileupload-1.3.1.jar和commons-io-2.4.jar。

下载地址:

http://central.maven.org/maven2/commons-fileupload/commons-fileupload/1.3.1/commons-fileupload-1.3.1.jar

http://central.maven.org/maven2/commons-io/commons-io/2.4/commons-io-2.4.jar

如果是maven项目,在pom.xml中增加:

<!-- https://mvnrepository.com/artifact/commons-fileupload/commons-fileupload -->
<dependency><groupId>commons-fileupload</groupId><artifactId>commons-fileupload</artifactId><version>1.3.1</version>
</dependency>
<!-- https://mvnrepository.com/artifact/commons-io/commons-io -->
<dependency><groupId>commons-io</groupId><artifactId>commons-io</artifactId><version>2.4</version>
</dependency>

路由中upload方法接受form提交的file文件,并且上传到服务器:

IndexController.java代码如下:

package com.test.web.controller;import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;import javax.servlet.http.HttpServletRequest;import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.shiro.SecurityUtils;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;import com.alibaba.fastjson.JSONObject;
import com.test.web.message.response.JSONResult;/*** IndexController* * */
@Controller
public class IndexController {private static final String FAR_SERVICE_DIR = "http://192.168.30.39:8080/receive";//远程服务器接受文件的路由private static final long yourMaxRequestSize = 10000000;@RequestMapping("/")public String index(Model model) throws IOException {return "/index";}@RequestMapping("/upload")public String upload(HttpServletRequest request) throws Exception {// 判断enctype属性是否为multipart/form-databoolean isMultipart = ServletFileUpload.isMultipartContent(request);if (!isMultipart)throw new IllegalArgumentException("上传内容不是有效的multipart/form-data类型.");// Create a factory for disk-based file itemsDiskFileItemFactory factory = new DiskFileItemFactory();// Create a new file upload handlerServletFileUpload upload = new ServletFileUpload(factory);// 设置上传内容的大小限制(单位:字节)upload.setSizeMax(yourMaxRequestSize);// Parse the requestList<?> items = upload.parseRequest(request);Iterator iter = items.iterator();while (iter.hasNext()) {FileItem item = (FileItem) iter.next();if (item.isFormField()) {// 如果是普通表单字段String name = item.getFieldName();String value = item.getString();// ...} else {// 如果是文件字段String fieldName = item.getFieldName();String fileName = item.getName();String contentType = item.getContentType();boolean isInMemory = item.isInMemory();long sizeInBytes = item.getSize();// ...//上传到远程服务器InputStream uploadedStream = item.getInputStream();HashMap<String, InputStream> files = new HashMap<String, InputStream>();files.put(fileName, uploadedStream);uploadToFarService(files);uploadedStream.close();}}return "redirect:/";}public void uploadToFarService(HashMap<String, InputStream> files) {try {String BOUNDARY = "---------7d4a6d158c9"; // 定义数据分隔线URL url = new URL(FAR_SERVICE_DIR);HttpURLConnection conn = (HttpURLConnection) url.openConnection();// 发送POST请求必须设置如下两行conn.setDoOutput(true);conn.setDoInput(true);conn.setUseCaches(false);conn.setRequestMethod("POST");conn.setRequestProperty("connection", "Keep-Alive");conn.setRequestProperty("user-agent","Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1)");conn.setRequestProperty("Charsert", "UTF-8");conn.setRequestProperty("Content-Type","multipart/form-data; boundary=" + BOUNDARY);OutputStream out = new DataOutputStream(conn.getOutputStream());byte[] end_data = ("\r\n--" + BOUNDARY + "--\r\n").getBytes();// 定义最后数据分隔线Iterator iter = files.entrySet().iterator();int i=0;while (iter.hasNext()) {i++;Map.Entry entry = (Map.Entry) iter.next();String key = (String) entry.getKey();InputStream val = (InputStream) entry.getValue();String fname = key;File file = new File(fname);StringBuilder sb = new StringBuilder();sb.append("--");sb.append(BOUNDARY);sb.append("\r\n");sb.append("Content-Disposition: form-data;name=\"file" + i+ "\";filename=\"" + key + "\"\r\n");sb.append("Content-Type:application/octet-stream\r\n\r\n");byte[] data = sb.toString().getBytes();out.write(data);DataInputStream in = new DataInputStream(val);int bytes = 0;byte[] bufferOut = new byte[1024];while ((bytes = in.read(bufferOut)) != -1) {out.write(bufferOut, 0, bytes);}out.write("\r\n".getBytes()); // 多个文件时,二个文件之间加入这个in.close();}out.write(end_data);out.flush();out.close();// 定义BufferedReader输入流来读取URL的响应BufferedReader reader = new BufferedReader(new InputStreamReader(conn.getInputStream(), "UTF-8"));String line = null;while ((line = reader.readLine()) != null) {System.out.println(line);}} catch (Exception e) {System.out.println("发送POST请求出现异常!" + e);e.printStackTrace();}}}

服务端

我们仍然在基础项目上fileController中实现接收文件。代码如下:

FileController.java

package com.test.web.controller;import java.io.File;
import java.util.Iterator;
import java.util.List;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;/*** IndexController* * */
@Controller
public class FileController {//private static final String STORE_FILE_DIR="/usr/local/image/";//文件保存的路径private static final String STORE_FILE_DIR="D:\\";//文件保存的路径@RequestMapping("/receive")public String receive(HttpServletRequest request,HttpServletResponse response) throws Exception {// 判断enctype属性是否为multipart/form-databoolean isMultipart = ServletFileUpload.isMultipartContent(request);if (!isMultipart)throw new IllegalArgumentException("上传内容不是有效的multipart/form-data类型.");// Create a factory for disk-based file itemsDiskFileItemFactory factory = new DiskFileItemFactory();// Create a new file upload handlerServletFileUpload upload = new ServletFileUpload(factory);// Parse the requestList<?> items = upload.parseRequest(request);Iterator iter = items.iterator();while (iter.hasNext()) {FileItem item = (FileItem) iter.next();if (item.isFormField()) {// 如果是普通表单字段String name = item.getFieldName();String value = item.getString();// ...} else {// 如果是文件字段String fieldName = item.getFieldName();String fileName = item.getName();String contentType = item.getContentType();boolean isInMemory = item.isInMemory();long sizeInBytes = item.getSize();String filePath=STORE_FILE_DIR+fileName;//写入文件到当前服务器磁盘File uploadedFile = new File(filePath);// File uploadedFile = new File("D:\haha.txt");item.write(uploadedFile);}}response.setCharacterEncoding("UTF-8");  response.getWriter().println("上传成功");return null;}}

我们需要把服务端发布到 远程服务器上 使用tomcat等运行起来。

如果项目中有shiro拦截的话记得设置成  /receive = anon 。让接收文件的路由不被拦截。

然后运行客户端,选择文件就可以上传了。对安全有要求的,可以在客户端加一个key,服务器端接收到请求后验证key,没问题的话 再写入目录和文件。

java上传文件到远程服务器(一)---HttpURLConnection方式相关推荐

  1. 向服务器上传文件的命令,上传文件到远程服务器的命令

    上传文件到远程服务器的命令 内容精选 换一换 将文件上传至Windows云服务器一般会采用MSTSC远程桌面连接的方式.本节为您介绍本地Windows计算机通过远程桌面连接,上传文件至Windows云 ...

  2. 上传文件到服务器指令,上传文件到远程服务器的命令

    上传文件到远程服务器的命令 内容精选 换一换 将文件上传至Windows云服务器一般会采用MSTSC远程桌面连接的方式.本节为您介绍本地Windows计算机通过远程桌面连接,上传文件至Windows云 ...

  3. java上传文件到服务器,java上传文件到云服务器

    java上传文件到云服务器 内容精选 换一换 安装传输工具在本地主机和Windows云服务器上分别安装数据传输工具,将文件上传到云服务器.例如QQ.exe.在本地主机和Windows云服务器上分别安装 ...

  4. 文件怎么上传远程服务器,怎么上传文件到远程服务器

    怎么上传文件到远程服务器 内容精选 换一换 将文件上传至Windows云服务器一般会采用MSTSC远程桌面连接的方式.本节为您介绍本地Windows计算机通过远程桌面连接,上传文件至Windows云服 ...

  5. Git上传本地文件到服务器,git上传文件到远程服务器

    git上传文件到远程服务器 内容精选 换一换 将文件上传至Windows云服务器一般会采用MSTSC远程桌面连接的方式.本节为您介绍本地Windows计算机通过远程桌面连接,上传文件至Windows云 ...

  6. JAVA上传文件图片到服务器保存

    这里我记录一个比较简单方便操作的JAVA上传文件图片到服务器并且保存! 首先是页面 html的   我这是提交一个文件和类型 <div style="border: 1px solid ...

  7. java上传文件图片到服务器保存,Java上传文件图片到服务器的方法

    这里我记录一个比较简单方便操作的java上传文件图片到服务器并且保存,具体内容如下 首先是页面html的   我这是提交一个文件和类型 我是添加一张临时图片得到微信的media_id保存数据库! en ...

  8. Mac上传文件到远程服务器

    Mac上传文件到远程服务器,可以利用mac自带的终端来进行上传,使用sftp方式 终端shell菜单-> 新建远程连接 sftp方式,输入远程服务器ip 3. 然后连接,连的时候会让输入密码,输 ...

  9. Ftp实现上传文件至远程服务器

    服务器安装FTP服务 1.安装vsftpd yum -y install vsftpd 2.关闭匿名访问 vim /etc/vsftpd/vsftpd.conf 将anonymous_enable的值 ...

最新文章

  1. 大数据下的电商新打法
  2. 谷歌员工怒了 900人联名抗议 刚成立的AI道德委员会处境尴尬
  3. Angular--页面间切换及传值的四种方法
  4. 制作win7+ubuntu +winPE+CDlinux多系统启动U盘
  5. Arduino总结一
  6. vue.js 组件之间传递数据 1
  7. Linux文件编程(2)
  8. Spring常用注解的讲解
  9. PHP MySQL学生宿舍管理系统源代码_php高校学生宿舍管理系统
  10. window.onload 函数不执行处理
  11. js获取ip本机地址
  12. 960H 、SDI和百万高清,谁会率先出局?
  13. UCOSII 学习笔记(卢有亮视频相关习题)
  14. win gvim erlang 环境配置
  15. python中mysqldb模块_Python学习之MySQLdb模块
  16. MiniGUI中的几个画线函数
  17. ar军事作战数字三维仿真沙盘开发
  18. 什么是docker,它与虚拟机有什么区别?
  19. php fpm的pool,php-fpm的pool、PHP慢执行日志、open_basedir、php-fpm进程管理
  20. c语言功率算电量,电功率你理解透了吗?怎么算功率因数?1度电是多少?

热门文章

  1. 安泰科普:宽带功率放大器原理是什么样的
  2. Android常用控件之ExpandableList的使用
  3. 计算机通信与网络大纲中英文,《计算机通信网络》教学大纲(电子信息)
  4. python dict get default_Python locale.getdefaultlocale方法代碼示例
  5. 计算给定数据集的香农熵
  6. 积极准备、谨慎行动——应对多核编程革命
  7. 用LoadRunner进行脚本录制
  8. Python 自动发送邮件实战案例,人人都可以学会
  9. j-link “the connected j-link is defective“问题的解决
  10. 入门指南:菜鸟如何学习数据分析?