Trigger SQL Server 2000

Published on November 2016 | Categories: Documents | Downloads: 55 | Comments: 0 | Views: 1125
of 21
Download PDF   Embed   Report

Comments

Content

Triggers are special types of Stored Procedures that are defined to execute automatically in place of or after data modifications. They can be executed automatically on the INSERT, DELETE and UPDATE triggering actions. There are two different types of triggers in Microsoft SQL Server 2000. They are INSTEAD OF triggers and AFTER triggers. These triggers differ from each other in terms of their purpose and when they are fired. In this article we shall discuss each type of trigger. First of all, let's create a sample database with some tables and insert some sample data in those tables using the script below:

Create Database KDMNN GO

USE KDMNN GO

CREATE TABLE [dbo].[User_Details] ( [UserID] [int] NULL , [FName] [varchar] (50) NOT NULL , [MName] [varchar] (50) NULL , [LName] [varchar] (50) NOT NULL , [Email] [varchar] (50) ) ON [PRIMARY] GO NOT NULL

CREATE TABLE [dbo].[User_Master] ( [UserID] [int] IDENTITY (1, 1) NOT NULL , [UserName] [varchar] (50) NULL , [Password] [varchar] (50) NULL ) ON [PRIMARY] GO

ALTER TABLE [dbo].[User_Master] WITH NOCHECK ADD CONSTRAINT [PK_User_Master] PRIMARY KEY CLUSTERED ( [UserID] ) GO ON [PRIMARY]

ALTER TABLE [dbo].[User_Details] ADD CONSTRAINT [FK_User_Details_User_Master] FOREIGN KEY ( [UserID] ) REFERENCES [dbo].[User_Master] ( [UserID] ) GO

INSERT INTO USER_MASTER(USERNAME, PASSWORD) SELECT 'Navneeth','Navneeth' UNION SELECT 'Amol','Amol' UNION SELECT 'Anil','Anil' UNION SELECT 'Murthy','Murthy'

INSERT INTO USER_DETAILS(USERID, FNAME, LNAME, EMAIL) SELECT 1,'Navneeth','Naik','[email protected]' UNION SELECT 2,'Amol','Kulkarni','[email protected]' UNION SELECT 3,'Anil','Bahirat','[email protected]' UNION SELECT 4,'Murthy','Belluri','[email protected]'

AFTER Triggers The type of trigger that gets executed automatically after the statement that triggered it completes is called an AFTER trigger. An AFTER trigger is a trigger that gets executed automatically before the transaction is committed or rolled back. Using the below script, first we shall create a trigger on the table USER_MASTER for the INSERT event of the table.

USE KDMNN Go

CREATE TRIGGER trgInsert ON User_Master FOR INSERT AS Print ('AFTER Trigger [trgInsert] executed !!') GO – Trigger

BEGIN TRANSACTION DECLARE @ERR INT

INSERT INTO USER_MASTER(USERNAME, PASSWORD) VALUES('Damerla','Damerla')

SET @ERR = @@Error IF @ERR = 0 BEGIN ROLLBACK TRANSACTION PRINT 'ROLLBACK TRANSACTION' END ELSE BEGIN COMMIT TRANSACTION PRINT 'COMMIT TRANSACTION'

END

Output AFTER Trigger [trgInsert] (1 row(s) affected) ROLLBACK TRANSACTION – Trigger executed !!

By looking at the output, we can conclude that before the transaction is rolled back or committed, the AFTER trigger gets executed automatically. A table can have several AFTER triggers for each of the three triggering actions i.e., INSERT, DELETE and UPDATE. Using the below script, we shall create two triggers on the table User_Master for the INSERT triggering action.

CREATE TRIGGER trgInsert2 ON User_Master FOR INSERT AS BEGIN Print ('AFTER Trigger [trgInsert2] executed !!') END GO – Trigger

CREATE TRIGGER trgInsert3 ON User_Master

FOR INSERT AS BEGIN Print ('AFTER Trigger [trgInsert3] executed !!') END GO – Trigger

BEGIN TRANSACTION DECLARE @ERR INT

