Как ограничить обновления, разрешенные для таблицы - PullRequest
0 голосов
/ 05 апреля 2011

У нас есть таблица, которую необходимо заблокировать особым образом, и мы ищем лучший (надежность - это приоритет, а производительность - второй) способ ее достижения. Правила, касающиеся этой таблицы, заключаются в том, что новые записи могут быть добавлены свободно, но после их внесения, за одним исключением, они никогда не должны изменяться. Для записей в этой таблице будет разрешена одна действительная команда обновления, все остальные обновления или удаления должны быть заблокированы. Вот грубый пример подхода, который мы разработали до сих пор, есть ли хорошие способы улучшить его?

Таблица выглядит так:

CREATE TABLE [dbo].[Table_1](
    ID int IDENTITY(1,1) PRIMARY KEY NOT NULL
    ,data1 varchar(64) NULL
    ,data2 varchar(64) NULL
    ,data3 int NULL
    ,data4 bit NULL
    ,ModifiedBy VARCHAR(32)
    ,ModifiedDtTm DATETIME
)

Единственное допустимое обновление будет через процесс, который похож на это:

UPDATE dbo.Table_1
SET 
    data4 = 1
    ,ModifiedBy = @User
    ,ModifiedDtTm = GETDATE()
WHERE ID = @ID

Нам нужно заблокировать таблицу, чтобы создать два следующих триггера:

CREATE TRIGGER [dbo].[Table_1_UpdtLock] 
   ON  [dbo].[Table_1]
   INSTEAD OF UPDATE
AS 
BEGIN
    IF COLUMNS_UPDATED() = 0x70
        UPDATE dbo.Table_1
        SET 
            data4 = I.data4
            ,ModifiedBy = I.ModifiedBy
            ,ModifiedDtTm = I.ModifiedDtTm
        FROM dbo.Table_1 AS T
            INNER JOIN INSERTED AS I
                ON T.ID = I.ID
        WHERE I.data4 = 1
    ELSE
    BEGIN
        RAISERROR ('Table is locked.', 16, 0)
        ROLLBACK
    END
END

и

CREATE TRIGGER [dbo].[Table_1_DelLock]    
   ON  [dbo].[Table_1]
   INSTEAD OF DELETE
AS 
BEGIN
      ROLLBACK
      RAISERROR ('Table is locked.', 16, 0)
END

Это еще не было реализовано, и мы пытаемся убедиться, что у нас все правильно с первого раза, поскольку возможны юридические последствия, если эти данные будут повреждены или потеряны.

Кто-нибудь может видеть любые дыры, которые позволили бы кому-то редактировать данные в этой таблице? Единственное, что мне известно на данный момент, - это то, что таблицу можно обрезать без активации триггера удаления. Лучший ответ, который у меня есть на данный момент, - установить ссылку на ФК на эту таблицу.

Какие-нибудь потенциальные проблемы с производительностью, которые выделяются?

Предложения для лучшего подхода?

Спасибо за помощь.

РЕДАКТИРОВАТЬ:

Должен отметить, что доступ к базе данных будет ограничен настолько жестко, насколько мы можем это сделать. Однако в DBO всегда есть учетная запись, и наши SA обычно мало знают о том, что мы делаем с какой-либо конкретной базой данных. Я знаю, что люди с этими разрешениями могут обойти все, что мы создадим, цель на этом уровне - предотвратить несчастные случаи. Я также должен отметить, что мы хотим, чтобы он выдавал ошибку, если кто-то пытается выполнить незаконное обновление, он не должен молча завершаться сбоем или выполнять частичное обновление разрешенных полей.

Ответы [ 2 ]

2 голосов
/ 05 апреля 2011

Добавление в таблицу триггера для вставки или обновления может решить эту проблему.Вы также можете проверить учетную запись пользователя в базе данных и иметь ограничения для доступа к таблицам.

РЕДАКТИРОВАТЬ :

Вы можете увидеть плюсы и минусы наличия триггера здесь .Вы также можете увидеть его влияние на производительность здесь .

0 голосов
/ 06 апреля 2011

кажется сложным и, возможно, имеет нечеткое ребро.

почему бы просто не заменить все обновленные значения без вывода сообщений старым значением?

в oracle, в триггере обновления я бы написал что-тонапример:

:new.id := :old.id;
:new.data1 := :old.data1;

и т. д.

, затем убедитесь, что ни один пользователь не имеет прав на удаление таблицы.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...