2013-03-25 4 views
2

У меня есть база данных SQL Server 2008. К нему подключены три терминала (A, B, C). В базе данных есть таблица SampleTable, которая реагирует на любую деятельность терминала. Каждый раз, когда на каком-либо терминале есть какая-либо активность, вошедшая в этот БД, новая строка вставляется в SampleTable.Запретная вставка в таблицу при определенных условиях

Я хочу перенаправить трафик с одного (C) трех терминалов на запись в таблицу RealTable, а не на SampleTable, но я должен сделать это на уровне DB, поскольку службы, которые записывают активность терминала в DB, ​​находятся в Black Box.

У меня уже есть триггеры, работающие на SampleTable с логикой перенаправления, но проблема в том, что строки все еще вставлены в SampleTable.

Какое самое чистое решение для этого. Я уверен, что удаление строк в триггере ввода плохо, плохо, плохо.

Пожалуйста, помогите.

Edit:

Наша текущая логика что-то вроде этого (это псевдо-код):

ALTER TRIGGER DiffByTerminal 
ON SampleTable 
AFTER INSERT 
AS 
DECLARE @ActionCode VARCHAR(3), 
    @ActionTime DATETIME, 
    @TerminalId INT 

    SELECT @ActionCode = ins.ActionCode, 
    @ActionTime = ins.ActionTime, 
    @TerminalId = ins.TerminalId 
    FROM inserted ins 

IF(@TerminalId = 'C') 
BEGIN 

    INSERT INTO RealTable 
    ( 
     ... 
    ) 
    VALUES 
    (
     @ActionCode, 
     @ActionTime, 
     @TerminalId 
    ) 
END 
+1

Что такое триггер? Самый чистый, вероятно, нужно вставить через хранимую процедуру, чтобы у вас было красивое место для добавления дополнительной логики. –

+1

Какова ваша существующая логика? Это звучит как идеальное использование для триггера «INSTEAD OF» – JNK

+0

Мы не можем изменить логику вставки строки, поэтому она должна быть триггером или что-то вроде триггера. @JNK Пожалуйста, см. Мой отредактированный ответ. – nzic

ответ

3

Чтобы «перехватить» что-либо перед тем, как строка вставлена ​​в таблицу, вам нужно триггер INSTEAD OF, а не триггер AFTER. Таким образом, вы можете оставить свой существующий триггер (который также включал порочную логику, которая приняла на себя все вставки будет однорядные) и создать этот INSTEAD OF триггер вместо:

DROP TRIGGER DiffByTerminal; 
GO 

CREATE TRIGGER dbo.DiffByTerminal 
ON dbo.SampleTable 
INSTEAD OF INSERT 
AS 
BEGIN 
    SET NOCOUNT ON; 

    INSERT dbo.RealTable(...) SELECT ActionCode, ActionTime, TerminalID 
    FROM inserted 
    WHERE TerminalID = 'C'; 

    INSERT dbo.SampleTable(...) SELECT ActionCode, ActionTime, TerminalID 
    FROM inserted 
    WHERE TerminalID <> 'C'; 
END 
GO 

Это будет обрабатывать однорядные вставки и многорядные вставки, состоящие of (a) только C (b) только не-C и (c) смесь.

+0

Хорошо, пожалуйста, дайте мне немного времени, чтобы проверить это, но просто смотреть на это кажется идеальным решением. – nzic

+0

Кажется, все работает нормально. Поскольку для этой таблицы заданы некоторые другие триггеры (SampleTable), я предполагаю, что любой «ПОСЛЕ ВСТАВКИ» будет происходить после того, как строка фактически вставлена ​​в SampleTable, отфильтрованную «триггером INSTEAD OF INSERT». Не могли бы вы подтвердить? – nzic

+0

Да, срабатывает триггер AFTER ПОСЛЕ того, как строка была вставлена. Конечно, вы можете отменить его с откатом, но это также приведет к отмене всего, что сделали триггер (ы) INSTEAD OF. Зачем вам нужно несколько триггеров? –

1

Один из самых простых решения для вас ВМЕСТО триггера. Просто говоря, это триггер, который «срабатывает» по самому действию, которое вы решите, и позволяет «переопределить» поведение по умолчанию для действия.

Вы можете переопределить операторы INSERT, DELETE и UPDATE для определенной таблицы/представления (вы используете ее много с представлениями, которые объединяют данные из разных таблиц, и вы хотите сделать вставку в виде) с помощью триггера INSTEAD OF, где вы может поставить вашу логику. внутри триггера вы можете снова вызвать INSERT, когда это уместно, и вам не нужно беспокоиться о рекурсии. Триггеры INSTEAD OF не будут применяться к операторам внутри самого кода запуска.

Наслаждайтесь.

+0

Видя мой отредактированный ответ, можете ли вы быть более конкретным? Tnx – nzic

+0

Sry ... не вопрос, но ответ – nzic

Смежные вопросы