Showing posts with label trigger. Show all posts
Showing posts with label trigger. Show all posts

Tuesday, March 20, 2012

Big problem with triggers

I have little problem and I dont have any idea how to make my trigger.

I have table MyTable where I have many column with almost same name and same
type (Grp1,Grp2,Grp3,Grp4...Grp50 char(1)).
I`d like to make some trigger on UPDATE this table. I must to check which
column was changed.

For example to check if Grp1 was changed I can try this:

ALTER TRIGGER MyTrigger
ON MyTable
AFTER UPDATE
AS
DECLARE @.OldValue char(1)
DECLARE @.NewValue char(1)
BEGIN
SET @.OldValue = (SELECT Grp1 FROM DELETED)
SET @.NewValue = (SELECT Grp1 FROM INSERTED)

IF (@.OldValue <> @.NewValue)
BEGIN
...
...
...
END
END

Of course I can do this step by step, for all columns, but it`s not good
option.
I tried to make this trigger more dynamicaly, but this not worked (Server:
Msg 208, Level 16, State 1, Line 1
Invalid object name 'DELETED'.)

ALTER TRIGGER MyTrigger
ON MyTable
AFTER UPDATE
AS
DECLARE @.OldValue char(1)
DECLARE @.NewValue char(1)
DECLARE @.MyQry VarChar(1000)
DECLARE @.ActGrp VarChar(2)
BEGIN
@.ActGrp = '1'
SET @.MyQry ='
SET @.OldValue = (SELECT Grp'+@.ActGrp+' FROM DELETED)
SET @.NewValue = (SELECT Grp'+@.ActGrp+' FROM INSERTED)

IF (@.OldValue <> @.NewValue)
BEGIN
...
...
...
END
'
END

