HttpURLConnection下载
HttpURLConnection下载步骤
1,将要下载的路径封装成一个url对象(一定是可以下载的路径)
2,通过url获取conn,并设置conn的各种属性,最重要的是setRequestMethod("GET");
3,判断code,如果是200,通过conn获取要下载的文件大小len
4,在本地创建一个RandomAccessFile文件,并设置长度 raf.setLength(len);
5,定义线程个数threadCount,每个线程要下载的字节大小threadSize,线程的开始下载位置startIndex,结束下载位置endIndex
6,for循环,给线程的threadId,线程的开始位置startIndex,endIndex进行赋值,并开启线程
7,定义一个MyThread类继承Thread,要放在主类的外面
8,定义threadId,startIndex,endIndex,并通过构造方法进行初始化
9,将要下载的路径封装成url对象
10,设置conn的属性,是重要的是设置请求头属性range ,conn.setRequestProperty("range" , "bytes="+startIndex+"-"+endIndex);
如果range属性设置错误会出现416,作用,设置请求的文件的起始位置
11,获取响应码,如果是206,获取输入流
12,创建一个RandomAccessFile,并设置raf.seek(startIndex),表示从这个位置开始写出
13,将输入流is中的数据放入到内存,raf将内存中的数据写出到文件,并可以设置写出的位置
14,关闭输入流is和随机访问流raf
注意事项:
1,要下载的路径一定是一个可下载的文件
2,在知道要下载文件大小后,通过raf创建本地文件,一定要设置文件的大小为len
3,在子线程中设置请求头range的时候一定要注意格式,conn.setRequestProperty("range","bytes:"+startIndex+"-"+endIndex);不然会出现416错误
4,在创建raf对象后,一定要设置要写的开始位置 raf.seek(startIndex);
5,下载的时候是请求方式是get,一定不能是Post不然会是411错误
HttpURLConnection断点续传下载步骤
1,在循环往外的写前,定义一个total用来记录从开始到现在写的字节个数
2,在循环里面,定义一个线程的当前位置int currentIndex = total + startIndex;
3,创建一个随机访问流,并设置模式为"rwd",直接写入硬盘
4,在设置请求头range前,创建一个bufferedReader,读取文件里面的数据,并将数据转换为int类型
5,然后将startIndex = 读取的结果
注意事项:
要使用RandomAccessFile(file,"rwd")来写,不然写出的文件内容为0,这样读取的时候字符串转换为数据就为异常
HttpURLConnection断点续传完善
问题,每次下载完,.txt文件也写完了,如果不删除,下次下载的时候直接下载完成了
解决方案:
1,在每个线程下载完之后,就将该.txt文件删除
2,删除如果删不掉,因为没有写完之后,没有关raf的流
package com.heima.download;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.InputStream;
import java.io.RandomAccessFile;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
public class Download {
public static void main(String[] args) {
try {
URL url = new URL("http://img1.3lian.com/2015/w2/60/d/41.jpg");
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
conn.setReadTimeout(5000);
conn.setConnectTimeout(5000);
int code = conn.getResponseCode();
System.out.println(code);
if (code == 200) {
int len = conn.getContentLength();
RandomAccessFile raf = new RandomAccessFile(
new File("fuck.jpg"), "rw");
raf.setLength(len);
int threadCount = 3;
int startIndex;
int endIndex;
int threadSize = len / threadCount;
for (int threadId = 0; threadId < threadCount; threadId++) {
startIndex = threadId * threadSize;
endIndex = (threadId + 1) * threadSize - 1;
if (threadId == threadCount - 1) {
endIndex = len - 1;
}
System.out.println(threadId);
new MyThread(threadId, startIndex, endIndex).start();
}
}
} catch (Exception e) {
}
}
}
class MyThread extends Thread {
int threadId;
int startIndex;
int endIndex;
MyThread(int threadId, int startIndex, int endIndex) {
this.threadId = threadId;
this.startIndex = startIndex;
this.endIndex = endIndex;
}
@Override
public void run() {
try {
URL url = new URL("http://img1.3lian.com/2015/w2/60/d/41.jpg");
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
conn.setConnectTimeout(5000);
conn.setReadTimeout(5000);
File file = new File(threadId+".txt");
if(file.exists()){
BufferedReader br = new BufferedReader(new FileReader(file));
startIndex = Integer.parseInt(br.readLine());
br.close();
}
System.out.println("线程"+threadId+"从"+startIndex+"开始下载");
conn.setRequestProperty("Range", "bytes="+startIndex+"-"+endIndex);
int code = conn.getResponseCode();
if(code == 206){
System.out.println("线程"+threadId+"开始下载");
InputStream is = conn.getInputStream();
RandomAccessFile raf = new RandomAccessFile(new File("fuck.jpg"), "rw");
raf.seek(startIndex);
int len = -1;
byte[] buffer = new byte[1024*10];
int total = 0;
while((len = is.read(buffer)) != -1){
raf.write(buffer, 0, len);
total = total + len;
int currentIndex = total + startIndex;
RandomAccessFile raf1 = new RandomAccessFile(new File(threadId+".txt"), "rwd");
raf1.write((currentIndex+"").getBytes());
raf1.close();
}
is.close();
raf.close();
System.out.println("线程"+threadId+"下载结束");
File file1 = new File(threadId+".txt");
file1.delete();
}
} catch (Exception e) {
e.printStackTrace();
}
}
}