2016-08-22 4 views
0

私は同じ問題をここに関連しているBuilding a snapshot table from audit records。コードの一部は私の問題を部分的に解決しますmsでの監査証跡からのスナップショットテーブルsql

Select * into #temp from (
SELECT Audit.PrimaryKeyValue as ID,Audit.FieldName,OldValue FROM audit left  JOIN (
SELECT Audit.FieldName,Audit.PrimaryKeyValue, MAX(UpdateDate) AS dateadded FROM audit GROUP BY FieldName,PrimaryKeyValue 
) maxtimestamp ON audit.FieldName = maxtimestamp.FieldName AND audit.updateDate = maxtimestamp.dateadded 
where PrimaryKeyField='Id' and cast(UpdateDate as date)<[email protected]) src 
pivot(
max(src.OldValue) 
for FieldName in (Centrala,ID_Grup,Pi, Ci, Pmt, Pneta, Rpp, Pd, UD, Suport1, Suport2, Suport3, Stare, 
Motiv, Observatii, Comentarii, Un, Data_ADD, Modified_Date, Scada, Fuel_base) 
) piv; 

特定の瞬間に監査証跡表からレコードに基づいてテーブルのスナップショットを取得する方法。 テンポラリの実際のテーブルをコピーして、監査の内容に基づいて値を更新することは、解決策ですか? 私の英語は貧しいです! ありがとうございます!

プライマリ・テーブルの構造は以下の通りである:

[ID] [int] IDENTITY(1,1) NOT NULL, 
[Centrala] [int] NOT NULL, 
[ID_grup] [nvarchar](50) NULL, 
[Pi] [float] NULL, 
[Ci] [float] NULL, 
[Pmt] [float] NULL, 
[Pneta] [float] NULL, 
[Rpp] [float] NULL, 
[Pd] [float] NULL, 
[UD] [nvarchar](50) NULL, 
[Suport1] [nvarchar](255) NULL, 
[Suport2] [nvarchar](255) NULL, 
[Suport3] [nvarchar](255) NULL, 
[Stare] [int] NULL, 
[Motiv] [nvarchar](max) NULL, 
[Observatii] [nvarchar](max) NULL, 
[Comentarii] [nvarchar](max) NULL, 
[Un] [varchar](10) NULL, 
[Data_ADD] [date] NULL, 
[Modified_Date] [date] NULL, 
[Scada] [nvarchar](100) NULL, 
[Fuel_base] [nvarchar](255) NULL, 

および監査テーブルの構造は以下の通りである:

[AuditID] [int] IDENTITY(1,1) NOT NULL, 
[Type] [char](1) NULL, 
[TableName] [varchar](128) NULL, 
[PrimaryKeyField] [varchar](1000) NULL, 
[PrimaryKeyValue] [varchar](1000) NULL, 
[FieldName] [varchar](128) NULL, 
[OldValue] [varchar](1000) NULL, 
[NewValue] [varchar](1000) NULL, 
[UpdateDate] [datetime] NULL, 
[UserName] [varchar](128) NULL 

ユーザーは全体の行および監査テーブルキャッチを削除包括プライマリ・テーブル内の値を変更することができすべての変更。特定の日付に元のテーブルの内容を含むレポートを作成する必要があります。私は監査テーブルの列名は表現力があると思います。タイプには、更新、挿入、削除の3つの値 'U'、 'I'、 'D'があります。別の問題は、監査テーブルにプライマリテーブルの行の変更が含まれていて、スナップショットの日付がAuditのupdateDateよりも低い場合、OldValue else NewValueを選択する必要があるということです。合ってます? @ Nick.McDermaidありがとうございました!

+0

テーブルの最新のビューを常に見たいのですか、またはいつでもテーブルを見る必要がありますか?元のレコードに順番に監査行を適用するだけで済みます。特別な別のテーブルでスナップショットを生成しますか? DDLを投稿してください –

答えて

0

私は非常に醜い解決策を見つけましたが、私は誰かがよりよい解決策を持っているか、このコードを向上させることができれば、それは私を助けてください今

Declare @data date  
select @data='2016.02.2' 
select * into #Grup1 from Grupuri 
--Apply to actual values most oldest values from Audit 
select * into #temp from ( 
SELECT 
Audit.PrimaryKeyValue as ID,Audit.FieldName,OldValue 
FROM audit inner JOIN (
SELECT Audit.FieldName,Audit.PrimaryKeyValue, min(UpdateDate) AS dateadded    FROM audit GROUP BY FieldName,PrimaryKeyValue 
) maxtimestamp ON audit.FieldName = maxtimestamp.FieldName AND audit.updateDate = maxtimestamp.dateadded 
where PrimaryKeyField='Id' and TableName='Grupuri') src 
pivot(
max(src.OldValue) 
for FieldName in (Centrala,ID_Grup,Pi, Ci, Pmt, Pneta, Rpp, Pd, UD, Suport1, Suport2, Suport3, Stare, 
Motiv, Observatii, Comentarii, Un, Data_ADD, Modified_Date, Scada, Fuel_base) 
) piv; 

UPDATE #Grup1 SET Pi= (case When b.Pi is not null then b.Pi else #Grup1.Pi end), 
       Ci=case When b.Ci is not null then b.Ci else #Grup1.Ci end, 
       Pmt=case When b.Pmt is not null then b.Pmt else #Grup1.Pmt end, 
       Pneta=case When b.Pneta is not null then b.Pneta else #Grup1.Pneta end, 
       Rpp=case When b.Rpp is not null then b.Rpp else #Grup1.Rpp end, 
       Pd=case When b.Pd is not null then b.Pd else #Grup1.Pd end, 
       UD=case When b.Ud is not null then b.Ud else NULL end, 
       Suport1=case When b.Suport1 is not null then b.Suport1 else #Grup1.Suport1 end, 
       Suport2=case When b.Suport2 is not null then b.Suport2 else #Grup1.Suport2 end, 
       Suport3=case When b.Suport3 is not null then b.Suport3 else #Grup1.Suport3 end, 
       Stare=case When b.Stare is not null then b.Stare else #Grup1.Stare end, 
       Motiv=case When b.Motiv is not null then b.Motiv else #Grup1.Motiv end, 
       Observatii=case When b.Observatii is not null then b.Observatii else #Grup1.Observatii end, 
       Comentarii=case When b.Comentarii is not null then b.Comentarii else #Grup1.Comentarii end, 
       Un=case When b.Un is not null then b.Un else #Grup1.Un end, 
       Scada= case When b.Scada is not null then b.Scada else #Grup1.Scada end, 
       Fuel_base=case When b.Fuel_base is not null then b.Fuel_base else #Grup1.Fuel_base end 
FROM #temp b WHERE #Grup1.id = b.id 
--Apply new values updated up to @data 
select * into #temp1 from ( 
SELECT 
Audit.PrimaryKeyValue as ID,Audit.FieldName,NewValue 
FROM audit left JOIN (
SELECT Audit.FieldName,Audit.PrimaryKeyValue, MAX(UpdateDate) AS dateadded FROM audit GROUP BY FieldName,PrimaryKeyValue 
) maxtimestamp ON audit.FieldName = maxtimestamp.FieldName AND audit.updateDate = maxtimestamp.dateadded 
    where PrimaryKeyField='Id' and TableName='Grupuri' 
    and cast(UpdateDate as date) <[email protected]) src 
    pivot(
    max(src.NewValue) 
    for FieldName in (Centrala,ID_Grup,Pi, Ci, Pmt, Pneta, Rpp, Pd, UD, Suport1, Suport2, Suport3, Stare, 
    Motiv, Observatii, Comentarii, Un, Data_ADD, Modified_Date, Scada, Fuel_base)) piv; 

UPDATE #Grup1 SET Pi= (case When b.Pi is not null then b.Pi else #Grup1.Pi end), 
       Ci=case When b.Ci is not null then b.Ci else #Grup1.Ci end, 
       Pmt=case When b.Pmt is not null then b.Pmt else #Grup1.Pmt end, 
       Pneta=case When b.Pneta is not null then b.Pneta else #Grup1.Pneta end, 
       Rpp=case When b.Rpp is not null then b.Rpp else #Grup1.Rpp end, 
       Pd=case When b.Pd is not null then b.Pd else #Grup1.Pd end, 
       UD=case When b.Ud is not null then b.Ud else '-' end, 
       Suport1=case When b.Suport1 is not null then b.Suport1 else #Grup1.Suport1 end, 
       Suport2=case When b.Suport2 is not null then b.Suport2 else #Grup1.Suport2 end, 
       Suport3=case When b.Suport3 is not null then b.Suport3 else #Grup1.Suport3 end, 
       Stare=case When b.Stare is not null then b.Stare else #Grup1.Stare end, 
       Motiv=case When b.Motiv is not null then b.Motiv else #Grup1.Motiv end, 
       Observatii=case When b.Observatii is not null then b.Observatii else #Grup1.Observatii end, 
       Comentarii=case When b.Comentarii is not null then b.Comentarii else #Grup1.Comentarii end, 
       Un=case When b.Un is not null then b.Un else #Grup1.Un end, 
       Scada= case When b.Scada is not null then b.Scada else #Grup1.Scada end, 
       Fuel_base=case When b.Fuel_base is not null then b.Fuel_base else #Grup1.Fuel_base end 
    FROM #temp1 b 
    WHERE #Grup1.id = b.id 

    Delete from #Grup1 where Data_ADD>@data 

    Select * from #Grup1 
    union 
    Select Old_ID,Centrala,ID_Grup,Pi, Ci, Pmt, Pneta, Rpp, Pd, UD, Suport1,Suport2, Suport3, Stare, Motiv, 
    Observatii, Comentarii, Un, Data_ADD, Modified_Date, Scada, Fuel_base From  DeletedGrupuri where Deleted<[email protected] and Old_ID is not null order by ID 
    drop table #temp 
    drop table #temp1 
    drop table #Grup1 

で正常に動作と思います。また、このプロセスを簡略化するために、Auditテーブルの設計を変更するために公開しています。 ありがとうございました!

関連する問題