註記與補充:Using an Asynchronous Controller in ASP.NET MVC
AsyncController的使用情境:
第一、需要耗費長時間處理的request。
第二、non-CPU bound的request。
non-CPU bound意指不需要使用CPU的作業或者request……等等。例如自網路下載資源或者IO的存取......等等。
Request如何被Thread Pool處理
就一般(同步)的情形而言,.Net Framework維護一組執行緒,每一個request會被指派一個執行緒負責處理相對應的程序,但是當待命的執行緒的數量耗盡時,後續的request會被Web Server以queue的方式儲存,當queue的容量耗盡後,網頁將會出現HTTP 503 status (Server Too Busy)的錯誤訊息。
非同步的Request的處理
Step1、由Thread Pool取得一個執行緒處理一個Request。
Step2、執行緒將Request指派給予非同步作業之後,由Thread Pool回收Thread。
Step3、待非同步作業完成後,將會通知ASP.Net。
Step4、再由Thread Pool取得一個執行緒(未必是步驟一的執行緒)負責繼續處理非同步作業的執行結果。
非同步的Request的處理的優點在於當一個作業包含網路下載資源、IO存取與CPU處理的指令時,可以讓執行緒專注在CPU處理的指令,至於網路下載資源與IO存取則交由非同步作業執行,以減少執行緒被鎖定的時間長度,也就是增加Thread Pool中可以使用的執行緒數量,以提高CPU的使用率,縮短使用者等待的時間。
舉例而言,假設目前有十筆資料必須處理,自網路下載資源預計共耗費二秒,CPU處理預計共耗費三秒,而IO存取共耗費一秒,倘若前述三項指令交由同一個執行緒(以同步的方式)處理,共計耗費六秒,但是透過非同步的方式處理,最樂觀的情形是僅需耗費三秒(更精確的說應該是大約三點三秒)。
建議使用非同步的情境
第一、大量下載網路資源(network-bound)或者大量的IO存取(I/O-bound),而不是大量使用中央處理器的運算能力(CPU-bound)。
第二、經由測試結果得知被鎖定的執行緒是IIS的效能瓶頸。
第三、以平行處理為優先考量,而不是以簡化程式碼為優先考量。
第四、提供一個機制協助ASP.Net MVC的使用者可以在執行時期中途取消一個必須耗費冗長時間執行的作業。
備註:
[1]參考資料來源的程式碼是ASP.Net MVC 4/C# 5之前的寫法。若欲參考ASP.Net MVC 4/C# 5的寫法,請參考補充資料來源[1]。
參考資料來源:
[1]Using an Asynchronous Controller in ASP.NET MVC
http://msdn.microsoft.com/en-us/library/ee728598(v=vs.100).aspx
補充資料來源:
[1]Asynchronous Controllers in ASP .NET MVC
http://tech.pro/tutorial/1252/asynchronous-controllers-in-asp-net-mvc