Trouble with MySQLi and while loops - php

I have this code here within a class:
function getRolePerms($role)
{
if (is_array($role))
{
$roleSQL = "SELECT * FROM `role_perms` WHERE `roleID` IN (" . implode(",",$role) . ") ORDER BY `ID` ASC";
} else {
$roleSQL = "SELECT * FROM `role_perms` WHERE `roleID` = " . floatval($role) . " ORDER BY `ID` ASC";
}
var_dump($roleSQL);
$this->database->dbquery($roleSQL);
$perms = array();
while($row = $this->database->result->fetch_assoc())
{
$pK = strtolower($this->getPermKeyFromID($row['permID']));
var_dump($pK);
if ($pK == '') { continue; }
if ($row['value'] === '1') {
$hP = true;
} else {
$hP = false;
}
$perms[$pK] = array('perm' => $pK,'inheritted' => true,'value' => $hP,'Name' => $this->getPermNameFromID($row['permID']),'ID' => $row['permID']);
}
return $perms;
}
The var_dump() for $roleSQL is:
SELECT * FROM role_perms WHERE roleID = 1 ORDER BY ID ASC
and for $pK:
Admin
When running the query in the database directly i get a result with 8 rows.
Why is it that the loop does not recognize the multiple rows.
Also if i add the statement:
var_dump($this->database->result->fetch_assoc());
It dumps the array of the first row then the loop does the second row.
Im really baffled,
Please help

The culprit is this line here:
$perms[$pK] = array('perm' => $pK,'inheritted' => true,'value' => $hP,'Name' => $this->getPermNameFromID($row['permID']),'ID' => $row['permID']);
What happens is that all of the 8 rows you expect result in $pK == 'Admin'. When you do $perms[$pK] = array(...), each one of the 8 loop iterations ends up writing to the same array key. In the end, there is only one value in the array.
If you change it to
$perms[] = array(...);
it should work as expected, because each iteration will add a new array element with a unique integer key.
Side note:
Avoid doing this:
$roleSQL = "SELECT * FROM `role_perms` WHERE `roleID` = " . floatval($role) ...
Since roleID surely is an integer, use the right tool for the job: intval($role).

Lol the answer actually lies outside the loop.
Calling this function $this->getPermKeyFromID($row['permID']) actually override the results from the database as it was using the same database object. I fixed it by storing the results in a separate variable local to that loop.

Related

How to assign value to an array in while loop in php from mysqli result to make a counter to filter another while loop?

How to assign value to an array in while loop in php from mysqli result to make a counter to filter another while loop??
I want to assign something like this for my counter variable:
$counter = array("6:00 Am" => 0, "8:00 Am" => 0, "10:00 Am" => 0);
For this code:
//This is from transaction table
$stm2 = "SELECT tr_sched FROM transaction WHERE tr_date = CURRENT_DATE()";
$res2 = $conn->query($res2);
while($rows5 = $res2->fetch_assoc())
{
//Not working
$counter[] = array($rows5['tr_sched'] => 0)
}
So I can filter this another while loop if the schedule time is greater than to my limit variable, like this:
//This is from my schedule table
$stm = "SELECT sc_time FROM schedule GROUP BY sc_time";
$res = $conn->query($stm);
$counter = array();
while($row4 = $res4->fetch_assoc())
{
//Note working
if($counter[$row4['sc_time']] >= $limit/*=10*/)
{
echo "<option disabled="">" . $row4['sc_time'] . "</option>";
}
else
{
echo "<option>" . $row4['sc_time'] . "</option>";
}
}
The goal of all the codes above is to display all schedule time from schedule table as an option for select element and if the schedule time is already have a 10 records or greater than(limit variable) on my transaction table for today it will display as option but disable so it can't be selected by user.
I hope you get what I mean, I will try to keep active to answer if you have something to clarify about my question.
You don't need the while loop at all.
You can use array functions to populate the array with static values.
$stm2 = "SELECT tr_sched FROM transaction WHERE tr_date = CURRENT_DATE()";
$res2 = $conn->query($stm2);
// get values from a single column
$keys = array_column($res2->fetch_all(MYSQLI_ASSOC), 'tr_sched');
// create an array with all values as 0 and keys from $keys
$counter = array_fill_keys($keys, 0);
Of course, don't reset the array later on with $counter = array();
If you want to loop anyway, then you can use a simple foreach loop.
$stm2 = "SELECT tr_sched FROM transaction WHERE tr_date = CURRENT_DATE()";
$res2 = $conn->query($stm2);
foreach($res2 as $rows5) {
$counter[$rows5['tr_sched']] = 0;
}

PHP: If MYSQL Result greater than 0, add to array?

