Removed legacy methods from DB and DBCubrid classes.

Added Query object to hold together query parts. 
Updated structure of query cache file to return Query object. 
Added support for array query arguments - used in the IN clause.

git-svn-id: http://xe-core.googlecode.com/svn/branches/1.5.0-DB@8438 201d5d3c-b55e-5fd7-737f-ddc643e51545
This commit is contained in:
ucorina 2011-06-02 13:06:08 +00:00
parent c384f6c753
commit 0cd318fcf5
9 changed files with 210 additions and 891 deletions

View file

@ -17,17 +17,6 @@
var $count_cache_path = 'files/cache/db';
var $cond_operation = array( ///< operations for condition
'equal' => '=',
'more' => '>=',
'excess' => '>',
'less' => '<=',
'below' => '<',
'notequal' => '<>',
'notnull' => 'is not null',
'null' => 'is null',
);
var $fd = NULL; ///< connector resource or file description
var $result = NULL; ///< result
@ -328,15 +317,15 @@
require_once(_XE_PATH_.'classes/db/queryparts/expression/StarExpression.class.php');
require_once(_XE_PATH_.'classes/db/queryparts/order/OrderByColumn.class.php');
require_once(_XE_PATH_.'classes/db/queryparts/limit/Limit.class.php');
require_once(_XE_PATH_.'classes/db/queryparts/Query.class.php');
$output = include($cache_file);
if( (is_a($output, 'Object') || is_subclass_of($output, 'Object')) && !$output->toBool()) return $output;
$output->_tables = ($output->_tables && is_array($output->_tables)) ? $output->_tables : array();
// execute appropriate query
switch($output->action) {
switch($output->getAction()) {
case 'insert' :
$this->resetCountCache($output->tables);
$output = $this->_executeInsertAct($output);
@ -350,6 +339,7 @@
$output = $this->_executeDeleteAct($output);
break;
case 'select' :
// TODO Add property for Query object for Arg_columns
$output->arg_columns = is_array($arg_columns)?$arg_columns:array();
$output = $this->_executeSelectAct($output);
break;
@ -363,232 +353,6 @@
return $output;
}
/**
* @brief check $val with $filter_type
* @param[in] $key key value
* @param[in] $val value of $key
* @param[in] $filter_type type of filter to check $val
* @return object
* @remarks this function is to be used from XmlQueryParser
**/
function checkFilter($key, $val, $filter_type) {
global $lang;
switch($filter_type) {
case 'email' :
case 'email_address' :
if(!preg_match('/^[_0-9a-z-]+(\.[_0-9a-z-]+)*@[0-9a-z-]+(\.[0-9a-z-]+)*$/is', $val)) return new Object(-1, sprintf($lang->filter->invalid_email, $lang->{$key} ? $lang->{$key} : $key));
break;
case 'homepage' :
if(!preg_match('/^(http|https)+(:\/\/)+[0-9a-z_-]+\.[^ ]+$/is', $val)) return new Object(-1, sprintf($lang->filter->invalid_homepage, $lang->{$key} ? $lang->{$key} : $key));
break;
case 'userid' :
case 'user_id' :
if(!preg_match('/^[a-zA-Z]+([_0-9a-zA-Z]+)*$/is', $val)) return new Object(-1, sprintf($lang->filter->invalid_userid, $lang->{$key} ? $lang->{$key} : $key));
break;
case 'number' :
case 'numbers' :
if(is_array($val)) $val = join(',', $val);
if(!preg_match('/^(-?)[0-9]+(,\-?[0-9]+)*$/is', $val)) return new Object(-1, sprintf($lang->filter->invalid_number, $lang->{$key} ? $lang->{$key} : $key));
break;
case 'alpha' :
if(!preg_match('/^[a-z]+$/is', $val)) return new Object(-1, sprintf($lang->filter->invalid_alpha, $lang->{$key} ? $lang->{$key} : $key));
break;
case 'alpha_number' :
if(!preg_match('/^[0-9a-z]+$/is', $val)) return new Object(-1, sprintf($lang->filter->invalid_alpha_number, $lang->{$key} ? $lang->{$key} : $key));
break;
}
return new Object();
}
/**
* @brief returns type of column
* @param[in] $column_type_list list of column type
* @param[in] $name name of column type
* @return column type of $name
* @remarks columns are usually like a.b, so it needs another function
**/
function getColumnType($column_type_list, $name) {
if(strpos($name, '.') === false) return $column_type_list[$name];
list($prefix, $name) = explode('.', $name);
return $column_type_list[$name];
}
/**
* @brief returns the value of condition
* @param[in] $name name of condition
* @param[in] $value value of condition
* @param[in] $operation operation this is used in condition
* @param[in] $type type of condition
* @param[in] $column_type type of column
* @return well modified $value
* @remarks if $operation is like or like_prefix, $value itself will be modified
* @remarks if $type is not 'number', call addQuotes() and wrap with ' '
**/
function getConditionValue($name, $value, $operation, $type, $column_type) {
if(!in_array($operation,array('in','notin','between')) && $type == 'number') {
if(is_array($value)){
$value = join(',',$value);
}
if(strpos($value, ',') === false && strpos($value, '(') === false) return (int)$value;
return $value;
}
if(!is_array($value) && strpos($name, '.') !== false && strpos($value, '.') !== false) {
list($table_name, $column_name) = explode('.', $value);
if($column_type[$column_name]) return $value;
}
switch($operation) {
case 'like_prefix' :
if(!is_array($value)) $value = preg_replace('/(^\'|\'$){1}/', '', $value);
$value = $value.'%';
break;
case 'like_tail' :
if(!is_array($value)) $value = preg_replace('/(^\'|\'$){1}/', '', $value);
$value = '%'.$value;
break;
case 'like' :
if(!is_array($value)) $value = preg_replace('/(^\'|\'$){1}/', '', $value);
$value = '%'.$value.'%';
break;
case 'notin' :
if(is_array($value))
{
$value = $this->addQuotesArray($value);
if($type=='number') return join(',',$value);
else return "'". join("','",$value)."'";
}
else
{
return $value;
}
break;
case 'in' :
if(is_array($value))
{
$value = $this->addQuotesArray($value);
if($type=='number') return join(',',$value);
else return "'". join("','",$value)."'";
}
else
{
return $value;
}
break;
case 'between' :
if(!is_array($value)) $value = array($value);
$value = $this->addQuotesArray($value);
if($type!='number')
{
foreach($value as $k=>$v)
{
$value[$k] = "'".$v."'";
}
}
return $value;
break;
default:
if(!is_array($value)) $value = preg_replace('/(^\'|\'$){1}/', '', $value);
}
return "'".$this->addQuotes($value)."'";
}
/**
* @brief returns part of condition
* @param[in] $name name of condition
* @param[in] $value value of condition
* @param[in] $operation operation that is used in condition
* @return detail condition
**/
function getConditionPart($name, $value, $operation) {
switch($operation) {
case 'equal' :
case 'more' :
case 'excess' :
case 'less' :
case 'below' :
case 'like_tail' :
case 'like_prefix' :
case 'like' :
case 'in' :
case 'notin' :
case 'notequal' :
// if variable is not set or is not string or number, return
if(!isset($value)) return;
if($value === '') return;
if(!in_array(gettype($value), array('string', 'integer'))) return;
break;
case 'between' :
if(!is_array($value)) return;
if(count($value)!=2) return;
}
switch($operation) {
case 'equal' :
return $name.' = '.$value;
break;
case 'more' :
return $name.' >= '.$value;
break;
case 'excess' :
return $name.' > '.$value;
break;
case 'less' :
return $name.' <= '.$value;
break;
case 'below' :
return $name.' < '.$value;
break;
case 'like_tail' :
case 'like_prefix' :
case 'like' :
return $name.' like '.$value;
break;
case 'in' :
return $name.' in ('.$value.')';
break;
case 'notin' :
return $name.' not in ('.$value.')';
break;
case 'notequal' :
return $name.' <> '.$value;
break;
case 'notnull' :
return $name.' is not null';
break;
case 'null' :
return $name.' is null';
break;
case 'between' :
return $name.' between ' . $value[0] . ' and ' . $value[1];
break;
}
}
/**
* @brief returns condition key
* @param[in] $output result of query
* @return array of conditions of $output
**/
function getConditionList($output) {
$conditions = array();
if(count($output->conditions)) {
foreach($output->conditions as $key => $val) {
if($val['condition']) {
foreach($val['condition'] as $k => $v) {
$conditions[] = $v['column'];
}
}
}
}
return $conditions;
}
/**
* @brief returns counter cache data
@ -693,30 +457,5 @@
$this->_query($query);
}
function addQuotesArray($arr)
{
if(is_array($arr))
{
foreach($arr as $k => $v)
{
$arr[$k] = $this->addQuotes($v);
}
}
else
{
$arr = $this->addQuotes($arr);
}
return $arr;
}
/**
* @brief Just like numbers, and operations needed to remove the rest
**/
function _filterNumber(&$value)
{
$value = preg_replace('/[^\d\w\+\-\*\/\.\(\)]/', '', $value);
if(!$value) $value = 0;
}
}
?>

