I need to build a WP_Query that filters the posts by some Advanced Custom Fields. The following bullet-points describe the functionality needed:
Today is greater than start_date and less than 'end_date'.
If today is the 'start_date', test if the the time is greater than the 'start_time'.
If today is the 'end_date', text if the time is less than the 'end_time'.
Retrieve only the first post, ordered by custom field 'priority'.
I am struggling to build the typical WHERE clausule, like:
SELECT * FROM x WHERE (
( 'start_date' < today AND 'end_date' > today )
OR
( 'start_date' = today AND 'start_hour' < now )
OR
( 'end_date' = today AND 'end_hour' > now )
)
ORDER BY y
LIMIT 0,1;
I have been some time thinking about it, I thought it would be possible by nesting meta_queries in the WP_Query args... Didn't work (see args underneath).
$now_date = date('Ymd');
$now_time = date('Hi');
$args = array(
'post_type' => 'post',
'cat' => 4, /* Bulletin */
'posts_per_page' => 1,
'post_parent' => 0,
'post_status' => 'publish',
'meta_query' => array(
'relation' => 'OR',
'meta_query' => array(
'relation' => 'AND',
array(
'key' => 'bu_from',
'compare' => '<',
'value' => $now_date,
'type' => 'NUMERIC'
),
array(
'key' => 'bu_to',
'compare' => '>',
'value' => $now_date,
'type' => 'NUMERIC'
)
),
'meta_query' => array(
'relation' => 'AND',
array(
'key' => 'bu_from',
'compare' => '=',
'value' => $now_date,
'type' => 'NUMERIC'
),
array(
'key' => 'bu_from_time',
'compare' => '<=',
'value' => $now_time,
'type' => 'NUMERIC'
)
),
'meta_query' => array(
'relation' => 'AND',
array(
'key' => 'bu_to',
'compare' => '=',
'value' => $now_date,
'type' => 'NUMERIC'
),
array(
'key' => 'bu_to_time',
'compare' => '>=',
'value' => $now_time,
'type' => 'NUMERIC'
)
)
),
'meta_key' => 'bu_priority',
'orderby' => 'meta_value',
'order' => 'ASC'
);
REQUEST that ignores all the meta_query:
/* Taken from var_dump($the_query); */
SELECT SQL_CALC_FOUND_ROWS wp_posts.ID
FROM wp_posts
INNER JOIN wp_term_relationships ON (wp_posts.ID = wp_term_relationships.object_id)
INNER JOIN wp_postmeta ON wp_posts.ID = wp_postmeta.post_id
WHERE 1=1
AND wp_posts.post_parent = 0
AND ( wp_term_relationships.term_taxonomy_id IN (4) )
AND wp_posts.post_type = 'post'
AND ((wp_posts.post_status = 'publish'))
AND (wp_postmeta.meta_key = 'bu_priority' )
GROUP BY wp_posts.ID
ORDER BY wp_postmeta.meta_value ASC
LIMIT 0, 1
;
After reviewing with the management what exactly do we need... I changed all quite all the logic involved here.
<!-- START: BULLETIN -->
<?php
$args = array(
'post_type' => 'post',
'cat' => 4, /* Bulletin */
'posts_per_page' => -1,
'post_parent' => 0,
'post_status' => 'publish',
'orderby' => 'ID',
'order' => 'DESC'
);
$the_query = new WP_Query( $args );
if ( $the_query->have_posts() ) :
// Start the Loop.
$added_cnt = 0;
$now = array( 'date' => date('md'), 'day' => date('N') );
$bulletins = array(
'1' => array(),
'2' => array(),
'3' => array(),
'4' => array(),
'5' => array()
);
while ( $the_query->have_posts() ) : $the_query->the_post();
if (
/* Scheduled by day and month */
(
( get_field('bu_schedule_by') == '1' )
&&
( get_field('bu_start_month').get_field('bu_start_day') <= $now['date'] )
&&
( get_field('bu_end_month').get_field('bu_end_day') >= $now['date'] )
)
||
/* Scheduled by day of the week */
(
( get_field('bu_schedule_by') == '2' )
&&
( in_array( $now['day'], get_field('bu_days_to_be_seen') ) )
)
) {
$bulletins[ get_field('bu_priority') ][ get_the_ID() ] = array();
$bulletins[ get_field('bu_priority') ][ get_the_ID() ][ 'title' ] = get_the_title();
$bulletins[ get_field('bu_priority') ][ get_the_ID() ][ 'subtitle' ] = get_field('bu_subtitle');
$bulletins[ get_field('bu_priority') ][ get_the_ID() ][ 'image' ] = get_field('bu_image');
$bulletins[ get_field('bu_priority') ][ get_the_ID() ][ 'content' ] = get_the_content();
$added_cnt++;
}
endwhile;
$bulletin = array();
$bu_priority = 1;
while ( ( $added_cnt > 0 ) && ( count($bulletin) == 0 ) ) {
if ( count($bulletins[$bu_priority]) > 0 ) {
$bulletin = reset($bulletins[$bu_priority]);
}
$bu_priority++;
}
$bu_image = $bulletin['image'];
echo '
<div class="section group section_opener custom_bulletin" style="margin-top: 4px; margin-bottom: 4px; padding: 0 !important;">
<div id="xmas_bg" class="col span_4_of_16"'.( !empty($bu_image) ? ' style="background-image: url('.$bu_image['url'].'); background-position: 50%; background-repeat: no-repeat; margin: 40px 0; height: 178px;"' : '' ).'></div>
<div id="xmas_title" class="col span_4_of_16" style="">
'.( $bulletin['title'] != '' ? '<h1 style="font-size: 28px; font-weight: 700;">'.$bulletin['title'].'</h1>' : '' ).'
'.( $bulletin['subtitle'] != '' ? '<h2 style="font-size: 23px; color: #c94446; font-weight: 300; margin-top: -8px;">'.$bulletin['subtitle'].'</h2>' : '' ).'
</div>
<div class="col span_1_of_16"></div>
<div id="xmas_copy" class="col span_6_of_16" style="padding: 80px 0; font-size: 14px !important;">
'.$bulletin['content'].'
</div>
<div class="col span_1_of_16"></div>
</div>
';
endif;
?>
<!-- END: BULLETIN -->
I am a novice when it comes to MSSQL and have been trying to convert the following MySQL query without any joy. I am connecting to a MySQL Database within Microsoft SQL Server Management Studio via ODBC. This works great and very simple queries work just fine. However the following query is a bit more complicated(and probably not as optimized as it could be), and I am not able to get it working.
First query below is the original MySQL Query, and the second query is my attempted MSSQL translation.
MySQL Query
SELECT timestamp, `First Name`, `Last Name`, `Email Address`, `Department`, `Case`, `Partner`, `Category`, `Tag Title`, `Question`, `Answer`,
MAX(CASE `Secondary Metric Question` WHEN 'Support' THEN `Secondary Metric Question` end) AS 'Metric 1 Title',
MAX(CASE `Secondary Metric Question` WHEN 'Support' THEN `Answer` end) AS 'Metric 1 Answer',
MAX(CASE `Secondary Metric Question` WHEN 'Completeness' THEN `Secondary Metric Question` end) AS 'Metric 2 Title',
MAX(CASE `Secondary Metric Question` WHEN 'Completeness' THEN `Answer` end) AS 'Metric 2 Answer',
MAX(CASE `Secondary Metric Question` WHEN 'Policy' THEN `Secondary Metric Question` end) AS 'Metric 3 Title',
MAX(CASE `Secondary Metric Question` WHEN 'Policy' THEN `Answer` end) AS 'Metric 3 Answer',
`Message`,
CASE `Reply Requested` WHEN 1 THEN "YES" ELSE "NO" END AS "Reply Requested",
`Response Session`
FROM (
SELECT T0.timestamp, T8.first_name AS 'First Name', T8.last_name AS 'Last Name', T8.email AS 'Email Address', T0.dept AS 'Department', T0.case AS 'Case', T0.partner AS 'Partner', T3.title AS 'Category', T2.title AS 'Question', T2.private_title AS 'Tag Title', T6.title AS 'Secondary Metric Question', T0.answer AS 'Answer', T4.key AS 'Message', T4.reply_requested AS 'Reply Requested', T0.response_session AS 'Response Session'
FROM responses AS T0
LEFT JOIN qrs_metrics AS T1
ON T0.qrs_metric_id = T1.qrs_metric_id
LEFT JOIN quick_responses AS T2
ON T1.qrs_id = T2.qrs_id
LEFT JOIN custom_categories AS T3
ON T2.category = T3.original_id AND T3.user_id = T2.user_id
LEFT JOIN rre_aggregates AS T4
ON T0.comment_id = T4.id
LEFT JOIN widget_responses AS T5
ON T0.widget = T5.id
LEFT JOIN secondary_metrics AS T6
ON T1.metric_id = T6.id
LEFT JOIN private_messages AS T7
ON T4.id = T7.comment_id AND T7.type = 3
LEFT JOIN users AS T8
ON T2.user_id = T8.user_id
WHERE T0.timestamp >= '2014-02-17 00:00:00'
AND T0.qrs_metric_id = T1.qrs_metric_id
) tmp_table
GROUP BY `Response Session`
MSSQL Translation Attempt
SELECT [timestamp], [First Name], [Last Name], [Email Address], [Department], [Case], [Partner], [Category], [Tag Title], [Question], [Answer],
MAX(CASE [Secondary Metric Question] WHEN 'Support' THEN [Secondary Metric Question] end) AS 'Metric 1 Title',
MAX(CASE [Secondary Metric Question] WHEN 'Support' THEN [Answer] end) AS 'Metric 1 Answer',
MAX(CASE [Secondary Metric Question] WHEN 'Completeness' THEN [Secondary Metric Question] end) AS 'Metric 2 Title',
MAX(CASE [Secondary Metric Question] WHEN 'Completeness' THEN [Answer] end) AS 'Metric 2 Answer',
MAX(CASE [Secondary Metric Question] WHEN 'Policy' THEN [Secondary Metric Question] end) AS 'Metric 3 Title',
MAX(CASE [Secondary Metric Question] WHEN 'Policy' THEN [Answer] end) AS 'Metric 3 Answer',
[Message],
CASE [Reply Requested] WHEN 1 THEN 'YES' ELSE 'NO' END AS 'Reply Requested',
[Response Session]
FROM (
SELECT T0.[timestamp], T8.first_name AS 'First Name', T8.last_name AS 'Last Name', T8.email AS 'Email Address', T0.dept AS 'Department', T0.[case] AS 'Case', T0.partner AS 'Partner', T3.title AS 'Category', T2.title AS 'Question', T2.private_title AS 'Tag Title', T6.title AS 'Secondary Metric Question', T0.answer AS 'Answer', T4.[key] AS 'Message', T4.reply_requested AS 'Reply Requested', T0.response_session AS 'Response Session'
FROM AZUREMYSQL...responses AS T0
LEFT JOIN AZUREMYSQL...qrs_metrics AS T1
ON T0.qrs_metric_id = T1.qrs_metric_id
LEFT JOIN AZUREMYSQL...quick_responses AS T2
ON T1.qrs_id = T2.qrs_id
LEFT JOIN AZUREMYSQL...custom_categories AS T3
ON T2.category = T3.original_id AND T3.user_id = T2.user_id
LEFT JOIN AZUREMYSQL...rre_aggregates AS T4
ON T0.comment_id = T4.id
LEFT JOIN AZUREMYSQL...widget_responses AS T5
ON T0.widget = T5.id
LEFT JOIN AZUREMYSQL...secondary_metrics AS T6
ON T1.metric_id = T6.id
LEFT JOIN AZUREMYSQL...private_messages AS T7
ON T4.id = T7.comment_id AND T7.type = 3
LEFT JOIN AZUREMYSQL...users AS T8
ON T2.user_id = T8.user_id
WHERE T0.timestamp >= '2014-02-17 00:00:00'
AND T0.qrs_metric_id = T1.qrs_metric_id
) tmp_table
GROUP BY [Response Session]
The current error I am receiveing in SSMS is
Column 'tmp_table.timestamp' is invalid in the select list because it is not contained in either an aggregate function or the GROUP BY clause.
If anyone can help out I would really appreciate it.
Thanks
You need to have all columns that are not aggregates in the GROUP BY.
Edit: Cant use DISTINCT here, perhaps with an nested select but GROUP BY will do just fine.
<pre>
<?php
class DB_mssql
{
function modifyQuery($query)
{
$query = str_replace("`", "", $query);
$query = str_replace( array('[',']') , '' , $query );
$tablesName = $this->getTableName($query);
$tableNamesWithoutAlise = $this->removeAliseName($tablesName);
$tableNamesWithPrefix = $this->prefixDBName($tableNamesWithoutAlise);
// Group By Function Call
$query = $this->getGroupBy($query);
// Order By Function Call
$query = $this->getOrderBy($query);
//replace Limit keyword with TOP keyword
$query = $this->getLimit($query);
// MSSQLDateFormat function call
$query = $this->getMSSQLDateFormat($query);
/*force index => WITH index*/
preg_match_all("#\sforce[\s]*index[\s]*\(\w*\)[\s]*#i",$query,$forceIndex);
if(!empty($forceIndex['0']['0']))
{
$forceString = $forceIndex['0']['0'].')';
$forceString = str_ireplace('force index','WITH (index',$forceString);
}
// Changed use index to with index
preg_match_all("#\suse[\s]*index[\s]*\(\w*\)[\s]*#i",$query,$useIndex);
if(!empty($useIndex['0']['0']))
{
$useString = $useIndex['0']['0'].')';
$useString = str_ireplace('use index','WITH (index',$useString);
}
/*Interval 10 date*/
preg_match_all("#INTERVAL\s[0-9]*\sday#i",$query,$intervalIndex);
if(!empty($intervalIndex[0][0]))
{
$intervalString = explode(" ",$intervalIndex[0][0]);
$intervalString = $intervalString[1];
} else {
$intervalString = '';
}
// Patterns
$patterns[0] ='#(?<![\w])secure_pgatxn.(?![\w][.])#i';
$patterns[1] ='#(?<![\w])secure_pga.(?![\w][.])#i';
$patterns[2] ='#\sIFNULL#i';
$patterns[3] = '#[\s]{1,}WHERE[\s]{1,}1#i';// where 1 should be replaced with WHERE 1=1
$patterns[4] ='#\sforce index[\s]*\(\w*\)[\s]*#i';// Force Index is replaced with With Index
$patterns[5] ='#\suse\sindex[\s]*\(\w*\)[\s]*#i';// use Index is replaced with with index
$patterns[6] ='#[\s]*&&{1}[\s]*#i';
$patterns[7] = '#IF[\s]*\([\s]*#i';// IF should be replaced with where IIF
$patterns[8] = '#now\([\s]*#i';// Now() function should be replaced with getutcdate()
$patterns[10] = '#[\W]DATE[\s]*\([\s]*#i';// Mysql Date() is changed to CONVERT (date,GETDATE())
$patterns[11] = '#DATE_FORMAT[\s]*\([\s]*#i';// date_format() function should be replaced with format
$patterns[12] = '#[\s]*(%Y{1}-%m{1}-%d{1})#i';// Change '%Y-%m-%d' patteren to 'yyyy-MM-dd'
$patterns[13] = '#%m{1} %d{1}#i';// Change '%m %d' patteren to 'MM dd' \'
$patterns[14] = '#DATE_SUB\([\s]*#i';// DATE_SUB() function accepts 3 parameters// curdate
$patterns[15] = '#CURDATE\([\s]*#i';// DATE_SUB() function accepts 3 parameters// curdate
$patterns[16] ='#\,[\s]*INTERVAL\s[0-9]*\sDAY#i';// INTERVAL 1 DAY is replaced with ''
$patterns[17] ='#[\s]*DATE_ADD\([\s]*#i';// Mysql Date() is changed to CONVERT (date,GETDATE())
$patterns[18] ='#[\s]*\|\|[\s]*#i'; // || to OR
$patterns[19] ='#(?<![\w])secure_lib.(?![\w][.])#i';
$patterns[20] = '#UCASE\([\s]*#i';
// Replacement Queries
$replacements[0] = ' ';
$replacements[1] = ' ';
$replacements[2] = ' ISNULL';
$replacements[3] = ' WHERE 1=1 ';
$replacements[4] = isset($forceString)?$forceString:''.' ';
$replacements[5] = isset($useString)?$useString:''.' ';
$replacements[6] = ' AND ';
$replacements[7] = 'IIF(';
$replacements[8] = 'GETDATE(';
$replacements[10] = ' CONVERT(date,';
$replacements[11] = 'FORMAT(';
$replacements[12] = 'yyyy-MM-dd';
$replacements[13] = 'MM dd';
$replacements[14] = ' DATEADD(DAY,-'.$intervalString.',';
$replacements[15] = 'GETDATE(';
$replacements[16] = '';
$replacements[17] = ' DATEADD(DAY,'.$intervalString.',';
$replacements[18] = ' OR ';
$replacements[19] = ' ';
$replacements[20] = 'UPPER(';
$query = preg_replace($patterns, $replacements, $query);
$query = $this->strReplaceTableName($query, $tableNamesWithPrefix);
return $query;
}
// Function To Change Limit to Top
function getLimit($query)
{
preg_match_all("#LIMIT[^\w]{1,}([0-9]{1,})[\s]*([\,]{0,})[\s]*([0-9]{0,})#i",$query,$matches);
$patterns = '#LIMIT[^\w]{1,}([0-9]{1,})[\s]*([\,]{0,})[\s]*([0-9]{0,})#i';
$replacements = '';
$query = preg_replace($patterns, $replacements, $query);
if(!empty($matches[1][0]) && empty($matches[3][0]))
{
$query = str_ireplace("SELECT ", "SELECT TOP ".$matches[1][0]." ", $query);
}
else if(!empty($matches[3][0]))
{
$limitQuery = " OFFSET ".$matches[1][0]." ROWS FETCH NEXT ".$matches[3][0]." ROWS ONLY";
if(stripos($query, "ORDER BY"))
{
$query .= $limitQuery;
}
else
{
$selectList = $this->selectList($query,"SELECT","FROM");
$selectList = $this->sqlParser($selectList);
$selectList = preg_replace('#[\s]as[\s]\w*#i', " ", $selectList);
$query .= " ORDER BY ".$selectList[0].$limitQuery;
}
}
return $query;
}
// Function To Change DateFormat
function getMSSQLDateFormat($query)
{
if(stripos($query, "%b %d"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'%b{1}[\s]*%d{1}\'[\s]*\)#iU",$query,$dateFormat);
if(!empty($dateFormat))
{
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0],"convert(char(3), ".$columnName.", 0)+' '+CONVERT(char(2), ".$columnName.", 4)",$query);
}
return $query;
}
else if(strpos($query, "%Y-%M"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'%Y{1}[\s]*-%M{1}\'[\s]*\)#iU",$query,$dateFormat);
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0],"DATENAME(year,".$columnName.")+'-'+DATENAME(month,".$columnName.")",$query);
return $query;
}
else if(stripos($query, "%Y-%m"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'%Y{1}[\s]*-%m{1}\'[\s]*\)#iU",$query,$dateFormat);
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0],"CONVERT(VARCHAR(7), ".$columnName.", 120)",$query);
return $query;
}
else if(stripos($query, "%M %d, %Y") || stripos($query, "%M %d. %Y"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'%M{1} %d{1}[\,|\.][\s]*%Y{1}\'[\s]*\)#iU",$query,$dateFormat);
foreach($dateFormat[0] as $key => $value)
{
$columnName = explode(",",$dateFormat[0][$key]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][$key],"CONVERT(VARCHAR(12), ".$columnName.", 107)",$query);
}
return $query;
}
else if(stripos($query, "%d/%m/%Y %H:%i:%S"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'\%d/\%m/\%Y[\s]*\%H:\%i:\%S\'[\s]*\)#iU",$query,$dateFormat);
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0],"CONVERT(VARCHAR(10), ".$columnName.", 103)+' '+CONVERT(VARCHAR(18),".$columnName.",108)",$query);
return $query;
}
else if(stripos($query, "%d%m%Y"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w]*.*\)#i",$query,$dateFormat);
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0]," REPLACE(CONVERT(VARCHAR(10),".$columnName.",103), '/','')",$query);
return $query;
}
else if(stripos($query, "%d/%m/%Y"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'\%d{1}/\%m{1}/\%Y{1}\'[\s]*\)#iU",$query,$dateFormat);
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0],"CONVERT(VARCHAR(10), ".$columnName.", 103)",$query);
return $query;
}
else if(stripos($query, "%d %M,%Y"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'\%d{1}[\s]*\%M{1}[,]\%Y{1}\'[\s]*\)#iU",$query,$dateFormat);
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0],"CONVERT(VARCHAR(11), ".$columnName.", 106)",$query);
return $query;
}
else if(stripos($query, "%H:00"))
{
preg_match_all("#DATE_FORMAT[\s]*\([\s]*[\w].*[,]{1}[\s]*\'[\s]*\%H{1}:00[\s]*\'[\s]*\)#iU",$query,$dateFormat);
$columnName = explode(",",$dateFormat[0][0]);
$columnName = str_ireplace("date_format(","",$columnName[0]);
$query = str_ireplace($dateFormat[0][0],"RIGHT(100 + DATEPART(HOUR, ".$columnName."),2)+':00'",$query);
return $query;
}
else if(stripos($query, "datediff"))
{
preg_match_all("#datediff[\s]*\([\s]*[\w].*[,]{1}[\s]*[\w].*[\s]*\)#iU",$query,$dateDiff);
if (isset($dateDiff[0])) {
foreach($dateDiff[0] as $key => $value)
{
$columnName = explode(",",$dateDiff[0][$key]);
if (count($columnName) < 3) {
$Param1 = substr($columnName[1],0,-1);
$Param2 = str_ireplace("datediff("," ",$columnName[0]);
$query = str_ireplace($dateDiff[0][$key],"datediff(DAY,$Param1,$Param2)",$query);
}
}
}
return $query;
}
else
{
return $query;
}
}
// Function To Select List To Order BY Clause
function getOrderBy($query)
{
/*Order By functionality starts*/
preg_match_all("#order[\s]by[^\w]{1,}([0-9]{1,})([\,]{0,})([0-9]{0,})#i",$query,$orderByNum);
if(!empty($orderByNum[0]))
{
$selectList = $this->selectList($query,"SELECT","FROM");
$orderByList = $this->orderByList($query,"ORDER BY","DESC");
$selectList = $this->sqlParser($selectList);
$selectList = preg_replace('#[\s]as[\s]{1,}\w*#i', " ", $selectList);
$orderByArr = explode(",",$orderByList);
$orderByArr = array_map('trim',$orderByArr);
/**Code for gropup by 1*/
if(!empty($orderByNum[0]))
{
$orderByCol=array();
foreach($orderByArr as $colno)
{
$orderByCol[]=$selectList[$colno-1];
}
}
if(!empty($orderByNum[0]))
{
$orderBy = implode(",",$orderByCol);
}
if(stripos($query, "ORDER BY"))
{
$query = preg_replace('#order[\s]by[^\w]{1,}([0-9]{1,})([\,]{0,})([0-9]{0,})([\,]{0,})([0-9]{0,})([\,]{0,})([0-9]{0,})([\,]{0,})([0-9]{0,})([\,]{0,})([0-9]{0,})([\,]{0,})([0-9]{0,})([\,]{0,})([0-9]{0,})([\,]{0,})([0-9]{0,})#i', "ORDER BY $orderBy ", $query);
}
}
return $query;
/*Ends here*/
}
// Function To Select List To Group BY Clause
function getGroupBy($query)
{
preg_match_all("#group[\s]by\s#i",$query,$groupByWord);
preg_match_all("#group[\s]by[^\w]{1,}([0-9]{1,})([\,]{0,})([0-9]{0,})#i",$query,$groupByNum);
$groupBy = !empty($groupByWord[0])?$groupByWord[0]:$groupByNum[0];
if(!empty($groupBy))
{
$selectList = $this->selectList($query,"SELECT","FROM");
$groupByList = $this->groupByList($query);
$selectList = $this->sqlParser($selectList);
$selectList = preg_replace("#[\s]as[\s]{1,}\w*#i", " ", $selectList);
$selectList = $this->removeAggregateFunc($selectList);
$groupByArr = explode(",",$groupByList);
$groupByArr = array_map('trim',$groupByArr);
/**Code for gropup by 1*/
if(!empty($groupByNum[0]))
{
$groupByCol=array();
foreach($groupByArr as $colno)
{
$groupByCol[]=$selectList[$colno-1];
}
}
if(!empty($groupByNum[0]))
{
$combineVal = array_merge_recursive($groupByCol,$selectList);
$combineVal = array_map('trim',$combineVal);
$combineVal = array_unique($combineVal);
$groupBy = implode(",",$combineVal);
}
else
{
$combineVal = array_merge_recursive($groupByArr,$selectList);
$combineVal = array_map('trim',$combineVal);
$combineVal = array_unique($combineVal);
$groupBy = implode(",",$combineVal);
}
$trimmed_array=array_map('trim',$groupByArr);
if(stripos($query, "ORDER BY"))
{
$query = preg_replace('#GROUP BY[\s\S]+?ORDER BY#i', "GROUP BY $groupBy ORDER BY ", $query);
}
else
{
$query = preg_replace('#GROUP BY[\s]{1,}.*#i', "GROUP BY ".$groupBy, $query);
}
}
return $query;
}
// Function To Remove Aggregate Function From group by list
function removeAggregateFunc($selectList)
{
if(!empty($selectList))
{
foreach($selectList as $key => $val)
{
if(stripos($val, "sum(") !== false)
{
unset($selectList[$key]);
}
else if(stripos($val, "count(") !== false)
{
unset($selectList[$key]);
}
else if(stripos($val, "MAX(") !== false)
{
unset($selectList[$key]);
}
else if(stripos($val, "MIN(") !== false)
{
unset($selectList[$key]);
}
else if(stripos($val, "AVG(") !== false)
{
unset($selectList[$key]);
}
}
}
return $selectList;
}
function groupByList($string){
if(stripos($string, "ORDER BY"))
{
preg_match_all("#group\sby(?s)(.*)order\sby#i",$string,$groupByOrderby);
return $groupByOrderby[1][0];
}
else if(stripos($string, "limit"))
{
preg_match_all("#group\sby(?s)(.*)\slimit#i",$string,$groupByLimit);
return $groupByLimit[1][0];
}
else if(stripos($string, "having"))
{
preg_match_all("#group\sby(?s)(.*)\shaving#iU",$string,$groupByHaving);
return $groupByHaving[1][0];
}
else
{
preg_match_all("#group\sby(?s)(.*)#i",$string,$groupBy);
return $groupBy[1][0];
}
}
function orderByList($string, $start, $end){
$string = ' ' . $string;
$ini = stripos($string, $start);
if ($ini == 0) return '';
$ini += strlen($start);
if(stripos($string, "DESC") === false)
{
return substr($string, $ini);
}
else
{
$len = stripos($string, $end, $ini) - $ini;
return substr($string, $ini, $len);
}
}
// Function Used to select column list from Mysql Query
function selectList($string, $start, $end){
preg_match_all("#select(?s)(.*)[\W]from#iU",$string,$selectFrom);
return $selectFrom[1][0];
}
// Function Used to select column list from Mysql Query
function sqlParser($str)
{
$str = str_split($str);
$tokens = array();
$token = "";
$stack = array();
foreach($str as $char) {
if($char == "," && empty($stack)) {
$tokens[] = trim($token);
$token = "";
} else {
$token = $token .$char;
if($char == '(') {
array_unshift($stack, $char);
}
if($char == ')') {
array_shift($stack);
}
}
}
$tokens[] = trim($token);
return $tokens;
}
// Function Used to get TableName from Mysql Query
function getTableName($query)
{
$tables = array();
$query_structure = explode( ' ', strtolower( preg_replace('!\s+!', ' ', $query) ) );
$searches_from = array_keys( $query_structure , 'from');
$searches_join = array_keys( $query_structure , 'join');
$searches_update = array_keys( $query_structure , 'update');
$searches_into = array_keys( $query_structure , 'into');
$searches = array_merge($searches_join , $searches_from , $searches_update , $searches_into);
foreach($searches as $search ){
if(isset($query_structure[$search+1])){
$tables[] = trim( $query_structure[$search+1] , '` ');
}
}
$patterns[1] ='#(?<![\w])secure_pgatxn.(?![\w][.])#i';
$patterns[2] ='#(?<![\w])secure_pga.(?![\w][.])#i';
$patterns[3] ='#(?<![\w])secure_lib.(?![\w][.])#i';
$replacements[1] = '';
$replacements[2] = '';
$replacements[3] = '';
$tables = preg_replace($patterns, $replacements,$tables);
return $tables;
}
// Function Used to Prefix Database Name. In MSSQL, we have to prefix DB Name
function prefixDBName($tableList)
{
$tableArray = array(
"job_queue_notification_log"=>"secure_pga.dbo.job_queue_notification_log"
,"old_pga_customer_card"=>"secure_pga.dbo.old_pga_customer_card"
);
$tableNamesWithPrefix = array();
foreach($tableList as $tableName) {
$tableNamesWithPrefix[$tableName] = $tableArray[$tableName];
}
return $tableNamesWithPrefix;
}
function getSubStr($query, $fromStr, $toStr) {
$fromStrLen = strlen($fromStr);
$startingPos = stripos($query, $fromStr) + $fromStrLen;
$endingPos = stripos($query, $toStr);
if(empty($endingPos))
{
return substr($query, $startingPos);
}
else{
return substr($query, $startingPos, ($endingPos - $startingPos));
}
}
function removeAliseName($tablesName) {
$cleanTablesName = array();
foreach($tablesName as $tableName) {
$temp = explode(" ",$tableName);
$cleanTablesName[] = trim($temp[0],"[]");
}
return $cleanTablesName;
}
function strReplaceTableName($query, $tableNames){
foreach($tableNames as $tableNameBare => $tableNameWithPrefix) {
if(strlen($tableNameBare)>3){
$patterns[]='#\b'.$tableNameBare.'\b#iU';
$replacements[]=$tableNameWithPrefix.'';
}
}
$query = preg_replace($patterns, $replacements, $query);
return $query;
}
// }}}
}
// Object Initializations
$DB_mssql = new DB_mssql();
//Mysql Query
$mysqlQuery = "SELECT id,name FROM table_name WHERE id = 16474 ORDER BY id DESC LIMIT 1,100";
//MSSQL Converted Query
$MssqlQuery = $DB_mssql->modifyQuery($mysqlQuery);
?>
</pre>