Server-side processing Datatables pagination Microsoft SQL - php

Im trying to setup pagination with datatables using PHP PDO with MS SQL, since "limit" is not applicable i find it really hard to make the code work.
I have tried the "TOP" syntax but it will only filter the specified number and the pagination wont work.
I have tried offset and fetch still not working.
These is the working code when Mysql is used and its so easy to understand and perform.
if($_POST["length"] != -1)
{
$query .= 'LIMIT ' . $_POST['start'] . ', ' . $_POST['length'];
}
These are the codes i tried (sorry im not really great in coding) :
//if($_POST["length"] != -1)
{
Trial 1 : //$query .= "TOP " . $_POST['start'] . " OFFSET " . $_POST['length'];
Trial 2 : //$query .= "SELECT * from item ORDER BY id DESC offset 0 rows fetch next 10 rows only ";
Trial 3 ://$query .="AND id BETWEEN ".intval( $_POST["start"] )." AND ".intval( $_POST["length"] );" "
}
The result should be a pagination with 10 filtered records each.enter image description here
Update 1:
Here is the screenshot of the query i tried to test it in a MS SQL server but getting an error (using MS SQL 2008)
SQL Query

Your approach depends on SQL Server version.
Approach, based on ORDER BY clause with OFFSET and FETCH as a paging solution requires SQL Server 2012+. Your syntax seems correct, so next code should work:
<?php
if ($_POST["length"] != -1) {
$query = "
SELECT *
FROM item
ORDER BY id DESC OFFSET ".($_POST['start']-1)." ROWS FETCH NEXT ".$_POST["length"]." ROWS ONLY
";
}
?>
For SQL Server 2008+, you may use ROW_NUMBER() as a paging solution:
<?php
if ($_POST["length"] != -1) {
$query =
"SELECT *
FROM (
SELECT
*,
ROW_NUMBER() OVER (ORDER BY id DESC) AS Rn
FROM item
)
WHERE Rn BETWEEN ".$_POST['start']." AND ".($_POST['start'] + $_POST['length'] - 1);
}
?>

In MSSQL to use the limit you will need to write your query like this:
ORDER BY X.Field
OFFSET 20 ROWS
FETCH NEXT 10 ROW ONLY OPTION (RECOMPILE)
And this will skip the first 20 records and fetch the next 10.

Related

MySQL query within another query's while loop php [duplicate]

I need connect in two tables... Help me please!
<?php
$tabela = mysql_query("SELECT * FROM rankpvp ORDER BY ratio DESC LIMIT 1");
while($pvp = mysql_fetch_assoc($tabela)){
$classe = mysql_query("SELECT * FROM char WHERE char_id = '".$pvp['char_id']."'");
echo ' classe: '.$classe['class'].'<br> Nome: '.$pvp['name'].'<br> Pontos: '.$pvp['ratio'].'<br> Kills: '.$pvp['kills'].'<br> '; } ?>
This can be done with one query
SELECT * FROM `char` WHERE char_id = (SELECT char_id FROM rankpvp ORDER BY ratio DESC LIMIT 1)
Note that char is a reserved word so it will have to be wrapped in back ticks. Maybe this is the actual problem you ran into (syntax error) rather than a problem with your while loop. Nevertheless, one query is the right way

Cant identify Error

