2012-09-09 29 views
6

我正在研究一個Web應用程序,它涉及用戶填寫跨多個頁面的多步表單。表單的頂部有標籤導航(這些鏈接不提交當前頁面)和底部的下一個按鈕(它提交)。我正在考慮處理表單提交/驗證的幾種策略:.NET中多頁表單的最佳實踐/設計MVC3

  1. 一個操作方法和每個表單頁面的查看。當你點擊下一頁時,它會將表單提交給下一頁的操作方法。如果有驗證錯誤,你將被重定向回到前一頁:

    • URL的是描述性的,可以複製粘貼
    • 只有重定向錯誤的情況下
    • 由於重定向沒有形式數據,我們失去了關於提交的上下文,這使得難以顯示某些錯誤消息
    • 如果用戶嘗試訪問他們尚未準備好的流中的某個步驟,則重定向用戶的驗證邏輯相同
  2. 一個操作方法和查看每個表單頁面。當你點擊下一頁時,它會將表單提交給當前頁面操作。如果存在驗證錯誤,則返回相同的視圖。否則,我們重定向到下一個頁面動作:

    • URL的是描述性的,可以複製粘貼
    • 導向是很常見的(不知道這是不好的)
    • 當顯示驗證錯誤,我們作爲表單提交了同樣的要求,所以我們有充分的機會來了無效的輸入
    • 傳遞額外的背景下,如果我們想,例如,添加「上一步」按鈕,還提出
  3. 的能力

    所有頁面的一個操作方法。 URL包含有關正在提交的步驟的其他上下文(例如MyController/MyAction/{step})。控制器消息根據驗證和當前步驟選擇要返回哪個視圖頁面。

    • URL的不是描述性的(例如,如果我提交步驟1到步驟2,然後該URL的用戶看到將是一樣的,不管第1頁(無效)或2頁是否返回
    • 沒有重定向
    • 當顯示驗證錯誤,我們是在爲表單提交了同樣的要求,所以我們有充分的機會來了無效的輸入
  4. 一種不同的方法,我還沒有在這裏列出

我試圖枚舉我所看到的一些每種方法的優點和缺點,但我很想知道:

  • 什麼是這些方法的其他優點和缺點?我的正確嗎?我列舉的一些缺點是否可以設計出來?
  • 有沒有一個標準的方法來解決這個問題,我應該使用?如果是這樣,爲什麼這是標準方法?
+0

聽起來像你需要接受處理請求和返回(在大多數情況下)視圖的行爲的概念。通過爲每個表單頁面執行操作,您可以擁有特定於該頁面上的數據的視圖模型。如果模型無效或者下一頁的視圖,該操作可以返回相同的視圖。不需要重定向。你可以在你的'form'中使用'hidden'輸入來傳遞上下文。 – HABO

+0

@HABO:但是如果我沒有重定向並且用戶在頁面1上提交了無效的內容,那麼即使返回的視圖是第1頁的無效視圖,他們是不是仍然會看到第2頁的url? – ChaseMedallion

+0

您的操作選擇適當的視圖返回:第1頁或第2頁。它的決定方式取決於您。瀏覽器顯示所得到的內容,但不需要通過重定向請求查詢不同的頁面。 – HABO

回答

2

我強烈建議選項2稍作修改。您可能還想考慮爲每個操作/視圖創建一個視圖模型。如果您有一個跨越所有頁面的模型,則所有屬性都將進行驗證,這意味着即使用戶只能在每個屏幕上編輯模型的一部分,他們也可以針對他們看不到的屬性獲取驗證警告。我們最近在一個項目中做了這個,它的工作非常好。您必須在後端對數據進行一些操作才能將所有內容合併到一起,但最終它是值得的。

正如你所說,你的網址將是深層次的鏈接,這意味着用戶可以複製/粘貼,更重要的是,他們可以添加頁面作爲他們的瀏覽器的最愛,讓他們回到同一個地方非常容易。在我看來,這使得選項3過時。

您還將受益於以下事實:您的所有導航邏輯都在一個地方發生。您必須在客戶端(您當前所在的頁面)上存儲「嚮導」的狀態,以便您的控制器知道如何處理提交。您需要分析嚮導的狀態,並決定用戶下一步需要去的地方。如果使用選項1,則不會知道「來自哪裏」,並且服務器驗證錯誤將很難顯示給客戶端。這是POST - REDIRECT - GET模式的一個很好的例子。每個頁面都有2個動作,一個GET可以接受簡單的ID,一個POST可以接受更復雜的模型。發佈服務器,找出下一步要去的地方,重定向到GET。

最後,考慮您的上一個按鈕直接鏈接到上一步,而不是提交表單。否則,用戶可能會陷入無效步驟。這發生在我們身上,並且一直很好地工作。

希望這是有幫助的。祝你好運!

+1

您提到了POST - REDIRECT - GET模式。是否存在頻繁重定向導致頁面轉換變慢的風險(尤其是因爲我們在每個請求中從數據庫加載模型的一部分)? – ChaseMedallion

+0

當然。這是你必須考慮的事情。 POST - REDIRECT - GET因爲網絡的無狀態性而工作得很好。但是,如果性能是一個問題(查詢速度慢等),那麼您可能需要考慮其他存儲解決方案(如No-SQL提供程序)或將對象存儲在會話中。 – Adam

+2

每個視圖有一個模型,步驟n如何知道步驟1和步驟2是否正確完成?例如,假設有人進入第三步,然後離開網站/應用程序。推測他們的進展存儲在會話中......但讓我們假設他們遠離會話足夠長的時間來衰減。他們直接回到第3頁的書籤。 聽起來我覺得每一步的'索引'操作都需要將會話中的每一個前一步都拉回合適的模型並重新驗證。在我看來,這將在第20步變得非常昂貴。 – Mir