INSERT INTO USER_MASTER(USERNAME, PASSWORD) VALUES('Damerla','Damerla')

SET @ERR = @@Error IF @ERR = 0 BEGIN ROLLBACK TRANSACTION PRINT 'ROLLBACK TRANSACTION' END ELSE BEGIN COMMIT TRANSACTION PRINT 'COMMIT TRANSACTION'

END

Output AFTER Trigger [trgInsert] AFTER Trigger [trgInsert2] AFTER Trigger [trgInsert3] (1 row(s) affected) ROLLBACK TRANSACTION – Trigger executed !! – Trigger executed !! – Trigger executed !!

From the output we can conclude that when the user tries to insert data in the table USER_MASTER, three triggers are executed automatically. That is, you can write several AFTER triggers on one table for each of the three triggering actions. Similarly, we can write several AFTER triggers on DELETE and UPDATE triggering actions. Note: If a table has multiple AFTER triggers, then you can specify which trigger should be executed first and which trigger should be executed last using the stored procedure sp_settriggerorder. All the other triggers are in an undefined order which you cannot control. An AFTER trigger can be created only on tables, not on views. Using the script below, first we shall create a simple view [vwUserMaster] which will fetch the Username and Password from the table USER_MASTER.

Create View vwUserMaster as SELECT USERNAME, PASSWORD FROM USER_MASTER

GO

CREATE TRIGGER trgOnView ON vwUserMaster FOR INSERT AS BEGIN Print ('AFTER Trigger [trgOnView] vwUserMaster !!') END GO –

Output Server: Msg 208, Level 16, State 4, Procedure trgOnView, Line 2 Invalid object name 'vwUserMaster'.

From the Output we can conclude that we cannot create an AFTER trigger on views. Like stored procedures and views, triggers can also be encrypted. The trigger definition is then stored in an unreadable form. Once encrypted, the definition of the trigger cannot be decrypted and cannot be viewed by anyone, including the owner of the trigger or the system administrator.

CREATE TRIGGER trgEncrypted ON User_Master WITH ENCRYPTION

FOR INSERT AS BEGIN Print ('AFTER Trigger [trgEncrypted] Encrypted Trigger executed !!') END GO –

SELECT sysobjects.name AS [Trigger Name], SUBSTRING(syscomments.text, 0, 26) AS [Trigger Definition], OBJECT_NAME(sysobjects.parent_obj) AS [Table Name], syscomments.encrypted AS [IsEncrpted]

FROM sysobjects INNER JOIN syscomments ON sysobjects.id = syscomments.id WHERE (sysobjects.xtype = 'TR')

Output Trigger Name IsEncrpted Trigger Definition Table Name

---------------------------------------------------------------trgInsert User_Master trgInsert1 User_Master trgInsert2 User_Master trgEncrypted User_Master CREATE TRIGGER trgInsert 0 CREATE TRIGGER trgInsert1 0 CREATE TRIGGER trgInsert2 0 恩Ꭻ羑 1 녪样窈 뾴䕭遚

Since the trigger trgEncrypted is created with the option WITH ENCRYPTION, the trigger definition is hidden and there is no way that one can easily decrypt the trigger code. We all know that the DML statements change or modify data. Sometimes it becomes necessary for the triggers to have the access to the changes being caused by the DML statements. SQL Server 2000 provides four different ways to determine the affects of the DML statements. The INSERTED and DELETED tables, popularly known as MAGIC TABLES, and update () and columns_updated() functions can be used to determine the changes being caused by the DML statements. The below table depicts the contents of the INSERTED and DELETED tables for three different table Events EVENT Insert Delete Update INSERTED Contains the inserted rows Empty Contains the rows after update DELETED Empty Contains the rows to be deleted Contains the rows before update

Note that the Magic Table does not contain the information about the columns of the data-type text, ntext, or image. Attempting to access these columns will cause an error. The update() function is used to find whether a particular column has been updated or not. This function is generally used for data checks.

CREATE TRIGGER trgUddate ON User_Details FOR UPDATE AS If UPDATE(FName) BEGIN PRINT('AFTER Trigger [trgUddate] Executed - First Name has been updated') ROLLBACK TRANSACTION END else If UPDATE(LName) BEGIN PRINT('AFTER Trigger [trgUddate] Executed - Last Name has been updated') ROLLBACK TRANSACTION END else If UPDATE(MName) BEGIN PRINT('AFTER Trigger [trgUddate] Executed - MName Name has been updated')

ROLLBACK TRANSACTION END else If UPDATE(Email) BEGIN PRINT('AFTER Trigger [trgUddate] Executed - Email has been updated') ROLLBACK TRANSACTION END GO

UPDATE User_Details SET MName = 'Diwaker' WHERE UserID = 1

Output AFTER Trigger [trgUddate] - Executed - MName Name has been updated Depending upon the column updated, a message will be displayed. With this feature we can determine which column in the table has been updated, and then proceed with the business rules to be implemented further. Columns_Update() function returns a varbinary data type representation of the columns updated. This function return a hexadecimal values from which we can determine which columns in the table have been updated.

INSTEAD OF Triggers

A trigger which gets executed automatically in place of triggering actions i.e., INSERT, DELETE and UPDATE is called an INSTEAD OF trigger. INSTEAD OF triggers gets executed automatically before the Primary Key and the Foreign Key constraints are checked, whereas the traditional AFTER triggers gets executed automatically after these constraints are checked.

CREATE TRIGGER trgAfterInsert On User_Details FOR INSERT AS BEGIN Print ('AFTER Trigger [trgAfterInsert] – Trigger executed !!') END

INSERT INTO USER_DETAILS(USERID, FNAME,LNAME, MNAME, EMAIL) VALUES(100, 'FName','LName','MName','[email protected]')

Output Server: Msg 547, Level 16, State 1, Line 1 INSERT statement conflicted with COLUMN FOREIGN KEY constraint 'FK_User_Details_User_Master'. The conflict occurred in database 'KDMNN', table 'User_Master', column 'UserID'. The statement has been terminated.

UserID 100 does not exist in the User_Master table, so the Foreign Key constraint has been checked and an error message is displayed. What we can conclude is: AFTER triggers gets executed automatically after the PK and FK constraints. Create Trigger trgInsteadInsert On User_Details INSTEAD OF INSERT AS BEGIN Print ('INSTEAD OF Trigger [trgInsteadInsert] – Trigger executed !!') END

INSERT INTO USER_DETAILS(USERID, FNAME,LNAME, MNAME, EMAIL) VALUES(100, 'FName','LName','MName','[email protected]')

Output INSTEAD OF Trigger [trgInsteadInsert] – Trigger executed !! (1 row(s) affected) Even if the UserID 100 does not exists in the User_Master table, the trigger gets gets executed automatically.

DROP Trigger trgInsteadInsert Unlike AFTER triggers, INSTEAD OF triggers can be created on views.

Create trigger trgOnView on vwUserMaster INSTEAD OF INSERT AS begin Print ('INSTEAD OF Trigger [trgOnView] vwUserMaster !!!') End –

INSERT INTO VWUSERMASTER(USERNAME, PASSWORD) VALUES('Damerla','Venkat')

Output INSTEAD OF Trigger [trgOnView] (1 row(s) affected) So whenever a user tries to insert data into the view vwUserMaster, the INSTEAD OF trigger trgOnView will automatically be executed. In SQL SERVER 2000, views can be used to INSERT/DELETE and UPDATE the data in the multiple tables, and this can be achieved using INSTEAD OF triggers. – vwUserMaster !!

CREATE VIEW vwUser AS SELECT

[User_Master].[Username], [User_Master].[Password], [User_Details].[FName], [User_Details].[MName], [User_Details].[LName], [User_Details].[Email] FROM [User_Master], [User_Details] WHERE [User_Master].[UserID]=[User_Details].[UserID]

CREATE TRIGGER tgrInsertData ON vwUser INSTEAD OF INSERT AS BEGIN Declare @UserName varchar(50) Declare @Password varchar(50) Declare @FName varchar(50) Declare @MName varchar(50) Declare @LName varchar(50) Declare @Email varchar(50)

SELECT @UserName = UserName, @Password = Password, @FName = FName, @MName = MName, @LName = LName, @Email = Email FROM INSERTED

INSERT INTO User_Master(UserName, Password) VALUES(@UserName, @Password)

INSERT INTO User_Details(UserID,FName,LName,MName,Email) VALUES(@@Identity, @FName, @LName, @MName, @Email)

END

INSERT INTO vwUser (UserName, Password, FName, LName, MName,Email) VALUES ('Dhananjay','Dhananjay','Dhananjay','Nagesh',NULL, '[email protected]'

Output

AFTER Trigger [trgInsert] AFTER Trigger [trgInsert2] AFTER Trigger [trgInsert3]

– Trigger executed !! – Trigger executed !! – Trigger executed !! – Trigger

AFTER Trigger [trgEncrypted] Encrypted executed !! (1 row(s) affected)

AFTER Trigger [trgAfterInsert] – Trigger executed !! (1 row(s) affected) Then check the data in the following tables User_Master and User_Details. The new row gets inserted in both the tables. A view or table can have only one INSTEAD OF trigger for each INSERT, UPDATE and DELETE events. We have seen that you can create any number of AFTER triggers on the table for the same event, whereas you cannot do that with INSTEAD OF triggers.

CREATE TRIGGER trgInsteadOfTrigger1 ON vwUserMaster INSTEAD OF UPDATE AS BEGIN Print ('INSTEAD OF Trigger [trgInsteadOfTrigger1] – Trigger executed !!') END

CREATE TRIGGER trgInsteadOfTrigger2

ON vwUserMaster INSTEAD OF UPDATE AS BEGIN Print ('INSTEAD OF Trigger [trgInsteadOfTrigger2] – Trigger executed !!') END

Output Server: Msg 2111, Level 16, State 1, Procedure trgInsteadOfTrigger2, Line 6 Cannot CREATE trigger 'trgInsteadOfTrigger2' for view 'vwUserMaster' because an INSTEAD OF UPDATE trigger already exists. From the output, it is clear that you cannot create two INSTEAD OF triggers on the view/ table for the same event. Note: An important point to be noted is that INSTEAD OF DELETE and INSTEAD OF UPDATE triggers cannot be defined on tables that have corresponding ON DELETE or ON UPDATE cascading referential integrity defined. At last, how would you know what are the triggers associated with the table and what type of the trigger it is? Whether AFTER or INSTEAD OF? The solution for this question is sp_helptrigger. This stored procedure gives all the information about the triggers such as Event on which the trigger gets executed, the type of the trigger, etc.

Sp_helptrigger User_Master

Output trigger_name trigger_owner isupdate isinsert isafter isinsteadof trgInsert 0 dbo 1 dbo 0 dbo 0 dbo 0 0 0 0 0 1 0 0 0 0 isdelete

trgInsert2 1 1 trgInsert3 1 1 trgEncrypted 1 1

Triggers can be used in the following scenarios, such as if the database is de-normalized and requires an automated way to update redundant data contained in multiple tables, or if customized messages and complex error handling are required, or if a value in one table must be validated against a non-identical value in another table. Triggers are a powerful tool that can be used to enforce the business rules automatically when the data is modified. Triggers can also be used to maintain the data integrity. But they are not to maintain data integrity. Triggers should be used to maintain the data integrity only if you are unable to enforce the data integrity using CONSTRAINTS, RULES and DEFAULTS. Triggers cannot be created on the temporary tables.

Navneeth Diwaker Naik ([email protected]) is an employee of Satyam Computers Services Limited, Hyderabad, Andhra Pradesh. [INDIA]. Published with the explicit written permission of the author. Copyright 2004.

Sponsor Documents

Or use your account on DocShare.tips

Hide

Forgot your password?

Or register your new account on DocShare.tips

Hide

Lost your password? Please enter your email address. You will receive a link to create a new password.

Back to log-in

Close