断点续传http head头信息分析及java实现

1,客户端第一次下载

客户端request head信息GET /test/micro.rar HTTP/1.1User-Agent:RANGE: bytes=0-Host: 10.10.246.126:8983Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2Connection: keep-alive服务端response head信息HTTP/1.1 206 Partial ContentLast-Modified: Wed, 11 Jan 2012 03:09:24 GMTContent-Length: 392725947Accept-Ranges: bytesContent-Range: bytes 0-392725946/392725947

2,客户端断点续传

客户端request head信息

GET /test/micro.rar HTTP/1.1User-Agent:RANGE: bytes=147193856-Host: 10.10.246.126:8983Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2Connection: keep-alive服务端response head信息

HTTP/1.1 206 Partial ContentLast-Modified: Wed, 11 Jan 2012 03:09:24 GMTContent-Length: 245532091Accept-Ranges: bytesContent-Range: bytes 147193856-392725946/392725947

3,客户端已经下载完毕后,再次下载

客户端request head信息

GET /test/micro.rar HTTP/1.1User-Agent:RANGE: bytes=392725947-Host: 10.10.246.126:8983Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2Connection: keep-alive

服务端response head信息HTTP/1.1 416 Requested Range Not SatisfiableLast-Modified: Wed, 11 Jan 2012 03:09:24 GMTContent-Length: 392725947Accept-Ranges: bytesContent-Range: bytes */392725947

根据以上特性,可以通过java构造支持断点续传功能服务器与客户端

第一部分:服务器端代码:

File file = new File(location);if (file.exists()) {long p = 0;long fileLength;fileLength = file.length();// get file contentInputStream ins = new FileInputStream(file);bis = new BufferedInputStream(ins);// tell the client to allow accept-rangesresponse.reset();response.setHeader("Accept-Ranges", "bytes");// client requests a file block download start byteif (request.getHeader("Range") != null) {response.setStatus(javax.servlet.http.HttpServletResponse.SC_PARTIAL_CONTENT);p = Long.parseLong(request.getHeader("Range").replaceAll("bytes=", "").replaceAll("-", ""));}// support multi-threaded download// respone format:// Content-Length:[file size] – [client request start bytes from file block]response.setHeader("Content-Length", new Long(fileLength – p).toString());if (p != 0) {// 断点开始// 响应的格式是:// Content-Range: bytes [文件块的开始字节]-[文件的总大小 – 1]/[文件的总大小]String contentRange = new StringBuffer("bytes ").append(new Long(p).toString()).append("-").append(new Long(fileLength – 1).toString()).append("/").append(new Long(fileLength).toString()).toString();response.setHeader("Content-Range", contentRange);// pointer move to seekbis.skip(p);}String fileName = file.getName();response.addHeader("Content-Disposition", "attachment;filename=" + fileName);while ((size = bis.read(buf)) != -1) {response.getOutputStream().write(buf,0,size);response.getOutputStream().flush();}bis.close();

第二部分:客户端代码

public class TestDownload {

/*** @param args*/public static void main(String[] args) {// TODO Auto-generated method stubHttpURLConnection httpURLConnection = null;URL url = null;BufferedInputStream bis = null;byte[] buf = new byte[10240];int size = 0;String fileName = "aaa.zip";String filePath = "C:\\Users\\Desktop";String remoteUrl = "http://127.0.0.1:8080/down.zip";

// 检查本地文件RandomAccessFile rndFile = null;File file = new File(filePath + "\\" + fileName);long remoteFileSize = getRemoteFileSzie(remoteUrl);long nPos = 0;if (file.exists()) {long localFileSzie = file.length();if (localFileSzie < remoteFileSize) {System.out.println("文件续传…");nPos = localFileSzie;} else {System.out.println("文件存在,重新下载…");file.delete();try {file.createNewFile();} catch (Exception e) {// TODO: handle exceptione.printStackTrace();}}} else {// 建立文件try {file.createNewFile();} catch (Exception e) {// TODO: handle exceptione.printStackTrace();}}// 下载文件try {url = new URL(remoteUrl);httpURLConnection = (HttpURLConnection)url.openConnection();// 设置User-AgenthttpURLConnection.setRequestProperty("User-Agent", "Net");// 设置续传开始httpURLConnection.setRequestProperty("Range", "bytes=" + nPos + "-");// 获取输入流bis = new BufferedInputStream(httpURLConnection.getInputStream());rndFile = new RandomAccessFile(filePath + "\\" + fileName, "rw");rndFile.seek(nPos);int i = 0;while ((size = bis.read(buf)) != -1) {//if (i > 500) break;rndFile.write(buf, 0, size);i++;}System.out.println("i=" + i);httpURLConnection.disconnect();} catch (Exception e) {// TODO: handle exceptione.printStackTrace();}}

public static long getRemoteFileSzie(String url) {long size = 0;try {HttpURLConnection httpUrl = (HttpURLConnection)(new URL(url)).openConnection();size = httpUrl.getContentLength();httpUrl.disconnect();} catch (Exception e) {// TODO: handle exceptione.printStackTrace();}return size;}}

我们可以沿途用镜头记录彼此的笑脸,和属于我们的风景。

断点续传http head头信息分析及java实现

相关文章:

你感兴趣的文章:

标签云: