2012-03-01 56 views
6

很多時候我碰到的在我的項目視圖拋出一個空引用異常的情況。MVC3瀏覽次數:處理空模型與技巧

@model Johnny.Application.TestModel 
<div>@(Model.SomeText)</div> 

這將引發一個錯誤,如果型號

但如何處理的人呢?我當然看不到任何地方的代碼示例,在視圖中丟棄代碼的醜陋空檢查。這使我相信大多數時候,控制器不應該返回空模型。但是你怎麼能用更多的技巧來強制執行呢?

現在只要有人不小心導致控制器返回一個空模型,視圖模型吹起來,看起來是有過錯的。實際上,這是控制器的錯。而且這個觀點甚至不能「捕捉」問題,只有模型的成員恰好被使用(當然這是大多數情況下)纔會這樣做。

由於種種原因,有些觀點可能需要處理空值。不過,我不希望這是多數情況。顯然這是在視圖和控制器之間設置一些「契約」的問題。

我不喜歡我見過的選項:

  1. 檢查模式爲null每它的使用時間。 非常跛腳
  2. 一個大if語句包裝用空模型 檢查整個視圖。想想浪費的代碼房地產。瘸!
  3. 添加如果檢查在頂部投擲。不錯,但看起來很傻。輕度跛腳。

我很想知道,如果像這些選項存在設置了「不空」的合同:

  • 像[NoNullModels]控制器方法的屬性。我懷疑這是否存在,因爲我不認爲控制器知道它所連接的視圖。
  • 在視圖中,像@ MVC3.HeyDontAllowNulls的指標或拋出異常(如上面的選項3)的其他一些標準的方式
+0

爲什麼你甚至會返回一個空模型? – 2012-03-01 15:18:55

+1

您是否嘗試過'@ Html.DisplayFor(m => m.SomeText)' – 2012-03-01 15:20:45

+0

在代碼示例主題上,Internet上99%的代碼示例沒有異常處理和輸入驗證。部分原因是懶惰,部分原因是它會混淆代碼示例說明的觀點。 – 2012-03-01 15:36:16

回答

2

我這裏Should one try to guard against null reference exceptions/index out of bounds exceptions in MVC views?問過類似的問題,並得到了良好的反應吧。簡而言之,最好在你的控制器中添加空檢查,甚至可以在單元測試中添加空檢查,而不是在你的視圖中。

+0

我沒有想過單元測試的方法,這是他們的實用性的好方案。由於我沒有「擁有」所有代碼,因此我無法使所有控制器單元都可以測試,所以我希望能夠在這些情況下找到視圖的後備選項。 – 2012-03-01 15:58:10

+0

我也承認,如果我有一個高度共享的視圖,它可以通過衆多的操作方法呈現出來,我肯定會試圖在視圖中的一個地方添加一個空檢查,而不是在其他十幾個地方即使我擁有所有的代碼。您可能會以違反MVC分離關注點爲代價稱之爲堅持DRY原則。 – 2012-03-01 16:06:30

+0

我越想越多,我越覺得視圖是添加內容的正確位置。其中一個原因是單個控制器操作可以路由到幾個不同的視圖。將它固定在控制器端並不有效,因爲它遲早會發生泄漏(就像我一直遇到的情況一樣!) – 2012-03-01 16:54:50

0

有許多喜好在這裏,一些你可以做的是:在你的數據層(自定義除外)

  1. 投擲RecordNotFoundException,並有一個全球性的異常過濾器捕獲這個
  2. 檢查空值從回來您的存儲庫並在個案情況下處理
  3. 裝飾您的控制器以查找不是CREATE方法(或任何您認爲可以的規則)的GET方法的空模型,並使用操作篩選器屬性在OnActionExecuted中檢查

即使我的「CREATE」視圖通常會得到一個模型,即使它是空的(儘管在它們中通常有一個IEnumerable <SelectListItem>),所以它們應該始終有模型前往它們。

0

我在我的視圖中檢查空值,有時候在它的某些部分需要它。

我也有時會在我的控制器中創建默認值,如果將有一個空值取決於你想要做什麼和什麼是可接受的。

我有一個例子,人們訂閱的東西,並設置通知的情況。如果他們沒有通知,我的模型的一個子對象是null。我不想設置默認值,所以我有一個檢查。在其他部分,我只是使用默認值。