views:

40

answers:

2

Hi,

I am not so experienced on databases, so bare with me. ;-) A quite simple FOR INSERT trigger keeps returning the error "Subquery returned more than 1 value.." when inserting more than one row at a time. When i insert rows into the table SOA.dbo.photos_TEST using a statement like;

INSERT INTO SOA.dbo.photos_TEST (id,length,picture,type,name,value,arrivaldatetime)
SELECT  VW.id, ... ,
FROM SOA.dbo.AeosPhotoTEST_VW vw
WHERE ...

The insert fails. But when i add a TOP(1) to the SELECT statement the trigger does not report an error. So probably the "SELECT VALUE FROM INSERTED" statement in the trigger does return all rows in the INSERTED table. Should i iterate in the trigger througg all the rows in INSERTED ? Any suggestion is welcome.

The current code of the trigger is;

SELECT @VALUE = (SELECT VALUE FROM INSERTED)

SET NOCOUNT ON

BEGIN
    DELETE FROM SOA.dbo.photos_TEST 
    WHERE   (value = @VALUE ) 
    AND (arrivaldatetime < (SELECT arrivaldatetime 
                FROM INSERTED
                WHERE value = @VALUE))
END
+3  A: 

Modify the T-SQL Trigger deletion logic to the following:

DELETE A
FROM SOA.dbo.photos_TEST A
   INNER JOIN INSERTED B on
       A.VALUE = B.VALUE
WHERE A.arrivaldatetime < B.arrivaldatetime 
John Sansom
Hi John, changing the trigger as you suggested still returns "Subquery returned more than 1 value. This is not permitted when the..." when adding more than 1 row.
pcvnes
+1 for teaching me a new trick. Much appreciated, thx.
Lieven
@pcvnes, it shouldn't. Are you certain you've changed the trigger? Can you post the updated script?
Lieven
Hi John, tried your solution again. This time cut-and-paste and it indeed works. Thanks! Can now start solving the next issue in my AFTER INSERT,UPDATE trigger is see.. What makes your solution 'better' above the SQL of Lieven? Is it less costly ?
pcvnes
@pcvnes: Excellent news. The two solutions to your problem are essentially the same.
John Sansom
+1  A: 

I assume you need to remove all old values. Adjusting your trigger as below does the trick.

Trigger

  BEGIN 
    DELETE p
    FROM  SOA.dbo.photos_TEST p
          INNER JOIN INSERTED i ON i.Value = p.Value
                                   AND i.ArrivalDateTime > p.ArrivalDateTime
  END
Lieven
@Lieven: You're welcome my friend. I know what you mean too. The day I stop learning is the day I look for a new career!
John Sansom
@John, thx for the edit. I still get excited learning new, faster ways of doing things. :)
Lieven
Hi Lieven, Thanks! This one also works ! Is it indeed that when you insert multiple rows into a table, the INSERTED table contains multiple rows and the trigger is only executed once ? I assumed that every row update resulted in a separate trigger event.
pcvnes
@Lieven: Correct. Keep in mind that SQL Server processes data in sets, and so a single Insert statement, results in a single fire of a given Trigger, regardless of the number of records to be inserted.
John Sansom