2
string filePath = ExportAndSaveInvoiceAsHtml(invoiceId);      

Response.AddHeader("Content-Disposition", "attachment;filename=" + Path.GetFileName(filePath));

Response.WriteFile(filePath);

// Using Response.End() solves the problem
// Response.End();

I want to enable users to download HTML invoice (from gridView of invoices). The resulting file contains the invoice file data + unwanted the page html also.

If i use Response.End(), it solves the problem, but then it always throws exception. Read in some threads that exception is by design. But then is it sure, it wont cause problem like response truncation or so anytime ?

How else can i write JUST the file data.

Btw, earlier we wrote invoice as PDF, and that time not using Response.End() caused incomplete file download.

Can someone give basics of writing custom data/file to Response stream.

Munish Goyal
  • 1,379
  • 4
  • 27
  • 49

2 Answers2

2

That's because the response is buffered. You have to call Response.End() to flush the buffers and ensure the client gets the complete response before the handler thread completes.

The ThreadAbortException thrown by Response.End() is by design and can safely be ignored.

Frédéric Hamidi
  • 258,201
  • 41
  • 486
  • 479
  • Well I have outer try block and now since this exception is ignorable i wrapped it inside dummy try { Response.End(); } catch(Exception ex) { Logger.LogException(ex); } – Munish Goyal Feb 01 '11 at 13:06
  • But its going into outer catch block also which has code to show error message to user. – Munish Goyal Feb 01 '11 at 13:06
  • @Munish, I'm afraid I don't understand: since you swallow the exception, it shouldn't propagate to the outer scope. (Also, you should catch `ThreadAbortException` instead of the generic `Exception` type). – Frédéric Hamidi Feb 01 '11 at 13:13
  • Exactly. Exception should not propagate, but it seems to be doing so. let me test it once again and will put up the result. – Munish Goyal Feb 01 '11 at 13:17
  • I found a solution to this. It looks like the ThreadAbortException gets propegated upwards no matter what. Every level in the chain needs to catch (ThreadAbortException err) { } as well whatever exceptions they were already catching. – SixOThree Oct 12 '12 at 20:03
1

Instead of Response.End() you can use

HttpContext.Current.ApplicationInstance.CompleteRequest()

This method tend to avoid throwing exceptions :)

Ozzy
  • 1,712
  • 11
  • 14
  • I get Compiler Error Message: CS0103: The name 'HttpContext' does not exist in the current context – Munish Goyal Feb 01 '11 at 12:55
  • 1
    Strange I had "using System.Web;" May be ambiguous name resolution problem. Anyway but compilation worked using full path. but functionality still the same. still coming as file + page data mix. – Munish Goyal Feb 01 '11 at 13:10