前言
最近同事詢問一個很奇怪的問題,在執行程式時會跳「System.NullReferenceException: 並未將物件參考設定為物件的執行個體。」的錯誤。但它錯誤的行號卻是在 new 一個 POCO 的 Class 。錯誤訊息如下,
System.NullReferenceException: 並未將物件參考設定為物件的執行個體。
於 xxx.Controllers.rmController.rmAction(String num) 於 D:xxx\Controllers\rmController.cs: 行 482
於 lambda_method(Closure , ControllerBase , Object[] )
於 System.Web.Mvc.ReflectedActionDescriptor.Execute(ControllerContext controllerContext, IDictionary2 parameters) 於 System.Web.Mvc.ControllerActionInvoker.InvokeActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor, IDictionary
2 parameters)
而在 Server 端的錯誤黃畫面中,原始碼程式錯誤,卻沒有明確顯示出錯誤的程式碼,如下,
測試
Controller 的程式碼如下,
1 | public ActionResult rmAction(string num) |
跟同事 Garry, Leo 一直想不透 new 一個 POCO 的 Class,怎麼可能會噴 NullReferenceException。
於是使用了各種方式來測試,例如直接在 View 或是直接建立 aspx 去測試,都不會錯誤。
後來同事將下一行的程式碼,也搬到 View 及 aspx 去試,錯誤就在正確的地方噴錯。
原來不是那個 new 錯誤,而是下一行的所造成的錯誤。
所以下次有類似的問題,可以試著將程式碼搬到 View or aspx 去測試,或許可以加快查問題的速度。
aspx 的 inline code 方式,我在 Debug 時蠻長使用的,因為直接新增一支 aspx 然後寫程式碼就可以驗證了。
808dk 的範例如下,
1 | <%@ Import Namespace="System" %> |
1 | <%@ Import Namespace="System" %> |
結論
從這例子中,可以發現,原來錯誤的行號也會騙人(如果 pdb 不對的話,行號或許也會不同)。
同一包建置出來的程式在 Local 或公司執行都沒有問題,部署到客戶端就噴錯,一度懷疑是否 web.config 有什麼差異。
最後同事以插旗子的方式去驗證不是掛在 new class 的地方。
將程式放到 aspx inline code 的方式,也是幫助我們快速找到問題的一個方式哦!
參考資料
Using inline code in ASP.NET (C# and VB.Net)
非常感謝同事 Garry, Leo 的分享