/** * Create a PostgreSQL Server Custom Connection. * This MUST NOT be used with the default connection ... as that is handled automatically. * * @param STRING $yhost :: db host * @param STRING $yport :: db port * @param STRING $ydb :: db name * @param STRING $yuser :: db user * @param STRING $ypass :: db pass * @param INTEGER $ytimeout :: connection timeout * @param ENUM $y_transact_mode :: transactional mode ('READ COMMITTED' | 'REPEATABLE READ' | 'SERIALIZABLE' | '' to leave it as default) * @param FLOAT $y_debug_sql_slowtime :: debug query slow time * @param ENUM $y_type :: server type: postgresql or pgpool2 * * @return RESOURCE :: the postgresql connection resource ID * * @access private * @internal * */ public static function server_connect($yhost, $yport, $ydb, $yuser, $ypass, $ytimeout, $y_transact_mode = '', $y_debug_sql_slowtime = 0, $y_type = 'postgresql') { //-- if (defined('SMART_FRAMEWORK_DBSQL_CHARSET')) { if ((string) SMART_FRAMEWORK_DBSQL_CHARSET != 'UTF8') { die('The SMART_FRAMEWORK_DBSQL_CHARSET must be set as: UTF8'); } //end if } else { die('The SMART_FRAMEWORK_DBSQL_CHARSET must be set ...'); } //end if else //-- //-- if (!function_exists('pg_connect')) { self::error('[PRE-CONNECT]', 'PHP-PgSQL', 'Check PgSQL PHP Extension', 'PHP Extension is required to run this software !', 'Cannot find PgSQL PHP Extension'); return; } //end if //-- if ((string) ini_get('pgsql.ignore_notice') != '0') { // {{{SYNC-PGSQL-NOTIF-CHECK}}} self::error('[PRE-CONNECT]', 'PHP-Inits-PgSQL', 'Check PgSQL PHP.INI Settings', 'SETTINGS: PostgreSQL Notifications need to be ENABLED in PHP.INI !', 'SET in PHP.INI this: pgsql.ignore_notice = 0'); return; } //end if //-- //-- connection timeout $timeout = (int) $ytimeout; //-- if ($timeout < 1) { $timeout = 1; } //end if if ($timeout > 60) { $timeout = 60; } //end if //-- //-- debug settings if ((string) SMART_FRAMEWORK_DEBUG_MODE == 'yes') { //-- $y_debug_sql_slowtime = (double) $y_debug_sql_slowtime; if ($y_debug_sql_slowtime <= 0) { $y_debug_sql_slowtime = (double) self::$slow_time; } //end if //-- if ($y_debug_sql_slowtime < 1.0E-7) { $y_debug_sql_slowtime = 1.0E-7; } elseif ($y_debug_sql_slowtime > 0.9999999000000001) { $y_debug_sql_slowtime = 0.9999999000000001; } //end if //-- self::$slow_time = (double) $y_debug_sql_slowtime; // update //-- } //end if //-- //-- debug inits if ((string) SMART_FRAMEWORK_DEBUG_MODE == 'yes') { SmartFrameworkRegistry::setDebugMsg('db', 'pgsql|slow-time', number_format(self::$slow_time, 7, '.', ''), '='); SmartFrameworkRegistry::setDebugMsg('db', 'pgsql|log', ['type' => 'metainfo', 'data' => 'Database Server: PgSQL (' . $y_type . ') / App Connector Version: ' . SMART_FRAMEWORK_VERSION . ' / Connection Charset: ' . SMART_FRAMEWORK_DBSQL_CHARSET]); SmartFrameworkRegistry::setDebugMsg('db', 'pgsql|log', ['type' => 'metainfo', 'data' => 'Connection Timeout: ' . $timeout . ' seconds / Fast Query Reference Time < ' . self::$slow_time . ' seconds']); } //end if //-- //-- if ((string) $ypass != '') { $password = (string) base64_decode((string) $ypass); } else { $password = ''; } //end if else //-- //-- {{{SYNC-CONNECTIONS-IDS}}} $the_conn_key = (string) $yhost . ':' . $yport . '@' . $ydb . '#' . $yuser . '>' . trim(strtoupper(str_replace(' ', '', (string) $y_transact_mode))) . '.'; //-- $connection = @pg_connect('host=' . $yhost . ' port=' . $yport . ' dbname=' . $ydb . ' user='******' password='******' connect_timeout=' . $timeout); // @pg_close($connection) (if is resource) ; but reusing connections policy dissalow disconnects //-- if (!is_resource($connection)) { self::error($yhost . ':' . $yport . '@' . $ydb . '#' . $yuser, 'Connection', 'Connect to PgSQL Server', 'NO CONNECTION !!!', 'Connection Failed to PgSQL Server !'); return; } //end if //-- if ((string) SMART_FRAMEWORK_DEBUG_MODE == 'yes') { SmartFrameworkRegistry::setDebugMsg('db', 'pgsql|log', ['type' => 'open-close', 'data' => 'Connected to PgSQL Server: ' . $the_conn_key, 'connection' => (string) $connection]); } //end if //-- //-- @pg_set_error_verbosity($connection, PGSQL_ERRORS_DEFAULT); // this must be reset to PGSQL_ERRORS_DEFAULT and must NOT use PGSQL_ERRORS_VERBOSE because will affect write-igdata notice messages //-- $tmp_pg_tracefile = 'tmp/logs/pgsql-trace.log'; //-- if ((string) SMART_FRAMEWORK_DEBUG_MODE == 'yes') { //-- if (defined('SMART_FRAMEWORK_DEBUG_SQL_TRACE')) { if (function_exists('pg_trace')) { @pg_trace($tmp_pg_tracefile, 'w', $connection); // pg_trace can cause some PHP versions to crash (Ex: Debian 6.0.6 with PHP 5.3 / Apache 2.0.x) } //end if } //end if //-- } //end if else //-- //-- $result = @pg_query_params($connection, 'SELECT pg_encoding_to_char("encoding") FROM "pg_database" WHERE "datname" = $1', array($ydb)); if (!$result) { self::error($connection, 'Encoding-Charset', 'Check Query Failed', 'Error=' . @pg_last_error($connection), 'DB=' . $ydb); return; } //end if $server_encoding = @pg_fetch_row($result); if (trim($server_encoding[0]) != trim(SMART_FRAMEWORK_DBSQL_CHARSET)) { self::error($connection, 'Encoding-Get-Charset', 'Wrong Server Encoding on PgSQL Server', 'Server=' . $server_encoding[0], 'Client=' . SMART_FRAMEWORK_DBSQL_CHARSET); return; } //end if @pg_free_result($result); //-- //-- $encoding = @pg_set_client_encoding($connection, SMART_FRAMEWORK_DBSQL_CHARSET); //-- if ($encoding < 0 or (string) @pg_client_encoding() != (string) SMART_FRAMEWORK_DBSQL_CHARSET) { self::error($connection, 'Encoding-Check-Charset', 'Failed to set Client Encoding on PgSQL Server', 'Server=' . SMART_FRAMEWORK_DBSQL_CHARSET, 'Client=' . @pg_client_encoding()); return; } //end if //-- if ((string) SMART_FRAMEWORK_DEBUG_MODE == 'yes') { SmartFrameworkRegistry::setDebugMsg('db', 'pgsql|log', ['type' => 'set', 'data' => 'SET Client Encoding [+check] to: ' . @pg_client_encoding(), 'connection' => (string) $connection, 'skip-count' => 'yes']); } //end if //-- //-- $transact = strtoupper((string) $y_transact_mode); switch ((string) $transact) { case 'SERIALIZABLE': case 'REPEATABLE READ': case 'READ COMMITTED': //-- $result = @pg_query($connection, 'SET SESSION CHARACTERISTICS AS TRANSACTION ISOLATION LEVEL ' . $transact); if (!$result) { self::error($connection, 'Set-Session-Transaction-Level', 'Failed to Set Session Transaction Level as ' . $transact, 'Error=' . @pg_last_error($connection), 'DB=' . $ydb); return; } //end if @pg_free_result($result); //-- $result = @pg_query('SHOW transaction_isolation'); $chk = @pg_fetch_row($result); if ((string) trim($chk[0]) == '' or (string) $transact != (string) strtoupper(trim($chk[0]))) { self::error($connection, 'Check-Session-Transaction-Level', 'Failed to Set Session Transaction Level as ' . $transact, 'Error=' . @pg_last_error($connection), 'DB=' . $ydb); return; } //end if if ((string) SMART_FRAMEWORK_DEBUG_MODE == 'yes') { SmartFrameworkRegistry::setDebugMsg('db', 'pgsql|log', ['type' => 'set', 'data' => 'SET Session Transaction Isolation Level [+check] to: ' . strtoupper($chk[0]), 'connection' => (string) $connection, 'skip-count' => 'yes']); } //end if @pg_free_result($result); //-- break; default: // LEAVE THE SESSION TRANSACTION AS SET IN CFG } //end switch //-- //-- export only at the end (after all settings) SmartFrameworkRegistry::$Connections['pgsql'][(string) $the_conn_key] = $connection; // export connection //-- //-- OUTPUT return $connection; //-- OUTPUT }