vkill'blog 何永鹏

asp 中自定义文件下载

10:04 , vkill
asp 中自定义文件下载

用到的主知识点:
ADODB.Stream 读取文件字节流
Response.BinaryWrite 输出字节流
Response.ContentType 指定响应的HTTP 内容类型

演示地址:
http://www.vkill.net/demo/download/download.asp?filename=01.jpg
http://www.vkill.net/demo/download/download.asp?filename=Jscript.chm

主代码:


<%@LANGUAGE="JAVASCRIPT" CODEPAGE="65001"%>
<%
/*====================================
download.asp
by:vkill  11/24/2008  version:0.1
使用方法:
使用 http://xxx.xxx/download.asp?filename=xxx.xxx 访问,会根据后缀名在相应的子文件下查找文件并输出,支持流输出和直接网页跳转到文件真实url地址
所有文件的根目录为变量 path 设置的值
相应后缀文件的子目录设置在 “设置附件根目录和相应后缀子目录” 这段设置
====================================*/
use_exist = 0  //是否使用判断文件存在否
use_limit = 1  //是否使用判断文件大小是否超出限制
append_maxsize = 2048000  //容许下载的文件最大2M
use_stream = 1  //是否使用流下载,用流下载耗内存
re_imgs = /^(gif|jpg|bmp)$/i  //需显示的图片类型,用在最后输出时是图片则直接显示在网页,不弹出下载框


filename = Request.QueryString("filename").Item
if (!filename) {
  Response.Write("错误:请正确使用本网页 e.g. http://www.vkill.net/demo/download/download.asp?filename=01.jpg")
  Response.End()
}

if (!(/^([^\x22\\\/:\*\?\|<>]+)\.([a-zA-Z_]{1,4})$/.exec(filename))) {
  Response.Write("错误:请输入合法的文件名")
  Response.End()
} else {
  n = RegExp.$1
  x = RegExp.$2
}

use_allow_xs = 0  //使用容许的后缀,如使用拒绝的后缀设置为0
if (use_allow_xs==1) {
  re_allow_xs = /^(gif|jpg)$/i
  if (!(re_allow_xs.test(x))) {
    Response.Write("错误:此后缀文件禁止下载")
    Response.End()
  }
} else {
  re_deny_xs = /^(asp|aspx|asa|asax|mdb)$/i
  if (re_deny_xs.test(x)) {
    Response.Write("错误:此后缀文件禁止下载")
    Response.End()
  }
}

//设置附件根目录和相应后缀子目录
path = "\\demo\\download\\append\\"  //相对于网站根目录的目录
if (/^(gif|jpg)$/i.test(x)) {
  path += "images\\"
} else if (/^(doc|chm|pdf)$/i.test(x)) {
  path += "books\\"
} else if (/^(txt)$/i.test(x)) {
  path += "txts\\"
} else {
  path += "others\\"
}
//获取文件的完整物理路径和完整url路径
file_full_path = Server.MapPath("/") + path + filename
file_full_url = "http:\/\/" + Request.ServerVariables("server_name") + ":" + Request.ServerVariables("server_port") + path + filename
file_full_url = file_full_url.replace(/\\/g,"/")

//判断文件是否存在和大小是否超过限制
if (use_exist==1) {
  try {
    fs = Server.CreateObject("Scripting.FileSystemObject")
  } catch(err) {
    Response.Write("错误:服务器不支持FSO组件")
    Response.End()
  }
  if (!fs.FileExists(file_full_path)) {
    Response.Write("错误:文件不存在")
    Response.End()
  }
  if (use_limit==1) {
    f=fs.GetFile(file_full_path)
    if (f.Size > append_maxsize) {
      Response.Write("错误:文件大小超出限制")
      Response.End()
    }
    f=null
  }
  fs=null
}

//输出
if (use_stream==1) {
  try {
    objstream = Server.CreateObject("ADODB.Stream")
  } catch(err) {
    Response.Write("错误:服务器不支持ADODB.Stream组件")
    Response.End()
  }
  objstream.Type = 1
  objstream.Open()
  objstream.LoadFromFile(file_full_path)
  if (use_limit==1) {
    if (objstream.Size > append_maxsize) {
      Response.Write("错误:文件大小超出限制")
      Response.End()
    }
  }
  Response.Buffer = true
     Response.Clear()
  if (!re_imgs.test(x)) {
    Response.ContentType = "application/octet-stream"
    Response.AddHeader("content-disposition", "attachment; filename=" + filename)
  } else {
    Response.ContentType = "images/*"
    Response.AddHeader("content-disposition", "image; filename=" + filename)
  }
  while (!objstream.EOS) {
    Response.BinaryWrite(objstream.Read(1024*64))
  }
  Response.Flush()
  objstream.Close()
  objstream=null
} else {
  if (!re_imgs.test(x)) {
    Response.ContentType = "application/ms-download"
  } else {
    Response.ContentType = "images/*"
  }
  Response.Redirect(file_full_url)
}

Response.End()
%>


Last modified by vkill on2008/11/25 10:05
类别:web | Tags: , , , , | 0 条评论, 716 次阅读
网友评论(0):
发表评论:

Nickname: 
Email:
Site URI: