我正在尝试使用 Jquery Ajax 请求从 FTP 服务器下载 PDF 文件。我提到了http://www.dave-bond.com/blog/2010/01/JQuery-ajax-progress-HMTL5/ .
我的 Jquery ajax 调用如下所示
$.ajax({
xhr: function () {
var xhr = new window.XMLHttpRequest();
//Download progress
xhr.addEventListener("progress", function (evt) {
console.log("Event :"+evt.lengthComputable);
if (evt.lengthComputable) {
var percentComplete = evt.loaded / evt.total;
//Do something with download progress
console.log(percentComplete);
}
}, false);
return xhr;
},
type: 'POST',
url: "Downloader.ashx",
success: function (data) {
//Do something success-ish
}
});
我的 C# 通用处理程序代码下载文件如下
public void ProcessRequest(HttpContext context)
{
DownLoadFilesFromFTp("MyFile.pdf", "Foldername");
}
public bool DownLoadFilesFromFTp(string fileName,string ftpFolder)
{
//Create FTP Request.
try
{
string Ftp_Host = System.Configuration.ConfigurationManager.AppSettings["Ftp_Host"];
string Ftp_UserName = System.Configuration.ConfigurationManager.AppSettings["Ftp_UserName"];
string Password = System.Configuration.ConfigurationManager.AppSettings["Password"];
string downloadpath= System.Configuration.ConfigurationManager.AppSettings["downloadpath"];
//Fetch the Response and read it into a MemoryStream object.
string ftpurl = Ftp_Host + ftpFolder + "/" + fileName;
FtpWebRequest reqFTP;
reqFTP = (FtpWebRequest)FtpWebRequest.Create(new Uri(ftpurl));
reqFTP.Credentials = new NetworkCredential(Ftp_UserName, Password);
reqFTP.KeepAlive = false;
reqFTP.Method = WebRequestMethods.Ftp.DownloadFile;
reqFTP.UseBinary = true;
reqFTP.Proxy = null;
reqFTP.UsePassive = false;
FtpWebResponse response = (FtpWebResponse)reqFTP.GetResponse();
Stream responseStream = response.GetResponseStream();
FileStream writeStream = null;
//if (fileName.Substring(fileName.Length - 3, 3) == "pdf" || fileName.Substring(fileName.Length - 3, 3) == "PDF")
//{
writeStream = new FileStream(downloadpath + fileName, FileMode.Create);
//}
int Length = 2048; // 2048;
Byte[] buffer = new Byte[Length];
int bytesRead = responseStream.Read(buffer, 0, Length);
while (bytesRead > 0)
{
writeStream.Write(buffer, 0, bytesRead);
bytesRead = responseStream.Read(buffer, 0, Length);
}
responseStream.Close();
writeStream.Close();
response.Close();
return true;
}
catch (WebException wEx)
{
return false;
}
catch (Exception ex)
{
return false;
}
}
当我运行代码时,文件会毫无问题地下载到文件夹中,并在 Ajax 调用中
如果(evt.lengthComputable){
当我对 evt 进行控制台时,我得到了以下结果
总是返回 false,所以我无法跟踪进度。
1)代码有什么问题吗?
2) 下载 pdf 时显示进度条的任何替代方法
请您参考如下方法:
对于上传的字节数,很容易显示进度条。只需监视 xhr.upload.onprogress
事件。浏览器知道它必须上传的文件的大小和上传数据的大小,因此它可以提供进度信息。
对于下载的字节数,这有点困难,因为在这种情况下浏览器唯一知道的是它接收的字节数。
The reason of
evt.lengthComputable
is0
is that the browser doesn't know how many bytes will be sent in the server request.
有一个解决方案,在服务器上设置一个 Content-Length header 就足够了,如下所示,以便获得浏览器将要接收的字节的总大小。
// prepare the response to the client. resp is the client Response
var resp = HttpContext.Current.Response;
// Add Content-Length of the file to headers
// if the headers is not set then the evt.loaded will be 0
resp.AddHeader("Content-Length", "lengthOfYourFile");