aboutsummaryrefslogtreecommitdiffstats
path: root/phpBB/includes
diff options
context:
space:
mode:
authorDavid M <davidmj@users.sourceforge.net>2007-06-07 05:58:45 +0000
committerDavid M <davidmj@users.sourceforge.net>2007-06-07 05:58:45 +0000
commitdd9c236e6a47fb93d2f39f746f2bac5efc62066d (patch)
treeda04db2d671b6c83f434b8097d99e1ab23e53eea /phpBB/includes
parent5e78e5ad95fb8608d693f8f6b5ac075cbe072e07 (diff)
downloadforums-dd9c236e6a47fb93d2f39f746f2bac5efc62066d.tar
forums-dd9c236e6a47fb93d2f39f746f2bac5efc62066d.tar.gz
forums-dd9c236e6a47fb93d2f39f746f2bac5efc62066d.tar.bz2
forums-dd9c236e6a47fb93d2f39f746f2bac5efc62066d.tar.xz
forums-dd9c236e6a47fb93d2f39f746f2bac5efc62066d.zip
- Oracle, woe is you... I will say this much, this fixes Oracle's handling of empty strings... We also fix custom profiles and now provide database size for Oracle...
git-svn-id: file:///svn/phpbb/trunk@7721 89ea8834-ac86-4346-8a33-228a782c2dd0
Diffstat (limited to 'phpBB/includes')
-rw-r--r--phpBB/includes/acp/acp_profile.php2
-rw-r--r--phpBB/includes/db/oracle.php114
-rw-r--r--phpBB/includes/functions_admin.php8
3 files changed, 119 insertions, 5 deletions
diff --git a/phpBB/includes/acp/acp_profile.php b/phpBB/includes/acp/acp_profile.php
index da11868cc2..2d4091f2f9 100644
--- a/phpBB/includes/acp/acp_profile.php
+++ b/phpBB/includes/acp/acp_profile.php
@@ -1508,7 +1508,7 @@ class acp_profile
case 'oracle':
// We are defining the biggest common value, because of the possibility to edit the min/max values of each field.
- $sql = 'ALTER TABLE ' . PROFILE_FIELDS_DATA_TABLE . " ADD \"$field_ident\" ";
+ $sql = 'ALTER TABLE ' . PROFILE_FIELDS_DATA_TABLE . " ADD $field_ident ";
switch ($field_type)
{
diff --git a/phpBB/includes/db/oracle.php b/phpBB/includes/db/oracle.php
index 360928e96d..c0d960506d 100644
--- a/phpBB/includes/db/oracle.php
+++ b/phpBB/includes/db/oracle.php
@@ -48,7 +48,7 @@ class dbal_oracle extends dbal
$connect = $sqlserver . (($port) ? ':' . $port : '') . '/' . $database;
}
- $this->db_connect_id = ($new_link) ? @ocinlogon($this->user, $sqlpassword, $connect, 'UTF8') : (($this->persistency) ? @ociplogon($this->user, $sqlpassword, $connect, 'UTF8') : @ocinlogon($this->user, $sqlpassword, $connect, 'UTF8'));
+ $this->db_connect_id = ($new_link) ? @ocinlogon($this->user, $sqlpassword, $connect, 'UTF8') : (($this->persistency) ? @ociplogon($this->user, $sqlpassword, $connect, 'UTF8') : @ocilogon($this->user, $sqlpassword, $connect, 'UTF8'));
return ($this->db_connect_id) ? $this->db_connect_id : $this->sql_error('');
}
@@ -86,6 +86,90 @@ class dbal_oracle extends dbal
}
/**
+ * Oracle specific code to handle the fact that it does not compare columns properly
+ * @access private
+ */
+ function _rewrite_col_compare($args)
+ {
+ if (sizeof($args) == 4)
+ {
+ if ($args[2] == '=')
+ {
+ return '(' . $args[0] . ' OR (' . $args[1] . ' is NULL AND ' . $args[3] . ' is NULL))';
+ }
+ else if ($args[2] == '<>')
+ {
+ // really just a fancy way of saying foo <> bar or (foo is NULL XOR bar is NULL) but SQL has no XOR :P
+ return '(' . $args[0] . ' OR ((' . $args[1] . ' is NULL AND ' . $args[3] . ' is NOT NULL) OR (' . $args[1] . ' is NOT NULL AND ' . $args[3] . ' is NULL)))';
+ }
+ }
+ else
+ {
+ return $this->_rewrite_where($args[0]);
+ }
+ }
+
+ /**
+ * Oracle specific code to handle it's lack of sanity
+ * @access private
+ */
+ function _rewrite_where($where_clause)
+ {
+ preg_match_all('/\s*(AND|OR)?\s*([\w_.]++)\s*(?:(=|<>)\s*((?>\'(?>[^\']++|\'\')*+\'|\d+))|((NOT )?IN\s*\((?>\'(?>[^\']++|\'\')*+\',? ?|\d+,? ?)*+\)))/', $where_clause, $result, PREG_SET_ORDER);
+ $out = '';
+ foreach ($result as $val)
+ {
+ if (!isset($val[5]))
+ {
+ if ($val[4] !== "''")
+ {
+ $out .= $val[0];
+ }
+ else
+ {
+ $out .= ' ' . $val[1] . ' ' . $val[2];
+ if ($val[3] == '=')
+ {
+ $out .= ' is NULL';
+ }
+ else if ($val[3] == '<>')
+ {
+ $out .= ' is NOT NULL';
+ }
+ }
+ }
+ else
+ {
+ $in_clause = array();
+ $sub_exp = substr($val[5], strpos($val[5], '(') + 1, -1);
+ $extra = false;
+ preg_match_all('/\'(?>[^\']++|\'\')*+\'|\d++/', $sub_exp, $sub_vals, PREG_PATTERN_ORDER);
+ foreach ($sub_vals[0] as $sub_val)
+ {
+ if ($sub_val !== "''")
+ {
+ $in_clause[] = $sub_val;
+ }
+ else
+ {
+ $extra = true;
+ }
+ }
+ if (!$extra)
+ {
+ $out .= $val[0];
+ }
+ else
+ {
+ $out .= ' ' . $val[1] . ' (' . $val[2]. ' ' . (isset($val[6]) ? $val[6] : '') . 'IN(' . implode(', ', $in_clause) . ') OR ' . $val[2] . ' is ' . (isset($val[6]) ? $val[6] : '') . 'NULL)';
+ }
+ }
+ }
+
+ return $out;
+ }
+
+ /**
* Base query method
*
* @param string $query Contains the SQL query which shall be executed
@@ -127,7 +211,6 @@ class dbal_oracle extends dbal
// We overcome Oracle's 4000 char limit by binding vars
if (strlen($query) > 4000)
{
-
if (preg_match('/^(INSERT INTO[^(]+)\\(([^()]+)\\) VALUES[^(]+\\((.*?)\\)$/s', $query, $regs))
{
if (strlen($regs[3]) > 4000)
@@ -151,13 +234,13 @@ class dbal_oracle extends dbal
unset($art);
}
}
- else if (preg_match_all('/^(UPDATE [\\w_]++\\s+SET )(\\w+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+)(?:, \\w+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+))*+)\\s+(WHERE.*)$/s', $query, $data, PREG_SET_ORDER))
+ else if (preg_match_all('/^(UPDATE [\\w_]++\\s+SET )([\\w_]+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+)(?:, [\\w_]+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+))*+)\\s+(WHERE.*)$/s', $query, $data, PREG_SET_ORDER))
{
if (strlen($data[0][2]) > 4000)
{
$update = $data[0][1];
$where = $data[0][3];
- preg_match_all('/(\\w++) = (\'(?:[^\']++|\'\')*+\'|\\d++)/', $data[0][2], $temp, PREG_SET_ORDER);
+ preg_match_all('/([\\w_]++) = (\'(?:[^\']++|\'\')*+\'|\\d++)/', $data[0][2], $temp, PREG_SET_ORDER);
unset($data);
$art = array();
@@ -180,6 +263,29 @@ class dbal_oracle extends dbal
}
}
+ switch (substr($query, 0, 6))
+ {
+ case 'DELETE':
+ if (preg_match('/^(DELETE FROM [\w_]++ WHERE)((?:\s*(?:AND|OR)?\s*[\w_]+\s*(?:(?:=|<>)\s*(?>\'(?>[^\']++|\'\')*+\'|\d+)|(?:NOT )?IN\s*\((?>\'(?>[^\']++|\'\')*+\',? ?|\d+,? ?)*+\)))*+)$/', $query, $regs))
+ {
+ $query = $regs[1] . $this->_rewrite_where($regs[2]);
+ unset($regs);
+ }
+ break;
+
+ case 'UPDATE':
+ if (preg_match('/^(UPDATE [\\w_]++\\s+SET [\\w_]+\s*=\s*(?:\'(?:[^\']++|\'\')*+\'|\\d++|:\w++)(?:, [\\w_]+\s*=\s*(?:\'(?:[^\']++|\'\')*+\'|\\d++|:\w++))*+\\s+WHERE)(.*)$/s', $query, $regs))
+ {
+ $query = $regs[1] . $this->_rewrite_where($regs[2]);
+ unset($regs);
+ }
+ break;
+
+ case 'SELECT':
+ $query = preg_replace_callback('/([\w_.]++)\s*(?:(=|<>)\s*(?>\'(?>[^\']++|\'\')*+\'|\d++|([\w_.]++))|(?:NOT )?IN\s*\((?>\'(?>[^\']++|\'\')*+\',? ?|\d++,? ?)*+\))/', array($this, '_rewrite_col_compare'), $query);
+ break;
+ }
+
$this->query_result = @ociparse($this->db_connect_id, $query);
foreach ($array as $key => $value)
diff --git a/phpBB/includes/functions_admin.php b/phpBB/includes/functions_admin.php
index 3a24c5db1c..28a5ab9983 100644
--- a/phpBB/includes/functions_admin.php
+++ b/phpBB/includes/functions_admin.php
@@ -2824,6 +2824,14 @@ function get_database_size()
$database_size = $row['size'];
}
break;
+
+ case 'oracle':
+ $sql = 'SELECT SUM(bytes) as dbsize
+ FROM user_segments';
+ $result = $db->sql_query($sql);
+ $database_size = ($row = $db->sql_fetchrow($result)) ? $row['dbsize'] : false;
+ $db->sql_freeresult($result);
+ break;
}
if ($database_size !== false)