自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

處理微軟MSF同步框架中的數(shù)據(jù)沖突

原創(chuàng)
開發(fā) 項目管理
在任何程序或從多個數(shù)據(jù)源同步數(shù)據(jù)的框架中都不能避免數(shù)據(jù)沖突,微軟同步框架(Microsoft Sync Framework即MSF)也不例外。但MSF有內(nèi)置的特性幫助開發(fā)人員處理大部分?jǐn)?shù)據(jù)沖突,我們一起來看看ADO.NET v1.0的MSF服務(wù)是如何幫助開發(fā)人員減少處理沖突的負(fù)擔(dān)的

【51CTO獨家特稿】如果你剛剛接觸微軟同步框架,你可以通過本文開始學(xué)習(xí),在下面的示例中,我們假設(shè)你已經(jīng)對MSF框架有所了解。

首先,我們需要理解什么是數(shù)據(jù)沖突,它是怎么產(chǎn)生的。圖1顯示了最常見的數(shù)據(jù)沖突,當(dāng)兩個源同時更新一行數(shù)據(jù)時的情況。例如,假設(shè)有兩個客戶端(客戶端A和客戶端B)更新了本地數(shù)據(jù)緩存,然后同時同步到同一個服務(wù)器,此時客戶端A和B接收到的是表x的同一個拷貝,客戶端A更新了表x中第17行的電話號碼,然后同步回服務(wù)器,與此同時,客戶端B更新了表x中第17行的email地址,當(dāng)客戶端B同步回服務(wù)器時,沖突就發(fā)生了,此時服務(wù)器要決定究竟那個要寫入主拷貝中。象這樣的例子在應(yīng)用程序邏輯中也存在,MSF提供了兩個不同的方法來定義這個邏輯。

圖- 1 常見的同步?jīng)_突實例

沖突類型和解決辦法

MSF定義了五個不同的沖突類型,它定義為ConflictType枚舉量:

◆ ClientInsertServerInsert 以相同的主鍵創(chuàng)建一個新行。

◆ ClientUpdateServerUpdate 相同的行被更新,這是最常見的沖突,如圖1所示。

◆ ClientUpdateServerDelete 在客戶端更新的行,但在服務(wù)器上已經(jīng)被刪除了。

◆ ClientDeleteServerUpdate 在客戶端刪除的行,但在服務(wù)器上已經(jīng)更新了。

◆ ErrorsOccurred 當(dāng)發(fā)生錯誤時使用“catch all”(停止一切)預(yù)防行被插入、更新或刪除。

當(dāng)你看了圖1中的例子后,你可能會認(rèn)為只有當(dāng)同步計劃是雙向的時候才會引發(fā)沖突,但并不僅僅是這樣。設(shè)想一個只上載的情況,客戶端不關(guān)心在服務(wù)器上的更新,它只是想將新的信息提交給服務(wù)器,該客戶端會創(chuàng)建一行數(shù)據(jù)并同步到客戶端。在某些情況下,有些討厭的用戶會打亂服務(wù)器判斷數(shù)據(jù)行的行為,可能造成服務(wù)器認(rèn)為這一行數(shù)據(jù)不再需要,因此將其刪除了。在那個時候,客戶端會對那一行做出修改并同步回服務(wù)器,但這也會造成沖突,因為客戶端更新的行,在服務(wù)器上已經(jīng)被刪除了。這種情況下,只有將更新操作改為插入操作才能解決這個沖突。

除上面描述的沖突類型外,MSF還定義了三個內(nèi)置的行為來解決沖突,它們定義在ApplyAction枚舉量中:

◆ Continue 這是默認(rèn)的行為,它允許你繼續(xù)到列表中下一個沖突。

◆ RetryApplyingRow 將會重新嘗試應(yīng)用對行的修改,除非你使用某種方法修改了數(shù)據(jù),否則就會失?。ㄍǔJ窃诖a中使用自定義的沖突解決方案,匹配業(yè)務(wù)邏輯解決沖突)。

◆ RetryWithForceWrite 將會強制應(yīng)用程序修改行(覆蓋任何沖突的數(shù)據(jù))。

在接下來的內(nèi)容中,我們將會看到這些行為對某些沖突類型的處理結(jié)果。

使用ApplyChangeFailed解決沖突

知道沖突類型很重要,但你也需要知道是哪一行發(fā)生了沖突,MSF在DbServerSyncProvider和SqlCeClientSyncProvider上都提供了ApplyChangeFailed事件,允許你審查沖突信息,然后決定如何處理。在服務(wù)器和客戶端SyncProvider上都有可能引發(fā)事件,取決于同步的階段,ApplyChangeFailedEventArgs對象具有Action和Conflict屬性,Action屬性用于解決沖突,只要將其設(shè)為前一小節(jié)描述的ApplyAction類型的一個值即可;Conflict屬性描述了更詳細(xì)的沖突信息,如它的類型和發(fā)生沖突的行。

