簡體   English   中英

如何基於另一個SQL Server表的單列中的更改添加一個SQL Server表的行和時間戳

[英]How to add a row and timestamp one SQL Server table based on a change in a single column of another SQL Server table

[更新:2/20/19]我找到了一個非常簡單的解決方案來解決此問題。

CREATE TRIGGER TriggerClaims_History on Claims
AFTER INSERT
AS
BEGIN
    SET NOCOUNT ON
    INSERT INTO Claims_History
    SELECT name, status, claim_date
    FROM Claims
    EXCEPT SELECT name, status, claim_date FROM Claims_History
END
GO

我正在為我正在處理的項目建立一個SQL Server數據庫。 重要信息:我有3個表-注冊,取消和聲明。 服務器上每天都有文件填充這些表。 這些文件不是增量(即每天放置在服務器上的每個新文件都包含來自以前所有文件的數據),因此,我能夠簡單地刪除所有表,創建表,然后每天從文件中填充表。 我的問題是關於我的索賠表-由於表將在每晚被刪除和創建,因此我需要一種跟蹤所有不同狀態更改的方法。

我正在努力找出解決此問題的最佳方法。

我正在考慮創建一個每晚不刪除的Claims_history表。 本質上,我希望每次將新的初始記錄添加到Claims表時填充我的Claims_history表。 然后,我將要掃描Claims表,並且僅當狀態列發生更改(即Claims.status!= Claims_history.status)時,才在Claims_history表中添加一行。

第一天:

select * from claims          

id | name     | status
 1 | jane doe | received

select * from claims_history  

id | name     | status   | timestamp
 1 | jane doe | received | datetime

第二天:

select * from claims          

id | name     | status
 1 | jane doe | processed

select * from claims_history  

id | name     | status    | timestamp
 1 | jane doe | received  | datetime
 1 | jane doe | processed | datetime

是否有可以執行此操作的SQL腳本? 我還希望每次添加新行(狀態更改)時,都會在Claims_history表中自動填充timestamp字段。 我知道我可以編寫一個python腳本來處理類似的事情,但如果可能的話,我想將其保留在SQL中。 謝謝。

根據您的問題,需要在更新 Claims.status列后創建一個觸發器 ,使用此鏈接知道並了解如何執行簡單的觸發器非常簡單,請單擊此處創建asimple sql server觸發器

那么好像在查詢中操作dateTime時有很多問題,這將建議您使用UNIX時間而不是使用datetime,您可以使用Long或bigInt UNix時間將日期存儲為數字以了解當前時間,只需使用查詢SELECT UNIX_TIMESTAMP ()

一種非常常見的方法是使用臨時表和生產(或最終)表。 您所有的ETL將截斷並加載臨時表(易失性),然后執行存儲過程,該過程僅將新記錄添加到最終表中。 這就要求您以這種方式處理的所有數據都具有某種形式的密鑰 ,該密鑰可以明確標識一行。

如果您的文件突然更改格式或格式不正確怎么辦? 您將刪除表,直到修復ETL才能將其加載回去。 這種方法可以避免您的麻煩,因為在加載臨時表時該過程將失敗,並且不會影響最終表。 您也可以出於歷史原因保留已刪除的記錄,而不是刪除它們。

我更喜歡將登台表分成適當的架構,例如:

CREATE SCHEMA Staging
GO

CREATE TABLE Staging.Claims (
    ID INT,
    Name VARCHAR(100),
    Status VARCHAR(100))

現在,您將文件中的所有負載都放入這些臨時表中,首先將它們截斷:

TRUNCATE TABLE Staging.Claims

BULK INSERT Staging.Claims
FROM '\\SomeFile.csv'
WITH
    --...

加載該表后,您將執行一個特定的SP,該SP在過渡內容和最終表之間添加增量。 您可以在此處添加所需的任何邏輯,例如僅對新記錄進行插入,或插入已在另一個表上更新的現有值。 例如:

CREATE TABLE dbo.Claims (
    ClaimAutoID INT IDENTITY PRIMARY KEY,
    ClaimID INT,
    Name VARCHAR(100),
    Status VARCHAR(100),
    WasDeleted BIT DEFAULT 0,
    ModifiedDate DATETIME,
    CreatedDate DATETIME DEFAULT GETDATE())
GO

CREATE PROCEDURE Staging.UpdateClaims
AS
BEGIN

    BEGIN TRY

        BEGIN TRANSACTION

            -- Update changed values
            UPDATE C SET
                Name = S.Name,
                Status = S.Status,
                ModifiedDate = GETDATE()
            FROM
                Staging.Claims AS S
                INNER JOIN dbo.Claims AS C ON S.ID = C.ClaimID -- This has to be by the key columns
            WHERE
                ISNULL(C.Name, '') <> ISNULL(S.Name, '') AND
                ISNULL(C.Status, '') <> ISNULL(S.Status, '')

            -- Insert new records
            INSERT INTO dbo.Claims (
                ClaimID,
                Name,
                Status)
            SELECT
                ClaimID = S.ID,
                Name = S.Name,
                Status = S.Status
            FROM
                Staging.Claims AS S
            WHERE
                NOT EXISTS (SELECT 'not yet loaded' FROM dbo.Claims AS C WHERE S.ID = C.ClaimID) -- This has to be by the key columns

            -- Mark deleted records as deleted
            UPDATE C SET
                WasDeleted = 1,
                ModifiedDate = GETDATE()
            FROM
                dbo.Claims AS C
            WHERE
                NOT EXISTS (SELECT 'not anymore on files' FROM Staging.Claims AS S WHERE S.ClaimID = C.ClaimID) -- This has to be by the key columns


        COMMIT

    END TRY

    BEGIN CATCH

        DECLARE @v_ErrorMessage VARCHAR(MAX) = ERROR_MESSAGE()

        IF @@TRANCOUNT > 0
            ROLLBACK

        RAISERROR (@v_ErrorMessage, 16, 1)

    END CATCH

END

這樣,您就可以始終使用dbo.Claims ,並且記錄也不會丟失(只是更新或插入)。


如果您需要檢查特定聲明的最新狀態,可以創建一個視圖:

CREATE VIEW dbo.vClaimLastStatus 
AS
WITH ClaimsOrdered AS
(
    SELECT
        C.ClaimAutoID,
        C.ClaimID,
        C.Name,
        C.Status,
        C.ModifiedDate,
        C.CreatedDate,
        DateRanking = ROW_NUMBER() OVER (PARTITION BY C.ClaimID ORDER BY C.CreatedDate DESC)
    FROM
        dbo.Claims AS C
)
SELECT
    C.ClaimAutoID,
    C.ClaimID,
    C.Name,
    C.Status,
    C.ModifiedDate,
    C.CreatedDate,
FROM
    ClaimsOrdered AS C
WHERE
    DateRanking = 1

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM