2 つの異なるインスタンスで動作する多くの SSB を実装しています。これらは、非同期トリガーに基づくデータ プッシュパターンです。
私のSQL 情報は以下の通りです。 2.0.50727.5448 オペレーティング システム 6.1.7601
私のシナリオは主に以下のとおりです
複数のレコードは、テーブルまたは1 つのレコードに一括で挿入されます。
このデータは別の DB に送信されます。
アクティブ化手順は、 BEGIN TRAN と END TRAN の間で開始されます。
このメッセージを検証します。
検証に失敗した場合は、このメッセージをキューから削除し、別の SSB オブジェクトを使用してそのメッセージが無効であったことから、ACkを送り返します。
それ以外の場合は、メッセージが正常に読み取られたことを知らせるACKが送信されます。
次に、Activation Procedure は別の Procedure を呼び出して、メッセージ bodyを処理します。
この USP_Process_Records もBEGIN TRAN と END TRAN の間にあります。
非常に多くの理由により、この手順は、私が行ったいくつかのビジネスニーズに従って失敗する可能性があります.
Pro SQL Server 2008 Service Broker になります。
したがって、アクティベーション手順では、 USP_Process_Records の失敗状態になるか、 BEGIN CATCH 部分に移動してトランザクションをロールバックし、失敗 ACK を送信します。
最後に、前の読み取り成功確認応答はまったく送信されず、2 回目は正常に送信されることがわかりました。
そのため、Broker Service のトランザクション管理について非常に混乱しています。
個別のタスクごとに BEGIN TRAN を使用し、受信および処理 UPS から削除する必要がありますか?
USP_Process_Records 内でも TRY、CATCH を使用して、USP_Receive_Records にエラーを返す必要がありますか?
この問題を回避するには、TRY、CATCH ブロック ar Receive を変更する必要があります
最後に、後で何か問題が発生した場合でもすべての ack を送信し、Poison メッセージとロールバックをまったく回避したいと考えています。前もって感謝します。
-ところで、私はrusanu ブログを Broker Service Error HandlingとRead Pro SQL Server 2008 Service Broker Transaction Management 部分に使用しました。
以下の USP のサンプルを見つけてください。
--USP_Receive_Records
BEGIN TRY
BEGIN TRAN
WHILE 1=1
BEGIN
SELECT @ReplyMessage = NULL, @TargetDlgHandle = NULL
WAITFOR (RECEIVE TOP(1)
@TargetDlgHandle=Conversation_Handle
,@ReplyMessage = CAST(message_body AS XML)
,@ReplyMessageName = Message_Type_Name
FROM Q_Service_Receive), TIMEOUT 1000
IF @TargetDlgHandle IS NULL
BREAK
--Check if the message has the same message type expected
IF @ReplyMessageName=N'Service_Msg'
BEGIN
--Send Batch Read Success ACK
--Send ACK Here
EXEC [dbo].[USP_ACKMsg_Send] @ACKMsg, @Service_Msg;
--Handle ACK Send failed!
-- Execute the USP_Service_Msg_Process for the batch rows
EXECUTE USP_Service_Msg_Process @ReplyMessageName, @RC OUTPUT;
--Case Processing Succeeded
IF @RC=0
BEGIN
--Send Batch Read Success ACK
END
--SEND ACK Processing failed with Return Code to define cause of the error
ELSE
BEGIN
--Send Batch Processing Failed ACK
END
END
END CONVERSATION @TargetDlgHandle;
END
COMMIT TRAN;
END TRY
BEGIN CATCH
if (XACT_STATE()) = -1
BEGIN
rollback transaction;
END;
if (XACT_STATE()) = 1
BEGIN
DECLARE @error int, @message nvarchar(4000), @handle uniqueidentifier;
SELECT @error = ERROR_NUMBER(), @message = ERROR_MESSAGE();
END conversation @handle with error = @error description = @message;
COMMIT;
END
END CATCH
END
--USP_Process_Records
BEGIN TRAN
While(@nCount <= @nodesCount)
BEGIN
IF(@S_HIS_Status = '02')
BEGIN
-- check N_Paid_Trans_ID is not nuul or zero or empty
IF( @N_GET_ID IS NULL OR @N_GET_ID = 0 OR @N_GET_ID = '')
BEGIN
SET @RC = 8
RETURN;
END
EXECUTE USP_Handle_Delivered_Service @N_GET_ID, @RC OUTPUT
SELECT @myERROR = @@ERROR--, @myRowCount = @@ROWCOUNT
IF @myERROR <> 0 OR @RC <> 0
BEGIN
ROLLBACK TRAN
END
END
--A lot of similar cases
END TRAN