WernerK: Hilfe bei SQL Trigger

Hallo, ich hatte bisher noch nie mit Trigger gearbeitet, bzw. einen selbst erstellt.

Eine Tabelle hat folgende Spalten: (vereinfacht) -----------------------------------------------------------------—

myID, Name, Contact, Flag_Changed

-----------------------------------------------------------—

Folgende Aufgabe:

Wenn jemand z.b. den Name oder Contact ändert, soll automatisch eine "1" in die Spalte "Flag_Changed" geschrieben werden.

Würde dieser Trigger diese Aufgabe erfüllen, bzw. funktionieren?

CREATE TRIGGER [dbo].[after_update] ON [dbo].[MYTABLE]
AFTER UPDATE AS 
BEGIN
    DECLARE @myID AS INT
    SELECT @myID = [myID]
    FROM INSERTED

    UPDATE MYTABLE 
    SET MYTABLE.Flag_Changed = 1
    WHERE [myID] = @myID

Gruss

Werner

  1. Hallo

    Würde dieser Trigger diese Aufgabe erfüllen, bzw. funktionieren?

    CREATE TRIGGER [dbo].[after_update] ON [dbo].[MYTABLE]
    AFTER UPDATE AS 
    BEGIN
        DECLARE @myID AS INT
        SELECT @myID = [myID]
        FROM INSERTED
    
        UPDATE MYTABLE 
        SET MYTABLE.Flag_Changed = 1
        WHERE [myID] = @myID
    

    Abgesehen vom Umstand, dass zu einem Anfang auch ein Ende gehört, dass zum Tabellennamen auch das dbo notiert wird und dass ein UPDATE meines Wissens nach nicht mit SET arbeitet, also abgesehen von den nicht schlüssigen Dingen, sieht der Code schlüssig aus.

    -- der Code davor
    UPDATE dbo.MYTABLE 
         dbo.MYTABLE.Flag_Changed = 1
         WHERE dbo.MYTABLE.[myID] = @myID
    END
    

    Die Angabe von dbo.MYTABLE kannst du bei den Spaltennamen aber auch weglassen.

    Tschö, Auge

    --
    Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
    Toller Dampf voraus von Terry Pratchett
    1. Tach!

      [...] und dass ein UPDATE meines Wissens nach nicht mit SET arbeitet

      Das SET ist sogar ein zwingend notwendiger Bestandteil eines Update-Statements.

      also abgesehen von den nicht schlüssigen Dingen, sieht der Code schlüssig aus.

      Was ist, wenn der Update-Trigger mit dem UPDATE drin den Update-Trigger triggert?

      Zudem setzt der Trigger das Flag immer und nicht nur wenn die beiden Felder geändert wurden.


      Bei MySQL jedenfalls würde ich einen BEFORE-Trigger nehmen, aber der MS SQL Server hat sowas wohl nicht. Mit dem kann man Werte vor dem Speichern anpassen.

      dedlfix.

      1. Hallo

        [...] und dass ein UPDATE meines Wissens nach nicht mit SET arbeitet

        Das SET ist sogar ein zwingend notwendiger Bestandteil eines Update-Statements.

        Stimmt, ich war gedanklich <del>einerseits bei der Schreibweise, die MySQL anbietet und die analog zu INSERT funktioniert und andererseits</del> bei SET als Befehl zur Änderung einer Variablen ausßerhalb eines Queries.

        Ich sollte Feierabend machen.

        also abgesehen von den nicht schlüssigen Dingen, sieht der Code schlüssig aus.

        Was ist, wenn der Update-Trigger mit dem UPDATE drin den Update-Trigger triggert?

        Gute Frage. Ich benutze in MS SQL einen Trigger AFTER UPDATE, in dem die Ausführung zusätzlich mit IF UPDATE ([Feldname]) auf die Reaktion auf die Änderung dieses bestimmten Feldes beschränkt wird, dessen Wert zu allem Überfluss innerhalb des Triggers geändert wird. Deine Frage impliziert die Vermutung, dass der Trigger in einer Endlosschleife landen müsste. Das tut er aber nicht.

        Zudem setzt der Trigger das Flag immer und nicht nur wenn die beiden Felder geändert wurden.

        Wir enden also bei „abgesehen von weiteren als den vorgenannten Bedingungen“. 😀


        Bei MySQL jedenfalls würde ich einen BEFORE-Trigger nehmen, aber der MS SQL Server hat sowas wohl nicht. Mit dem kann man Werte vor dem Speichern anpassen.

        Die MS-SQL-Doku nennt in dieser Hinsicht FOR, AFTER und INSTEAD OF als mögliche Werte. AFTER und INSTEAD OF sind mMn selbsterklärend, zu FOR schweigt sich die verlinkte Seite allerdings leider aus.

        Tschö, Auge

        --
        Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
        Toller Dampf voraus von Terry Pratchett
        1. Hallo Auge,

          Stimmt, ich war gedanklich <del>einerseits bei der Schreibweise, die MySQL anbietet und die analog zu INSERT funktioniert und andererseits</del> bei SET als Befehl zur Änderung einer Variablen ausßerhalb eines Queries.

          Wolltest Du das hier?

          Stimmt, ich war gedanklich einerseits bei der Schreibweise, die MySQL anbietet und die analog zu INSERT funktioniert und andererseits bei SET als Befehl zur Änderung einer Variablen ausßerhalb eines Queries.

          Durchstreichen geht so: ~~Durchstreichen~~

          Rolf

          --
          sumpsi - posui - clusi
          1. Hallo

            … <del>einerseits bei der Schreibweise, die MySQL anbietet und die analog zu INSERT funktioniert und andererseits</del> …

            Wolltest Du das hier?

            einerseits bei der Schreibweise, die MySQL anbietet und die analog zu INSERT funktioniert und andererseits

            Durchstreichen geht so: ~~Durchstreichen~~

            Sagen wir mal so, ich wollte den Abschnitt als obsolet kennzeichnen. Eine Durchstreichung hätte mir gefallen, habe ich aber nicht gekannt und meine Markierung ist offensichtlich auch so angekommen. Dennoch danke für die Aufklärung. Ich hoffe, ich merke mir das bis zum nächsten Mal. 😀

            Tschö, Auge

            --
            Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
            Toller Dampf voraus von Terry Pratchett
            1. Hallo Auge,

              Ich hoffe, ich merke mir das bis zum nächsten Mal. 😀

              Es gibt auch noch Gunnars Textrick. 😀

              Bis demnächst
              Matthias

              --
              Rosen sind rot.
              1. Hallo

                Ich hoffe, ich merke mir das bis zum nächsten Mal. 😀

                Es gibt auch noch Gunnars Textrick. 😀

                Hmm, geht es um ein Rick für Text oder ein Trick für Tex (oder gar TeX)? 😉

                Tschö, Auge

                --
                Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
                Toller Dampf voraus von Terry Pratchett
                1. Hallo Auge,

                  Ich hoffe, ich merke mir das bis zum nächsten Mal. 😀

                  Es gibt auch noch Gunnars Textrick. 😀

                  Hmm, geht es um ein Rick für Text oder ein Trick für Tex (oder gar TeX)? 😉

                  Ich sehe, du hast den Smiley richtig interpretiert.

                  Bis demnächst
                  Matthias

                  --
                  Rosen sind rot.
      2. Hallo

        Was ist, wenn der Update-Trigger mit dem UPDATE drin den Update-Trigger triggert?

        Das funktioniert nur, wenn es für die Tabelle erlaubt wurde (RECURSIVE_TRIGGERS). Standardmäßig gibt es an der Stelle keine solche.

        Tschö, Auge

        --
        Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
        Toller Dampf voraus von Terry Pratchett
      3. Hallo,

        <<Zudem setzt der Trigger das Flag immer und nicht nur wenn die beiden Felder geändert wurden.>>

        Also das war ja nur ein Beispiel. Es sind ca. 10 Felder die vom User geändert werden können. Sobald hier etwas geändert wird, sollte der Trigger greifen.

        Aber stimmt: Was passiert wenn der Trigger selbst einen Update macht? Löst er dann wieder den eigenen Trigger aus? Oder könnte man den Trigger ausschließen, wenn die Spalte "Flag_Changed" betroffen ist?

        Gruss Werner

        1. Hallo,

          ich muss nochmals wegen des Triggers nachhaken. Ich hatte diesen wie oben jetzt aktiviert. Beim Testen ist mir jetzt aber Folgendes aufgefallen.

          Ein PHP Script macht zu einer bestimmten Zeit einen Update auf diese Tabelle und setzt alle Zeilen in der Spalte "FLag_Changed" auf 0 zurück.

          UPDATE [dbo].[MYTABLE] SET FLAG_CHANGED = 0
          

          Offensichtlich reagiert dann der Trigger auch auf diesen Update und er setzte dann in der ersten Zeile der Tabelle die Spalte "Flag_Changed" auf 1.

          Kann man den Trigger irgendwie verändern oder so gestalten, dass er NICHT auf Updates der Spalte FLAG_CHANGED reagiert?

          Gruss Werner

          1. Hallo,

            ich habe in den Trigger nun noch Folgendes hinzugefügt:

            If NOT UPDATE(FLAG_CHANGED) OR NOT UPDATE([FLAG_NEW])

            Nun reagiert der Trigger nicht mehr auf Änderungen in diesen Spalten.

            Gruss

            Werner