I have a MYSQL table with a list of services that user's provide:
The Enum values in these columns can be 0 or 1.
0 represents a service not offered and 1 represents a service offered.
Cleaning Tour Guide Cooking Parties
0 1 0 1
I am then running the following query In MYSQL to fetch my rows in the table:
<?php $myBio = $conn->query("SELECT * FROM user_data, user_services WHERE user_data.user_id = user_services.user_id AND user_id = $p_id");
if ($myBio->num_rows > 0) {
$row = $myBio->fetch_assoc();?>
I want to generate a list of the services the user provides (where the service has a value greater than 0) - and separate the list with commas like so:
Tour Guide, Parties
I am trying to do this by using an array:
$os = array(if($row['cleaning'] > 0) { echo 'cleaning';}, if($row['tour'] >0) { echo 'Tour Guide'; });
I am trying to use PHP if statements to decipher if a service is 0 or 1 before adding it to my list.
I do not believe it is possible to combine php if statements within an array.
Please can someone show me how I can achieve my desired result? Thanks in advance
Use array_keys() with the optional search parameter:
$services = array_keys($row, 1);
Example:
$row = [
'Cleaning' => 0,
'Tour Guide' => 1,
'Cooking' => 0,
'Parties' => 1,
];
$services = array_keys($row, 1);
var_export($services);
Result:
array (
0 => 'Tour Guide',
1 => 'Parties',
)
Demo
If your database columns have a speaking name, you can do it like this:
<?php
$arrayServices = array();
$arrayAllServices = array('Cleaning','Tour Guide','Cooking','Parties');
foreach($arrayAllServices as $service) {
if($row[$service] > 0) {
$arrayServices[] = $service;
}
}
$sServices = join(', ', $arrayServices);
echo $sServices;
If the speaking names are different from the column names, you need a second array to look up translations.
Would something like this achieve what you want?
$results=array();
if ($row['cleaning']>0) $results[]='Cleaning';
if ($row['tour']>0) $results[]='Tour Guide';
// ...
Also, please heed #tadman's comment about prepared statements!
<?php
$myResults = array();
$myBio = $conn->query("SELECT * FROM user_data, user_services WHERE user_data.user_id = ? AND user_id = ?");
$stmt->bind_param("ss",$user_services.user_id,$p_id);
$stmt->execute();
$result = $stmt->get_result();
if($result->num_rows === 0) exit('No rows');
while($row = $result->fetch_assoc())
{
$tempArray = array();
$Cleaning = $row['Cleaning'];
$Tour_Guide = $row['TourGuide'];
$Cooking = $row['Cooking'];
$Parties = $row['Parties'];
if($Cleaning == 1)
array_push($tempArray,$Cleaning)
if($Cleaning == 1)
array_push($tempArray,$Cleaning)
if($Cooking == 1)
array_push($tempArray,$Cooking )
if($Parties == 1)
array_push($tempArray,$Parties )
array_push($myResults,$tempArray);
}
?>
You will then get the myResult array which will be an array of arrays, you can then loop over the sub arrays to check values and construct the strings you intend to make.

How to get Fetch_array data

I am making Tournament mod. And I do not know how to correctly do some operations with fetched array.
What my code is doing, is that it takes data from Tournament table and add it to array. Then print it in HTML table, so all users can see the place where he has.
How can I correctly get the first, second, third array data for the first 3 winners and give them a price? And how can I deal with players who have the same amount of points?
Right now the query below seems to not work too, all statements are positiv and it should execute the function.
if($counter == 1) {
$GLOBALS['DATABASE']->query("UPDATE ".USERS." SET `atm` = `atm` + 20000 WHERE `id` = ".$recordRow['id_owner']." ;");
}
Sorry, my English is not good and I tried to search for the answers but didn't find anything, because i do not know for what PHP solution should i search.
My code:
$recordFetch = $GLOBALS['DATABASE']->query("SELECT *FROM `uni1_tournament` ORDER BY wons DESC;");
$counter = 0;
$RangeList = array();
while ($recordRow = $GLOBALS['DATABASE']->fetch_array($recordFetch)) {
$counter += 1;
$RangeList[] = array(
'id' => $recordRow['id_owner'],
'name' => $recordRow['name'],
'points' => $recordRow['wons']*5,
'counter' => $counter,
);
if($t_time > TIMESTAMP) {
if($counter == 1) {
$GLOBALS['DATABASE']->query("UPDATE ".USERS." SET `atm` = `atm` + 20000 WHERE `id` = ".$recordRow['id_owner']." ;");
}
elseif($counter == 2) {
//to do;
} elseif($counter == 3) {
//to do;
}
}
}
Make query like this "select * from uni1_tournament GROUP BY points ORDER BY
points desc limit 3";
If you're using regular mysql or mysqli (been a while since I have for either, moved to doctrine a while back), fetch_array needs to be ran on the results and not the GLOBALS['DATABASE'] variable (guessing this a global variable for the database connection).
Try changing
while ($recordRow = $GLOBALS['DATABASE']->fetch_array($recordFetch)) {
to
while ($recordRow = $recordFetch->fetch_array()) {
In order to use your original formatting, I believe fetch_array needed to be mysqli_fetch_array instead.
i.e
while ($recordRow = $GLOBALS['DATABASE']->mysqli_fetch_array($recordFetch)) {

How do you clear Static variables in PHP?

I have created a function which is using recursion to find out childs of Given User. as shown below :
function recursionFunc($param) {
$q = "select cust_id,amount,position from testtab where parent_id = $param";
$res = mysql_query($q);
static $i = 0;
while ($row = mysql_fetch_assoc($res)) {
$i++;
recursionFunc($row['cust_id']);
}
return array('totalChild'=>$i);
}
There are two cases:
I want to call recursionFunc() for each user i am having
Recursion will be done in order to find childs of a user.
Now i want to call this function in while loop in order to fetch childs of all user i am having.
Since i am using static variable $i to store the value of childs.
Now when function will be called for the first user it returns correct value of childs but return wrong value in all other cases.
AS show Below
$cutData = "select cust_id from testtab";
$ress = mysql_query($cutData);
while ($raw = mysql_fetch_assoc($ress)) {
$response = recursionFunc($raw['cust_id']);
echo '<pre>'.$raw['cust_id'];
print_r($response);
echo '<br>';
}
Outputs
1Array ( [totalChild] => 7 ) 2Array ( [totalChild] => 10 ) 3Array ( [totalChild] => 12 )
It will be great if you can help me .
Thanks in advance.

codeigniter pass array to query

I'm trying to pass an array to a model which has a query. I'm not sure how to correctly pass the array or if i have to manipulate the array somehow.
I have this array:
Array
(
[0] => 1
[1] => 2
)
I have a controller with this line:
$ratings = $this->login_model->get_ratings($mechanicIds); // get the mechanic ratings
I have this model:
function get_ratings($mechanicId)
{
$sql = "select m.mechanic_id,
m.mechanic_name,
m.city,
m.state,
count(mr.rating_id) as num_ratings,
round(avg(mr.rating_id),2) avg_rating
from mechanic m, mechanic_rating mr, rating r
where m.mechanic_id in (?)
and m.mechanic_id = mr.mechanic_id
and mr.rating_id = r.rating_id";
$query = $this->db->query($sql, $mechanicId);
if($query->num_rows() > 0)
{
return $query->result_array();
}
else
{
return false;
}
}
It actually returns results, but the problem is it only returns the results 1 row when it should be returning 2 since there are 2 results in my array. Anyone know what i'm doing wrong?
I found this question which helped.
Below is the code I used.
Controller that contains this:
$mIds_size = count($mIds);
$i = 1;
foreach($mIds as $row)
{
if($i == $mIds_size)
{
$mechanicIds .= $row;
}
else
{
$mechanicIds .= $row.', ';
}
$i++;
}
$ratings = $this->login_model->get_ratings($mechanicIds); // get the mechanic ratings
Model which contains this:
function get_ratings($mechanicId)
{
$this->db->escape($mechanicId);
$sql = "select m.mechanic_id,
m.mechanic_name,
m.city,
m.state,
count(mr.rating_id) as num_ratings,
round(avg(mr.rating_id),2) avg_rating
from mechanic m, mechanic_rating mr, rating r
where m.mechanic_id in ($mechanicId)
and m.mechanic_id = mr.mechanic_id
and mr.rating_id = r.rating_id
group by mechanic_id";
$query = $this->db->query($sql, $mechanicId);
if($query->num_rows() > 0)
{
return $query->result_array();
}
else
{
return false;
}
}
Change this line:
$query = $this->db->query($sql, $mechanicId);
to this:
$query = $this->db->query($sql, array(implode(', ',$mechanicId)));
as per the manual
To pass an array into a raw query (not built with helper methods) for an IN condition, use the ? placeholder without wrapping in parentheses.
When binding the array to the placeholder, you must declare your array inside of an array. In other words, the "parameters" (2nd) argument of query() method expects an array which relates to each ? in the SQL string. Because the first ? is bound to an array, the $mechanicIds array must be declared as the first element of the "parameters" argument. I have tested this advice to work successfully in a CodeIgniter3 instance that I have access to.
$sql = "SELECT m.mechanic_id,
m.mechanic_name,
m.city,
m.state,
COUNT(mr.rating_id) AS num_ratings,
ROUND(AVG(mr.rating_id), 2) AS avg_rating
FROM mechanic AS m,
mechanic_rating AS mr,
rating AS r
WHERE m.mechanic_id IN ? /* <--- here */
AND m.mechanic_id = mr.mechanic_id
AND mr.rating_id = r.rating_id";
$query = $this->db->query($sql, [$mechanicIds]);
The DB_driver.php core file contains this portion of code in compile_binds() which escapes each value in the array and wraps the comma-joined string in parentheses before returning the sql string.
...
do
{
$c--;
$escaped_value = $this->escape($binds[$c]);
if (is_array($escaped_value))
{
$escaped_value = '('.implode(',', $escaped_value).')';
}
$sql = substr_replace($sql, $escaped_value, $matches[0][$c][1], $ml);
}
while ($c !== 0);
...

Categories