本文转载:http://www.cnblogs.com/TianFang/archive/2007/01/03/610739.html

断点续传的原理很简单,就是在Http的请求和应答的报文头上和一般的下载有所不同而已。

普通方式请求服务器上的一个文时,所发出的请求和接受到的服务器如下:

request header:
Cache-Control: no-cache
Connection: close
Pragma: no-cache
Accept: */*
Host: localhost response header:
200
Content-Type: application/octet-stream
Content-Disposition: attachment;FileName=time.pdf 当服务器支持断点续传时,请求和应答如下: request header:
Cache-Control: no-cache
Connection: close
Pragma: no-cache
Accept: */*
Host: localhost
Range: bytes=15360- response header:
206
Content-Type: application/octet-stream
Content-Disposition: attachment;FileName=time.pdf 两个报文的不同部分已用红色部分标记出来。可以看出: 客户端报文头中通过Range报文头来标识客户期望的下载位置。
服务器的应答号为200时表示是从文件头开始下载,而206表示是从文件的特定位置开始传输,客户端从该应答号可以看出服务器是否支持断点续传。
也就是说,支持断点续传的时候可以从文件任一部分开始下载,而普通的方式只能从文件头开始下载。 要使得服务器支持断点续传,需要解决以下几个问题: 1。需要判断客户端是否是续传请求,如果是续传请求时,需要获取客户端所需的文件范围。 从上面的分析可以看到,当客户端为断点传输时,报文头里会增加Range字段,则可以通过如下方式判断是否是断点传输请求。 string range = request.Headers["Range"];
bool isResume = string.IsNullOrEmpty(range); 2。对客户端做正确的应答相应,以通知客户端服务器支持端点续传 当为断点传输请求时,对客户端的相应号可以通过如下方式设置: response.StatusCode = 206; 3。传送客户端所需正确的内容 传送客户端所需正确的内容一般需要经过以下几个步骤 通过分析range来获取客户端的文件请求范围。
断点传输请求时,所需的长度比文件的长度短,故需要正确的设置response.ContentLength64属性。
正确传输所需的内容
代码示例: static void ProcessHttpClient(object obj)
{
HttpListenerContext context = obj as HttpListenerContext;
HttpListenerRequest request = context.Request;
HttpListenerResponse response = context.Response; FileStream fs = File.OpenRead(@"f:\123.pdf"); //待下载的文件 long startPos = 0;
string range = request.Headers["Range"];
bool isResume = string.IsNullOrEmpty(range);
if (isResume) //断点续传请求
{
//格式bytes=9216-
startPos = long.Parse(range.Split('=')[1].Split('-')[0]);
response.StatusCode = 206;
response.ContentLength64 = fs.Length - startPos;
fs.Position = startPos; //设置传送的起始位置
}
else
{
response.ContentLength64 = fs.Length;
} Console.WriteLine("request header");
Console.WriteLine(request.Headers.ToString()); response.ContentType = "application/octet-stream"; string fileName = "time.pdf";
response.AddHeader("Content-Disposition", "attachment;FileName=" + fileName);
Stream output = response.OutputStream; try
{
Console.WriteLine("response header");
Console.WriteLine(response.Headers.ToString());
CopyStream(fs, output); //文件传输
output.Close();
}
catch (HttpListenerException e) //在未写完所有文件时,如果客户端关闭连接,会抛此异常
{
Console.WriteLine(e.Message);
//output.Close(); //如果执行此函数会抛异常在写入所有字节之前不能关闭流。
}
} static void CopyStream(Stream orgStream, Stream desStream)
{
byte[] buffer = new byte[1024]; int read = 0;
while ((read = orgStream.Read(buffer, 0, 1024)) > 0)
{
desStream.Write(buffer, 0, read); System.Threading.Thread.Sleep(1000); //模拟慢速设备
}
}

  

