我正在開發一個應用程序,該應用程序在收到PayPal即時付款通知時應創建產品(如運輸保險單)。不幸的是,PayPal有時會發送重複通知。此外,還有另一個第三方在從PayPal獲得更新時同時執行Web服務更新。IsolationLevel.RepeatableRead以防止重複
下面是涉及的數據庫表的基本圖。
// table "package"
// columns packageID, policyID, other data...
//
// table "insurancepolicy"
// columns policyID, coverageAmount, other data...
這裏是什麼,我想要做一個基本圖:
using (SqlConnection conn = new SqlConnection(...))
{
sqlTransaction sqlTrans = conn.BeginTransaction(IsolationLevel.RepeatableRead);
// Calls a stored procedure that checks if the foreign key in the transaction table has a value.
if (PackageDB.HasInsurancePolicy(packageID, conn))
{
sqlTrans.Commit();
return false;
}
// Insert row in foreign table.
int policyID = InsurancePolicyDB.Insert(coverageAmount, conn);
if (policyID <= 0)
{
sqlTrans.Rollback();
return false;
}
// Assign foreign key to parent table. If this fails, roll back everything.
bool assigned = PackageDB.AssignPolicyID(packageID, policyID, conn);
if (!assigned)
{
sqlTrans.Rollback();
return false;
}
}
如果有兩個(或更多)的線程(或進程或應用程序)在同一時間做這個,我想第一個線程在沒有policyID的情況下鎖定「包」行,直到創建策略並將策略ID分配給包表。然後,在policyID分配給包表後,鎖將被釋放。我希望調用這個相同代碼的另一個線程在讀取包行時暫停,以確保它沒有第一個policyID。當第一個事務的鎖被釋放時,我希望第二個事務會看到policyID在那裏,因此返回時不插入任何行到策略表中。
注意:由於CRUD數據庫設計的,每一個存儲過程的參與設置讀取(選擇),創建(插入),或更新。
這是正確使用RepeatableRead事務隔離嗎?
謝謝。
什麼是包裝:政策關係?它是1:1嗎? – Constantin 2008-09-23 23:43:37
它是n:1。父表實際上不是「包」,我只是爲了說明而稱他們爲「包」。實際上,這些「包裹」就像是可以組合並一起運輸的訂單,整個包裹只有一份保險單。 – devlord 2008-09-24 01:14:06