I have some code that is supposed to show certain things depending if a radio button is pressed.
When no is selected, it hides entries in a table with a status_id of 15.
When yes is selected, it shows entries in a table with a status_id of 15
if($_REQUEST['statusVal']=="") {
$condition1= " AND MO.status_id <>'15'";
}
if($_REQUEST['statusVal']=="archive") {
$condition1 =" ";
} if($_REQUEST['statusVal']=="all") {
$condition1= " AND MO.status_id <>'15'";
}
$mode = $_REQUEST['mode'];
$mode_toggle = $_REQUEST['mode_toggle'];
$sql="SELECT MO.ssrs_id,MO.member_id,MO.assr_user_id,MO.product_id,MO.component_id,MO.status_id,MO.summary,MO.priority,V.product_name,M.component,T.name,S.statusTitle,S.flag_id FROM ".ASSR_SSRS." MO,".PRODUCTS." V,".PROD_COMPONENTS." M,".ASSR_USER." T ,".ASSR_STATUS." S WHERE MO.product_id=V.product_id AND MO.assr_user_id=T.assr_user_id AND MO.component_id=M.component_id AND MO.status_id=S.status_id AND MO.member_id='$memberID' ORDER BY MO.lastupdate DESC".$condition1;
$row_count = getRowCount($sql);
$sql .= $GLOBALS[sql_page];
$result=mysql_query($sql) or die(mysql_error());
I get this error when it is shown on the web browser (using latest Chrome)
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'AND MO.status_id <>'15' LIMIT 0,10' at line 1
Please help me
This is your query
$sql="
SELECT
MO.ssrs_id,
MO.member_id,
MO.assr_user_id,
MO.product_id,
MO.component_id,
MO.status_id,
MO.summary,
MO.priority,
V.product_name,
M.component,
T.name,
S.statusTitle,
S.flag_id
FROM ".ASSR_SSRS." MO,".PRODUCTS." V,".PROD_COMPONENTS." M,".ASSR_USER." T ,".ASSR_STATUS." S
WHERE
MO.product_id=V.product_id
AND MO.assr_user_id=T.assr_user_id
AND MO.component_id=M.component_id
AND MO.status_id=S.status_id
AND MO.member_id='$memberID'
ORDER BY MO.lastupdate DESC".$condition1;
Here you are appending the dynamic condition at the end and this makes the query invalid when you have some conditions for $condition1 something as
order by MO.lastupdate DESC AND MO.status_id <>'15' and hence the syntax is wrong
It should be as
$sql="
SELECT
MO.ssrs_id,
MO.member_id,
MO.assr_user_id,
MO.product_id,
MO.component_id,
MO.status_id,
MO.summary,
MO.priority,
V.product_name,
M.component,
T.name,
S.statusTitle,
S.flag_id
FROM ".ASSR_SSRS." MO,".PRODUCTS." V,".PROD_COMPONENTS." M,".ASSR_USER." T ,".ASSR_STATUS." S
WHERE
MO.product_id=V.product_id
AND MO.assr_user_id=T.assr_user_id
AND MO.component_id=M.component_id
AND MO.status_id=S.status_id
AND MO.member_id='$memberID'
".$condition1."
ORDER BY MO.lastupdate DESC";
You are adding condition after ORDER BY clause, which is error.
Following is the corrected SQL:
$sql="SELECT MO.ssrs_id,MO.member_id,MO.assr_user_id,MO.product_id,MO.component_id,
MO.status_id,MO.summary,MO.priority,V.product_name,M.component,T.name,
S.statusTitle,S.flag_id FROM ".ASSR_SSRS." MO,".PRODUCTS."
V,".PROD_COMPONENTS." M,".ASSR_USER." T ,".ASSR_STATUS." S WHERE
MO.product_id=V.product_id AND MO.assr_user_id=T.assr_user_id AND
MO.component_id=M.component_id AND MO.status_id=S.status_id AND
MO.member_id='$memberID' " . $condition1 . "ORDER BY MO.lastupdate DESC";

Can I change values in a SQL array in PHP and resort?

I have a SELECT statement that pulls a limited number of items based on the value of one of the fields. (ie ORDER BY rate LIMIT 15).
However, I need to do some comparisons that and change the value of rate, and subsequently could alter the results that I want.
I could pull everything (without the LIMIT), alter the rate, re-sort, and then just process the number that I need. However, I don't know if it's possible to alter values in a php result array. I'm using:
$query_raw = "SELECT dl.dragon_list_id, dl.dragon_id, dl.dragon_name, dl.dragon_level, d.type, d.opposite, d.image, dr.dragon_earn_rate
FROM dragon_list dl
LEFT JOIN dragons d ON d.dragon_id = dl.dragon_id
LEFT JOIN dragon_rates dr ON dr.dragon_id = dl.dragon_id
AND dr.dragon_level = dl.dragon_level
WHERE dl.dragon_id IN (
SELECT dragon_id
FROM dragon_elements
WHERE element_id = 3
)
AND dl.dragon_list_id NOT IN (
SELECT dh.dragon_list_id
FROM dragon_to_habitat dh, dragon_list dl
WHERE dl.user_id = 1
AND dh.dragon_list_id = dl.dragon_list_id
AND dl.is_deleted = 0
)
AND dl.user_id = " . $userid . "
AND dl.is_deleted = 0
ORDER BY dr.dragon_earn_rate DESC, dl.dragon_name
LIMIT 15;";
$query = mysqli_query($link, $query_raw);
if (!$query) {
echo "DB Error, could not query the database\n";
echo 'MySQL Error: ' . mysqli_error($link);
exit;
}
$d = mysqli_fetch_array($d_query);
Well, after a lot of research and some trial and error I found my answers....
Yes, I CAN alter the result rows using something like:
$result['field'] = $newvalue;
I also learned I could reset the pointer by using:
mysqli_data_seek($d_query,0);
However, when I reset the counter, I lost the changes I made. So ultimately, I'm still a little stuck, but individually I had the answers.

Get total rows count of table

I want to get all rows count in my sql.
Table's first 2 columns look like that
My function looks like that
$limit=2;
$sql = "SELECT id,COUNT(*),dt,title,content FROM news ORDER BY dt DESC LIMIT " . $limit;
$stmt = $this->db->prepare($sql);
$stmt->execute();
$stmt->bind_result($id, $total, $datetime, $title, $content);
$stmt->store_result();
$count = $stmt->num_rows;
if ($count > 0) {
while ($stmt->fetch()) {
Inside loop, I'm getting exact value of $total, but MySQL selects only 1 row - row with id number 1. (and $count is 1 too)
Tried this sql
SELECT id,dt,title,content FROM news ORDER BY dt DESC LIMIT 2
All goes well.
Why in first case it selects only 1 row? How can I fix this issue?
for ex my table has 5 rows. I want to get 2 of them with all fields, and get all rows count (5 in this case) by one query.
Remove COUNT(*). You will only ever get 1 row if you leave it in there.
Try adding GROUP BY dt if you want to use COUNT(*) (not sure why you're using it though).
EDIT
Fine, if you insist on doing it in a single call, here:
$sql = "SELECT id,(SELECT COUNT(id) FROM news) as total,dt,title,content FROM news ORDER BY dt DESC LIMIT " . $limit;
This is likely cause by the variable $limit being set to 1, or not being set and mysql defaulting to 1. Try changing your first line to
$sql = "SELECT id,COUNT(*),dt,title,content FROM news ORDER BY dt DESC";
EDIT
Change to:
$sql = "SELECT SQL_CALC_FOUND_ROWS,id,dt,title,content FROM news ORDER BY dt DESC LIMIT " . $limit;
And then use a second query with
SELECT FOUND_ROWS( )
to get the number of rows that match the query
This totally wreaks of a HW problem... why else besides a professor's retarded method to add complexity to a simple problem would you not want to run two queries?
anyways.... here:
SELECT id, (SELECT COUNT(*) FROM news) AS row_count, dt, title, content FROM news ORDER BY dt DESC LIMIT

Need little help with Mysql paging (LIMIT)

I have this code:
$page = $_GET['page'];
$res_per_page = $_GET['res_per_page'];
$start_point = (($page * $res_per_page) - $res_per_page);
$query.= " LIMIT $start_point, $res_per_page";
$qry_result = mysql_query($query) or die(mysql_error());
$total_pages = ceil($nr_ads / $res_per_page);
The variable '$nr_ads' is the total nr of ads...
The code works fine, but I wonder how I can figure out which ads are showing, ex:
Showing ads 10 - 20
Thanks...
print 'Showing ads ' . $start_point . ' - ' . min($nr_ads, $start_point + res_per_page);
Basically you've already got you starting point (which is given to your LIMIT clause in the SQL. The "end point" is calculated by adding $res_pre_page to this starting point. On the last page, however, you may only have 2 records - therefore you should use the min() function to print e.g. "Showing ad 60 - 62".
Follow up: Another answer mentions the risk of SQL injection. You'll be safe by using:
$page = intval($_GET['page']);
$res_per_page = max(1, intval($_GET['res_per_page'])); // To avoid division by zero :)
The simplest way would be to create an ID field in your table and use that to display the information you want, your query would be modified like so:
LIMIT $start_point, $res_per_page ORDER BY ad_id ASC
from there, you can get the first result and the last result and use it to output the information you are gathering.
One very important security note the following code can cause remote SQL injection:
$query.= " LIMIT $start_point, $res_per_page";
It is highly recomended you change it to:
$query.= " LIMIT $start_point, ".mysql_real_escape_string($res_per_page)." ORDER BY ad_id ASC";

Categories