ApplyChangeFailedEventArgs對象還有一個Context屬性,它允許你修改正在同步的數(shù)據(jù),你可以使用它創(chuàng)建自己的沖突解決方案,這樣你在處理復(fù)雜數(shù)據(jù)沖突時可以更加得心應(yīng)手。

我們來看一些例子吧,我們創(chuàng)建了一個項目,顯示一個跟蹤顧客喜歡的數(shù)字的表,窗體的上半部分顯示了服務(wù)端數(shù)據(jù)拷貝,窗體的下半部分顯示了客戶端緩存中的數(shù)據(jù)拷貝,我們可以修改任何一半的數(shù)據(jù),然后保存數(shù)據(jù)到服務(wù)器和客戶端,接著嘗試同步數(shù)據(jù),如果遇到數(shù)據(jù)沖突,會顯示一個自定義窗體,讓我們選擇一個ApplyAction類型來解決沖突。

圖- 2 沖突解決方案示例窗體

我們通過修改數(shù)據(jù)緩存文件(.sync)的后端代碼使用partial類將ApplyChangeFailed事件聯(lián)系起來,在我們的例子代碼如下:

public partial class DataConflictsDataCacheServerSyncProvider

{

partial void OnInitialized()

{

this.ApplyChangeFailed += new

System.EventHandler(

DataConflictsDataCacheServerSyncProvider_ApplyChangeFailed);}

void DataConflictsDataCacheServerSyncProvider_ApplyChangeFailed(object sender,

Microsoft.Synchronization.Data.ApplyChangeFailedEventArgs e)

{

ConflictResolverForm cr = new ConflictResolverForm();

cr.Text = "Server Data Conflict Detected";

cr.ApplyChangeEventArgs = e;

cr.ShowDialog();

}

}

public partial class DataConflictsDataCacheClientSyncProvider

{

void DataConflictsDataCacheClientSyncProvider_ApplyChangeFailed(

object sender, Microsoft.Synchronization.Data.ApplyChangeFailedEventArgs e)

{

ConflictResolverForm cr = new ConflictResolverForm();

cr.Text = "Client Data Conflict Detected";

cr.ApplyChangeEventArgs = e;

cr.ShowDialog();

}

}

我們還必須將下面的代碼添加到客戶端SyncProvider的構(gòu)造器中(你可以在.designer.cs代碼文件中找到它):

this.ApplyChangeFailed +=new

System.EventHandler

(DataConflictsDataCacheClientSyncProvider_ApplyChangeFailed);

在ConflictResolverForm中,我們通過設(shè)置合適的ApplyAction告訴同步框架如何解決沖突,如下:

applyChangeEventArgs.Action = Microsoft.Synchronization.Data.ApplyAction.Continue;

applyChangeEventArgs.Action = Microsoft.Synchronization.Data.ApplyAction.RetryApplyingRow;

applyChangeEventArgs.Action = Microsoft.Synchronization.Data.ApplyAction.RetryWithForceWrite;

這些行為將會一一為你展示。

#p#

例1. ClientUpdateServerUpdate

在這個例子中,我們同時修改了服務(wù)端和客戶端CustomerId等于2的行,然后嘗試重新同步,在服務(wù)器端,我們修改了FirstName字段的值為Chad,在客戶端,我們修改FavoriteNumber字段的值為5。在服務(wù)器端SyncProvider上我們遇到了ClientUpdateServerUpdate沖突:

圖- 3 在服務(wù)器上遇到了ClientUpdateServerUpdate沖突

如果我們選擇繼續(xù),服務(wù)器端的修改就會勝出,客戶端的修改將會丟失:

圖- 4 在服務(wù)器上遇到ClientUpdateServerUpdate沖突選擇了ApplyAction.Continue行為后的結(jié)果

如果我們選擇了RetryApplyingRow,會重新陷入錯誤,因為我們還沒有修改數(shù)據(jù),因此我們僅僅需要再次顯示我們的沖突解決窗體。

如果我們選擇RetryWithForceWrite,客戶端的修改會勝出,而服務(wù)器端的修改就會丟失:

圖- 5 在服務(wù)器上遇到ClientUpdateServerUpdate沖突選擇了ApplyAction.RetryWithForceWrite行為后的結(jié)果

例2. ClientInsertServerInsert

在這個例子中,我們在服務(wù)器上插入了一行數(shù)據(jù),CustomerId(主鍵)等于3,我們也在客戶端插入了一行數(shù)據(jù),CustomerId(主鍵)也等于3。

圖- 6 在服務(wù)器和客戶端都插入一行數(shù)據(jù)

