5.资源下载断点续传实现

1需求场景

当我们下载文件时由于某种原因中断了连接,导致文件只下载了一部分到本地。
但是我们又不想重新开始下载,现在我们需要继续接着上次中断处继续下载文件。

2编程实现

这样的需求很难实现吗?其实不难。
git地址完整代码路径:
断点续传Demo完整代码路径

1)创造断点场景

首先为了重现暂停下载的场景,可以用这个方法:

/**
 * 下载网络资源的一部分
 * @param startPosition 起始下载位置
 * @param endPosition  终止下载位置
 * @param urlAddress 网络资源的url
 */
public static void download(long startPosition, long endPosition,String urlAddress){
    
    
    try {
    
    
        URL url = new URL(urlAddress);// 获得网络资源的URL
        HttpURLConnection connection = (HttpURLConnection) url
                .openConnection();// 获得连接对象
        connection.setRequestProperty("User-Agent", "NetFox");// 设置请求属性
        String rangeProperty = "bytes=" + startPosition + "-";// 定义请求范围属性
        if (endPosition > 0) {
    
    
            rangeProperty += endPosition;// 调整请求范围属性
        }
        connection.setRequestProperty("RANGE", rangeProperty);// 设置请求范围属性
        connection.connect();// 连接网络资源
        InputStream in = connection.getInputStream();// 获得输入流对象
        String file = url.getFile();// 获得文件对象
        String name = file.substring(file.lastIndexOf('/') + 1);// 获得文件名
        FileOutputStream out = new FileOutputStream(name, true);// 创建输出流对象,保存下载的资源
        byte[] buff = new byte[2048];// 创建字节数组
        int len = 0;// 定义存储读取内容长度的变量
        len = in.read(buff);// 读取内容
        while (len != -1) {
    
    
            out.write(buff, 0, len);// 写入磁盘
            len = in.read(buff);// 读取内容
        }
        out.close();// 关闭流
        in.close();// 关闭流
        connection.disconnect();// 断开连接
    } catch (Exception e) {
    
    
        e.printStackTrace();
    }
}

测试:

public static void main(String[] args) throws IOException {
    
    
    String urlAddress="https://cn.bing.com/sa/simg/Flag_Feedback.png";
    CoreCode.download(0,CoreCode.getResourceLength(urlAddress)-100,urlAddress);
}

运行之,结果如下:
在这里插入图片描述
打开看看:(因为这是不完整的,所以打不开是正常的)
在这里插入图片描述

2)实现断点续传

然后就是我们的核心代码,实现断点续传的方法。
此程序的逻辑起始很简单:
首先判断该文件是否是暂停下载的文件
如果是则获取其大小和完整资源的大小得到下载区间
然后接着这个下载区间进行下载即可。

/**
 * 支持自动断点续传的下载方法
 * @param urlStr 网络资源的url
 */
public static void downloadResource(String urlStr){
    
    
    long startPosition=0;
    long endPosition=0;
    try {
    
    
        URL url = new URL(urlStr);// 获得网络资源的URL
        HttpURLConnection connection = (HttpURLConnection) url
                .openConnection();// 获得连接对象
        String file = url.getFile();// 获得文件对象
        String name = file.substring(file.lastIndexOf('/') + 1);// 获得文件名
        File fileOb=new File(name);
        //判断是否是暂停下载的文件
        if(fileOb.exists()){
    
    
            startPosition=fileOb.length();
            endPosition=getResourceLength(urlStr);
        }
        connection.setRequestProperty("User-Agent", "NetFox");// 设置请求属性
        String rangeProperty = "bytes=" + startPosition + "-";// 定义请求范围属性
        if (endPosition > 0) {
    
    
            rangeProperty += endPosition;// 调整请求范围属性
        }
        connection.setRequestProperty("RANGE", rangeProperty);// 设置请求范围属性
        connection.connect();// 连接网络资源
        InputStream in = connection.getInputStream();// 获得输入流对象
        FileOutputStream out = new FileOutputStream(name, true);// 创建输出流对象,保存下载的资源
        byte[] buff = new byte[2048];// 创建字节数组
        int len = 0;// 定义存储读取内容长度的变量
        len = in.read(buff);// 读取内容
        while (len != -1) {
    
    
            out.write(buff, 0, len);// 写入磁盘
            len = in.read(buff);// 读取内容
        }
        out.close();// 关闭流
        in.close();// 关闭流
        connection.disconnect();// 断开连接
    } catch (Exception e) {
    
    
        e.printStackTrace();
    }
}

/**
 * 给定url地址获取资源的大小(以字节为单位)
 * @param urlStr
 * @return
 * @throws IOException
 */
public static long getResourceLength(String urlStr) throws IOException {
    
    
    URL url=new URL(urlStr);
    URLConnection urlConnection=url.openConnection();
    urlConnection.connect();
    return urlConnection.getContentLength();
}

测试:

public static void main(String[] args) throws IOException {
    
    
    String url="https://cn.bing.com/sa/simg/Flag_Feedback.png";
    CoreCode.downloadResource(url);
}

断点续传后,可以看到,完整的文件被下载了下来,顺利打开:
在这里插入图片描述

欢迎大家提出自己的看法。

猜你喜欢

转载自blog.csdn.net/c1776167012/article/details/120635031