2016-09-27 7 views
2

私は、通常のクエリを使用してSQLステートメントをしようとすると、それはこのように正常に動作します:それはトリガーでは動作しません。しかしデバッグ私のSQL Serverのトリガ更新

UPDATE TraineeMonthlyShopItemListRecord 
SET Data01 = 1 
WHERE TraineeID = '553' 
    AND ShopItemListID = '17' 
    AND RecordID IN (SELECT a.recordid 
        FROM TraineeMonthlyHourRecord a 
        JOIN MonthlyHourRecord b ON a.RecordID = b.RecordID 
        WHERE b.Month = '201609' 
        AND a.TraineeID = '553' 
        GROUP BY a.RecordID 
        HAVING COUNT(*) = 1) 

。私は成功したトリガーを保存することができますが、私は、テーブル内のレコードを挿入し、手動でそれをテストするとき、私はエラーを取得しておいてください。ここでは

Incorrect syntax near 'MonthlyHourRecord'

は私のトリガーコードで、見ていると悪事何ができるかを参照してください、ありがとう!

SET ANSI_NULLS ON 
GO 
SET QUOTED_IDENTIFIER ON 
GO 

ALTER TRIGGER [dbo].[t2] 
ON [dbo].[TraineeShopItemListRecord] 
AFTER INSERT  
AS  
BEGIN 
    declare @TraineeID varchar(10) 
    declare @MM varchar(10) 
    declare @YYYY varchar(10) 
    declare @ShopItemListID varchar(20) 
    declare @RecordID varchar(10) 
    declare @YYYYMM varchar(10) 
    declare @RecordTime datetime 
    declare @DD varchar(10) declare @test varchar(10) 
    declare @DataDD varchar(10) 
    declare @Quantity varchar(10) 
    declare @SQL nvarchar(200) 

    SELECT @ShopItemListID = ShopItemListID from inserted 
    SELECT @RecordTime = RecordTime from inserted 
    SELECT @Quantity = Quantity from inserted 

    SET @MM = substring(CONVERT(varchar,@RecordTime, 112),5,2) 
    SET @YYYY = substring(CONVERT(varchar,@RecordTime, 112),1,4) 
    SET @DD = substring(CONVERT(varchar,@RecordTime, 112),7,2) 

    SELECT @TraineeID = TraineeID from inserted 

    SET @YYYYMM = @[email protected] 
    SET @DataDD = 'Data'[email protected] 

    SET @SQL = 'UPDATE TraineeMonthlyShopItemListRecord SET  '[email protected]+'='[email protected]+' WHERE TraineeID ='''[email protected]+''' and ShopItemListID='''[email protected]+''' and RecordID IN (SELECT DISTINCT a.RecordID from TraineeMonthlyHourRecord a JOIN MonthlyHourRecord b on a.RecordID = b.RecordID WHERE b.Month ='''[email protected]+''' and a.TraineeID ='''[email protected]+''' GROUP BY a.RecordID HAVING COUNT(*) = 1)' 

    EXEC sp_executesql @SQL 
END 
+1

あなたのトリガがあり** MAJOR **あなたはそれが呼び出されることになりますと仮定しているように見えるという点で欠陥**一度行あたり** - つまり**ない**ケース。トリガは**文ごとに** **起動します。したがって、このトリガを起動させる 'INSERT'文が25行挿入された場合、トリガは一度**発生しますが、' Inserted'擬似テーブルは25行あります。あなたのコードがここで選択する25行のうちどれですか? 'SELECT @Quantity =数量が挿入されました ' - それは非決定論的です。**任意の行**を取得し、**すべての他の行を無視します**。これを考慮に入れてトリガーを書き直す必要があります。 –

+0

提案していただきありがとうございます。それを書き直すにはどうすればよいでしょうか? – autopenta

+0

'Inserted'(と' Deleted')に**複数の行**が含まれることを考慮する必要があります。したがって、個々の列の値を取得するのではなく、** set-based **演算を使用する必要があります。 –

答えて

0

コメントが大きいので、回答に書きます。

あなたが更新する必要がテーブルを結合するには、この

SELECT TraineeID, 
     ShopItemListID, 
     RecordTime, 
     Quantity, 
     substring(CONVERT(varchar,@RecordTime, 112),1,4)+substring(CONVERT(varchar,@RecordTime, 112),5,2) as YYYYMM 
     'Data'+substring(CONVERT(varchar,@RecordTime, 112),7,2) as DataDD 
FROM inserted 

を使用することができます。

この試してみて:

;WITH cte AS (
SELECT TraineeID, 
     ShopItemListID, 
     RecordTime, 
     Quantity, 
     substring(CONVERT(varchar,@RecordTime, 112),1,4)+substring(CONVERT(varchar,@RecordTime, 112),5,2) as YYYYMM 
     'Data'+substring(CONVERT(varchar,@RecordTime, 112),7,2) as DataDD 
FROM inserted 
) 

UPDATE tm 
SET Data01 = c.Quantity 
FROM TraineeMonthlyShopItemListRecord tm 
INNER JOIN cte c 
    ON c.TraineeID = tm.TraineeID 
     AND tm.ShopItemListID = c.ShopItemListID 
CROSS APPLY (
    SELECT a.RecordID 
    FROM TraineeMonthlyHourRecord a 
    INNER JOIN MonthlyHourRecord b 
     ON a.RecordID = b.RecordID 
    WHERE b.Month = c.YYYYMM 
     AND a.TraineeID = c.TraineeID 
    GROUP BY a.RecordID 
    HAVING COUNT(*) = 1 
) a 
WHERE a.RecordID = tm.RecordID 
+0

ありがとうございました。 – autopenta

+0

私の喜び!これがあなたを助けることを願って:) – gofr1

関連する問題