ASP.NET用HttpListener实现文件断点续传的更多相关文章

  1. B/S大文件断点续传

    一. 功能性需求与非功能性需求 要求操作便利,一次选择多个文件和文件夹进行上传:支持PC端全平台操作系统,Windows,Linux,Mac 支持文件和文件夹的批量下载,断点续传.刷新页面后继续传输. ...

  2. [Asp.net 5] Options-配置文件(2)

    很久之前写过一篇介绍Options的文章,2016年再打开发现很多变化.增加了新类,增加OptionMonitor相关的类.今天就对于这个现在所谓的新版本进行介绍. 老版本的传送门([Asp.net ...

  3. asp.net和js读取文件的MD5值的方法

    前言 文件的md5值,即文件签名,为了验证文件的正确性,是否被恶意篡改等.每个文件有一个唯一的md5值. 最近公司开发的app文件包的校验就有用到文件md5值. 一.asp.net获取 ①和上传文件一 ...

  4. Asp.Net实现无刷新文件上传并显示进度条(非服务器控件实现)(转)

    Asp.Net实现无刷新文件上传并显示进度条(非服务器控件实现) 相信通过Asp.Net的服务器控件上传文件在简单不过了,通过AjaxToolkit控件实现上传进度也不是什么难事,为什么还要自己辛辛苦 ...

  5. iOS开发之网络编程--使用NSURLConnection实现大文件断点续传下载+使用输出流代替文件句柄

    前言:本篇讲解,在前篇iOS开发之网络编程--使用NSURLConnection实现大文件断点续传下载的基础上,使用输出流代替文件句柄实现大文件断点续传.    在实际开发中,输入输出流用的比较少,但 ...

  6. asp.net word ecxel类型文件在线预览

    asp.net word ecxel类型文件在线预览 首先得引用COM: Microsoft Excel 10 Object Library Microsoft Word 10 Object Libr ...

  7. ASP.NET- Web.Config配置大文件上传

    在web.config中的<system.web></system.web>内加入如下代码: <httpRuntime executionTimeout="60 ...

  8. 关于asp.net C# 导出Excel文件 打开Excel文件格式与扩展名指定格式不一致的解决办法

    -----转载:http://blog.csdn.net/sgear/article/details/7663502 关于asp.net C# 导出Excel文件 打开Excel文件格式与扩展名指定格 ...

  9. Asp.Net读取服务器EXE文件的方法!(超简单实例)

    Asp.Net读取服务器EXE文件的方法!(超简单实例) Process process = new Process(); process.StartInfo.FileName = "d:\ ...

随机推荐

  1. Spring+MyBatis实践—中文乱码

    多种中文乱码问题及解决: jsp页面乱码 表单提交乱码 URL中文参数乱码 1.jsp页面乱码解决(2步): 新建jsp页面: <%@ page language="java" ...

  2. Python图形图像处理库的介绍之Image模块

    http://onlypython.group.iteye.com/group/wiki/1372-python-graphics-image-processing-library-introduce ...

  3. .net和MVC中的json值和List<T>和DataTable的一些转换

    1.List<T>集合转换为Json值 List<ReportModel> dtList = new List<ReportModel>(); JsonResult ...

  4. MongoDB实战指南(七):MongoDB复制集之复制集工作机制

    http://www.cnblogs.com/longshiyVip/p/5097336.html 概述了复制集,整体上对复制集有了个概念,但是复制集最重要的功能之——自动故障转移是怎么实现的呢?数据 ...

  5. WCF - Developers Tools

    For developing a WCF service application, there are mainly two tools – Microsoft Visual Studio and C ...

  6. JavaScript功能一览

    // 10) throw "太大"; if(x0) { c_start=document.cookie.indexOf(c_name + "=") if (c_ ...

  7. [Hadoop源码解读](一)MapReduce篇之InputFormat

    平时我们写MapReduce程序的时候,在设置输入格式的时候,总会调用形如job.setInputFormatClass(KeyValueTextInputFormat.class);来保证输入文件按 ...

  8. UVA 11754 Code Feat 中国剩余定理+暴力

    lrj白书例题,真好 #include <stdio.h> #include <iostream> #include <vector> #include <m ...

  9. HDU-1896 Stones

    http://acm.hdu.edu.cn/showproblem.php?pid=1896 题意:一个人从0开始走起,遇到偶数个石头就踢.要是同一位置有多个石头,则先扔最重的石头(也就是扔的最近的那 ...

  10. [codevs1073]家族

    题目描述 Description 若某个家族人员过于庞大,要判断两个是否是亲戚,确实还很不容易,现在给出某个亲戚关系图,求任意给出的两个人是否具有亲戚关系. 规定:x和y是亲戚,y和z是亲戚,那么x和 ...