2017-05-05 7 views
-1

以上の値を返しましたが、私はサブクエリが1つの以上の値を返し、エラーSQL Serverのトリガ:サブクエリは、私は次のステートメントを使用して、別のテーブルからレコードを更新しようとしているトリガーを使用

を取得します。 =、!=、<、< =、>、> =、またはサブクエリが式として使用されている場合は、これは許可されません。ステートメントは終了されました。ここで

私はあなたが引き金でINSERTEDまたはDELETEDテーブルからサブクエリを使用する場合は、あなたがよりよい複数行の操作をサポートする構文を使用する必要があります

ALTER TRIGGER [dbo].[WO-A] 
ON [dbo].[WORKORDERS] 
AFTER UPDATE, INSERT, 
AS 
    IF ((SELECT ROUTING FROM INSERTED) LIKE 'Assy' 
      or (SELECT ROUTING FROM INSERTED) LIKE 'L&P' 
      or (SELECT ROUTING FROM INSERTED) LIKE 'ASSY FD' 
      or (SELECT ROUTING FROM INSERTED) LIKE 'ASSY BD' 

      or (SELECT ROUTING FROM INSERTED) LIKE 'RGA' 
      ) 
     BEGIN 
      set nocount on 
     IF TRIGGER_NESTLEVEL() > 1 
     RETURN 
    UPDATE T1 
    SET 
    [Assembly Notes]=T2.[Assembly Notes], 
    [Assy SO Confirm]=T2.[ASSEMBLY LOOKUP C], 
    [CALC COLOR]=T2.[COLOR], 
    [PILOT SIZE]=T2.[PILOT SIZE2], 
    [NO OF HOLES]=T2.[BOLT HOLES2], 
    [C/S OD]=T2.[C/S OD2], 
    [DISC OD]=T2.[DISC OD], 
    [C/S ANGLE2]=T2.[C/S ANGLE2], 
    [BH SIZE2]=T2.[BH SIZE2], 
    [SHORT WO PN]=t2.[CALC STOCK NO], 
    [CALC OFF-SET]=T2.[CALC OFF-SET], 
    [RUN OUT LAT]=T2.[RUN OUT LAT], 
    [RUN OUT RAD]=T2.[RUN OUT RAD], 
    [BOM SECONDRY DISC]=T2.[BOM - SECONDARY DISC], 
    [BH SPEC]=T2.[BH SPEC], 
    [BH CIRCLE2]=T2.[BH CIRCLE2], 
    [DISC THICKNESS2]=T2.[DISC THICKNESS], 
    [MRP BOM PARTS 1]=T2.[WHL BOM PART 1 PN], 
    [MRP BOM PARTS 2]=T2.[WHL BOM PART 2 PN], 
    [MRP BOM PARTS 3]=T2.[WHL BOM PART 3 PN], 
    [MRP BOM PARTS 4]=T2.[WHL BOM PART 4 PN], 
    --[ASSY PN-S]=T2.[CALC STOCK NO], 
    [SHORT WO PN2]=T2.[CALC STOCK NO], 
    [WO SALES DESCRIPTION] = T2.[Description for Sales], 
    --[Assy SO Confirm]=T2.[Assembly Lookup C], 
    [CUSTOMER PN]=T2.[CUSTOMER PN], 
    [MRP Wheel]=T2.[BOM WHEEL PN], 
    [TIRE PN]=T2.[BOM tire], 
    [TIRE SIZE]=T2.[TIRE SIZE], 
    [TIRE SUPPLIER]=T22.[Manufacturer], 
    [TIRE QUANTITY]=CASE WHEN T1.[TIRE PN]!='' THEN T1.[QUANTITY] 
    WHEN T1.[TIRE PN] IS NOT NULL THEN T1.[QUANTITY] 
    ELSE '' 
    END, 
    [RIM PN (MRP)]=t2.[BOM - RIM PN], 
    [WO Popularity]=t2.[POPULARITY], 
    --[RIM QUANTITY]=t2.[q 
    [WEIGHT]=T2.[unitWeight],--?? CHECK WETHER RIGHT COLUMN 
    --[ASSY DESC FOR LABEL] 
    SIZE=T21.[SIZE], 
    [MRP BLK DISC]=T21.[BLK DISC PN], 
    [WHEEL PN 1]=NULL, 

    [WHEEL PN 1-S]=NULL, 
    [ASSY PN-S]=NULL, 
    [MO ASSY PN]=null 

FROM WORKORDERS T1 
    INNER JOIN inserted i ON T1.[WORK ORDER #] = i.[WORK ORDER #] 
    CROSS APPLY (SELECT TOP 1 * 
       FROM [ASSEMBLIES] T2 
       WHERE t1.[ASSY PN] = T2.[ASSEMBLY LOOKUP V 1]) T2 
    CROSS APPLY (SELECT TOP 1 * 
       FROM [TIRES] T22 
       WHERE T22.[Tire Lookup H] = T2.[BOM Tire]) T22 

    CROSS APPLY (SELECT TOP 1 * 
       FROM [WHEELS] T21 
       WHERE T2.[BOM WHEEL] = T21.[WHEEL LOOKUP V]) T21 
     END 
+1

。トリガーは、常に複数の行で動作するように記述してください。 –

+0

2つ以上の行が挿入されている場合、Ifのclasesは複数の行を取得し、失敗します(私は信じています) –

+5

トリガーは** MAJOR **の脆弱性が** once行ごと** - それは**ではありません**。トリガは**文ごとに** **起動します。したがって、このトリガを起動させる 'INSERT'文が25行挿入された場合、トリガは一度**発生しますが、' Inserted'擬似テーブルは25行あります。あなたのコードがここで選択する25行のうちどれですか? 'SELECT ROUTING FROM INSERTED' - それは非決定論的なので、あなたは**任意の行**を得て、**あなたは**他のすべての行を無視します**。これを考慮に入れてトリガーを書き直す必要があります。 –

答えて

0

これらのROUTING値に制限されている間は、複数行の挿入/更新が有効です。

クロス・アプライには実際にorder by句が必要ですが、そうでなければランダムな行を取得して予期せぬ結果が出る可能性があります(必要に応じて、正しいインデックスを使用できます)。あなたが/時以上の1行を挿入するに更新するかどうかを確認する場合は、(ETC ..「アッシー」のような(INSERTEDからのルーティングを選択))最初からそのエラーを取得します

ALTER TRIGGER [dbo].[WO-A] 
    ON [dbo].[WORKORDERS] 
    AFTER UPDATE, INSERT, 
    AS 
BEGIN 
    SET NOCOUNT ON; 
      IF TRIGGER_NESTLEVEL() > 1 
      RETURN 
    ELSE 
     UPDATE T1 
     SET 
     [Assembly Notes]=T2.[Assembly Notes], 
     [Assy SO Confirm]=T2.[ASSEMBLY LOOKUP C], 
     [CALC COLOR]=T2.[COLOR], 
     [PILOT SIZE]=T2.[PILOT SIZE2], 
     [NO OF HOLES]=T2.[BOLT HOLES2], 
     [C/S OD]=T2.[C/S OD2], 
     [DISC OD]=T2.[DISC OD], 
     [C/S ANGLE2]=T2.[C/S ANGLE2], 
     [BH SIZE2]=T2.[BH SIZE2], 
     [SHORT WO PN]=t2.[CALC STOCK NO], 
     [CALC OFF-SET]=T2.[CALC OFF-SET], 
     [RUN OUT LAT]=T2.[RUN OUT LAT], 
     [RUN OUT RAD]=T2.[RUN OUT RAD], 
     [BOM SECONDRY DISC]=T2.[BOM - SECONDARY DISC], 
     [BH SPEC]=T2.[BH SPEC], 
     [BH CIRCLE2]=T2.[BH CIRCLE2], 
     [DISC THICKNESS2]=T2.[DISC THICKNESS], 
     [MRP BOM PARTS 1]=T2.[WHL BOM PART 1 PN], 
     [MRP BOM PARTS 2]=T2.[WHL BOM PART 2 PN], 
     [MRP BOM PARTS 3]=T2.[WHL BOM PART 3 PN], 
     [MRP BOM PARTS 4]=T2.[WHL BOM PART 4 PN], 
     --[ASSY PN-S]=T2.[CALC STOCK NO], 
     [SHORT WO PN2]=T2.[CALC STOCK NO], 
     [WO SALES DESCRIPTION] = T2.[Description for Sales], 
     --[Assy SO Confirm]=T2.[Assembly Lookup C], 
     [CUSTOMER PN]=T2.[CUSTOMER PN], 
     [MRP Wheel]=T2.[BOM WHEEL PN], 
     [TIRE PN]=T2.[BOM tire], 
     [TIRE SIZE]=T2.[TIRE SIZE], 
     [TIRE SUPPLIER]=T22.[Manufacturer], 
     [TIRE QUANTITY]=CASE WHEN T1.[TIRE PN]!='' THEN T1.[QUANTITY] 
     WHEN T1.[TIRE PN] IS NOT NULL THEN T1.[QUANTITY] 
     ELSE '' 
     END, 
     [RIM PN (MRP)]=t2.[BOM - RIM PN], 
     [WO Popularity]=t2.[POPULARITY], 
     --[RIM QUANTITY]=t2.[q 
     [WEIGHT]=T2.[unitWeight],--?? CHECK WETHER RIGHT COLUMN 
     --[ASSY DESC FOR LABEL] 
     SIZE=T21.[SIZE], 
     [MRP BLK DISC]=T21.[BLK DISC PN], 
     [WHEEL PN 1]=NULL, 

     [WHEEL PN 1-S]=NULL, 
     [ASSY PN-S]=NULL, 
     [MO ASSY PN]=null 

    FROM WORKORDERS T1 
     INNER JOIN inserted i ON T1.[WORK ORDER #] = i.[WORK ORDER #] 
     CROSS APPLY (SELECT TOP 1 * 
        FROM [ASSEMBLIES] T2 
        WHERE t1.[ASSY PN] = T2.[ASSEMBLY LOOKUP V 1]) T2 
     CROSS APPLY (SELECT TOP 1 * 
        FROM [TIRES] T22 
        WHERE T22.[Tire Lookup H] = T2.[BOM Tire]) T22 

     CROSS APPLY (SELECT TOP 1 * 
        FROM [WHEELS] T21 
        WHERE T2.[BOM WHEEL] = T21.[WHEEL LOOKUP V]) T21 
    WHERE i.ROUTING IN ('Assy', 'L&P', 'ASSY FD', 'ASSY BD', 'RGA') 
END 
+0

ありがとうございますが、私はまだ同じエラーが発生します – Joe

0

を使用するコードです。例えば

このサブクエリ(SELECT ROUTING FROM INSERTED LIKE 'Assy')は、その後if操作は失敗し、複数の行を返す場合。ここにあなたがIF ((SELECT ROUTING FROM INSERTED) LIKE 'Assy'...

を使用この場合、一度に1行しか挿入または更新できません。たとえば、次のようなクエリを使用することはできません。

UPDATE [dbo].[WORKORDERS] 
SET ROUTING='L' 
WHERE ... --Queries that return more than one row 
関連する問題