-
Простая трехзвенка: [Клиент (TClientDataSet + TSocketConnection)] -> локальная сеть -> [Сервер приложений (TDataSetProvider + IBX)] -> [Firebird]
(Удаленный модуль - instancing: Multiple Instance, threading model: Apartment).
Все компоненты из поставки Delphi5, сервер Firebird v.1.0.3 (довольно-таки старые :)).
При подключении клиента и срабатывании IBDatabase1.Connected := True возникает задержка в зависимости от железа от 1 до 5 сек. Если во время этой паузы другой клиент пытается подключиться или уже подключенный клиент пытается обратиться к базе, оба намертво зависают.
При убивании клиентов, сервер приложений самостоятельно не глушится, приходится его процесс тоже вручную завершать.
В общем-то проблему решил добавлением глобальной переменной в модуль гл.формы сервера и работой с ней как:
const LockedServer: Boolean = False;
procedure TRdmCommon.IBDatabase1BeforeConnect(Sender: TObject); begin if LockedServer then raise Exception.Create('Занят сервер.'); LockedServer := True; end;
procedure TRdmCommon.IBDatabase1AfterConnect(Sender: TObject); begin LockedServer := False; end;
Понятно, что клиенты "готовы" к такому исключению.
Громоздско, но if LockedServer then raise Exception.Create('Занят сервер.'); добавил во все процедуры сервера приложений, где есть обращение к базе.
Работает, конечно, но все эти заплатки какие-то некрасивые. Подскажите, может быть кто-то сталкивался с подобной вещью и она ликвидируется как-то радикально?
-
При замене Threading Model с Apartment-а на Single проблема снялась. А вот почему - черт ее знает :)
-
Респект Роману Игнатьеву за статью "MIDAS - практическое применение". Проблема была не в Apartment-е, а в указании пути к базе. Вместо "Путь..." указать localhost:"Путь..."
-
> Проблема была не в Apartment-е, а в указании пути к базе. > Вместо "Путь..." указать localhost:"Путь..."
Также будет глючить. Может быть чуть пореже, но 100% , что будет. Нельзя допускать одновременных коннектов к FireBird в рамках одного приложения. Самая простая защита - это поместить код IBDatabase1.Connected := True; и соответственно IBDatabase1.Connected := False; В критическую секцию.
-
> При подключении клиента и срабатывании IBDatabase1.Connected > := True возникает задержка в зависимости от железа от 1 > до 5 сек.
Это слишком большая задержка. Расширение в имени файла базы данных не GDB случаем? Если так, то его необходимо переименовать (обычно на FDB). Также можно попробовать обновить FireBird (новые версии вроде как пошустрее).
-
> Нельзя допускать одновременных коннектов к FireBird в рамках одного приложения.
Ты где это выкурил ?
Утверждение справедливо только для Firebird Embedded версии ниже 3.0
-
> Ты где это выкурил ?
Проверил. Опытным путем так сказать. Выделил для этого время, накатал несколько тестов. Тесты показали соответствующие результаты. С результатами тестов ознакомлены разработчики, а также те, кто регулярно читает соответствующий форум на sql.ru.
> Утверждение справедливо только для Firebird Embedded версии > ниже 3.0
Утверждение справедливо для ЛЮБЫХ версий FireBird. С появлением FB2.5 ситуация стала намного лучше. Но тесты показывают, что синхронизация все равно необходима. О том же самом периодически напоминает автор сайта ibase.ru. Возможно, что дело сейчас даже не в клиентской библиотеке, а в реализации TIBDatabase.
-
Бредятина какая-то.
Одно из моих внедрений - симметричная ERP-система на постоянных 500-800 коннектов уверенно себя чувствует. "Симметричная" потому, что к базе коннектятся не только из клиентского приложения, но она еще имеет веб морду для дилеров на Апаче+ПыХПых. При этом: 1) для сервера все веб коннекты идут от одного приложения (Апача) (порядка 400 штук). 2) клиентское приложение все отчеты на пред.просмотр строит в отдельных тредах, имеющих свое отдельное подключение, чтобы юзер мог в случае тяжелого отчета работать с чем-то другим или просто "передумать".
-
Мне это ни о чем не говорит. Не указано ни версии FireBird, ни места, где используется TIBDatabase. Что за ПыХПых: это CGI или DLL? Что-то мне подсказывает, что никаких одновременных подключений в параллельных потоках с использованием TIBDatabase в данной системе нет. В таком случае зачем было это приводить, показать как все круто?
-
> Самая простая защита - это поместить код > IBDatabase1.Connected := True; > и соответственно > IBDatabase1.Connected := False; > В критическую секцию.
А как в случае ошибки грамотнее ее обработать?
Вернуть клиенту с предложением попытаться позже или Sleep на сервере на некоторое время и повторная попытка? Или же у кого как?
>Расширение в имени файла базы данных не GDB случаем?
Да GDB, конечно. Перелез на с IB на FB, а это как-то упустил :) Спасибо
-
> А как в случае ошибки грамотнее ее обработать?
Прошу прощения, спутал-с CriticalSection с try ...
|