2012-09-13 22 views
0

假設我有一個簡單的表單來管理我的Rails 2.x支持的網站。防止多個用戶之間的表單提交衝突(Rails 2.x)

<form action="/products/123"> 

    Price: 
    <input type="text" name="product[price]" value="12.99"></input> 

    Description: 
    <textarea name="product[description]"> 
    A long and descriptive block of text goes here. 
    </textarea> 

    <input type="submit"></input> 
</form> 
  1. 聯繫莎莉要更改說明。
  2. Admin Sally用這個表單打開頁面,並開始在textarea寫一些新的銷售副本。
  3. 幾秒鐘後,管理員決定這個產品需要上市銷售
  4. 聯繫打開的頁面與它的形式
  5. 聯繫降低價格爲$ 9.99加入
  6. Admin Joe提交表格,將數據庫中的價格設置爲9.99美元
  7. 管理Sally已完成寫入副本並提交for米,但她的瀏覽器價格領域仍然說12.99美元。
  8. Joe變得生氣,並大叫莎莉改變價格回來,即使她不知道她只是這樣做。

所以更新數據庫包含的內容薩利曾在形式,去除集,而她與該頁面開放工作的價格。

當然,我不是第一個遇到這樣的問題,但我從來沒有處理它。首先,這類問題是否有名字?其次,有什麼解決方案使其吸收更少?


幾個想到的解決方案,但有些具有嚴重的缺點。

  • 如果updated_at時間戳從打開表單時發生更改,請勿保存記錄。但是,您想要保存的內容會發生什麼?您必須將想要更改的內容複製到表單外,重新加載編輯表單,然後重新粘貼,希望沒有其他人在此期間編輯任何內容。

  • 表單加載時禁用了大多數字段,要求管理員「解鎖」他們想要編輯的字段,並且只有未鎖定的字段在提交時纔會發送到服務器。這大大減少了大規模衝突的可能性,但是在內容編輯過程中增加了一些點擊,即使99%的時間都可以。

  • 基於JS的解決方案,可以進行髒字段檢查,禁用與表單加載時具有相同值的任何表單輸入,因此只有更改過的字段纔會提交,我想這是迄今爲止最好的選項。但它聽起來有點複雜,並且涉及將表單提交處理程序與頁面上的模型轉換爲JSON。

但是,我相信我不是第一個有這個問題的人。那麼是否有這樣的標準解決方案?

回答

2

您是否檢查了此項:http://api.rubyonrails.org/classes/ActiveRecord/Locking/Optimistic.html

UPDATE

那麼,它並沒有真正解釋做什麼,如果lock_version是錯誤的,但至少它比updated_at我想好。這一切都取決於誰贏了,爲什麼。如果Sally沒有觸及價格,保存時從Joe的數據更新價格似乎是合理的。只需將原始值添加爲隱藏字段,並將其與Sally的輸入進行比較,以防萬一lock_version錯誤。如果他們都修改相同的領域,那麼,沒有運氣。有人應該贏,或者你可以回到編輯頁面並突出顯示接受的變化。

+0

好酷,我想這就是軌道標準的方式。然而,它要求你自己做的難的部分'然後你負責處理衝突,通過拯救異常並回滾,合併,或以其他方式應用解決衝突所需的業務邏輯。「聽起來很棘手。 –

+0

我想現在我想這樣做,並且一個救援,告訴用戶在一個新標籤中再次打開表單,並將他們想要的編輯複製到非陳舊錶單中。不理想,但我猜衝突解決很少很簡單。 –