Ответ 1:
Самое дешевое решение - завести поле, в которое будет
записываться ID usera перед началом операции.
Перед началом
обновления данных выполняете следующее. 1. При старте программы
каждому юзеру раздаете уникальный ID. 2. Перед началом обновления
данных записываете ID в поле в и коммитете данные. После этого поле
будет залочено для этого юзера. 3. Вносите изменения. 4. В
блокирующее поле записываете 0 и коммитете.
Перед началом
обновления, проверяете чему равно значение блокирующего поля. Если
оно не нулевое, то вы не только сможете сообщить, что
запись заблокирована, но и сказать кем именно.
Если не делать
ничего подобного то запросто при многопользовательской работе можно
получить deadlock на сервере а есть не очень хорошо.
Ответ 2:
Так сделать нельзя. Можно по другому. Оцени критические ситуации
и поставь проверку на триггер или еще лучше сделай с
помощью CHECK. Например: колличество на складе не может быть
меньше 0 CHECK TOVAR_COUNT>0 Если один из клиентов изменил
количество , а второй попытался снять больше чем есть на складе - то
сервер выдаст ошибку, которую ты можешь обработать
программой.
Очень хорошая книга по этой теме П.В. Шумаков -
Дельфи 3 и разработка приложений баз данных. После ее прочтения
80% твоих вопросов будут решены.
Ответ 3:
Думаю, что Вашу задачу можно решить следующим путем. На
сервере метод, который осуществляет обработку данных. "закрыть"
критической секцией.
В начале критическую секцию необходимо
объявить в составе класса или отдельно:
SectionLock: TCriticalSection;
|
Затем:
procedure TForm1.FormCreate(Sender: TObject);
begin
SectionLock := TCriticalSection.Create;
end;
procedure TForm1.FormDestroy(Sender: TObject);
begin
SectionLock.Free;
end;
|
Теперь при инициализации Вашего метода можно использовать
SectionLock:
SectionLock.Acquire;
try
DoSomething;
finally
SectionLock.Release;
end;
// или
SectionLock.Enter;
try
DoSomething;
finally
SectionLock.Leave;
end;
|
Когда поток достигает критической секции, то все что заключено в
этой секции перестает реагировать на любые внешние воздействия до
момента выхода из критической секции. Теперь на попытку обращения к
серверу другого клиента в качестве результата можно возвращать
значение, которое будет идентифициороваться как "Занято". Например:
if Lock then
"Ответ - занято"
SectionLock.Enter;
try
Lock := True;
DoSomething;
finally
SectionLock.Leave;
Lock := False;
end;
|
P.S. Что бы сервер мог одновременно реагировать на несколько
запросов, его необходимо реализовать в СОМ технологии. |