當(dāng)我們嘗試同步時,在服務(wù)器SyncProvider上我們遇到了ClientInsertServerInsert沖突:

圖- 7 在服務(wù)器上遇到的ClientInsertServerInsert沖突

如果我們選擇繼續(xù),我們會遇到另一個沖突ClientInsertServerInsert,不過這次沖突是在客戶端SyncProvider上:

圖- 8 在客戶端上的ClientInsertServerInsert沖突

如果我們再次選擇繼續(xù),你會看到兩邊的數(shù)據(jù)都沒有改變,每個數(shù)據(jù)庫都保持了它們自己的修改,實際上就是忽略了沖突。

圖- 9 在服務(wù)器上遇到ClientInsertServerInsert沖突,在客戶端上選擇ApplyAction.Continue行為后的結(jié)果

和前面的例子一樣,如果我們選擇RetryApplyingRow,我們將會繼續(xù)得到一個沖突對話框。

如果我們選擇RetryWithForceWrite,在客戶端上不會再出現(xiàn)沖突,客戶端的修改將會上載,覆蓋服務(wù)器上的修改:

圖- 10 在服務(wù)器上遇到ClientInsertServerInsert沖突,選擇ApplyAction.RetryWithForceWrite行為后的結(jié)果

使用ConflictResolver解決客戶端沖突

如果指定一種解決方案不能滿足你的需要,并且你想精簡你的代碼,MSF在SqlCeClientSyncProvider上提供了一個附加屬性ConflictResolver,你可以單獨設(shè)置它的屬性為下面三個值的一個來解決所有五種沖突:

◆ ClientWins

◆ ServerWins

◆ FireEvent

默認(rèn)情況下,最后一個選項FireEvent是默認(rèn)值。

設(shè)置ConflictResolver的代碼可以和ApplyChangeFailed處理程序一起添加到客戶端SyncProvider的構(gòu)造器中:

this.ConflictResolver.ClientDeleteServerUpdateAction = 

Microsoft.Synchronization.Data.ResolveAction.ServerWins;

this.ConflictResolver.ClientUpdateServerDeleteAction =

Microsoft.Synchronization.Data.ResolveAction.ClientWins;

this.ConflictResolver.ClientInsertServerInsertAction =

Microsoft.Synchronization.Data.ResolveAction.FireEvent;

this.ConflictResolver.ClientUpdateServerUpdateAction =

Microsoft.Synchronization.Data.ResolveAction.FireEvent;

this.ApplyChangeFailed +=new 

System.EventHandler

(DataConflictsDataCacheClientSyncProvider_ApplyChangeFailed);

在上面的例子中,我們總是允許更新勝過刪除,我們通過在為ApplyChangeFailed事件定義的處理程序中自定義業(yè)務(wù)邏輯讓更新沖突得到解決。

小結(jié)

所有數(shù)據(jù)同步解決方案都需要數(shù)據(jù)沖突解決方案,使用微軟的同步框架(MSF),它有一套內(nèi)置的沖突解決機制,讓你可以定義簡單的沖突解決方案(ConflictResolver),也可以定義復(fù)雜的沖突的解決方案(通過ApplyChangeFailed事件自定義業(yè)務(wù)邏輯解決方案)。

【編輯推薦】

  1. 項目管理利刃之MSF
  2. 解讀MSF團(tuán)隊管理的秘密
  3. 軟件項目管理總體流程設(shè)計
責(zé)任編輯:彭凡 來源: 51CTO.com
相關(guān)推薦

2010-03-21 19:05:19

微軟MSF

2013-08-14 09:48:02

微軟REEF

2022-05-31 09:52:04

Edge瀏覽器微軟

2017-09-09 16:22:51

PHP-MSF服務(wù)器服務(wù)框架

2025-03-27 08:00:00

邊緣計算SymmetricD開源軟件

2010-09-16 09:44:56

2009-05-26 10:21:07

2023-11-06 08:01:09

Go同步異步

2017-09-20 07:37:13

Swoole企業(yè)微服務(wù)框架

2010-03-30 17:27:47

Visual Stud

2012-05-17 09:28:06

代碼審查Java代碼

2017-09-06 17:05:54

大數(shù)據(jù)處理流程處理框架

2009-03-24 08:56:23

數(shù)據(jù)同步多線程Java

2018-04-03 10:33:15

大數(shù)據(jù)

2021-08-08 08:04:38

微軟macOS OneDrive

2010-09-26 13:30:08

DHCP協(xié)議故障處理

2013-03-14 09:54:54

jQueryJS

2021-04-02 12:55:14

數(shù)據(jù)處理Apache Falc開發(fā)

2013-12-16 17:17:01

OpenMp數(shù)據(jù)處理

2024-09-12 15:43:46

C#代碼后端
點贊
收藏

51CTO技術(shù)棧公眾號