sql server это Редактирование записей базы данных несколькими пользователями




sql server что это (7)

Я разработал таблицы базы данных (нормализованные на сервере MS SQL) и создал автономный оконный интерфейс для приложения, которое будет использоваться несколькими пользователями для добавления и редактирования информации. Мы добавим веб-интерфейс, чтобы позднее можно было искать на нашей производственной площадке.

Я обеспокоен тем, что, если два пользователя начнут редактировать одну и ту же запись, последним для фиксации обновления будет «победитель», и важная информация может быть потеряна. Множество решений приходит на ум, но я не уверен, что я собираюсь создать большую головную боль.

  1. Не делайте ничего и надейтесь, что два пользователя никогда не будут редактировать одну и ту же запись одновременно. - Никогда не бывало, но что делать?
  2. Подпрограмма редактирования могла хранить копию исходных данных, а также обновления, а затем сравнивать, когда пользователь закончил редактирование. Если они отличаются показами пользователей и обновлений comfirm - потребовалось бы хранить две копии данных.
  3. Добавьте последний обновленный столбец DATETIME и проверьте его совпадение, когда мы обновляем, а затем показываем различия. - требуется новый столбец в каждой из соответствующих таблиц.
  4. Создайте таблицу редактирования, которая регистрируется, когда пользователи начнут редактировать запись, которая будет проверяться, и не позволят другим пользователям редактировать одну и ту же запись. - потребует внимательного анализа потока программ, чтобы предотвратить блокировку блокировок и записей, если пользователь выйдет из программы.

Есть ли какие-то лучшие решения или я должен пойти на один из них?


Другой вариант - проверить, что значения в записи, которые вы меняете, по-прежнему такие же, как и при запуске:

SELECT 
    customer_nm,
    customer_nm AS customer_nm_orig
FROM demo_customer
WHERE customer_id = @p_customer_id

(отобразите поле customer_nm и пользователь изменит его)

UPDATE demo_customer
SET customer_nm = @p_customer_name_new
WHERE customer_id = @p_customer_id
AND customer_name = @p_customer_nm_old

IF @@ROWCOUNT = 0
    RAISERROR( 'Update failed: Data changed' );

Вам не нужно добавлять новый столбец в свою таблицу (и поддерживать его в актуальном состоянии), но вам нужно создать более подробные инструкции SQL и передать «новые» и «старые» поля в хранимую процедуру.

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


База данных сделает это за вас. Посмотрите на «select ... for update», который предназначен именно для такого рода вещей. Это даст вам возможность блокировки записи на выбранных строках, которые затем можно выполнить или отменить.



@ Марк Харрисон: SQL Server не поддерживает этот синтаксис ( SELECT ... FOR UPDATE ).

Эквивалент SQL Server - это SELECT оператора SELECT UPDLOCK .

Дополнительную информацию см. В электронной документации по SQL Server .


- сначала создайте файл (время обновления), чтобы сохранить последнюю запись обновления - когда любой пользователь выбирает запись сохранить время выбора, сравнивайте время выбора времени и времени обновления, если (время обновления)> (выберите время), что означает, что другой пользователь обновляет эту запись после выбора запись


Классический подход заключается в следующем:

  • добавьте логическое поле, «заблокированное» для каждой таблицы.
  • по умолчанию установите значение false.
  • когда пользователь начинает редактирование, вы делаете это:

    • заблокируйте строку (или всю таблицу, если вы не можете заблокировать строку)
    • проверьте флаг в строке, которую хотите изменить
    • если флаг имеет значение true, тогда
      • сообщите пользователю, что они не могут редактировать эту строку в данный момент
    • еще
      • установите флаг в true
    • освободить замок

    • при сохранении записи установите флаг в значение false


SELECT FOR UPDATE и эквиваленты хороши, если вы удерживаете блокировку на микроскопическом уровне времени, но для макроскопического количества (например, пользователь загружает данные и не нажал «сохранить», вы должны использовать оптимистичный параллелизм, как указано выше. Я всегда думаю, что это неправильно, это более пессимистично, чем «побеждает последний писатель», что обычно считается единственной альтернативой.)





database