UPDATE 語句可以復寫為 DELETE/INSERT 配對

本文說明 Update 語句可復寫為 DELETE/INSERT 組。

原始產品版本: SQL S
原始 KB 編號: 238254

摘要

如果更新屬於唯一條件約束的任何數據行,SQL Server 會將更新實作為「延遲更新」,這表示做為一對 DELETE/INSERT 作業。 這個「延遲更新」會導致複寫將一對 DELETE/INSERT 語句傳送給訂閱者。 還有其他可能導致延遲更新的情況。 因此,您在訂閱者端的觸發程式或自定義預存程式中實 UPDATE 作的任何商業規則也應該包含在 DELETE/INSERT 觸發程式或自定義預存程式中。

其他相關資訊

事務複製中的預設行為是使用 INSERTUPDATEDELETE 自定義預存程式,在訂閱者端套用變更。

INSERT 在發行者端所做的語句會透過 INSERT 預存過程調用套用至訂閱者。 同樣地, DELETE 語句會透過 DELETE 預存過程調用來套用。

不過,當語句執行為「延遲更新」時 UPDATE ,記錄讀取器代理程式會在散發資料庫中放置一對 DELETE/INSERT 預存程式呼叫,以套用至訂閱者,而不是更新預存過程調用。 例如,假設您有一 TABLE1個名為 的發行數據表,其中包含下列三個數據行:

  • col1 int
  • col2 int
  • col3 varchar(30)

的唯一唯一條件約束是透過主鍵條件約束 TABLE1 在 上 col1 定義。 假設您有一筆記錄(1,1,『達拉斯』)。

當您執行此程式碼時:

UPDATE TABLE1 set col1 = 3 where col3 = 'Dallas'

UPDATE語句是由 SQL Server 實作為語句組INSERTDELETE/,因為您正在更新 col1,其已定義唯一索引。 因此,記錄讀取器會在散發資料庫中放置一對 DELETE/INSERT 呼叫。 這可能會影響訂閱者端觸發程式或自定義預存程式中出現的任何商業規則。 您應該在 和 INSERT 觸發程式或預存程式中納入其他商業規則DELETE,以處理這種情況。

如果您想要將單一數據列更新複寫為 UPDATE 語句, DELETE 而不是 或 INSERT 配對,您可以啟用 追蹤旗標 8207

此外,如果您在發行集中使用水平篩選,而且更新的數據列不符合篩選條件,則只會 DELETE 將過程調用傳送給訂閱者。 如果先前更新的數據列不符合篩選條件,但在更新之後符合條件,則只會 INSERT 透過復寫程式傳送過程調用。

在上述範例中,假設您也有在 上 TABLE1定義的水平篩選: where col3 = 'Dallas'。 如果您執行此程式代碼:

UPDATE table1 set col3 = 'New York' where col1 = 3

記錄讀取器代理程式只會將 DELETE 預存過程調用套用至訂閱者,因為更新的數據列不符合水平篩選準則。

現在,如果您執行此程式碼:

UPDATE table1 set col3 = 'Dallas' where col1 = 3

記錄讀取器只會 INSERT 產生預存過程調用,因為數據列先前不符合篩選條件。

UPDATE雖然作業是在發行者端執行,但只會在訂閱者端套用適當的命令。