Artikel KB ini mengatakan bahwa ASP.NET Response.End()
membatalkan utas.
Reflektor menunjukkan bahwa tampilannya seperti ini:
public void End()
{
if (this._context.IsInCancellablePeriod)
{
InternalSecurityPermissions.ControlThread.Assert();
Thread.CurrentThread.Abort(new HttpApplication.CancelModuleException(false));
}
else if (!this._flushing)
{
this.Flush();
this._ended = true;
if (this._context.ApplicationInstance != null)
{
this._context.ApplicationInstance.CompleteRequest();
}
}
}
Bagi saya ini agak kasar. Seperti yang dikatakan artikel KB, kode apa pun dalam aplikasi berikut Response.End()
ini tidak akan dieksekusi, dan itu melanggar prinsip paling tidak heran. Ini hampir seperti Application.Exit()
di aplikasi WinForms. Pengecualian utas dibatalkan yang disebabkan oleh Response.End()
tidak dapat ditangkap, jadi mengelilingi kode dalam try
... finally
tidak akan memuaskan.
Itu membuat saya bertanya-tanya apakah saya harus selalu menghindari Response.End()
.
Adakah yang bisa menyarankan, kapan saya harus menggunakan Response.End()
, kapan Response.Close()
dan kapan HttpContext.Current.ApplicationInstance.CompleteRequest()
?
ref: entri blog Rick Strahl .
Berdasarkan input yang saya terima, jawaban saya adalah, Ya, Response.End
berbahaya , tetapi berguna dalam beberapa kasus terbatas.
- gunakan
Response.End()
sebagai lemparan yang tidak dapat ditandingi, untuk segera mengakhiriHttpResponse
dalam kondisi luar biasa. Dapat bermanfaat saat debugging juga. HindariResponse.End()
untuk melengkapi respons rutin . - gunakan
Response.Close()
untuk segera menutup koneksi dengan klien. Per posting blog MSDN ini , metode ini tidak dimaksudkan untuk pemrosesan permintaan HTTP normal. Sangat tidak mungkin Anda memiliki alasan yang bagus untuk memanggil metode ini. - gunakan
CompleteRequest()
untuk mengakhiri permintaan normal.CompleteRequest
menyebabkan pipa ASP.NET melompat ke depan keEndRequest
acara, setelahHttpApplication
acara saat ini selesai. Jadi, jika Anda meneleponCompleteRequest
, maka tulis sesuatu lebih ke respons, tulis itu akan dikirim ke klien.
Edit - 13 April 2011
Kejelasan lebih lanjut tersedia di sini:
- Posting yang berguna di Blog MSDN
- Analisis yang berguna oleh Jon Reid
Response.End
ThreadAbortException
baik-baik saja.Response.Redirect
danServer.Transfer
keduanya memanggilResponse.End
dan juga harus dihindari.Jawaban:
Jika Anda telah menggunakan logger pengecualian pada aplikasi Anda, itu akan dipermudah dengan
ThreadAbortException
s dariResponse.End()
panggilan - panggilan jinak ini . Saya pikir ini adalah cara Microsoft untuk mengatakan "Hentikan!".Saya hanya akan menggunakan
Response.End()
jika ada kondisi luar biasa dan tidak ada tindakan lain yang mungkin. Mungkin kemudian, mencatat pengecualian ini mungkin benar-benar menunjukkan peringatan.sumber
TL; DR
Per MSDN, Jon Reid , dan Alain Renon:
Kinerja ASP.NET - Manajemen Pengecualian - Menulis Kode yang Menghindari Pengecualian
Solusi ThreadAbortException
Response.End dan Response.Close tidak digunakan dalam pemrosesan permintaan normal ketika kinerja penting. Response.End adalah cara yang mudah dan berat untuk menghentikan pemrosesan permintaan dengan penalti kinerja terkait. Response.Close adalah untuk penghentian segera tanggapan HTTP di tingkat IIS / socket dan menyebabkan masalah dengan hal-hal seperti KeepAlive.
Metode yang disarankan untuk mengakhiri permintaan ASP.NET adalah HttpApplication.CompleteRequest. Perlu diingat bahwa rendering ASP.NET harus dilewati secara manual sejak HttpApplication.CompleteRequest melompati sisa pipa aplikasi IIS / ASP.NET, bukan pipeline Halaman ASP.NET (yang merupakan satu tahap dalam pipeline aplikasi).
Kode
Hak Cipta © 2001-2007, C6 Software, Inc sebaik yang saya tahu.
Referensi
HttpApplication.CompleteRequest
Respon
Respon. Tutup
sumber
Pertanyaan ini muncul di dekat bagian atas semua pencarian google untuk informasi tentang respons. . (mengganti metode render terlalu rumit untuk tugas sederhana IMO)
sumber
Pada pertanyaan "Saya masih tidak tahu perbedaan antara Response.Close dan CompleteRequest ()" Saya akan mengatakan:
Lebih suka CompleteRequest (), jangan gunakan Response.Close ().
Lihat artikel berikut untuk ringkasan yang dilakukan dengan baik dari kasus ini.
Ketahuilah bahwa bahkan setelah memanggil CompleteRequest () beberapa teks (mis. Redndered dari kode ASPX) akan ditambahkan ke aliran output respons. Anda dapat mencegahnya dengan mengganti metode Render dan RaisePostBackEvent seperti yang dijelaskan dalam artikel berikut .
BTW: Saya setuju dengan pencegahan menggunakan Response.End (), terutama ketika menulis data ke aliran http untuk meniru unduhan file. Kami telah menggunakan Response.End () di masa lalu hingga file log kami menjadi penuh dengan ThreadAbortExceptions.
sumber
Saya tidak setuju dengan pernyataan " Response.End berbahaya ". Jelas tidak berbahaya. Respon. Dan melakukan apa yang dikatakannya; itu mengakhiri eksekusi halaman. Menggunakan reflektor untuk melihat bagaimana penerapannya seharusnya hanya dipandang sebagai pelajaran.
Rekomendasi 2cent saya
HINDARI digunakan
Response.End()
sebagai aliran kontrol.JANGAN gunakan
Response.End()
jika Anda perlu menghentikan eksekusi permintaan dan sadarilah bahwa (biasanya) * tidak ada kode yang akan dieksekusi melewati titik itu.*
Response.End()
dan ThreadAbortException s.Response.End()
melempar ThreadAbortException sebagai bagian dari implementasi saat ini (seperti dicatat oleh OP).Untuk melihat cara menulis kode yang harus berurusan dengan ThreadAbortExceptions, lihat @ Mehrdad membalas SO Bagaimana saya bisa mendeteksi threadabortexception di blok akhirnya di mana ia mereferensikan RuntimeHelpers.ExecuteCodeWithGuaranteedCleanup Method dan Daerah Eksekusi yang Terkendala
Artikel Rick Strahl yang disebutkan adalah instruktif, dan pastikan untuk membaca komentar juga. Perhatikan bahwa masalah Strahl spesifik. Dia ingin mendapatkan data ke klien (gambar) dan kemudian memproses pembaruan basis data pelacakan-pelacakan yang tidak memperlambat penyajian gambar, yang menjadikannya masalah melakukan sesuatu setelah Respons. Akhir telah dipanggil.
sumber
Saya tidak pernah mempertimbangkan menggunakan Response.End () untuk mengontrol aliran program.
Namun Response.End () dapat berguna misalnya saat menyajikan file ke pengguna.
Anda telah menulis file ke respons dan Anda tidak ingin hal lain ditambahkan ke respons karena dapat merusak file Anda.
sumber
Saya telah menggunakan Response.End () di kedua .NET dan Classic ASP untuk secara paksa mengakhiri sesuatu sebelumnya. Misalnya, saya menggunakannya ketika ada sejumlah upaya login yang pasti. Atau ketika halaman aman diakses dari login yang tidak diautentikasi (contoh kasar):
Saat menyajikan file ke pengguna saya akan menggunakan Flush, Akhir dapat menyebabkan masalah.
sumber
Saya hanya menggunakan Response.End () sebagai mekanisme pengujian / debugging
Menilai dari apa yang telah Anda posting dalam hal penelitian, saya akan mengatakan itu akan menjadi desain yang buruk jika diperlukan Response.End
sumber
Pada asp klasik, saya memiliki TTFB (Time To First Byte) dari 3 hingga 10 detik pada beberapa panggilan ajax, jauh lebih besar daripada TTFB pada halaman biasa dengan lebih banyak panggilan SQL.
Ajax yang dikembalikan adalah segmen HTML yang akan disuntikkan ke halaman.
TTFB beberapa detik lebih lama dari waktu render.
Jika saya menambahkan response.end setelah render, TTFB sangat berkurang.
Saya bisa mendapatkan efek yang sama dengan memancarkan "</body> </html>", tetapi ini mungkin tidak berfungsi saat mengeluarkan json atau xml; di sini response.end diperlukan.
sumber