2012-03-29 85 views
1

我需要使用我的SQL Server上的時鐘寫一個時間到我的一個表,所以我想我只是使用GETDATE()。問題是由於INSTEAD OF觸發器,我得到一個錯誤。當另一列是標識列時,是否有方法將一列設置爲GETDATE()?LINQ to SQL與INSTEAD OF觸發器和一個標識列

這是LINQ到SQL:

internal void LogProcessPoint(WorkflowCreated workflowCreated, int processCode) 
{ 
    ProcessLoggingRecord processLoggingRecord = new ProcessLoggingRecord() 
    { 
     ProcessCode = processCode, 
     SubId  = workflowCreated.SubId, 
     EventTime = DateTime.Now // I don't care what this is. SQL Server will use GETDATE() instead. 
    }; 

    this.Database.Add<ProcessLoggingRecord>(processLoggingRecord); 
} 

這是表。 EventTime是我想要的GETDATE()。我不希望該列爲空。

enter image description here

這裏是觸發:

ALTER TRIGGER [Master].[ProcessLoggingEventTimeTrigger] 
    ON [Master].[ProcessLogging] 
    INSTEAD OF INSERT 
AS 
BEGIN 
    SET NOCOUNT ON; 
    SET IDENTITY_INSERT [Master].[ProcessLogging] ON; 

    INSERT INTO ProcessLogging (ProcessLoggingId, ProcessCode, SubId, EventTime, LastModifiedUser) 
     SELECT ProcessLoggingId, ProcessCode, SubId, GETDATE(), LastModifiedUser FROM inserted 

    SET IDENTITY_INSERT [Master].[ProcessLogging] OFF; 
END 

沒有進入所有我已經試過了變化,這最後的嘗試產生此錯誤:

出現InvalidOperationException 會員自動同步失敗。對於成員在插入後進行AutoSynced,該類型必須具有自動生成的標識或插入後未由數據庫修改的鍵。

我可以從我的實體中刪除EventTime,但我不想這樣做。如果它已經消失,那麼在INSERT和GETDATE()期間將會使用NULL。

有沒有一種方法可以簡單地在INSERT的EventTime列上使用GETDATE()?

注:我不想使用C#的DateTime.Now,原因有二:1。 其中一個刀片由SQL Server本身產生的(從另一個存儲過程) 2.時間可以在不同的機器不同,我想知道我的流程發生的速度。

回答

2

Bob,

看來你試圖在這裏解決兩個不同的問題。其中之一必須使用「替代者」觸發器處理L2S錯誤,而使用「SQL Server」框中的日期使用另一個列作爲列。我認爲你可能會遇到與觸發器和L2S無關的問題。您可能想嘗試一種使用After觸發器的方法,就像這樣。我認爲這會解決你的問題。

ALTER TRIGGER [Master].[ProcessLoggingEventTimeTrigger] 
ON [Master].[ProcessLogging] 
AFTER INSERT 

AS 
BEGIN 
UPDATE [Master].[ProcessLogging] SET EventTime = GETDATE() WHERE ProcessLoggingId = (SELECT ProcessLoggingId FROM inserted) 
END 
+0

完美的工作!謝謝! – 2012-03-29 17:58:41

1

您是否嘗試過使用EventTime表的默認值(getdate())? 您不需要在觸發器中設置該值,它會自動設置。

默認值用於未明確提供值的情況,例如,

INSERT INTO ProcessLogging (ProcessLoggingId, ProcessCode, SubId, LastModifiedUser) 
    SELECT ProcessLoggingId, ProcessCode, SubId, LastModifiedUser FROM inserted 

enter image description here

+0

但是,只有當數據爲NULL時纔會使用,對嗎? – 2012-03-29 17:28:07

+0

更新回答問題詳情 – Phil 2012-03-29 17:29:56

+0

這就是我想要做的,但問題在於ID列。我得到不同的錯誤。讓我試試你的*精確*場景。 – 2012-03-29 17:34:24

2

不要使用觸發器,使用defualt:

create table X 
(id int identity primary key, 
value varchar(20), 
eventdate datetime default(getdate())) 

insert into x(value) values('Try') 
insert into x(value) values('this') 

select * from X 

這是更好的。

+0

如果您可以使用默認值,則幾乎總是最好使用觸發器。 – HLGEM 2012-03-29 18:12:34

0

鮑勃,

我看最好是不要使用SQL Server的觸發器;它有很多缺點,不建議用於數據庫性能增強。請查看SQL Authority博客,以獲取有關Triggers problems的更多信息。

您可以通過以下步驟實現你想要的,而不觸發:

  1. 變化Eventime列允許空
  2. 集EVENTTIME列缺省值GETDATE()。所以它總是會有一個當前的插入值。
  3. 請勿將您的LinqToSQL代碼中的EventTime值設置爲DateTime.Now,因此它將採用SQL Server中的默認值。
相關問題