2017-04-11 22 views
0

トリガーはどのように動作するべきかについて多くの答えがありますが、コードが挿入されて実行されるという点で私の夢はユニークですが、@type変数は誤った答えになります。クエリをテーブル参照と孤立して実行すると、正しい答えが返されます。それは私が偽を得るトリガーの一部としてのみです。トリガーの更新が失敗するのはなぜですか?

クエリの一部が関数を呼び出すが、これもすべて単独で実行されたときに機能するので、トリガに何か他のものがあると不思議に思うだろう。


SQL:

ALTER TRIGGER [dbo].[MPH_I_TEST_GROUP_REQUEST_PRINTS] 
ON [dbo].[MPH_PRINT_TEST_QUEUE] 
FOR INSERT,UPDATE 
AS 

DECLARE @V_Refno NUMERIC(10) 
DECLARE @V_User_Modif VARCHAR(30) 

BEGIN 
SET @V_User_Modif = suser_sname() 
SELECT @V_Refno = tgreq_refno FROM inserted 

--> Get details of test type 
DECLARE @car_sponts VARCHAR(8000) 
DECLARE @type VARCHAR(50) 

SET @type = 'blank' 
SELECT @car_sponts = CONVERT(VARCHAR(8000),sypro.long_value) 
FROM 
    system_profiles sypro (NOLOCK) 
WHERE 
    sypro.code = 'MPH_CARD_PRT_SPONTS' 
AND (sypro.archv_flag = 'N' OR sypro.archv_flag IS NULL) 

--> Update type based on tests ordered 
SELECT 
    @type = CASE WHEN COUNT(*) > 0 THEN 'CARDIO' ELSE 'type fail' END --> Does the request belong in a service point noted in system profile MPH_CARD_PRT_SPONTS 
FROM  
    test_group_requests tgreq (NOLOCK) 
INNER JOIN 
    test_form_requests tfreq (NOLOCK) ON tgreq.tgreq_refno = tfreq.tgreq_refno 
INNER JOIN 
    test_requests tereq (NOLOCK) ON tfreq.tfreq_refno = tereq.tfreq_refno 
INNER JOIN 
    test_definitions tstdf (NOLOCK) ON tereq.tstdf_refno = tstdf.tstdf_refno 
INNER JOIN 
    test_locations tstlc (NOLOCK) ON tstlc.tstdf_refno = tstdf.tstdf_refno 
WHERE 
    tgreq.tgreq_refno IN (SELECT tgreq_refno FROM inserted) 
AND (tstlc.archv_flag = 'N' OR tstlc.archv_flag IS NULL) 
AND tstlc.spont_refno IN 
    (
    SELECT DISTINCT spont.spont_refno FROM service_points spont (NOLOCK) WHERE (spont.archv_flag = 'N' OR spont.archv_flag IS NULL) AND spont.code IN (SELECT Item FROM [dbo].[MPH_PARSELIST](@car_sponts)) 
    ) 

--> Update test type to print queue 
UPDATE mph_print_test_queue 
SET mph_print_test_queue.type = 'updated ' + @type 
FROM 
    inserted,mph_print_test_queue 
WHERE 
    mph_print_test_queue.tgreq_refno = inserted.tgreq_refno 

END 

だから、現在のすべてのレコードは、彼らが挿入/更新する「心臓」の基準を満たした場合にも「型の更新タイプは失敗」を取得。

ありがとうございます。 Phil。また、この更新プログラムを試しました


UPDATE mph_print_test_queue 
SET mph_print_test_queue.type = 'updated cardio' 
FROM  
    inserted,test_group_requests tgreq (NOLOCK) 
INNER JOIN 
    test_form_requests tfreq (NOLOCK) ON tgreq.tgreq_refno = tfreq.tgreq_refno 
INNER JOIN 
    test_requests tereq (NOLOCK) ON tfreq.tfreq_refno = tereq.tfreq_refno 
INNER JOIN 
    test_definitions tstdf (NOLOCK) ON tereq.tstdf_refno = tstdf.tstdf_refno 
INNER JOIN 
    test_locations tstlc (NOLOCK) ON tstlc.tstdf_refno = tstdf.tstdf_refno 
WHERE 
    tgreq.tgreq_refno = inserted.tgreq_refno 
AND (tstlc.archv_flag = 'N' OR tstlc.archv_flag IS NULL) 
AND tstlc.spont_refno IN 
    (
    SELECT DISTINCT spont.spont_refno FROM service_points spont (NOLOCK) WHERE (spont.archv_flag = 'N' OR spont.archv_flag IS NULL) AND spont.code IN (SELECT Item FROM [dbo].[MPH_PARSELIST](@car_sponts)) 
    ) 
+3

問題番号1は「SELECT V_Refno = tgreq_refno FROM inserted」です。挿入されたコレクションには複数の行を含めることができますが、このトリガーは1つの行のみを想定しています。すべてのトリガーは、挿入/削除が複数の行を持ち、スカラーではなくSETSで動作すると常に仮定しなければなりません。更新では、V_Refnoには、複数の行が更新された場合など、挿入された最後の行の値のみが格納されます。 – pmbAustin

+0

@pmbAustin \t ありがとうございます。問題はどこかにあり、まだ喜んでいないことを知っています。私が先に試したバッチ更新はどちらもうまくいかないので、魔法のタッチは何ですか?私はメインスレッドの最後にアップデートを追加しました。 –

+1

また、どこにでもノーロックヒントを飛ばし続ける前に、これを見てみたいかもしれません。多くの人が気付くよりははるかに邪悪です。 http://blogs.sqlsentry.com/aaronbertrand/bad-habits-nolock-everywhere/そして、あなたのアップデートでは、本当にANSI-92スタイルの結合を使用すべきです。 http://sqlblog.com/blogs/aaron_bertrand/archive/2009/10/08/bad-habits-to-kick-using-old-style-joins.aspx –

答えて

0

を私はようやく家に帰る途中で電球の瞬間を得ました。挿入されたテーブルに更新をリンクせず、一致するレコードに従ってバッチ更新のみを行います。

申し訳ありませんが、投稿する前にこれを取得しないでください。長い一日。

関連する問題