Я посмотрел вокруг на SO и нашел много похожих вопросов:
Но у меня все еще есть проблемы с моим триггером для обновления нескольких строк при вставке нескольких строк в таблицу.
Схема кода
У меня есть таблица резервирования, которая имеет столбцы ReservationID и TourComponentID соответственно. Когда я вставляю в таблицу резервирований, у меня есть следующий триггер для обновления таблицы TourComponent с помощью ReservationID из строки, только что вставленной в таблицу резервирования, с соответствующим TourComponentID:
CREATE TRIGGER [TR_Reservation_CurrentReservation] ON [Reservation] AFTER INSERT AS
UPDATE tc
SET tc.[CurrentReservationId] = I.ReservationID
FROM [tour].[TourComponent] tc
JOIN INSERTED I on I.TourComponentID = tc.TourComponentID
End
Этот триггер отлично работает при обновлении одного tourComponent для нового резервирования (вставка одной строки в таблицу резервирования). Однако если я попытаюсь обновить несколько компонентов тура (вставив несколько строк в таблицу резервирования, чтобы обновить несколько строк в таблице TourComponent), обновится только первый компонент тура, любые строки.
Другие ответы и исследования показали мне, что
Триггеры НЕ выполняются один раз на строку, а скорее как набор на основе
операция выполняется только один раз для всей операции DML. Так что вы
нужно рассматривать это как любую другую дату обновления с оператором соединения.
Таким образом, я ожидал, что мое соединение с таблицей INSERTED обработало несколько строк, или я неправильно понял это?
Интересно, что если я запишу переменные триггера для TourComponentID, ReservationID и INSERTED rowcount во временную таблицу foo, я увижу, что в мою временную таблицу вставлены две записи, каждая с числом строк равным 1.
Используя sql profiler, чтобы поймать фактический sql, выполненный во время выполнения, и запустив его вручную для базы данных, я получаю две строки, обновляемые по желанию. Только при использовании Entity Framework для обновления базы данных, т.е. при запуске приложения, я обнаружил, что обновлена только одна строка.
Я попытался записать значения в таблицу FOO в триггере
INSERT INTO FOO (TourComponentID, ReservationID, Rowcounts )
SELECT i.TourComponentID, I.ReservationID, 1 --@ReservationId
FROM
INSERTED I
При этом в журнал заносятся две строки с числом строк, равным 1, и правильными значениями tourcomponentsID и bookingID, но в таблице TourComponent по-прежнему обновляется только одна строка.
Любые предложения с благодарностью.
UPDATE
Идентификаторы компонентов тура передаются в виде строки в сообщении Ajax в действие MVC, где заполняются модели компонентов тура, а затем передаются для обновления по одному в коде
public void UpdateTourComponents(IEnumerable<TourComponent> tourComponents)
{
foreach (var tourComponent in tourComponents)
{
UpdateTourComponent(tourComponent);
}
}
вот вызов UpdateTourComponent
public int UpdateTourComponent(TourComponent tourComponent)
{
return TourComponentRepository.Update(tourComponent);
}
и последний звонок для обновления
public virtual int Update(TObject TObject)
{
Dictionary<string, List<string>> newChildKeys;
return Update(TObject, null, out newChildKeys);
}
Таким образом, вставки происходят по одному, поэтому мой триггер вызывается один раз для каждого компонента TourComponent. Вот почему при подсчете @@ Rowcount в INSERTED и записи в Foo я получаю значение 1. Когда я запускаю вставки вручную, я получаю правильные ожидаемые результаты, поэтому я согласен с тестами @Slava Murygin, что проблема, вероятно, не связана с Сам триггер. Я подумал, что это может быть проблема со скоростью, если мы запускаем запросы один за другим, поэтому я поместил ожидание в триггер и в код, но это не помогло.
Обновление 2
Я использовал профилировщик SQL для захвата SQL, который запускается, когда работают только первые триггеры вставки.
Интересно, что когда EXACT тот же sql запускается в SQL Management Studio, триггер работает как положено, и оба компонента тура обновляются с идентификатором резервирования.
Стоит также упомянуть, что все ограничения были удалены со всех таблиц.
Любые другие предложения, что может быть причиной этой проблемы?