:(

Can anybody help me? How can I easy check all Grp1...Grp50 to know where
colums was changed?Hi

Triggers are activated on a statement and not per row changed, therefore the
use of variables in your trigger to store old and new values will not
produce predictable results.

In general it is better to keep your triggers as short as possible to avoid
prolonging your transactions. If you are trying to produce and audit trail
then I would keep the comparisons external to the trigger and follow the
example of auditing in
http://msdn.microsoft.com/library/d...create_4hk5.asp

John

"BUSHII" <piotrl@.robcom.com.pl> wrote in message
news:cbbcqa$g62$1@.atlantis.news.tpi.pl...
> I have little problem and I dont have any idea how to make my trigger.
> I have table MyTable where I have many column with almost same name and
same
> type (Grp1,Grp2,Grp3,Grp4...Grp50 char(1)).
> I`d like to make some trigger on UPDATE this table. I must to check which
> column was changed.
> For example to check if Grp1 was changed I can try this:
> ALTER TRIGGER MyTrigger
> ON MyTable
> AFTER UPDATE
> AS
> DECLARE @.OldValue char(1)
> DECLARE @.NewValue char(1)
> BEGIN
> SET @.OldValue = (SELECT Grp1 FROM DELETED)
> SET @.NewValue = (SELECT Grp1 FROM INSERTED)
>
> IF (@.OldValue <> @.NewValue)
> BEGIN
> ...
> ...
> ...
> END
> END
>
> Of course I can do this step by step, for all columns, but it`s not good
> option.
> I tried to make this trigger more dynamicaly, but this not worked (Server:
> Msg 208, Level 16, State 1, Line 1
> Invalid object name 'DELETED'.)
> ALTER TRIGGER MyTrigger
> ON MyTable
> AFTER UPDATE
> AS
> DECLARE @.OldValue char(1)
> DECLARE @.NewValue char(1)
> DECLARE @.MyQry VarChar(1000)
> DECLARE @.ActGrp VarChar(2)
> BEGIN
> @.ActGrp = '1'
> SET @.MyQry ='
> SET @.OldValue = (SELECT Grp'+@.ActGrp+' FROM DELETED)
> SET @.NewValue = (SELECT Grp'+@.ActGrp+' FROM INSERTED)
>
> IF (@.OldValue <> @.NewValue)
> BEGIN
> ...
> ...
> ...
> END
> '
> END
> :(
> Can anybody help me? How can I easy check all Grp1...Grp50 to know where
> colums was changed?sql

Saturday, February 25, 2012

Better proformance using join or sub-query?

All,
I am using a trigger to keep a "transaction date" column up-to-date with
the datetime the record was lasted inserted/updated. My question is which
SQL statement would provide better performance:
Update tablename set transdate = getdate() where primarykey in (select
primarykey from inserted)
or
update tablename set transdate = getdate
from tablename, inserted
where tablename.primarykey = inserted.primarykey
Thanks,
James K.I recommend
update tablename set transdate = getdate
from tablename, inserted
where tablename.primarykey = inserted.primarykey
Roji. P. Thomas
Net Asset Management
https://www.netassetmanagement.com
"-=JLK=-" <jknowlto-nospam@.dtic.mil> wrote in message
news:eowog0nGFHA.2740@.TK2MSFTNGP12.phx.gbl...
> All,
> I am using a trigger to keep a "transaction date" column up-to-date
> with the datetime the record was lasted inserted/updated. My question is
> which SQL statement would provide better performance:
> Update tablename set transdate = getdate() where primarykey in (select
> primarykey from inserted)
> or
> update tablename set transdate = getdate
> from tablename, inserted
> where tablename.primarykey = inserted.primarykey
> Thanks,
> James K.
>|||I think the second one
Madhivanan|||JKL
I'd go with the first one. The probelm with the second one is that under
some conditions you can get a different ( wrong) output
David Portas has written some script/test about this
CREATE TABLE Countries
(countryname VARCHAR(20) NOT NULL PRIMARY KEY,
capitalcity VARCHAR(20));
CREATE TABLE Cities
(cityname VARCHAR(20) NOT NULL,
countryname VARCHAR(20) NOT NULL
REFERENCES Countries (countryname),
CONSTRAINT PK_Cities
PRIMARY KEY (cityname, countryname));
INSERT INTO Countries (countryname, capitalcity) VALUES ('USA', NULL);
INSERT INTO Countries (countryname, capitalcity) VALUES ('UK', NULL);
INSERT INTO Cities VALUES ('Washington', 'USA');
INSERT INTO Cities VALUES ('London', 'UK');
INSERT INTO Cities VALUES ('Manchester', 'UK');
The MS-syntax makes it all too easy for the developer to slip-up by
writing ambiguous UPDATE...FROM statements where the JOIN criteria is
not unique on the right side of the join.
Try these two identical UPDATE statements with a small change to the
primary key in between.
UPDATE Countries
SET capitalcity = cityname
FROM Countries JOIN Cities /* evil UPDATE... FROM syntax */
ON Countries.countryname = Cities.countryname;
SELECT * FROM Countries;
ALTER TABLE Cities DROP CONSTRAINT PK_Cities;
ALTER TABLE Cities ADD CONSTRAINT PK_Cities PRIMARY KEY (countryname,
cityname);
UPDATE Countries
SET capitalcity = cityname
FROM Countries JOIN Cities /* don't do this! */
ON Countries.countryname = Cities.countryname;
SELECT * FROM Countries;
You get this from the first SELECT statement:
countryname capitalcity
-- --
UK London
USA Washington
and this from the second:
countryname capitalcity
-- --
UK Manchester
USA Washington
"-=JLK=-" <jknowlto-nospam@.dtic.mil> wrote in message
news:eowog0nGFHA.2740@.TK2MSFTNGP12.phx.gbl...
> All,
> I am using a trigger to keep a "transaction date" column up-to-date
with
> the datetime the record was lasted inserted/updated. My question is which
> SQL statement would provide better performance:
> Update tablename set transdate = getdate() where primarykey in (select
> primarykey from inserted)
> or
> update tablename set transdate = getdate
> from tablename, inserted
> where tablename.primarykey = inserted.primarykey
> Thanks,
> James K.
>|||Uri,
The original poster want to update the column the getDate().
I think, As long as you dont depend on the joined table for the
value to update, you are safe.
Roji. P. Thomas
Net Asset Management
https://www.netassetmanagement.com
"Uri Dimant" <urid@.iscar.co.il> wrote in message
news:Of9GdAoGFHA.2420@.TK2MSFTNGP14.phx.gbl...
> JKL
> I'd go with the first one. The probelm with the second one is that under
> some conditions you can get a different ( wrong) output
> David Portas has written some script/test about this
> CREATE TABLE Countries
> (countryname VARCHAR(20) NOT NULL PRIMARY KEY,
> capitalcity VARCHAR(20));
> CREATE TABLE Cities
> (cityname VARCHAR(20) NOT NULL,
> countryname VARCHAR(20) NOT NULL
> REFERENCES Countries (countryname),
> CONSTRAINT PK_Cities
> PRIMARY KEY (cityname, countryname));
> INSERT INTO Countries (countryname, capitalcity) VALUES ('USA', NULL);
> INSERT INTO Countries (countryname, capitalcity) VALUES ('UK', NULL);
> INSERT INTO Cities VALUES ('Washington', 'USA');
> INSERT INTO Cities VALUES ('London', 'UK');
> INSERT INTO Cities VALUES ('Manchester', 'UK');
> The MS-syntax makes it all too easy for the developer to slip-up by
> writing ambiguous UPDATE...FROM statements where the JOIN criteria is
> not unique on the right side of the join.
> Try these two identical UPDATE statements with a small change to the
> primary key in between.
> UPDATE Countries
> SET capitalcity = cityname
> FROM Countries JOIN Cities /* evil UPDATE... FROM syntax */
> ON Countries.countryname = Cities.countryname;
> SELECT * FROM Countries;
> ALTER TABLE Cities DROP CONSTRAINT PK_Cities;
> ALTER TABLE Cities ADD CONSTRAINT PK_Cities PRIMARY KEY (countryname,
> cityname);
> UPDATE Countries
> SET capitalcity = cityname
> FROM Countries JOIN Cities /* don't do this! */
> ON Countries.countryname = Cities.countryname;
> SELECT * FROM Countries;
> You get this from the first SELECT statement:
> countryname capitalcity
> -- --
> UK London
> USA Washington
> and this from the second:
> countryname capitalcity
> -- --
> UK Manchester
> USA Washington
>
>
> "-=JLK=-" <jknowlto-nospam@.dtic.mil> wrote in message
> news:eowog0nGFHA.2740@.TK2MSFTNGP12.phx.gbl...
> with
>|||On Fri, 25 Feb 2005 13:00:35 +0530, avnrao wrote:

>Umi, can you please explain the rationale behind it.
Hi Av.,
Mind if I do instead of Uri?
The ANSI syntax and the proprietary UPDATE FROM syntax behave only the
same if for each row in the updated table that satisfies the WHERE
clause, exactly one row in the other table matches the join criteria.
If it's possible that no rows are matched, the ANSI syntax will set the
column to NULL, unless excluded from the update in the WHERE clause. The
UPDATE FROM syntax will not update this row: since it doesn't satisfy
the join criteria, it won't be updated even if it does meet the
requirements of the WHERE clause.
(Note: this difference can be circumvened by using outer join instead of
inner join to make the joined update behave exactly as the ANSI version)
The biggest difference is when one row to be updated can be matched
against more than one row in the source table. This is what's happening
in David's script, as posted by Uri.
In the ANSI version, if the subquery in the SET clause returns more than
one row, you'll get an error message. That ensures that you will revisit
the query and change it so that it will always return exactly one row -
the row that you want it to return.
The UPDATE FROM syntax won't throw an error if a row in the table to be
updated matches against multiple rows from the source. Instead, SQL
Server will just pick one of these rows and use that one to determine
the new values in your table. Or rather, in case you want the full
details, it will update the same row over and over again with each
matching row - and since the result of all but the last change is
overwritten, the net effect is that only the results from the row
processed last will stick.
The above explains why the result of an UPDATE FROM where one row to be
updated matches more than one row from the source is completely
unpredictable: the result will be from the last row processed, but there
is no way to predict the order of evaluation SQL Server will choose for
your query. David's example shows how an index can change the order, but
there are other possibilities: parallellism, available memory, workload,
and the possibility to "piggy-back" another query are just some examples
of how the order of evaluation (and hence the result of the update) may
change between successive execution, even if no schema or data has been
changed!
I hope this helps.
Best, Hugo
--
(Remove _NO_ and _SPAM_ to get my e-mail address)

Tuesday, February 14, 2012

Best way to insert a DateModified in updates

how do i update the date modified Field in my DB. i was thinking of update trigger? i am using ASP 2 with DetailsView for Editing(Updates in SQL term). i can make a Update SP but think that might not be needed

If you use the SP you can define the date now to a variable. @.datenow = GetDate()|||

In the Update procedure, you can just "SET dateModified=GETDATE()".

In my view, Triggers are a little bad in the respect that they are hidden. If you look at a simple SQL statement, you really can't "trace" the code execution completely if your DB has a whole pile of Triggers firing all the time, which means, things might be happening that the SQL statement writer isn't aware of, and that can cause problems.

Of course, their not overall bad, but my personal preference is to use an SP, unless a Trigger is specifically required or for some odd reason more effecient.

Best way to inform .NET app of change in DB content

Previously had a 'prototype' (.NET 1.0, SQL Server 2000, CCW to .NET) whereby an update trigger called out to our .NET app. Obvioulsy now SQL Server 2005 is nearly upon us I'd like to explore a better mechanism in order to consider the next phase of deployment (.NET 2, SQL Server 2005).

I have a number of servers that 'cache' data from a table in SQL Server. At some later time one of the servers may update a set of the data. When this occurs I'd like to alert the other servers that the data has changed so they can refresh/drop it from the local cache/ The data can cover a number of rows from one of the DB tables (depends on how the cache is configured). The table is simply a persistent object store.

With .NET being an integral part of SQL2005, does anyone have any guidance on how to achieve this efficiently. I'd like to think there would be a .NET event mechanism built in, but I've not seen anything like this!

Thanks in advance!You can use SQL Server Notification Services: http://www.devx.com/dbzone/Article/28522|||

You can use the SqlNotification class in .NET 2.0 - this can be used in both SQL Server 2000 and SQL Server 2005

|||

Thank you both for your answers! I had look at SQL Notification Services but wondered if this is too 'heavyweight' for my needs. I'll take a close look at the .NET 2 feature.

|||You can test it out by visiting http://msdn.demoservers.com and look for the SQL Server 2005 and ADO.NET hands-on lab as this covers using the SqlNotification and SqlDependency objects in .NET 2.0|||Look up topics on Query Notifications and SqlDependency in the 2005 MSDN Library. Note that these are not the same as Notification Services. They're much lighter-weight, and focused on firing application events rather than sending external notifications. -- Adam MachanicSQL Server MVPhttp://www.datamanipulation.net-- <adamhearn@.discussions..microsoft.com> wrote in message news:68627a2a-01ab-42f4-b950-54dd2e1a3041@.discussions.microsoft.com...Previously had a 'prototype' (.NET 1.0, SQL Server 2000, CCW to .NET) whereby an update trigger called out to our .NET app. Obvioulsy now SQL Server 2005 is nearly upon us I'd like to explore a better mechanism in order to consider the next phase of deployment (.NET 2, SQL Server 2005).I have a number of servers that 'cache' data from a table in SQL Server. At some later time one of the servers may update a set of the data. When this occurs I'd like to alert the other servers that the data has changed so they can refresh/drop it from the local cache/ The data can cover a number of rows from one of the DB tables (depends on how the cache is configured). The table is simply a persistent object store.With .NET being an integral part of SQL2005, does anyone have any guidance on how to achieve this efficiently. I'd like to think there would be a .NET event mechanism built in, but I've not seen anything like this!Thanks in advance!

Best way to inform .NET app of change in DB content

Previously had a 'prototype' (.NET 1.0, SQL Server 2000, CCW to .NET) whereby an update trigger called out to our .NET app. Obvioulsy now SQL Server 2005 is nearly upon us I'd like to explore a better mechanism in order to consider the next phase of deployment (.NET 2, SQL Server 2005).

I have a number of servers that 'cache' data from a table in SQL Server. At some later time one of the servers may update a set of the data. When this occurs I'd like to alert the other servers that the data has changed so they can refresh/drop it from the local cache/ The data can cover a number of rows from one of the DB tables (depends on how the cache is configured). The table is simply a persistent object store.

With .NET being an integral part of SQL2005, does anyone have any guidance on how to achieve this efficiently. I'd like to think there would be a .NET event mechanism built in, but I've not seen anything like this!

Thanks in advance!You can use SQL Server Notification Services: http://www.devx.com/dbzone/Article/28522|||

You can use the SqlNotification class in .NET 2.0 - this can be used in both SQL Server 2000 and SQL Server 2005

|||

Thank you both for your answers! I had look at SQL Notification Services but wondered if this is too 'heavyweight' for my needs. I'll take a close look at the .NET 2 feature.

|||You can test it out by visiting http://msdn.demoservers.com and look for the SQL Server 2005 and ADO.NET hands-on lab as this covers using the SqlNotification and SqlDependency objects in .NET 2.0|||Look up topics on Query Notifications and SqlDependency in the 2005 MSDN Library. Note that these are not the same as Notification Services. They're much lighter-weight, and focused on firing application events rather than sending external notifications. -- Adam MachanicSQL Server MVPhttp://www.datamanipulation.net-- <adamhearn@.discussions..microsoft.com> wrote in message news:68627a2a-01ab-42f4-b950-54dd2e1a3041@.discussions.microsoft.com...Previously had a 'prototype' (.NET 1.0, SQL Server 2000, CCW to .NET) whereby an update trigger called out to our .NET app. Obvioulsy now SQL Server 2005 is nearly upon us I'd like to explore a better mechanism in order to consider the next phase of deployment (.NET 2, SQL Server 2005).I have a number of servers that 'cache' data from a table in SQL Server. At some later time one of the servers may update a set of the data. When this occurs I'd like to alert the other servers that the data has changed so they can refresh/drop it from the local cache/ The data can cover a number of rows from one of the DB tables (depends on how the cache is configured). The table is simply a persistent object store.With .NET being an integral part of SQL2005, does anyone have any guidance on how to achieve this efficiently. I'd like to think there would be a .NET event mechanism built in, but I've not seen anything like this!Thanks in advance!