0

次のリリースの一部として数百万行を更新する必要がありますが、更新するとトランザクションログがいっぱいになり、失敗します。私にはいくつかのアイデアがありますが、私はSQLの専門家ではないので、私が気付いていない落とし穴があると確信しています。

関連するポイント:

  1. スクリプトを運用チームに渡す必要があるため、手動で介入しないT-SQLメソッドが必要です。
  2. どうやら、トランザクションログは15分ごとにリサイクルされます。WAITFOR DELAY '00:15:00'(以下のようにcatchブロックでtry-catchを使用してループを作成することを考えました)
  3. (編集)データ以外は変更できません。
  4. (編集)これは、外部キー列を別の既存のキーに変更する単純な更新です。

ありがとう、

フィル

DECLARE
    @AffectedRows int

SET @AffectedRows = 0

WHILE @AffectedRows < @RowsToUpdate
BEGIN
    BEGIN TRY
        BEGIN TRAN
        -- Do some updates  
        SET @AffectedRows = @AffectedRows + @@RowCount
        COMMIT TRAN
    END TRY
    BEGIN CATCH
        PRINT ERROR_MESSAGE()
        WAITFOR DELAY '00:15:00'
    END CATCH
END

PRINT @AffectedRows
4

3 に答える 3

2

結局、私がすでに書いた例が最もうまくいきました。トランザクションログの完全なエラーがキャッチにキャッチされ、15分はログがリサイクルされるのに十分な長さです。

DECLARE 
    @AffectedRows int 

SET @AffectedRows = 0 

WHILE @AffectedRows < @RowsToUpdate 
BEGIN 
    BEGIN TRY 
        BEGIN TRAN 
        -- Do some updates   
        SET @AffectedRows = @AffectedRows + @@RowCount 
        COMMIT TRAN 
    END TRY 
    BEGIN CATCH 
        PRINT ERROR_MESSAGE() 
        WAITFOR DELAY '00:15:00' 
    END CATCH 
END 

PRINT @AffectedRows
于 2010-06-22T11:45:18.393 に答える
1

いくつかのポイント/アイデア:

  1. トランザクションログを任意のサイズに拡張して、いっぱいにならないようにすることができます。
  2. トランザクションログが大きくなりすぎる場合は、いつでもDBをバックアップして、ログを切り捨てることができます。
  3. データをバッチで処理できます(一度に100万回実行)
  4. データを作業テーブルにコピーし、処理が完了したらsp_renameを入力できます。
于 2010-06-21T10:14:27.163 に答える
0

あなたはニブリングの削除/更新を再発明しています:)

このアプローチを見てください。単一の行よりも大きなブロックを実行できます。

http://www.sqlservervideos.com/video/nibbling-deletes/

http://sqladvice.com/blogs/repeatableread/archive/2005/09/20/12795.aspx

于 2010-06-21T10:23:03.543 に答える