开发者

Response.TransmitFile Not downloading, and throwing no Errors

开发者 https://www.devze.com 2023-02-20 20:36 出处:网络
I\'m currently using a HttpResponse to download files from my Server. I already have a couple functions being used to download Excel/Word files, but I\'m having trouble getting my simple Text file (.t

I'm currently using a HttpResponse to download files from my Server. I already have a couple functions being used to download Excel/Word files, but I'm having trouble getting my simple Text file (.txt) to download.

With the text file I'm basically dumping contents of a TextBox into a File, attempting to download the file with the HttpResponse and then delete the Temporary Text File.

Here is an example of my code that works for the Excel/Word documents:

protected void linkInstructions_Click(object sender, EventArgs e)
{
    String FileName = "BulkAdd_Instructions.doc";
    String FilePath = Server.MapPath("~/TempFiles/BulkAdd_Instructions.doc");
    System.Web.HttpResponse response = System.Web.HttpContext.Current.Response;
    response.ClearContent();
    response.Clear();
    response.ContentType = "application/x-unknown";
    response.AddHeader("Content-Disposition", "attachment; filename=" + FileName + ";");
    response.TransmitFile(FilePath);
    response.Flush();
    response.End();  
}

And here is the chunk of code that doesn't work.

Taking Note that the code runs without throwing any errors. The File is created, and Deleted, but never dumped to the User.

protected void saveLog(object sender, EventArgs e开发者_如何转开发)
{ 
    string date = DateTime.Now.ToString("MM_dd_yyyy_hhmm");     //  Get Date/Time
    string fileName = "BulkLog_"+ date + ".txt";                //  Stitch File Name + Date/Time
    string logText = errorLog.Text;                             //  Get Text from TextBox
    string halfPath = "~/TempFiles/" + fileName;                //  Add File Name to Path
    string mappedPath = Server.MapPath(halfPath);               //  Create Full Path

    File.WriteAllText(mappedPath, logText);                     //  Write All Text to File

    System.Web.HttpResponse response = System.Web.HttpContext.Current.Response;
    response.ClearContent();
    response.Clear();
    response.ContentType = "text/plain";
    response.AddHeader("Content-Disposition", "attachment; filename=" + fileName);
    response.TransmitFile(mappedPath);                //  Transmit File
    response.Flush();

    System.IO.File.Delete(mappedPath);                //  Delete Temporary Log
    response.End();
}


It is because you are deleting the file before it can send.

From MSDN - HttpResponse.End Method

Sends all currently buffered output to the client, stops execution of the page, and raises the EndRequest event.

Try putting your System.IO.File.Delete(mappedPath); line after the response.End(); in my test just then it seemed to be working.

Also, might be a good idea to check if the file exists first, cant see any file.Exists in there, don't want any null reference exceptions, and to set the Content-Length.

EDIT: here is the code I used in a project at work a while ago, might help you out a bit.

// Get the physical Path of the file
string filepath = System.Web.Hosting.HostingEnvironment.ApplicationPhysicalPath + folder + filename;

// Create New instance of FileInfo class to get the properties of the file being downloaded
FileInfo file = new FileInfo(filepath);

// Checking if file exists
if (file.Exists)
{                            
    // Clear the content of the response
    Response.ClearContent();

    // LINE1: Add the file name and attachment, which will force the open/cance/save dialog to show, to the header
    Response.AddHeader("Content-Disposition", String.Format("attachment; filename={0}", file.Name));

    // Add the file size into the response header
    Response.AddHeader("Content-Length", file.Length.ToString());

    // Set the ContentType
    Response.ContentType = ReturnFiletype(file.Extension.ToLower());

    // Write the file into the response (TransmitFile is for ASP.NET 2.0. In ASP.NET 1.1 you have to use WriteFile instead)
    Response.TransmitFile(file.FullName);

    // End the response
    Response.End();

    //send statistics to the class
}

And here is the Filetype method I used

//return the filetype to tell the browser. 
//defaults to "application/octet-stream" if it cant find a match, as this works for all file types.
public static string ReturnFiletype(string fileExtension)
{
    switch (fileExtension)
    {
        case ".htm":
        case ".html":
        case ".log":
            return "text/HTML";
        case ".txt":
            return "text/plain";
        case ".doc":
            return "application/ms-word";
        case ".tiff":
        case ".tif":
            return "image/tiff";
        case ".asf":
            return "video/x-ms-asf";
        case ".avi":
            return "video/avi";
        case ".zip":
            return "application/zip";
        case ".xls":
        case ".csv":
            return "application/vnd.ms-excel";
        case ".gif":
            return "image/gif";
        case ".jpg":
        case "jpeg":
            return "image/jpeg";
        case ".bmp":
            return "image/bmp";
        case ".wav":
            return "audio/wav";
        case ".mp3":
            return "audio/mpeg3";
        case ".mpg":
        case "mpeg":
            return "video/mpeg";
        case ".rtf":
            return "application/rtf";
        case ".asp":
            return "text/asp";
        case ".pdf":
            return "application/pdf";
        case ".fdf":
            return "application/vnd.fdf";
        case ".ppt":
            return "application/mspowerpoint";
        case ".dwg":
            return "image/vnd.dwg";
        case ".msg":
            return "application/msoutlook";
        case ".xml":
        case ".sdxl":
            return "application/xml";
        case ".xdp":
            return "application/vnd.adobe.xdp+xml";
        default:
            return "application/octet-stream";
    }
}


I stumbled across this post in my search, and noticed that it wasn't useful in telling us why the UpdatePanel caused the issue in the first place.

The UpdatePanel is an asynchronous postback, and Response.TransmitFile needs a full postback to work properly.

The control that triggers the asynchronous postback needs to be made a trigger in the UpdatePanel:

<Triggers>        
<asp:PostBackTrigger ControlID="ID_of_your_control_that_causes_postback" />
</Triggers>


Thank you for the follow up on what your problem was. I've spent hours trying to figure out why no error code was being thrown despite the fact that nothing happened. Turns out it was my AJAX UpdatePanel mysteriously and covertly getting in the way.


I resolved this issue. The Response object requires a full postback in order for it to download an Excel file generated on the server.. but the full postback was being prevented by the UpdatePanel on my webform, which contained my export button. So.. inside the UpdatePanel tag, I changed this...

<asp:AsyncPostBackTrigger ControlID="btnExport" EventName="Click" />

...to this to resolve the issue:

<asp:PostBackTrigger ControlID="btnExport"/>


Also try this for saving text on client side (Chrome only now) without the round trip to Server.

Here is another flash base one...


I ended up fixing the issue on my own. It turns out it was an Ajax Problem not allowing my Button to Postback properly. This stopped the TransmitFile from being fired.

Thanks for the help!

0

精彩评论

暂无评论...
验证码 换一张
取 消