|
php.net | support | documentation | report a bug | advanced search | search howto | statistics | random bug | login |
PatchesPull RequestsHistoryAllCommentsChangesGit/SVN commits
[2005-05-27 11:12 UTC] tony2001@php.net
[2005-09-08 11:49 UTC] tony2001@php.net
|
|||||||||||||||||||||||||||
Copyright © 2001-2025 The PHP GroupAll rights reserved. |
Last updated: Mon Oct 27 16:00:01 2025 UTC |
Description: ------------ We have several web-based php-db-applications in use. In case of db-maintenance (when the db is down), the applications (of course) fail to deliver db contents. After restarting the db, the web-application still cannot connect to the db. A webserver restart is required. For me, this seems to be a bug related oci8-clients (I'm using oracle instant client as well as the older oracle 9 client) or PHP. So I reported this problem to Oracle Support and I got the suggestion to fix the problem in PHP. Expected result: ---------------- Here is Oracle's solution: I have received your request and will try to help you. First of all there are two ways in OCI8 and higher to establish a connection 1. Design for optimized Access against one or multiple DBs by splitting up the "Connect" into Access path (he Library loading etc) and one or multiple Sessions OCIServerAttach() OCISessionBegin() -- OCI DB ACCESS -- OCISessionEnd() .... OCISessionBegin() -- OCI DB ACCESS -- OCISessionEnd() OCIServerDetach() This Design allows to switch between Servers and Sessions 2. "Plain" Design - OCILogon() -- OCI DB ACCESS -- OCILogoff() furtheron, I have downloaded the source of PHP and checked where the connect is established. As you can see, ocilogon() uses the first "smart" way - enabling to remember if a previously server was attached by retrieving the hash values: ocilogon --> oci_connect --> oci_do_connect static void oci_do_connect(INTERNAL_FUNCTION_PARAMETERS,int persistent,int exclusive) ...... connection = (oci_connection *) ecalloc(1,sizeof(oci_connection)); if (!connection) { goto CLEANUP; } server = _oci_open_server(dbname,persistent); if (!server) { goto CLEANUP; } if (exclusive) { /* exlusive session can never be persistent!*/ persistent = 0; } else { /* if our server-context is not persistent we can't */ persistent = (server->persistent) ? persistent : 0; } session = _oci_open_session(server,username,password,persistent,exclusive,charset); ............. static oci_server *_oci_open_server(char *dbname,int persistent) { oci_server *server, *pserver = NULL; TSRMLS_FETCH(); /* check if we already have this server open we will reuse servers within a request no matter if the user requested persistent connections or not! but only as pesistent requested connections will be kept between requests! */ /* TODO either keep servers global or don't reuse them at all */ zend_ts_hash_find(persistent_servers, dbname, strlen(dbname)+1, (void **) &pserver); ....... CALL_OCI_RETURN(OCI(error), OCIServerAttach( server->pServer, OCI(pError), (text*)server->dbname, strlen(server->dbname), (ub4) OCI_DEFAULT ) ); Unfortunatly, there is no "force" parameter which can be used to force a ServerAttach - nor supports PHP the second, plain way for dumb Logon/Logoff. for my opinion this is a PHP Bug and a fix would be to put a while clause (3 Attempts) round ServerAttach / SessionBegin to allow a forced ServerAttach if Hash code states server is available - but DB was bounced - resulting in lost server context.