mirror of
https://github.com/sigmasternchen/php-doc-en
synced 2025-03-16 08:58:56 +00:00
Merge DRCP & FAN sections from the README
git-svn-id: https://svn.php.net/repository/phpdoc/en/trunk@291902 c90b9560-bf6c-de11-be94-00142212c4b1
This commit is contained in:
parent
96eed35c31
commit
09c4f4d0b5
1 changed files with 399 additions and 57 deletions
|
@ -2,63 +2,405 @@
|
|||
<!-- $Revision$ -->
|
||||
<chapter xml:id="oci8.connection" xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<title>Connection Handling</title>
|
||||
<para>
|
||||
The OCI8 extension provides three different functions for connecting
|
||||
to Oracle. The information in this section is intended to help
|
||||
determine which is most appropriate for an application.
|
||||
</para>
|
||||
<para>
|
||||
Connecting to an Oracle server is a reasonably expensive operation
|
||||
in terms of the time that it takes to complete.
|
||||
The <function>oci_pconnect</function> function uses a persistent
|
||||
cache of connections that can be re-used across different script
|
||||
requests. This means that the connection overhead will typically
|
||||
only occur once per PHP process (or Apache child).
|
||||
</para>
|
||||
<para>
|
||||
If the application connects to Oracle using a different set of
|
||||
credentials for each web user, the persistent cache employed by
|
||||
<function>oci_pconnect</function> will become less useful as the
|
||||
number of concurrent users increases, to the point where it may
|
||||
start to adversely affect the overall performance of the Oracle
|
||||
server due to maintaining too many idle connections. If the
|
||||
application is structured in this way, it is recommended to either
|
||||
tune the application using
|
||||
the <link linkend="ini.oci8.max-persistent">oci8.max_persistent</link>
|
||||
and <link linkend="ini.oci8.persistent-timeout">oci8.persistent_timeout</link>
|
||||
configuration settings (these will give control over the persistent
|
||||
connection cache size and lifetime), use Oracle 11g Database
|
||||
Resident Connection Pooling, or use
|
||||
<function>oci_connect</function> instead.
|
||||
</para>
|
||||
<para>
|
||||
Both <function>oci_connect</function>
|
||||
and <function>oci_pconnect</function> employ a connection cache; if
|
||||
multiple calls to
|
||||
<function>oci_connect</function> use the same parameters in a given
|
||||
script, the second and subsequent calls return the existing
|
||||
connection handle. The cache used
|
||||
by <function>oci_connect</function> is cleaned up at the end of the
|
||||
script run, or when the connection handle is explicitly closed. The
|
||||
function <function>oci_pconnect</function> has similar behaviour,
|
||||
although its cache is maintained separately and survives between
|
||||
HTTP requests.
|
||||
</para>
|
||||
<para>
|
||||
This caching feature is important to remember, because it means the
|
||||
two handles are not transactionally isolated (they are in fact the
|
||||
same connection handle, so there is no isolation of any kind). If
|
||||
the application needs two separate, transactionally isolated
|
||||
connections, then use <function>oci_new_connect</function>.
|
||||
</para>
|
||||
<para>
|
||||
The function <function>oci_new_connect</function> always creates a
|
||||
new connection to the Oracle server, regardless of what other
|
||||
connections might already exist. High traffic web applications
|
||||
should try to avoid using
|
||||
<function>oci_new_connect</function>, especially in the busiest sections of
|
||||
the application.
|
||||
</para>
|
||||
<section>
|
||||
<title>Connection Functions</title>
|
||||
<para>
|
||||
The OCI8 extension provides three different functions for
|
||||
connecting to Oracle. The standard connection function
|
||||
is <function>oci_connect</function>. This creates a connection to
|
||||
an Oracle database and returns a resource used by subsequent
|
||||
database calls.
|
||||
</para>
|
||||
<para>
|
||||
Connecting to an Oracle server is a reasonably expensive operation
|
||||
in terms of the time that it takes to complete.
|
||||
The <function>oci_pconnect</function> function uses a persistent
|
||||
cache of connections that can be re-used across different script
|
||||
requests. This means that the connection overhead will typically
|
||||
only occur once per PHP process (or Apache child).
|
||||
</para>
|
||||
<para>
|
||||
If the application connects to Oracle using a different set of
|
||||
credentials for each web user, the persistent cache employed by
|
||||
<function>oci_pconnect</function> will become less useful as the
|
||||
number of concurrent users increases, to the point where it may
|
||||
start to adversely affect the overall performance of the Oracle
|
||||
server due to maintaining too many idle connections. If the
|
||||
application is structured in this way, it is recommended to either
|
||||
tune the application using
|
||||
the <link linkend="ini.oci8.max-persistent">oci8.max_persistent</link>
|
||||
and <link linkend="ini.oci8.persistent-timeout">oci8.persistent_timeout</link>
|
||||
configuration settings (these will give control over the persistent
|
||||
connection cache size and lifetime), use Oracle 11g Database
|
||||
Resident Connection Pooling, or use
|
||||
<function>oci_connect</function> instead.
|
||||
</para>
|
||||
<para>
|
||||
Both <function>oci_connect</function>
|
||||
and <function>oci_pconnect</function> employ a connection cache; if
|
||||
multiple calls to
|
||||
<function>oci_connect</function> use the same parameters in a given
|
||||
script, the second and subsequent calls return the existing
|
||||
connection handle. The cache used
|
||||
by <function>oci_connect</function> is cleaned up at the end of the
|
||||
script run, or when the connection handle is explicitly closed. The
|
||||
function <function>oci_pconnect</function> has similar behavior,
|
||||
although its cache is maintained separately and survives between
|
||||
HTTP requests.
|
||||
</para>
|
||||
<para>
|
||||
This caching feature means the two handles are not transactionally
|
||||
isolated (they are in fact the same connection handle, so there is
|
||||
no isolation of any kind). If the application needs two separate,
|
||||
transactionally isolated connections, then
|
||||
use <function>oci_new_connect</function>.
|
||||
</para>
|
||||
<para>
|
||||
The <function>oci_pconnect</function> cache is cleared and any
|
||||
database connections closed when the PHP process terminates, so
|
||||
effective use of persistent connections requires that PHP be an
|
||||
Apache module or used with FGCI, or similar. Persistent connections
|
||||
will not have any benefits over <function>oci_connect</function>
|
||||
when PHP is used with CGI or via the command-line.
|
||||
</para>
|
||||
<para>
|
||||
The function <function>oci_new_connect</function> always creates a
|
||||
new connection to the Oracle server, regardless of what other
|
||||
connections might already exist. High traffic web applications
|
||||
should avoid using
|
||||
<function>oci_new_connect</function>, especially in the busiest sections of
|
||||
the application.
|
||||
</para>
|
||||
</section>
|
||||
<section>
|
||||
<title>DRCP Connection Pooling</title>
|
||||
<para>
|
||||
PHP 5.3 (PECL OCI8 1.3) supports Oracle 11g Database Resident
|
||||
Connection Pooling (DRCP). DRCP allows more efficient use of
|
||||
database machine memory and provides high scalability. No, or
|
||||
minimal, application changes are needed to use DRCP.
|
||||
</para>
|
||||
<para>
|
||||
DRCP is suited for applications that connect using few database
|
||||
schemas and hold database connections open for a short period of
|
||||
time. Other applications should use Oracle's
|
||||
default <literal>Dedicated</literal> database server processes, or
|
||||
use <literal>Shared</literal> servers.
|
||||
</para>
|
||||
<para>
|
||||
DRCP benefits all three connection functions, but gives the highest
|
||||
scalability when connections are created
|
||||
with <function>oci_pconnect</function>.
|
||||
</para>
|
||||
<para>
|
||||
For DRCP to be available in OCI8, Oracle client libraries used by
|
||||
PHP and the version of the Oracle Database must both be 11g.
|
||||
</para>
|
||||
<para>
|
||||
Documentation on DRCP is found in several Oracle manuals. For
|
||||
example,
|
||||
see <link xlink:href="&url.oracle.drcp.configure;">Configuring
|
||||
Database Resident Connection Pooling</link> in the Oracle
|
||||
documentation for usage information.
|
||||
A <link xlink:href="&url.oracle.drcp.whitepaper;">DRCP
|
||||
white paper</link> contains background information on DRCP.
|
||||
</para>
|
||||
<para>
|
||||
To use DRCP, build PHP with the OCI8 1.3 extension and Oracle 11g
|
||||
libraries and then follow these steps:
|
||||
</para>
|
||||
<para>
|
||||
<itemizedlist>
|
||||
<listitem>
|
||||
<para>
|
||||
As a privileged database administrator, use a program like
|
||||
SQL*Plus to start the connection pool in the database:
|
||||
</para>
|
||||
<para>
|
||||
<informalexample>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
SQL> execute dbms_connection_pool.start_pool;
|
||||
]]>
|
||||
</screen>
|
||||
</informalexample>
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<para>
|
||||
Optionally
|
||||
use <literal>dbms_connection_pool.alter_param()</literal> to
|
||||
configure DRCP settings. The current pool settings can be
|
||||
queried from the <literal>DBA_CPOOL_INFO</literal> view.
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<para>
|
||||
Update the connection strings used. For PHP applications that
|
||||
currently connect using a Network Alias like:
|
||||
</para>
|
||||
<para>
|
||||
<informalexample>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
$c = oci_pconnect("myuser", "mypassword", "MYDB");
|
||||
]]>
|
||||
</screen>
|
||||
</informalexample>
|
||||
</para>
|
||||
<para>
|
||||
modify the tnsnames.ora file and add
|
||||
a <literal>(SERVER=POOLED)</literal> clause, for example:
|
||||
</para>
|
||||
<para>
|
||||
<informalexample>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
MYDB = (DESCRIPTION=(ADDRESS=(PROTOCOL=tcp) (HOST=myhost.dom.com)
|
||||
(PORT=1521))(CONNECT_DATA=(SERVICE_NAME=sales)
|
||||
(SERVER=POOLED)))
|
||||
]]>
|
||||
</screen>
|
||||
</informalexample>
|
||||
</para>
|
||||
<para>
|
||||
Alternatively, modify the Easy Connect syntax in PHP and add
|
||||
<literal>:POOLED</literal> after the service name:
|
||||
</para>
|
||||
<para>
|
||||
<informalexample>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
$c = oci_pconnect("myuser", "mypassword", "myhost.dom.com:1521/sales:POOLED");
|
||||
]]>
|
||||
</screen>
|
||||
</informalexample>
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<para>
|
||||
Edit &php.ini; and choose a connection class name. This name
|
||||
indicates a logical division of the connection pool and can be
|
||||
used to isolate pooling for separate applications. Any PHP
|
||||
applications with the same user name and connection class value
|
||||
will be able to share connections in the pool, giving greater
|
||||
scalability.
|
||||
</para>
|
||||
<para>
|
||||
<informalexample>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
oci8.connection_class = "MY_APPLICATION_NAME"
|
||||
]]>
|
||||
</screen>
|
||||
</informalexample>
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<para>
|
||||
Run the application, connecting to the 11g database.
|
||||
</para>
|
||||
</listitem>
|
||||
</itemizedlist>
|
||||
</para>
|
||||
<note>
|
||||
<para>
|
||||
Applications using Oracle 10g that require the performance of
|
||||
persistent connections can reduce the amount of database server
|
||||
memory needed by using Oracle <literal>Shared</literal> servers
|
||||
(previously known as Multi Threaded Servers). Refer to Oracle
|
||||
documentation for information.
|
||||
</para>
|
||||
</note>
|
||||
</section>
|
||||
<section>
|
||||
<title>DRCP Recommendations and Known Limitations</title>
|
||||
<para>
|
||||
Changing a password over DRCP connections will fail with the error
|
||||
<emphasis>ORA-56609: Usage not supported with DRCP</emphasis>.
|
||||
This is a documented restriction of Oracle Database 11g.
|
||||
</para>
|
||||
<para>
|
||||
With the OCI8 1.3 extension, persistent connections can now be
|
||||
closed by the user, allowing greater control over connection
|
||||
resource usage. Persistent connections will now also be closed
|
||||
automatically when there is no PHP variable referencing them, such
|
||||
as at the end of scope of a PHP user function. This will rollback
|
||||
any uncommitted transaction. These changes to persistent
|
||||
connections make them behave similarly to non-persistent
|
||||
connections, simplifying the interface, allowing for greater
|
||||
application consistency and predictability. Use
|
||||
<emphasis>oci8.old_oci_close_semantics = On</emphasis> to retain the
|
||||
historical behavior.
|
||||
</para>
|
||||
<para>
|
||||
If the Oracle Database is version 11.1.0.6, then the Oracle
|
||||
database patch for Oracle bug 6474441 must be applied to use DRCP.
|
||||
Without this patch, errors such as <emphasis>ORA-01000: maximum
|
||||
open cursors exceeded</emphasis>, <emphasis>ORA-01001 invalid
|
||||
cursor</emphasis> or <emphasis>ORA-01002 fetch out of
|
||||
sequence</emphasis> may occur. This bug was fixed in Oracle
|
||||
11.1.0.7 onwards.
|
||||
</para>
|
||||
<para>
|
||||
If the Oracle 11.1.0.6 database patch cannot be applied, one of the
|
||||
following three workarounds can be used instead:
|
||||
</para>
|
||||
<para>
|
||||
<itemizedlist>
|
||||
<listitem>
|
||||
<simpara>
|
||||
Connect using Oracle <literal>Dedicated</literal>
|
||||
or <literal>Shared</literal> servers instead of DRCP.
|
||||
</simpara>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<simpara>
|
||||
Set PHP's <link linkend="ini.oci8.statement-cache-size">oci8.statement_cache_size</link>
|
||||
to 0.
|
||||
</simpara>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<simpara>
|
||||
Set an event in the database initialization parameter file:
|
||||
<emphasis>event="56699 trace name context forever, level 128"</emphasis>.
|
||||
</simpara>
|
||||
</listitem>
|
||||
</itemizedlist>
|
||||
</para>
|
||||
<para>
|
||||
Oracle Database 11.1.0.7 and the Oracle Database 11.1.0.6 patch for
|
||||
Oracle bug 6474441 allow PHP applications with DRCP connection to
|
||||
use a database <literal>LOGON</literal> trigger to set session
|
||||
properties at the time of session creation. Examples of such
|
||||
settings are the NLS language and the date format.
|
||||
</para>
|
||||
<para>
|
||||
If the Oracle 11.1.0.6 database patch cannot be applied, one of the
|
||||
following workarounds can be used instead
|
||||
of using <literal>LOGON</literal> triggers:
|
||||
</para>
|
||||
<para>
|
||||
<itemizedlist>
|
||||
<listitem>
|
||||
<simpara>
|
||||
After logon, explicitly set the session properties using PHP
|
||||
application code.
|
||||
</simpara>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<simpara>
|
||||
Connect using Oracle <literal>Dedicated</literal>
|
||||
or <literal>Shared</literal> servers instead of DRCP.
|
||||
</simpara>
|
||||
</listitem>
|
||||
</itemizedlist>
|
||||
</para>
|
||||
<para>
|
||||
The automatic re-establishment of PHP persistent connections after
|
||||
an Apache or FGCI process respawns means <literal>LOGON</literal>
|
||||
triggers in PHP are only recommended for setting session attributes
|
||||
and not for per-application user connection requests. This is even
|
||||
more so with DRCP due to the automatic pool sizing and with the
|
||||
way <literal>LOGON</literal> triggers fire with DRCP
|
||||
authentication.
|
||||
</para>
|
||||
</section>
|
||||
<section>
|
||||
<title>Fast Application Notification (FAN) Support</title>
|
||||
<para>
|
||||
FAN support gives fast connection failover, a high availability
|
||||
feature. This allows PHP OCI8 scripts to be notified when a
|
||||
database machine or database instance becomes unavailable. Without
|
||||
FAN, OCI8 can hang until a TCP timeout occurs and an error is
|
||||
returned, which might be several minutes. Enabling FAN in OCI8 can
|
||||
allow applications to detect errors and re-connect to an available
|
||||
database instance without the web user being aware of an outage.
|
||||
</para>
|
||||
<para>
|
||||
FAN support is available when the Oracle client libraries that PHP
|
||||
links with and the Oracle Database are either version 10gR2 or 11g.
|
||||
</para>
|
||||
<para>
|
||||
FAN benefits users of Oracle's clustering technology (RAC) because
|
||||
connections to surviving database instances can be immediately
|
||||
made. Users of Oracle's Data Guard with a broker will see the FAN
|
||||
events generated when the standby database goes online. Standalone
|
||||
databases will send FAN events when the database restarts.
|
||||
</para>
|
||||
<para>
|
||||
For active connections, when a machine or database instance becomes
|
||||
unavailable, a connection failure error will be returned by the
|
||||
OCI8 extension function currently being called. On a subsequent
|
||||
PHP script re-connect, a connection to a surviving database
|
||||
instance will be established. The OCI8 extension also
|
||||
transparently cleans up any idle connections affected by a database
|
||||
machine or instance failure so PHP connect calls will establish a
|
||||
fresh connection without the script being aware of any service
|
||||
disruption.
|
||||
</para>
|
||||
<para>
|
||||
When <link linkend="ini.oci8.events">oci8.events</link>
|
||||
is <literal>On</literal>, it is suggested to
|
||||
set <link linkend="ini.oci8.ping-interval">oci8.ping_interval</link>
|
||||
to -1 to disable pinging, since enabling FAN events provide
|
||||
pro-active connection management of idle connections made invalid
|
||||
by a service disruption.
|
||||
</para>
|
||||
<para>
|
||||
To enable FAN support in PHP, build PHP with Oracle 10gR2 or 11g
|
||||
libraries and then follow these steps:
|
||||
</para>
|
||||
<para>
|
||||
<itemizedlist>
|
||||
<listitem>
|
||||
<simpara>
|
||||
As a privileged database administrator, use a program like
|
||||
SQL*Plus to enable the database service to post FAN events, for
|
||||
example:
|
||||
</simpara>
|
||||
<para>
|
||||
<informalexample>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
SQL> execute dbms_service.modify_service(
|
||||
SERVICE_NAME => 'sales',
|
||||
AQ_HA_NOTIFICATIONS => TRUE);
|
||||
]]>
|
||||
</screen>
|
||||
</informalexample>
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<simpara>
|
||||
Edit php.ini and add
|
||||
</simpara>
|
||||
<para>
|
||||
<informalexample>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
oci8.events = On
|
||||
]]>
|
||||
</screen>
|
||||
</informalexample>
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<simpara>
|
||||
If the application does not already handle OCI8 error
|
||||
conditions, modify it to detect failures and take appropriate
|
||||
action. This may include re-connecting and re-executing
|
||||
statements.
|
||||
</simpara>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<simpara>
|
||||
Run the application, connecting to an Oracle 10gR2 or 11g database.
|
||||
</simpara>
|
||||
</listitem>
|
||||
</itemizedlist>
|
||||
</para>
|
||||
</section>
|
||||
</chapter>
|
||||
|
||||
<!-- Keep this comment at the end of the file
|
||||
|
|
Loading…
Reference in a new issue