轉:自動記錄資料庫預存程序的更新和改變,併產生日誌

來源:互聯網
上載者:User

轉:http://www.cnblogs.com/Carlwave/archive/2007/11/19/964216.html 自動記錄資料庫預存程序的更新和改變,併產生日誌

 

一、        簡介

使用環境:SQL Server

    在項目開發過程中,專案管理者通常都很希望對項目的開發進展有一個日誌的記錄。代碼的記錄和管理可以通過TFS或者VSS等工具去管理。但是資料庫卻沒有記錄開發日誌這一功能。這在實際開發中很不方便,特別是大量的預存程序改動。

       那麼針對這一個需求,在資料庫中定時執行一個Job,讓其自動記錄預存程序的改動,以完成對資料庫預存程序改動的一個記錄。

二、        實際效果

Sp_id

change_date

action_type

sp_name

755585830

2007-11-13

Added

Sp_a

451584747

2007-11-13

Update

Sp_b

2119014630

2007-11-13

Update

Sp_c

2119014630

2007-11-13

Update

Sp_d

771585887

2007-11-13

Deleted

Sp_e

       

三、        實現原理

由於資料庫中所有的預存程序代碼都記錄在系統資料表Sys_comments中,所以我們可以通過比較不同時間點代碼的方式去實現記錄一定時間範圍內的預存程序變化。

比如:在今天早上01:00我們把所有預存程序代碼從系統資料表中取出,並記錄。然後到明天早上再重複這一過程,將兩次取出的不同結果進行比較,取出有變化的預存程序並記錄,認為這些預存程序在這一時間範圍記憶體在更新。

四、        實現代碼

其實原理很簡單,就是一個迴圈比較的方式,所以也不需要大費周章的去介紹了,那麼下面就把實現相關的代碼和流程貼出來。

1建立資料表

 

在資料庫建立三張表,sps_old, sps_new, sps_log。

Sps_old:記錄前一次系統中所有預存程序代碼,以備比較

Sps_new:當前所有預存程序的代碼,與sps_log_old中的資料比較

Sps_log:記錄在兩個時間點範圍內變化的預存程序名字和變化時間

表結構:

/****** Sps_log ******/

CREATE TABLE [dbo].[sps_log](

       [sp_id] [int] NULL,

       [change_date] [datetime] NULL,

       [action_type] [char](10) COLLATE SQL_Latin1_General_CP1_CI_AS NULL,

       [sp_name] [varchar](150) COLLATE SQL_Latin1_General_CP1_CI_AS NULL

) ON [PRIMARY]

/****** Sps_new ******/----------------------------------------------------------------

CREATE TABLE [dbo].[sps_new](

       [sp_id] [int] NULL,

       [colid] [smallint] NULL,

       [sp_name] [varchar](150) COLLATE SQL_Latin1_General_CP1_CI_AS NULL,

       [sp_content] [varchar](4000) COLLATE SQL_Latin1_General_CP1_CI_AS NULL,

       [record_date] [datetime] NULL

) ON [PRIMARY]

/******Sps_old******/-----------------------------------------------------------------------------------

CREATE TABLE [dbo].[sps_old](

       [sp_id] [int] NULL,

       [colid] [smallint] NULL,

       [sp_name] [varchar](150) COLLATE SQL_Latin1_General_CP1_CI_AS NULL,

       [sp_content] [varchar](4000) COLLATE SQL_Latin1_General_CP1_CI_AS NULL,

       [record_date] [datetime] NULL

) ON [PRIMARY]

----------------------------------------------------------------------------------------------------------------

2建立進行比較用的預存程序,並記錄結果集

 

/*------------------------------------------------------------------------------------------------------

 -- Function   :      sps_log_add

 -- Description       :      record all sps change log

 --1 get all new sps (find sps which in new table not in old table)

 --2 get all deleted sps (find sps which in old table not in new table)

 --3 get all updated sps (find sps which in old talbe are not same in new table)

 -- any change will record into sps_log table

------------------------------------------------------------------------------------------------------*/

