Oracle: Как да открием прекратяване на клиентския процес, както работи за sqlplus?

Имам следния проблем в моето приложение, което се свързва с база данни на Oracle 10g:

Когато клиентът ми се срине, или процесът бъде прекратен чрез диспечера на задачите, или клиентът загуби връзка за известно време, съответният запис в изгледа на v$session остава.

Сега, когато се свържа с базата данни с sqlplus и убия sqlplus.exe през диспечера на задачите, записът на сесията се изтрива почти моментално.

Последното поведение би било предпочитано за моето приложение поради различни причини.

Какво прави sqlplus по различен начин и мога ли да го правя и в моите собствени приложения?


person Tim Meyer    schedule 09.03.2012    source източник
comment
Срещал съм такава разлика в поведението, когато използвам тънък клиентски драйвер на oracle, за разлика от OCI драйвер.   -  person Juergen Hartelt    schedule 09.03.2012


Отговори (3)


SQL*Plus използва OCI - Oracle Call Interface. Това е обширен API (над четиристотин извиквания на функции. OCI предоставя много методи за обработка на връзки и сесии. Не знам със сигурност, но бих предположил, че SQL*Plus използва OCILogon2(), за да регистрира специална сесия за потребителя, и поставя нещо в манипулатора на сесията, което му позволява да открие кога сесията ABEND.

Така че вероятно приложението ви не използва OCI за свързване на базата данни. Ако искате да научите повече за OCI, можете да прочетете документите. Бъдете предупредени, това са неща на доста ниско ниво! Научете повече.

person APC    schedule 09.03.2012
comment
Използвам Qt, който предлага приставката QSQLOCI, която е Qt обвивка около OCI. Предполагам, че ще разгледам QSQLOCI слоя. - person Tim Meyer; 09.03.2012
comment
Този слой използва OCIServerAttach и OCISessionBegin; Не можах да намеря срещане на OCILogon или OCILogon2. Знаете ли дали ServerAttach/SessionBegin е алтернатива на OCILogon или те не са свързани? - person Tim Meyer; 09.03.2012

Можете да зададете sqlnet.expire_time=minutes_to_check в $ORACLE_HOME/network/admin/sqlnet.ora; няма да е моментално като oci, но ще изчисти мъртвите връзки.

person Adam Musch    schedule 09.03.2012
comment
Това почиства ли само мъртви връзки? Или ще засегне и връзки, които са били неактивни за повече от minutes_to_check? - person Tim Meyer; 12.03.2012
comment
Всъщност прави и двете. Нашите системи са настроени по този начин, тъй като тогава няма значение за капацитета на клиентското приложение и повечето от нашите Java приложения използват групиране на връзки, така че да могат да рестартират мъртва връзка в своя пул. - person Adam Musch; 12.03.2012
comment
Има ли начин да зададете нещо подобно само за текущата сесия? Проблемът е, че целевият сървър се използва за няколко приложения (не само нашите) и трябва да гарантираме, че другите приложения няма да спрат да работят, когато искаме да променим нещо на сървъра - person Tim Meyer; 13.03.2012
comment
Не доколкото ми е известно - ще трябва да използвате OCI слоя, както препоръчва APC. - person Adam Musch; 14.03.2012

По-нататъшно разследване показа, че въпреки че sqlplus се държи различно при спиране на процеса, всъщност той се държи по същия начин, когато мрежовият кабел е изключен за секунда => Висящата сесия ще остане на сървъра.

Сега създадох потребителски профил с ограничен idle_time, който е присвоен на потребителите, от които се нуждая. Фонова нишка изпраща заявки "keepalive", за да предотврати връзката да бъде SNIPED от PMON.

Вижте другия ми въпрос Oracle: idle_time изглежда се игнорира, ако сте интересувате се от това, което направих и вижте отговора какво трябва да направите, за да накарате idle_time да работи.

person Tim Meyer    schedule 15.03.2012