How to add results of multiple queries to an array in PDO? - php

Below is my code
$stmt = $db->prepare("SELECT * FROM inbox ORDER BY `date` DESC ");
$stmt->execute(array());
$row = $stmt->fetchAll(PDO::FETCH_ASSOC);
$uniques = count(array_unique($row, SORT_REGULAR));
for ($i=0; $i < $uniques; $i++) {
$inbox_id = $row[$i]["inbox_id"];
$stmt = $db->prepare("SELECT * FROM messages WHERE inbox_id=? AND seen=? ORDER BY `date` DESC");
$stmt->execute(array($inbox_id, 0));
$row_msg = $stmt->fetchAll(PDO::FETCH_ASSOC);
}
return $row_msg;
But this is nor returning all data.It is only returning values got from first iteration only.

you can use:
$row_msg[$i] = $stmt->fetchAll(PDO::FETCH_ASSOC);

Your PDO statement is prepared every round inside the loop, that is not necessary and i hope the inbox_id column is a primary key in the inbox table:
$stmt1 = $db->query("SELECT `inbox_id` FROM inbox ORDER BY `date` DESC ");
$stmt2 = $db->prepare("SELECT * FROM messages WHERE inbox_id=? AND seen=0 ORDER BY `date` DESC");
while($id = $stmt1->fetchColumn(0)) {
$stmt2->execute(array($id));
$row_msg[$id] = $stmt2->fetchAll(PDO::FETCH_ASSOC);
}
return $row_msg;
If you do not want a multidimensional array you can just add the row to the result array by using array_merge() (PHP Manual: array_merge) inside the loop (instead of the line with $row_msg[$id]):
$row_msg = array_merge($row_msg, $stmt2->fetchAll(PDO::FETCH_ASSOC));

Related

How do I output 4 random records from the database and store them in 4 different variables?

I would like to output 4 random records from the database and store them in 4 different variables.
I would like to continue working with the variables.
How do I get this done?
$stmt = $pdo->prepare("SELECT * FROM carditems WHERE status = ? ORDER BY rand() LIMIT 4 ");
$stmt->execute([1]);
while($row = $stmt->fetch()){
var_dump($row['idItem']);
}
$stmt = $pdo->prepare("SELECT * FROM carditems WHERE status = ? ORDER BY rand() LIMIT 4 ");
$stmt->execute([1]);
$array = [];
while($row = $stmt->fetch()){
$array[] = $row['idItem'];
}
var_dump($array);
It's not 4 variables, but 4 array elements to be used further in your code
You can do this using PDO method fetchAll() and PHP method list:
$stmt = $pdo->prepare("SELECT * FROM carditems WHERE status = ? ORDER BY rand() LIMIT 4 ");
$stmt->execute([1]);
list($v1, $v2, $v3, $v4) = $stmt->fetchAll();
var_dump($v1, $v2, $v3, $v4);
fetchAll get all records into array,
list decomposits array to separate variables. In case when array have less values then list variables count the variables will be NULL
PHP PDO test online

Is there a way to sort PHP array_merge based on raw[2]?