CREATE procedure [dbo].[sps_log_add]

as

-- clear out sps_new

truncate table sps_new

-- fill into sps_new

insert into       sps_new

(sp_id,colid,sp_name,sp_content,record_date)

select

       a.id,

       a.colid,

       b.name,

       a.[text],

       getdate()

from

       syscomments a

left join

       sysobjects b

 on a.id = b.id

where b.type='P' and b.name not like 'dt_%'

-- Find new sp

insert into

       sps_log

select distinct

       sp_id,

       getdate(),

       'Added',

       sp_name

from

       sps_new

where

       sp_id not in (select distinct sp_id from sps_old)

-- Find deleted sp

insert into

       sps_log

select distinct

       sp_id,

       getdate(),

       'Removed',

       sp_name

from

       sps_old

where

       sp_id not in (select distinct sp_id from sps_new)

-- compare existing sp

DECLARE @ProcID int

declare @count_new int

declare @count_old int

declare @text_new varchar(4000)

declare @text_old varchar(4000)

declare @name varchar(150)

declare @i int

DECLARE SearchProc CURSOR FOR

select distinct

       sp_id

from

       sps_new

where

       sp_id in (select distinct sp_id from sps_old)

order by

       sp_id

open SearchProc

FETCH NEXT FROM SearchProc

INTO @ProcID

WHILE @@FETCH_STATUS >=0

BEGIN

       -- colid quantity

       select @count_new=count(colid) from sps_new where sp_id = @ProcID

      select @count_old=count(colid) from sps_old where sp_id = @ProcID

-- if count of colid is unequal, sp was updated.

       if @count_new <> @count_old

              begin

                     -- Record change

                     insert into       sps_log(sp_id,change_date,action_type) values(@ProcID,getdate(),'Update')

              end

       else -- @count_new = @count_old, if count of colid is equal

              begin

                     set @i=1 -- Reset Counter

                     while @i<=@count_new -- colid

                     begin

                                   -- sp content

select @text_new = sp_content from sps_new

where sp_id = @ProcID and colid = @i

                                   select @text_old = sp_content from sps_old

where sp_id = @ProcID and colid = @i

-- if content is different, sp was updated.

                                   if @text_new <> @text_old        

                                          begin      

                                                 -- Record change

                                                 select @name = [name] from sysobjects where id=@ProcID

                                                 insert into sps_log(sp_id,change_date,action_type,sp_name)

values(@ProcID,getdate(),'Update',@name)

                                          end

                                   set @i= @i+1 -- Counter + 1

                     end

              end

       FETCH NEXT FROM SearchProc

    INTO @ProcID

END

CLOSE SearchProc

DEALLOCATE SearchProc

-- clear out sps_new

truncate table sps_old

-- fill into sps_old with sps_new

insert into sps_old select * from sps_new

----------------------------------------------------------------------------------------------------------------------

3建立一個預存程序從sps_log中擷取指定時間內的資料

 

/*

 -- Function   : sps_log_get

 -- Description       : Show sps change in a period of time

*/

CREATE PROCEDURE [dbo].[sps_log_get]

@from_date datetime,

@to_date datetime

as

       select

              sp_name,

              action_type,

              CONVERT(varchar(10),change_date,102) as change_date

       from

              sps_log

       where

              change_date between @from_date and @to_date

       group by

              sp_name,action_type,CONVERT(varchar(10),change_date,102)

       order by

              CONVERT(varchar(10),change_date,102) asc

五、        實際應用和配置

在資料庫中建立一個Job,代碼為exec sps_log_add,一般運行可以設定為每天的零晨,一天一次比較合理,這樣便能把每天做的改動記錄下來。

六、        查看日誌

直接運行預存程序exec sps_log_get ‘2007-11-01’,’2007-11-30’。便能查看所有在這一段時間內的預存程序變化。
 

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.