View file

@ -121,6 +121,7 @@
/**
* @brief handles quatation of the string variables from the query
**/
// TODO Make sure this is handled in DBParser class
function addQuotes($string)
{
if (!$this->fd) return $string;
@ -561,97 +562,11 @@
}
}
/**
* @brief return the condition
**/
function getCondition ($output)
{
if (!$output->conditions) return;
$condition = $this->_getCondition ($output->conditions, $output->column_type, $output);
if ($condition) $condition = ' where '.$condition;
return $condition;
}
function _getCondition ($conditions, $column_type, &$output)
{
$condition = '';
foreach ($conditions as $val) {
$sub_condition = '';
foreach ($val['condition'] as $v) {
if (!isset ($v['value'])) continue;
if ($v['value'] === '') continue;
if(!in_array(gettype($v['value']), array('string', 'integer', 'double', 'array'))) continue;
$name = $v['column'];
$operation = $v['operation'];
$value = $v['value'];
$type = $this->getColumnType ($column_type, $name);
$pipe = $v['pipe'];
$value = $this->getConditionValue ($name, $value, $operation, $type, $column_type);
if (!$value) {
$value = $v['value'];
if (strpos ($value, '(')) {
$valuetmp = $value;
}
elseif (strpos ($value, ".") === false) {
$valuetmp = $value;
}
else {
$valuetmp = '"'.str_replace('.', '"."', $value).'"';
}
}
else {
$tmp = explode('.',$value);
if (count($tmp)==2) {
$table = $tmp[0];
$column = $tmp[1];
if ($column_type[$column] && (in_array ($table, $output->tables) ||
array_key_exists($table, $output->tables))) {
$valuetmp = sprintf('"%s"."%s"', $table, $column);
}
else {
$valuetmp = $value;
}
}
else {
$valuetmp = $value;
}
}
if (strpos ($name, '(') > 0) {
$nametmp = $name;
}
elseif (strpos ($name, ".") === false) {
$nametmp = '"'.$name.'"';
}
else {
$nametmp = '"'.str_replace('.', '"."', $name).'"';
}
$str = $this->getConditionPart ($nametmp, $valuetmp, $operation);
if ($sub_condition) $sub_condition .= ' '.$pipe.' ';
$sub_condition .= $str;
}
if ($sub_condition) {
if ($condition && $val['pipe']) {
$condition .= ' '.$val['pipe'].' ';
}
$condition .= '('.$sub_condition.')';
}
}
return $condition;
}
/**
* @brief handles insertAct
**/
// TODO Rewrite with Query object as input
function _executeInsertAct ($output)
{
$query = '';
@ -683,6 +598,7 @@
/**
* @brief handles updateAct
**/
// TODO Rewrite with Query object as input
function _executeUpdateAct ($output)
{
$query = '';
@ -717,6 +633,7 @@
/**
* @brief handles deleteAct
**/
// TODO Rewrite with Query object as input
function _executeDeleteAct ($output)
{
$query = '';
@ -746,62 +663,40 @@
return $result;
}
function getSelectSql($query){
$select = $query->getSelect();
if($select == '') return new Object(-1, "Invalid query");
$select = 'SELECT ' .$select;
$from = $query->getFrom();
if($from == '') return new Object(-1, "Invalid query");
$from = ' FROM '.$from;
$where = $query->getWhere();
if($where != '') $where = ' WHERE ' . $where;
$groupBy = $query->getGroupBy();
if($groupBy != '') $groupBy = ' GROUP BY ' . $groupBy;
$orderBy = $query->getOrderBy();
if($orderBy != '') $orderBy = ' ORDER BY ' . $orderBy;
$limit = $query->getLimit();
if($limit != '') $limit = ' LIMIT ' . $limit;
return $select . ' ' . $from . ' ' . $where . ' ' . $groupBy . ' ' . $orderBy . ' ' . $limit;
}
/**
* @brief Handle selectAct
*
* to get a specific page list easily in select statement,\n
* a method, navigation, is used
**/
function _executeSelectAct($output){
$query = '';
$select = 'SELECT ';
foreach($output->columns as $column){
if($column->show())
$select .= $column->getExpression() . ', ';
}
$select = substr($select, 0, -2);
$from = 'FROM ';
$simple_table_count = 0;
foreach($output->tables as $table){
/*if($simple_table_count > 0) $from .= ', ';
$from .= $table->toString() . ' ';
if(!$table->isJoinTable()) $simple_table_count++;
*/
if($table->isJoinTable() || !$simple_table_count) $from .= $table->toString() . ' ';
else $from .= ', '.$table->toString() . ' ';
$simple_table_count++;
}
$where = '';
if(count($output->conditions) > 0){
foreach($output->conditions as $conditionGroup){
$where .= $conditionGroup->toString();
}
if(trim($where) != '') $where = 'WHERE ' . $where;
}
$groupBy = '';
if($output->groups) if($output->groups[0] !== "")
$groupBy = 'GROUP BY ' . implode(', ', $output->groups);
$orderBy = '';
if(count($output->orderby) > 0){
$orderBy = 'ORDER BY ';
foreach($output->orderby as $order){
$orderBy .= $order->toString() .', ';
}
$orderBy = substr($orderBy, 0, -2);
}
$limit = '';
if(count($output->limit) > 0){
$limit = 'limit ';
$limit .= $output->limit->toString();
}
$query = $select . ' ' . $from . ' ' . $where . ' ' . $groupBy . ' ' . $orderBy . ' ' . $limit;
// TODO Rewrite with Query object as input
function _executeSelectAct($queryObject){
$query = $this->getSelectSql($queryObject);
//$query = sprintf ("select %s from %s %s %s %s", $columns, implode (',',$table_list), implode (' ',$left_join), $condition, //$groupby_query.$orderby_query);
//$query .= (__DEBUG_QUERY__&1 && $output->query_id)?sprintf (' '.$this->comment_syntax, $this->query_id):'';
@ -856,453 +751,6 @@
$buff->data = $data;
}
return $buff;
}
/*function _executeSelectAct ($output)
{
// tables
$table_list = array ();
foreach ($output->tables as $key => $val) {
$table_list[] = '"'.$this->prefix.$val.'" as "'.$key.'"';
}
$left_join = array ();
// why???
$left_tables = (array) $output->left_tables;
foreach ($left_tables as $key => $val) {
$condition = $this->_getCondition ($output->left_conditions[$key], $output->column_type, $output);
if ($condition) {
$left_join[] = $val.' "'.$this->prefix.$output->_tables[$key]. '" "'.$key.'" on ('.$condition.')';
}
}
$click_count = array();
if(!$output->columns){
$output->columns = array(array('name'=>'*'));
}
$column_list = array ();
foreach ($output->columns as $key => $val) {
$name = $val['name'];
$click_count = '%s';
if ($val['click_count'] && count ($output->conditions) > 0) {
$click_count = 'incr(%s)';
}
$alias = $val['alias'] ? sprintf ('"%s"', $val['alias']) : null;
$_alias = $val['alias'];
if ($name == '*') {
$column_list[] = $name;
}
elseif (strpos ($name, '.') === false && strpos ($name, '(') === false) {
$name = sprintf ($click_count,$name);
if ($alias) {
$column_list[$alias] = sprintf('"%s" as %s', $name, $alias);
}
else {
$column_list[] = sprintf ('"%s"', $name);
}
}
else {
if (strpos ($name, '.') != false) {
list ($prefix, $name) = explode('.', $name);
if (($now_matchs = preg_match_all ("/\(/", $prefix, $xtmp)) > 0) {
if ($now_matchs == 1) {
$tmpval = explode ("(", $prefix);
$tmpval[1] = sprintf ('"%s"', $tmpval[1]);
$prefix = implode ("(", $tmpval);
$tmpval = explode (")", $name);
$tmpval[0] = sprintf ('"%s"', $tmpval[0]);
$name = implode (")", $tmpval);
}
}
else {
$prefix = sprintf ('"%s"', $prefix);
$name = ($name == '*') ? $name : sprintf('"%s"',$name);
}
$xtmp = null;
$now_matchs = null;
if($alias) $column_list[$_alias] = sprintf ($click_count, sprintf ('%s.%s', $prefix, $name)) . ($alias ? sprintf (' as %s',$alias) : '');
else $column_list[] = sprintf ($click_count, sprintf ('%s.%s', $prefix, $name));
}
elseif (($now_matchs = preg_match_all ("/\(/", $name, $xtmp)) > 0) {
if ($now_matchs == 1 && preg_match ("/[a-zA-Z0-9]*\(\*\)/", $name) < 1) {
$open_pos = strpos ($name, "(");
$close_pos = strpos ($name, ")");
if (preg_match ("/,/", $name)) {
$tmp_func_name = sprintf ('%s', substr ($name, 0, $open_pos));
$tmp_params = sprintf ('%s', substr ($name, $open_pos + 1, $close_pos - $open_pos - 1));
$tmpval = null;
$tmpval = explode (',', $tmp_params);
foreach ($tmpval as $tmp_param) {
$tmp_param_list[] = (!is_numeric ($tmp_param)) ? sprintf ('"%s"', $tmp_param) : $tmp_param;
}
$tmpval = implode (',', $tmp_param_list);
$name = sprintf ('%s(%s)', $tmp_func_name, $tmpval);
}
else {
$name = sprintf ('%s("%s")', substr ($name, 0, $open_pos), substr ($name, $open_pos + 1, $close_pos - $open_pos - 1));
}
}
if($alias) $column_list[$_alias] = sprintf ($click_count, $name). ($alias ? sprintf (' as %s', $alias) : '');
else $column_list[] = sprintf ($click_count, $name);
}
else {
if($alias) $column_list[$_alias] = sprintf($click_count, $name). ($alias ? sprintf(' as %s',$alias) : '');
else $column_list[] = sprintf($click_count, $name);
}
}
$columns = implode (',', $column_list);
}
$condition = $this->getCondition ($output);
$output->column_list = $column_list;
if ($output->list_count && $output->page) {
return ($this->_getNavigationData($table_list, $columns, $left_join, $condition, $output));
}
if ($output->order) {
$conditions = $this->getConditionList($output);
//if(in_array('list_order', $conditions) || in_array('update_order', $conditions)) {
foreach($output->order as $key => $val) {
$col = $val[0];
if(!in_array($col, array('list_order','update_order'))) continue;
if ($condition) $condition .= sprintf(' and %s < 2100000000 ', $col);
else $condition = sprintf(' where %s < 2100000000 ', $col);
}
//}
}
if (count ($output->groups)) {
foreach ($output->groups as $key => $value) {
if (strpos ($value, '.')) {
$tmp = explode ('.', $value);
$tmp[0] = sprintf ('"%s"', $tmp[0]);
$tmp[1] = sprintf ('"%s"', $tmp[1]);
$value = implode ('.', $tmp);
}
elseif (strpos ($value, '(')) {
$value = $value;
}
else {
$value = sprintf ('"%s"', $value);
}
$output->groups[$key] = $value;
if(count($output->arg_columns))
{
if($column_list[$value]) $output->arg_columns[] = $column_list[$value];
}
}
$groupby_query = sprintf ('group by %s', implode(',', $output->groups));
}
// apply when using list_count
if ($output->list_count['value']) {
$start_count = 0;
$list_count = $output->list_count['value'];
if ($output->order) {
foreach ($output->order as $val) {
if (strpos ($val[0], '.')) {
$tmpval = explode ('.', $val[0]);
$tmpval[0] = sprintf ('"%s"', $tmpval[0]);
$tmpval[1] = sprintf ('"%s"', $tmpval[1]);
$val[0] = implode ('.', $tmpval);
}
elseif (strpos ($val[0], '(')) $val[0] = $val[0];
elseif ($val[0] == 'count') $val[0] = 'count (*)';
else $val[0] = sprintf ('"%s"', $val[0]);
$index_list[] = sprintf('%s %s', $val[0], $val[1]);
}
if (count($index_list))
$orderby_query = ' order by '.implode(',', $index_list);
$orderby_query = sprintf ('%s for orderby_num() between %d and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
else {
if (count ($output->groups)) {
$orderby_query = sprintf ('%s having groupby_num() between %d'. ' and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
else {
if ($condition) {
$orderby_query = sprintf ('%s and inst_num() between %d'. ' and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
else {
$orderby_query = sprintf ('%s where inst_num() between %d'. ' and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
}
}
}
else {
if ($output->order) {
foreach ($output->order as $val) {
if (strpos ($val[0], '.')) {
$tmpval = explode ('.', $val[0]);
$tmpval[0] = sprintf ('"%s"', $tmpval[0]);
$tmpval[1] = sprintf ('"%s"', $tmpval[1]);
$val[0] = implode ('.', $tmpval);
}
elseif (strpos ($val[0], '(')) $val[0] = $val[0];
elseif ($val[0] == 'count') $val[0] = 'count (*)';
else $val[0] = sprintf ('"%s"', $val[0]);
$index_list[] = sprintf('%s %s', $val[0], $val[1]);
if(count($output->arg_columns) && $column_list[$val]) $output->arg_columns[] = $column_list[$key];
}
if (count ($index_list)) {
$orderby_query = ' order by '.implode(',', $index_list);
}
}
}
if(count($output->arg_columns))
{
$columns = array();
foreach($output->arg_columns as $col){
unset($tmpCol);
$tmpCol = explode('.', $col);
if(isset($tmpCol[1])) $col = $tmpCol[1];
if(strpos($col,'"')===false && strpos($col,' ')==false) $col = '"'.$col.'"';
if(isset($tmpCol[1])) $col = $tmpCol[0].'.'.$col;
$columns[] = $col;
}
$columns = join(',',$columns);
}
$query = sprintf ("select %s from %s %s %s %s", $columns, implode (',',$table_list), implode (' ',$left_join), $condition, $groupby_query.$orderby_query);
$query .= (__DEBUG_QUERY__&1 && $output->query_id)?sprintf (' '.$this->comment_syntax, $this->query_id):'';
$result = $this->_query ($query);
if ($this->isError ()) return;
$data = $this->_fetch ($result);
$buff = new Object ();
$buff->data = $data;
return $buff;
}
*/
/**
* @brief displays the current stack trace. Fetch the result
**/
function backtrace ()
{
$output = "<div style='text-align: left;'>\n";
$output .= "<b>Backtrace:</b><br />\n";
$backtrace = debug_backtrace ();
foreach ($backtrace as $bt) {
$args = '';
foreach ($bt['args'] as $a) {
if (!empty ($args)) {
$args .= ', ';
}
switch (gettype ($a)) {
case 'integer':
case 'double':
$args .= $a;
break;
case 'string':
$a = htmlspecialchars (substr ($a, 0, 64)).
((strlen ($a) > 64) ? '...' : '');
$args .= "\"$a\"";
break;
case 'array':
$args .= 'Array ('. count ($a).')';
break;
case 'object':
$args .= 'Object ('.get_class ($a).')';
break;
case 'resource':
$args .= 'Resource ('.strstr ($a, '#').')';
break;
case 'boolean':
$args .= $a ? 'True' : 'False';
break;
case 'NULL':
$args .= 'Null';
break;
default:
$args .= 'Unknown';
}
}
$output .= "<br />\n";
$output .= "<b>file:</b> ".$bt['line']." - ". $bt['file']."<br />\n";
$output .= "<b>call:</b> ".$bt['class']. $bt['type'].$bt['function'].$args."<br />\n";
}
$output .= "</div>\n";
return $output;
}
/**
* @brief paginates when navigation info exists in the query xml
*
* it is convenient although its structure is not good .. -_-;
**/
function _getNavigationData ($table_list, $columns, $left_join, $condition, $output) {
require_once (_XE_PATH_.'classes/page/PageHandler.class.php');
$column_list = $output->column_list;
$count_condition = count($output->groups) ? sprintf('%s group by %s', $condition, implode(', ', $output->groups)) : $condition;
$count_query = sprintf('select count(*) as "count" from %s %s %s', implode(', ', $table_list), implode(' ', $left_join), $count_condition);
if (count($output->groups)) {
$count_query = sprintf('select count(*) as "count" from (%s) xet', $count_query);
}
$count_query .= (__DEBUG_QUERY__&1 && $output->query_id)?sprintf (' '.$this->comment_syntax, $this->query_id):'';
$result = $this->_query($count_query);
$count_output = $this->_fetch($result);
$total_count = (int)$count_output->count;
$list_count = $output->list_count['value'];
if (!$list_count) $list_count = 20;
$page_count = $output->page_count['value'];
if (!$page_count) $page_count = 10;
$page = $output->page['value'];
if (!$page) $page = 1;
// total pages
if ($total_count) {
$total_page = (int) (($total_count - 1) / $list_count) + 1;
}
else {
$total_page = 1;
}
// check the page variables
if ($page > $total_page) $page = $total_page;
$start_count = ($page - 1) * $list_count;
if ($output->order) {
$conditions = $this->getConditionList($output);
//if(in_array('list_order', $conditions) || in_array('update_order', $conditions)) {
foreach ($output->order as $key => $val) {
$col = $val[0];
if(!in_array($col, array('list_order','update_order'))) continue;
if($condition) $condition .= sprintf(' and %s < 2100000000 ', $col);
else $condition = sprintf(' where %s < 2100000000 ', $col);
}
//}
}
if (count ($output->groups)) {
foreach ($output->groups as $key => $value) {
if (strpos ($value, '.')) {
$tmp = explode ('.', $value);
$tmp[0] = sprintf ('"%s"', $tmp[0]);
$tmp[1] = sprintf ('"%s"', $tmp[1]);
$value = implode ('.', $tmp);
}
elseif (strpos ($value, '(')) $value = $value;
else $value = sprintf ('"%s"', $value);
$output->groups[$key] = $value;
}
$groupby_query = sprintf (' group by %s', implode (',', $output->groups));
}
if ($output->order) {
foreach ($output->order as $val) {
if (strpos ($val[0], '.')) {
$tmpval = explode ('.', $val[0]);
$tmpval[0] = sprintf ('"%s"', $tmpval[0]);
$tmpval[1] = sprintf ('"%s"', $tmpval[1]);
$val[0] = implode ('.', $tmpval);
}
elseif (strpos ($val[0], '(')) $val[0] = $val[0];
elseif ($val[0] == 'count') $val[0] = 'count (*)';
else $val[0] = sprintf ('"%s"', $val[0]);
$index_list[] = sprintf ('%s %s', $val[0], $val[1]);
}
if (count ($index_list)) {
$orderby_query = ' order by '.implode(',', $index_list);
}
$orderby_query = sprintf ('%s for orderby_num() between %d and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
else {
if (count($output->groups)) {
$orderby_query = sprintf ('%s having groupby_num() between %d and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
else {
if ($condition) {
$orderby_query = sprintf ('%s and inst_num() between %d and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
else {
$orderby_query = sprintf('%s where inst_num() between %d and %d', $orderby_query, $start_count + 1, $list_count + $start_count);
}
}
}
if(count($output->arg_columns))
{
$columns = array();
foreach($output->arg_columns as $col){
unset($tmpCol);
$tmpCol = explode('.', $col);
if(isset($tmpCol[1])) $col = $tmpCol[1];
if(strpos($col,'"')===false && strpos($col,' ')==false) $col = '"'.$col.'"';
if(isset($tmpCol[1])) $col = $tmpCol[0].'.'.$col;
$columns[] = $col;
}
$columns = join(',',$columns);
}
$query = sprintf ("select %s from %s %s %s %s", $columns, implode (',',$table_list), implode (' ',$left_join), $condition, $groupby_query.$orderby_query);
$query .= (__DEBUG_QUERY__&1 && $output->query_id)?sprintf (' '.$this->comment_syntax, $this->query_id):'';
$result = $this->_query ($query);
if ($this->isError ()) {
$buff = new Object ();
$buff->total_count = 0;
$buff->total_page = 0;
$buff->page = 1;
$buff->data = array ();
$buff->page_navigation = new PageHandler ($total_count, $total_page, $page, $page_count);
return $buff;
}
$virtual_no = $total_count - ($page - 1) * $list_count;
while ($tmp = cubrid_fetch ($result, CUBRID_OBJECT)) {
if ($tmp) {
foreach ($tmp as $k => $v) {
$tmp->{$k} = rtrim($v);
}
}
$data[$virtual_no--] = $tmp;
}
$buff = new Object ();
$buff->total_count = $total_count;
$buff->total_page = $total_page;
$buff->page = $page;
$buff->data = $data;
$buff->page_navigation = new PageHandler ($total_count, $total_page, $page, $page_count);
return $buff;
}
}

View file

@ -1,72 +1,172 @@
<?php
class Query extends Object {
var $queryID;
var $action;
var $columns;
var $tables;
var $conditions;
var $groups;
var $orderby;
function select($columns= null){
$this->action = 'select';
function setQueryId($queryID){
$this->queryID = $queryID;
}
function setAction($action){
$this->action = $action;
}
function setColumns($columns){
if(!isset($columns) || count($columns) === 0){
$this->columns = array(new StarExpression());
return $this;
return;
}
if(!is_array($columns)) $columns = array($columns);
$this->columns = $columns;
return $this;
$this->columns = $columns;
}
function from($tables){
function setTables($tables){
if(!isset($tables) || count($tables) === 0){
$this->setError(true);
$this->setMessage("You must provide at least one table for the query.");
return $this;
return;
}
if(!is_array($tables)) $tables = array($tables);
$this->tables = $tables;
$this->tables = $tables;
}
function setConditions($conditions){
if(!isset($conditions) || count($conditions) === 0) return;
if(!is_array($conditions)) $conditions = array($conditions);
$this->conditions = $conditions;
}
function setGroups($groups){
if(!isset($groups) || count($groups) === 0) return;
if(!is_array($groups)) $groups = array($groups);
$this->groups = $groups;
}
function setOrder($order){
if(!isset($order) || count($order) === 0) return;
if(!is_array($order)) $order = array($order);
$this->orderby = $order;
}
function setLimit($limit){
if(!isset($limit)) return;
$this->limit = $limit;
}
// START Fluent interface
function select($columns= null){
$this->action = 'select';
$this->setColumns($columns);
return $this;
}
function from($tables){
$this->setTables($tables);
return $this;
}
function where($conditions){
if(!isset($conditions) || count($conditions) === 0) return $this;
if(!is_array($conditions)) $conditions = array($conditions);
$this->conditions = $conditions;
return $this;
$this->setConditions($conditions);
return $this;
}
function groupBy($groups){
if(!isset($groups) || count($groups) === 0) return $this;
if(!is_array($groups)) $groups = array($groups);
$this->groups = $groups;
$this->setGroups($groups);
return $this;
}
function orderBy($order){
if(!isset($order) || count($order) === 0) return $this;
if(!is_array($order)) $order = array($order);
$this->orderby = $order;
return $this;
$this->setOrder($order);
return $this;
}
function limit($limit){
if(!isset($limit)) return $this;
$this->limit = $limit;
return $this;
$this->setLimit($limit);
return $this;
}
function getSql(){
if($this->action == 'select') return $this->getSelectSql();
// END Fluent interface
function getAction(){
return $this->action;
}
function getSelect(){
$select = '';
foreach($this->columns as $column){
if($column->show())
$select .= $column->getExpression() . ', ';
}
if(trim($select) == '') return '';
$select = substr($select, 0, -2);
return $select;
}
function getFrom(){
$from = '';
$simple_table_count = 0;
foreach($this->tables as $table){
if($table->isJoinTable() || !$simple_table_count) $from .= $table->toString() . ' ';
else $from .= ', '.$table->toString() . ' ';
$simple_table_count++;
}
if(trim($from) == '') return '';
return $from;
}
function getWhere(){
$where = '';
if(count($this->conditions) > 0){
foreach($this->conditions as $conditionGroup){
$where .= $conditionGroup->toString();
}
if(trim($where) == '') return '';
}
return $where;
}
function getGroupBy(){
$groupBy = '';
if($this->groups) if($this->groups[0] !== "")
$groupBy = implode(', ', $this->groups);
return $groupBy;
}
function getOrderBy(){
if(count($this->orderby) === 0) return '';
$orderBy = '';
foreach($this->orderby as $order){
$orderBy .= $order->toString() .', ';
}
$orderBy = substr($orderBy, 0, -2);
return $orderBy;
}
function getLimit(){
$limit = '';
if(count($this->limit) > 0){
$limit = '';
$limit .= $this->limit->toString();
}
return $limit;
}
}

View file

@ -127,20 +127,20 @@ class QueryParser {
$prebuff .= "\n";
$buff = '';
$buff .= '$output->columns = ' . $columns->toString() . ';'.PHP_EOL;
$buff .= '$output->tables = ' . $tables->toString() .';'.PHP_EOL;
$buff .= '$output->conditions = '.$conditions->toString() .';'.PHP_EOL;
$buff .= '$output->groups = ' . $groups->toString() . ';';
$buff .= '$output->orderby = ' . $navigation->getOrderByString() .';';
$buff .= $navigation->getLimitString()?'$output->limit = ' . $navigation->getLimitString() .';':"";
$buff .= '$query->setColumns(' . $columns->toString() . ');'.PHP_EOL;
$buff .= '$query->setTables(' . $tables->toString() .');'.PHP_EOL;
$buff .= '$query->setConditions('.$conditions->toString() .');'.PHP_EOL;
$buff .= '$query->setGroups(' . $groups->toString() . ');'.PHP_EOL;
$buff .= '$query->setOrder(' . $navigation->getOrderByString() .');'.PHP_EOL;
$buff .= $navigation->getLimitString()?'$query->setLimit(' . $navigation->getLimitString() .');'.PHP_EOL:"";
return "<?php if(!defined('__ZBXE__')) exit();\n"
. sprintf('$output->query_id = "%s";%s', $this->query_id, "\n")
. sprintf('$output->action = "%s";%s', $this->action, "\n")
. '$query = new Query();'.PHP_EOL
. sprintf('$query->setQueryId("%s");%s', $this->query_id, "\n")
. sprintf('$query->setAction("%s");%s', $this->action, "\n")
. $prebuff
. $buff
. 'return $output; ?>';
. 'return $query; ?>';
}

View file

@ -14,6 +14,7 @@
}
function getValue(){
if(is_array($this->value)) return implode(',', $this->value);
return $this->value;
}
@ -34,12 +35,19 @@
if(!isset($this->value)) return;
if($column_type === '') return;
//if($column_type === '') $column_type = 'varchar';
if(in_array($column_type, array('date', 'varchar', 'char', 'bigtext')))
$this->value = '\''.$this->value.'\'';
if(in_array($column_type, array('date', 'varchar', 'char','text', 'bigtext'))){
if(!is_array($this->value))
$this->value = '\''.$this->value.'\'';
else {
$total = count($this->value);
for($i = 0; $i < $total; $i++)
$this->value[$i] = '\''.$this->value[$i].'\'';
}
}
}
function checkFilter($filter_type){
if(isset($this->value)){
if(isset($this->value) && $this->value != ''){
$val = $this->value;
$key = $this->name;
switch($filter_type) {

View file

@ -25,6 +25,19 @@
case 'like' :
$this->value = '%'.$value.'%';
break;
case 'in' :
if(is_array($value))
{
//$value = $this->addQuotesArray($value);
//if($type=='number') return join(',',$value);
//else
//$this->value = "['". join("','",$value)."']";
}
else
{
$this->value = $value;
}
break;
}
/*
//if(!in_array($operation,array('in','notin','between')) && is_array($value)){

View file

@ -18,6 +18,12 @@
function toString(){
if(!isset($this->value)) return;
// If value contains comma separated values and does not contain paranthesis
// -> default value is an array
if(strpos($this->value, ',') !== false && strpos($this->value, '(') === false) {
return sprintf('array(%s)', $this->value);
}
$str_pos = strpos($this->value, '(');
// // TODO Replace this with parseExpression
if($str_pos===false) return '\''.$this->value.'\'';

View file

@ -14,6 +14,8 @@
if(!$this->argument_name) $this->ignoreValue = true;
else $this->ignoreValue = false;
if(!$this->argument_name) $this->argument_name = $tag->attrs->name;
if(!$this->argument_name) $this->argument_name = str_replace('.', '_',$tag->attrs->column);
@ -26,6 +28,9 @@
}
if($tag->attrs->operation) $this->operation = $tag->attrs->operation;
// If we work with ConditionArgument, check if default value exists, and if yes, create argument
if($this->operation && $tag->attrs->default) $this->ignoreValue = false;
require_once(_XE_PATH_.'classes/xml/xmlquery/queryargument/validator/QueryArgumentValidator.class.php');
$this->argument_validator = new QueryArgumentValidator($tag, $this);

View file

@ -39,7 +39,7 @@
);
}
if($this->filter){
$validator .= sprintf("$%s_argument->checkFilter(%s);\n"
$validator .= sprintf("$%s_argument->checkFilter('%s');\n"
, $this->argument_name
, $this->filter
);