As far as we are aware, there is only one way in SQL Server to detect if any change has been made to a table and that is to use the Dynamic Management View sys.dm_db_index_usage_stats (http://msdn.microsoft.com/en-us/library/ms188755.aspx).
For my purposes, I created a function to make accessing the information easier.
create function [dbo].[_efnLastTableUpdateTime](@TableName varchar(255))
/* Function to return the last datetime that a table was modified.
Note that because this is from a dynamic management view, it is only
since the server was started, i.e. will return null if no change since
the server was started.
SQL2005 or later.
*/
returns datetime
as
begin
declare @Result datetime
set @Result = (
select top 1 [last_user_update]
from sys.dm_db_index_usage_stats
where object_id=object_id(@TableName)
order by [last_user_update] desc
)
return @Result
end
GO
Then I built into my descendant of TADOQuery a function to access it and a property to switch the functionality on or off. I can then call this on demand which results in a very efficient response.
function TMyADOQuery.HasBeenUpdatedSinceOpen(const ACloseIfHasBeen: boolean = false): boolean;
const
sSelectTableUpdateTime = 'select [dbo]._efnLastTableUpdateTime(''%s'')';
var
NewUpdateTime: TDateTime;
begin
Result := false;
if(_TrackUpdated) and (Active) and (_TableName > '') then begin
NewUpdateTime := TrackUpdateQuery.SelectScalarDate(Format(sSelectTableUpdateTime, [_TableName]), 0);
Result := (FLastUpdateTime <> NewUpdateTime);
FLastUpdateTime := NewUpdateTime;
end;
if(Result) and (ACloseIfHasBeen) then
Close;
end;
TrackUpdateQuery
is another instance of TADOQuery created internally and SelectScalarDate
is and extension on my TADOQuery class.
Note that the user must have the VIEW SERVER STATE permission granted to be able to access the management view.