stone2083

资源如何避免多线程下载

今天在一次会议中,有朋友问我,如何避免资源被迅雷等工具多线程下载?

确实,一些中小企业站点,尤其是个人站点,由于没有过多资金,服务器承受不了大的压力,站点提供的资源,一旦被迅雷等多线程工具下载,
对服务器的压力还是蛮客观的。

那么有什么办法避免多线程下载呢?其实最简单的办法,就是服务端根本就不要提供Content-Length值。试想一下,如果多线程下载工具得不到文件总大小值,如何分配去分配每个线程需要下载的量呢?不得已,只能通过单线程下载了。

以http下载为例,我写了一个提供下载的servlet,由于不返回Content-Length值(只返回了ContentType值),这个serlvet返回的流,只能单线程下载。
public class Download extends HttpServlet {

    
private static final long   serialVersionUID = 8401962046132204450L;

    
private static final String FILE_PATH        = "/home/jones/tmp/sample.zip";

    @Override
    
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.setContentType(
"application/octet-stream");

        OutputStream out 
= resp.getOutputStream();

        FileInputStream in 
= new FileInputStream(FILE_PATH);
        
int readLength = 0;
        
byte[] cache = new byte[1024];
        
while ((readLength = in.read(cache)) != -1) {
            out.write(cache, 
0, readLength);
        }
        in.close();

        out.flush();
        out.close();
    }
}

同样的道理,只要配置服务器不要返回Content-Length值,那么就可以有效避免多线程下载了。

posted on 2008-03-17 21:58 stone2083 阅读(849) 评论(2)  编辑  收藏 所属分类: misc

Feedback

# re: 资源如何避免多线程下载[未登录] 2008-07-18 09:33 agapple

如果所有的下载请求都经过servlet读入与写入,大量的下载请求会压垮服务器
我记得在javaeye看过robbin的一片文章,将下载文件直接推给网卡buffer,让操作系统负责处理下载请求, 比如lighttd的X-sendfile
  回复  更多评论   

# re: 资源如何避免多线程下载 2008-07-18 20:39 stone2083

文章的本意不是说通过servlet,来控制文件的下载。
而是站在协议的角度上,通过servlet的例子,来说明,只要修改content-length的值,就能达到“只允许单线程下载资源“的目的。
虽然,通过修改协议的规定,擅自修改http头信息的方式的做法,不符合规范。但是对于小站点来说,是一个成本最小的方法。
站点上的图片等,都是资源,如果都允许多线程下载,那么用户量一多,对于小网站来说,还是有点困难的。
文章采用servlet,仅仅用于举例说明.真正的应用上,可以通过修改apache,lighttpd,等web服务器的配置,来达到这个目的。

如果是资源的下载,那么肯定通过更为专业的ftp server来对外服务。而不是采用http协议。当然传统的ftp server,也是有IO消耗的。

至于楼上所说的X-sendfile,我也看过javaeye的文章(http://robbin.javaeye.com/blog/154538)。X-sendfile,确实是一个很先进的理念(至少我看来是,或许我是一个很老土的人)。
但是自己对这个没有任何尝试,也没有更多的评论资格。  回复  更多评论   


只有注册用户登录后才能发表评论。


网站导航: