Linq to SQL с триггером INSTEAD OF и столбцом идентификаторов - PullRequest
1 голос
/ 29 марта 2012

Мне нужно использовать часы на моем SQL Server, чтобы записать время в одну из моих таблиц, поэтому я подумал, что просто использую GETDATE ().Проблема в том, что я получаю ошибку из-за моего триггера INSTEAD OF.Есть ли способ установить один столбец в GETDATE (), если другой столбец является столбцом идентификаторов?

Это Linq-to-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.Чтобы члены были автоматически синхронизированы после вставки, тип должен иметь автоматически сгенерированный идентификатор или ключ, который не изменяется базой данных после вставки.

Я мог бы удалить EventTime из своей сущности, но я неЯ не хочу этого делать.Однако если этого не произошло, то во время INSERT будет использоваться значение NULL, и будет использоваться GETDATE ().

Есть ли способ, которым я могу просто использовать GETDATE () в столбце EventTime для INSERT?

Примечание: я не хочу использовать C # DateTime.Now по двум причинам: 1. Одна из этих вставок генерируется самим SQL Server (из другой хранимой процедуры) 2. Время может быть разным на разных машинах, и я 'Мне бы хотелось точно знать, как быстро происходят мои процессы.

Ответы [ 4 ]

2 голосов
/ 29 марта 2012

Не используйте триггер, используйте 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

Это намного лучше.

2 голосов
/ 29 марта 2012

Bob

Кажется, вы пытаетесь решить две разные проблемы здесь. Один из них связан с ошибкой L2S с помощью триггера вместо, а другой - с использованием даты в поле SQL Server для вашего столбца. Я думаю, что у вас могут быть проблемы с вместо триггеров и L2S. Возможно, вы захотите попробовать подход, который использует триггер после, как это. Я думаю, что это решит обе ваши проблемы.

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

AS 
BEGIN
UPDATE [Master].[ProcessLogging] SET EventTime = GETDATE() WHERE ProcessLoggingId = (SELECT ProcessLoggingId FROM inserted)
END 
1 голос
/ 29 марта 2012

Вы пытались использовать значение по умолчанию (getdate ()) для столбца EventTime? Тогда вам не нужно будет устанавливать значение в триггере, оно будет установлено автоматически.

Значение по умолчанию используется, если вы не указали значение явно, например,

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

enter image description here

0 голосов
/ 20 июля 2012

Боб,

Я вижу, что лучше не использовать триггеры в SQL-сервере;это имеет много недостатков и не рекомендуется для повышения производительности базы данных.Пожалуйста, проверьте блог SQL Authority для получения дополнительной информации о проблемах Триггеры .

Вы можете достичь того, что хотите, без триггеров, выполнив следующие действия:

  1. Изменить столбец Eventimeдля разрешения null
  2. Установите для столбца Eventtime по умолчанию значение GetDate ().Поэтому он всегда будет иметь текущее значение вставки.
  3. Не устанавливайте в качестве значения Eventtime значение DateTime.Now из кода LinqToSQL, поэтому он будет принимать значение по умолчанию в SQL Server.
...