I am creating a time attendance PHP script. I started from storing data in the database MySQL and use different tables for the Punch-in/Punch-out, Breaks, Lunch/Dinner breaks.
Each one of the casualties mentioned before have a table which is structured with an:
ID, start, end, flag
I have already tried to do this with the following code of foreach but unsuccessfully!
foreach ($total as $key => $row) {
$start[$key] = $row['start'];
}
$final = array_multisort($start, SORT_DESC, $total);
echo $final;
Here is the code that I have made with 2 SELECT MySQL queries
$result = mysqli_query($db, "SELECT * FROM time WHERE username =
'$user_check' ORDER BY start DESC");
$data = array();
while ($row = mysqli_fetch_assoc($result)) {
$data[] = $row;
} $db->next_result();
$result = mysqli_query($db, "SELECT * FROM break WHERE username =
'$user_check' ORDER BY start DESC");
$data2 = array();
while ($row = mysqli_fetch_assoc($result)) {
$data2[] = $row;
}
$total = array_merge ($data, $data2);
I would like to have 1 array of this 2 queries sorted DESC by start as I will use this array to populate a table in DESC order.
Use UNION ALL in your query, instead of merge arrays. Let the database do the work for you:
SELECT * FROM
(SELECT * FROM time WHERE username = '$user_check'
UNION ALL
SELECT * FROM break WHERE username = '$user_check'
) ORDER BY start DESC
PS: Your code is vulnerable to SQL Injection. You should use prepared statement instead.

MySQLi query to get maximal id in the table?

$mysqli = new mysqli("localhost","root","","mydatabase");
if ($result = $mysqli->prepare("SELECT MAX(`id`) AS `id` FROM `mytable` WHERE `row1`=? OR `row2`=?"))
{
$id = 2;
$result->bind_param("ii",$id,$id);
$result->execute();
$result->bind_result($max);
$result->close();
var_dump($max);
}
$mysqli->close();
Unfortunately this code always showing NULL, can u folk explain me how to reach a result?
updated:
in console mode staff like this works great. field id is int and incremental (as PRIMARY INDEX), other fields it's just a rows with a different int values, I cant change anything.
updated:
Well, seems I found the solution:
$mysqli = new mysqli("localhost","root","","mydatabase");
if ($result = $mysqli->prepare("SELECT MAX(`id`) AS `id` FROM `mytable` WHERE `row1`=? OR `row2`=?"))
{
$id = 2;
$result->bind_param("ii",$id,$id);
$result->execute();
$obj = $result->get_result()->fetch_object();
$max = $obj->id;
$result->close();
var_dump($max);
}
$mysqli->close();
this is it.
I figured it out this way:
$result = mysqli_query($con, "SELECT * FROM `TableName` ORDER BY `PID` DESC LIMIT 1");
$row = mysqli_fetch_array($result);
$pidmax=$row['PID'];
You still need to call fetch, as max will only be available after that point. See doc: http://php.net/manual/en/mysqli-stmt.bind-result.php
$result->bind_result($max);
/* fetch values */
while ($result->fetch()) {
printf("Max ID %i\n", $max);
}
$result->close();

How to replace the PHP sorting to SQL?

Pseudocode
$res = Query("SELECT * FROM `table` ORDER BY `date` DESC LIMIT 15");
SortArray(&$res, 'date', 'asc');
If describe in words, then take the last part of the data is sorted in descending order from the database, but to give the data sorted in ascending order.
Try:
$res = Query("SELECT * FROM ( SELECT * FROM `table` ORDER BY `date` DESC LIMIT 15) ORDER BY `date` ASC");
You can use a usort function to sort the array by specific key:
$res_array=array();
while($row=mysql_fetch_row($res))
$res_array[]=$row;
$new_arr = usort($res_array,"my_func");
function my_func($a, $b)
{
if ($a['date'] == $b['date']) {
return 0;
}
return ($a['date'] < $b['date']) ? -1 : 1;
}
*may need some debugging. take the idea.
Instead of making some magical SQL query, you should select 15 first rows in descending order. And then just read the results from the end.
$statement = $pdo->query('SELECT * FROM `table` ORDER BY `date` DESC LIMIT 15');
if ( ! $statement->execute())
{
throw new Exception('query failed !');
}
$data = $statement->fetchAll(PDO::FETCH_ASSOC);
while ( $row = array_pop($data))
{
var_dump( $row );
}

reducing mysql statements that differ only in ORDER BY field name

I'm trying to sort data by different fields ascending and descending. But I have different mysql pdo statements for the 4 fields I have (8 queries total):
$stmt1 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field1 DESC");
$stmt2 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field1 ASC");
$stmt3 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field2 DESC");
$stmt4 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field3 ASC");
$stmt5 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field3 DESC");
$stmt6 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field3 ASC");
$stmt7 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field4 DESC");
$stmt8 = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY field4 ASC");
Based on input, I pick the right statement and bind and execute it.
if ($sortcode == 1){
$stmt1->bindParam(':categ', $categ, PDO::PARAM_STR);
$stmt1->execute();
$fetched = $stmt1->fetchAll(PDO::FETCH_ASSOC);
} else if ($sortcode == 2){
$stmt2->bindParam(':categ', $categ, PDO::PARAM_STR);
$stmt2->execute();
$fetched = $stmt2->fetchAll(PDO::FETCH_ASSOC);
} else if ($sortcode == 3){
$stmt3->bindParam(':categ', $categ, PDO::PARAM_STR);
$stmt3->execute();
$fetched = $stmt3->fetchAll(PDO::FETCH_ASSOC);
}
//repeat the block 5 more times, for a total of 8
This doesn't look right at all. Since the select statements only differ int he name of the field and the desc/asc, is there a better way to get the $sortcode and compact the code that follows?
I guess I could state the question more specifically as: is there a way I could have a single statement/single pdo statement that binds the field name and asc/decs dynamically?
Use associative arrays to hold the prepared statements.
Your input is a column and a sorting method, right? So prepare the queries by:
$columns = array("field1", "field2", "field3", "field4");
$orders = array("asc", "desc");
$queries = array();
foreach($columns as $col) {
$queries[$column] = array();
foreach ($orders as $order) {
$queries[$column][$order] = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY $column $order");
}
}
Now, to look up the correct query, you don't need some synthetic code -- you just look it up by column and order directly.
To look up a query, instead of having your users input a number from 1-8, have them input a column and an order. Imagine that the column is in the variable $col and the order is in $ord. Just say $queries[$col][$ord].
If for some reason you have to use the number (why?), then you need a slightly different strategy. In that case, you store the queries by that number.
$columns = array("field1", "field2", "field3", "field4");
$orders = array("asc", "desc");
$queries = array();
$i = 0;
foreach($columns as $col) {
foreach ($orders as $order) {
$i = $i + 1;
$queries[$i] = $po->prepare("SELECT * FROM tabname WHERE categ=:categ ORDER BY $column $order");
}
}
In other words, you ought to be storing queries according to how you plan to look them up.
You can order by column number, which can be parameterized. Using an ORDER BY in this fashion is usually clearer if you specify the columns in the select clause. I'm not sure if ASC/DESC can be parameterized, though...
You can always build the queries dynamically. Store the map between $sortcode and the columns, the SELECT * FROM tabname WHERE categ=:categ part of the query, get the right column name based on $sortcode and add the ORDER BY ... part.

Categories