Same output in in MySQL update with foreach statement - php

I am trying to figure out how to update MySQL table with array.
The Tables has 4 fields. REGNO, BATCHNO, NAMES and ATTEN_SUM. The REGNO has the unique value.
$i = 0;
while($row_recordset = mysql_fetch_array($query_run)) {
echo "<tr>";
echo " <td>{$row_recordset['REGNO']}</td>
<td>{$row_recordset['NAME']}</td>
<td><input type='text' name='atten_ave".$i."'></td>
";
echo "</tr>";
$i++;
Here's my html code for the previous page after the update page.
foreach($_POST as $textbox => $values) {
$query_update = "UPDATE `grades` SET `ATTEN_SUM` = '$values' WHERE `BATCHNO` = '$sessionbatch'";
if(mysql_query($query_update)) {
echo 'SUCCESS';
} else{
die(mysql_error());
}
}
$_POST is a array from dynamic inputs from the previous page.
Here's the example of my output in the table.
REGNO | BATCHNO | NAME | ATTEN_SUM
====================================================
1 | ARPA 00-055 | Jason | 99
2 | ARPA 00-055 | Mark | 99
3 | ARPA 00-055 | Edgar | 99
It updates all the rows with the last value that I input.

html
//<input type='text' name='atten_ave".$i."'
<input type='text' name='atten_ave[]'...
php
//foreach($_POST as $textbox => $values) {
foreach($_POST['atten_ave'] as $textbox => $values) {
BUT this update is useless. it just update all record use last textbox.
i think you need to pass name or id to php,
then sql query add something like 'where id="$_POST['ID']"...
*CHECK mysql injections.

Well as you said, REGNO is the unique key, but you are updating on BATCHNO, which is not unique, according to your output.

If you look at the WHERE clause carefully, (WHERE BATCHNO = '$sessionbatch') you'll understand that it DOES update the SAME row each time and thus you see the last update.
Print the query statement, It'll be much clear to you.
if(mysql_query($query_update)) {
echo $query_update.'</br>';

1)
You should not use mysql_* functions anymore. They're deprecated and may potentially leave holes for mysql injections. You should learn to use either Mysqli or PDO.
2)
Your code is totally open to any possible mysql injection. You should use mysql_real_escape_string or see 1) above.
3)
With foreach($_POST) you're iterating through every $_POST item. I'm assuming (maybe I'm wrong) that you're submitting data from an HTML form. Try var_dump($_POST) and you'll see there are many values that are not related to what you want to do. For example:
<input type=”submit” value=”Some value” name="update">
will result in PHP
echo $_POST["update"];
// result: Some value
if you could post the output of var_dump($_POST) we could all see what you're passing inside of the foreach loop and perhaps give more detailed solution.

Related

display database value as a math operation as a PHP variable if value is stored in database using prefix $

I have a table named parameters where I have inserted a value like '$counter_sales+$counter_sales' in one column. Now in my PHP page I have fetched values from that table. When I am trying to echo something like $row10['column_name'] then it is only giving me result as '($counter_sales+$counter_sales)' but I want as its value as eg. 24000 to be displayed which actually I have mentioned for eg. say 12000 in variable $counter_sales in above line in same page. Is it possible ? Please help me. Actually want to code like that. In my table parameters there is a value '($counter_sales+$counter_sales)' and I want to use it like assigned value as mentioned in code.
<?php
$depart=1;
while($row10 = mysqli_fetch_assoc($selectedalldepartment))
{
$sqlsel1 = "select * from parameters ";
$sqlsel1q = mysqli_query($conn,$sqlsel1);
$row2 = mysqli_fetch_assoc($sqlsel1q);
//assigned counter sales value
$counter_sales = $row2["counter_sales"];
?>
<tr>
<td style="text-align:center;"><?php echo $depart; ?></td>
<td style="text-align:center;"><?php echo $row10["incentive"] ; ?></td>
</tr>
<?php
$depaz++;
$depart++;
}
?>
Here is my table:
user_id | user_name | incentive
1 | Goldy Shahu | ($counter_sales+$counter_sales)
The obvious way that may be dangerous, especially if anything may be stored in the column:
<?php eval("echo {$row10['incentive']};"); ?>
You should be able to use eval
http://php.net/manual/en/function.eval.php

Why are mySQL query results not displaying text from table when executed in PHP?

The below code is returning rows of checkboxes (the right number per the mySQL table) and with no error. The problem is that it is not grabbing the column values ((as per: ".$row['Zone'].": ".$row['RowNumber']. ))to place beside said checkboxes.
<?php
include'connect.php'
?>
<form method="post" action="chooseDate.php">
<?php
$sql = "
SELECT s.RowNumber, s.Zone,
FROM Seat AS s
LEFT JOIN Booking AS b, ON s.RowNumber = b.RowNumber,
AND b.PerfDate = ?,
AND b.PerfTime = ?,
WHERE b.RowNumber IS NULL,
GROUP BY s.RowNumber
";
$date = "$_POST[Date]";
$time = "$_POST[Time]";
$handle = $conn->prepare($sql);
$handle->execute(array($date, $time));
$res = $handle->fetchAll();
foreach($res as $row) {
echo "<input name='Seat' type='checkbox' value='".$row['Zone'].":
".$row['RowNumber']."'><br>";
}
?>
<input class="mybutton" type="submit" value="Choose Seat"/>
</form>
I have run queries using identical methods and they display the results as expected. The only difference here is that the query is LEFT JOIN. The results display in shell. This is a sample of the results and the expected output of one checkbox.
|**RowNumber**|**Zone**|
|-------------|--------|
|Z20 |box 4 |
Where am I going wrong? Thanks in advance.
Have you looked at the HTML output? You put the text inside the input element. The closing > is after the text.
You could fix that simply by just moving the > to the front, but I think it's bettter to generate a <label> element after the checkbox or surrounding the checkbox. If you give the checkbox an id, and the label a for attribute pointing to that id, the text is clickable too, which make an awesome UX. :)
So I suggest changing the for loop like this:
$idcounter = 0;
foreach($res as $row) {
$id = 'Seat' . ($idcounter++);
echo "<input name='Seat' type='checkbox' id='$id'><label for='$id'>".$row['Zone'].":".$row['RowNumber']."</label><br>";
}
Note that I removed the value attribute. I'm not sure if you would need it, but maybe you need both: the value and the label. If so you can put back that attribute like you had before, as long as you make sure to close the input element before opening the label.

How to do multi-part PHP query of mysql db

I have read through hundreds of posts on here and on other sites. I am not overly familiar with PHP and mysql, but already have my tables built in mysql, have called them using single checklists and filtered them based on date and time. However, in the multi-checkbox arena, I cannot seem to pin down what I'm doing wrong for an array code and customizing the resulting table. This is the basic html:
<html> <body> <form method="POST" action="php/minute_feedback.php">
Date: <input type="text" name="from_date" id="from_date" value="2016-04-07">
<input type="checkbox" name="check_list[]" value="gate" id="gate">
<input type="checkbox" name="check_list[]" value="pressure" id="pressure">
<input type="checkbox" name="check_list[]" value="flow" id="flow">
<input type="submit" name="submit" value="submit">
This is the basic PHP (I'll only include the date parameters vs. date & time to keep it shorter since the inclusion will be the same):
<?php
$servername = "myhostaddress.com";
$username = "myusername";
$password = "mypassword";
$dbname = "mydatabasename";
$conn=new mysqli($servername, $username, $password, $dbname);
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error);}
if($_POST['submit'] == "submit") {
$from_date = ($_POST['from_date']);
$to_date = ($_POST['from_date']);}
if(isset($_POST['submit'])) {
Now ... I know there should be some sort of an array code in here like:
$checklist[] = $_POST[check_list];
But - I'm not sure what the correct syntax/code is.
Next question is about my query. I've seen most queries using a WHERE + IN combo and a '*' for SELECT. However, I need something closer to:
$sql = "SELECT Fdate, Ftime, (list of variable columns from the checked options such as 'gate', 'pressure', 'flow' --> but only if they've been checked) FROM minute_db WHERE Fdate BETWEEN '$from_date' AND '$to_date'";
$result = $conn->query($sql);}
if ($result->num_rows > 0) {
Now - as for my table headers, I can use the following code if I had a single value being looked up:
echo "<table><tr><th>Date</th><th>Time</th><th>Level (ft)</th></tr>";}
But, I need the header to be dynamically populated with the results of the checked items (1, 2, or 3 or more variables as needed) plus the date and time records.
echo "<table>";}
else {
echo "0 results";}
$conn->close();
?>
My end result is that the user can enter a date and time range and choose which data to display, so for example, if they want to know just the gate setting and pressure on 4/7/2016, they'd enter that date and check those two boxes so they will get a table (no formatting below - just trying to represent), for example:
Date | Time | Gate Setting | Pressure
----------------------------------------------------
2016-04-07 | 11:00 | 21 | 50
I will ultimately have a table with tens of thousands of rows of data to select from (and will include limiters to the amount of data that can be pulled), and up to 56 columns of variables to select from. I'm not using any special/fancy math functions to group time periods, etc. - I've already manually separated it all out and uploaded it so it's ready to go. I've tried a lot of different solutions from the internet, but have ultimately failed. The * option for SELECT doesn't seem like what I what, neither does the IN option - but I am not sure (just speculating as neither has worked). I'm on a netfirms mysql platform, so it's pretty updated (and I'll be changing everything to mysqli to avoid whatever problems stem from not using it - so any feedback with that in advance would be AWESOME!!. I appreciate any ideas you have!
Thanks to Deep's solution above - it works perfectly as-is! AWESOME. As for the use of the table array, I was struggling because I could populate the table, but was getting duplicates of date and time (as noted in my replies above). However - I simply moved the script around a bit and it works. Now, the user will get back columns with the date, time, and then the additional variables they are looking for, side by side, across the page, as comparative values (note - I have not yet gotten to the point of mysqli or pdo, so if this is old, please update as you need). Hopefully this helps - and thanks again! So - from the sql line from Deep's post above (fully filled out), this is the table -->
$sql = "SELECT Fdate, {$wantedFields} Ftime FROM minute_db WHERE Fdate BETWEEN '$from_date' AND '$to_date' AND Ftime BETWEEN '$from_time' AND '$to_time'";
$result = $conn->query($sql);
}
if ($result->num_rows > 0) {
//header fields
echo "<table><tr><th>Date</th><th>Time</th>";
foreach($tableDynFields as $c) {
echo "<th>$c</th>";
}
echo "</tr>";
//results
while ($row = $result->fetch_assoc()) {
echo "<tr><td>".$row["Fdate"]."</td><td>".$row["Ftime"]." </td>";
foreach($tableDynFields as $c) {
echo "<td>".$row[$c]."</td>";
}
echo "</tr>";
}
echo "</table>";
//result set free
$result->free();
} else {
echo "query failed.<hr/>";
}
$conn->close();
?>
The only thing I'll add is if you're having to filter and sort through as much data as I am - tis good to either put a forced limiter at the end of the select statement, or something to that effect!
$checklist = $_POST['check_list'];
$allowedFields = [
'gate' => 'Gate',
'pressure' => 'Pressure',
'flow' => 'Flow',
'etc' => 'Other field title'
];
$wantedFields = [];
$tableDynFields = [];
foreach ($checklist as $field) {
if (array_key_exists($field, $allowedFields)) {
$wantedFields[] = $field;
$tableDynFields[] = $allowedFields[$field];
}
}
if ($wantedFields) {
$wantedFields = join(',', $wantedFields) . ',';
} else {
$wantedFields = '';
}
$sql = "SELECT Ftime, {$wantedFields} Fdate FROM ...';
// and here you have $tableDynFields array for table generation

SQL group names as table header rows using PHP

I'm trying to output a dynamic table using PHP that looks something like this:
Paul 56
Paul 6
Paul 78
Paul 34
Paul 76
Mark 56
Mark 5
Mark 34
Mark 87
Mark 23
Mark 765
Basically what I want to output is something like this:
<table>
<tr colspan="2">Name: Paul</tr>
<tr><td>56</td><td>Edit</td></tr>
<tr><td>6</td><td>Edit</td></tr>
<tr><td>78</td><td>Edit</td></tr>
<tr><td>34</td><td>Edit</td></tr>
<tr><td>76><td>Edit</td></tr>
<tr colspan="2">Name: Mark</tr>
<tr><td>56</td><td>Edit</td></tr>
<tr><td>5</td><td>Edit</td></tr>
<tr><td>34</td><td>Edit</td></tr>
<tr><td>87</td><td>Edit</td></tr>
<tr><td>23/td><td>Edit</td></tr>
<tr><td>765/td><td>Edit</td></tr>
</table>
What my PHP code looks like so far:
<?php
$name_holder = null;
for($i=0;$i<count($data);$i++) {
if($name_holder != $data[$i]->name){
$name_holder = $data[$i]->name;
//not sure what to do here??
}
echo "<tr>";
echo "<td align='left'>".$data[$i]->name."</td>";
echo "<td align='left'>".$data[$i]->hour."</td>";
echo "</tr>";
}
?>
SQL
SELECT name,hour FROM checkin_tbl GROUP BY name ORDER BY name ASC;
You don't need to group your data at the database level. It is possible to do it that way, but for each group you'd need another SELECT to read the related data, and will result in excessive numbers of queries being sent to the database.
I've thus elected to read the data in using a straight query, which would be something like this:
SELECT name,hour FROM checkin_tbl ORDER BY name ASC;
I've not supplied the database code below, as it is not clear what database you are using (e.g. MySQL) or what interface you are using (e.g. PDO). I've thus emulated a data source using an array - I'm sure you can swap this out with a fetchAll() or a foreach() and a row fetch().
Thus, try something like this:
<?php
// Data from your database
$rawData = [
['Paul', 56],
['Paul', 6],
['Mark', 56],
['Mark', 5],
];
// Let's reformat this
$out = [];
foreach ($rawData as $pair)
{
$name = $pair[0];
if (!isset($out[$name]))
{
$out[$name] = [];
}
// Pop the value on the list
$out[$name][] = $pair[1];
}
// Use this to look at your structure
#print_r($out);
?>
<!-- Here's your rendering section -->
<?php foreach ($out as $name => $data): ?>
<tr colspan="2"><td>Name: <?php echo htmlentities($name) ?></td></tr>
<?php foreach ($data as $item): ?>
<tr><td><?php echo htmlentities($item) ?></td><td>Edit</td></tr>
<?php endforeach ?>
<?php endforeach ?>
My strategy is to format the data as much as possible outside of the template - your code and another answer here (at the time of writing) are mixing logic and layout excessively in my opinion, and you need to separate them out.
This is why I have switched to opening/closing PHP tags in the rendering section: this is broadly HTML with PHP snippets where dynamic output is required. You'll benefit from tag matching and syntax colouration in your IDE if you do it this way.
I've added htmlentities() in to protect against XSS.
Looking at the desired situation, there is absolutely no need for a GROUP BY.
In fact this is actually hindering your from displaying all records for a given person. You will end up with one row per person, filled with the last record for that person.
In order to get the situation you desire, strip the GROUP BY.
A PHP solution COULD be.
$name_holder = null;
for($i=0;$i<count($data);$i++) {
if($name_holder != $data[$i]->name){
$name_holder = $data[$i]->name;
echo "<tr><td colspan='2'>Name: " . $name_holder . "</td></tr>"
}
echo "<tr>";
echo "<td align='left'>".$data[$i]->hour."</td>";
echo "<td align='left'>edit</td>";
echo "</tr>";
}
You were well on the way to a correct solution.
Background info on Grouping and your problem:
A good explanation is found here: http://www.tutorialspoint.com/sql/sql-group-by.htm
A demo that it will not work can be tested on the w3schools demo database: http://www.w3schools.com/sql/trysql.asp?filename=trysql_select_groupby
All records:
SELECT CustomerId, ShipperId FROM [Orders] WHERE ShipperId = 1
Grouped:
SELECT CustomerId, ShipperId FROM [Orders] WHERE ShipperId = 1 GROUP BY ShipperId

how to give a link to execute this

$sql=mysql_query("SELECT * FROM feedback.subject WHERE branch='cse'");
$row = mysql_fetch_assoc($sql) or die("error : $sql" .mysql_error());
$data =array();
$n=mysql_num_rows($sql);
while($row = mysql_fetch_array($sql))
{
$query_result_array[]=$row;
}
for($i=0;$i<$n;$i++)
{
$subid=$query_result_array[$i]['subid'];
$bt =$query_result_array[$i]['batch'];
$y =$query_result_array[$i]['year'];
$s = $query_result_array[$i]['semister'];
$subname=$query_result_array[$i]['subname'];
$tid = $query_result_array[$i]['tid'];
$sql2=mysql_query("SELECT * FROM teacher WHERE teacher.tid='$tid'");
$row2 =mysql_fetch_array($sql2);
$tname= $row2['tname'];
echo "<table id='table'>";
echo "<tr>";
echo "<td>".$bt."</td>";
echo "<td>CSE</td>";
echo "<td>".$y."</td>";
echo "<td>".$s."</td>";
echo "<td style='width:150px'>".$subname."</td>";
echo "<td style='width:150px'>".$row2['tname']."</td>";
echo '<form methode="get">
<input type="hidden" name="report">
<input type="submit" value="report">
</form>';
echo "</tr>";
echo "</table>";
}
function handler($x,$y){
session_regenerate_id();
$_SESSION['SUBID']=$x;
$_SESSION['TID']=$y;
echo 'report';
}
if(isset($_GET["report'$i'"]))
{
handler($query_result_array[$i]['subid'], $query_result_array[$i]['tid']);
unset ($_GET["report"]);
}
}
this results a table like
BATCH | BRANCH | YEAR | SEMISTER | SUBJECT NAME | TEACHER NAME | ACTION |
-------------------------------------------------------------------------------
9 CSE 4 1 DBMS ABC REPORT
9 CSE 4 1 WT XYZ REPORT
-------------------------------------------------------------------------------
when i click the report of a row suppose ('ABC' teacher) i want to carry the details ('ABC' and 'DBMS') to further process. but it always carrying the details of last person in the loop(here 'XYZ' and 'WT'). how to get that? is there any alternate process through i can call the handler function for a particular row which carries that particular row details.
just loop through query result array and inside of it place an if which detects when name is what you are looking for, at that moment, fetch current $query_result_array[$i] into a var that you want to carry the data further and break the loop.
If you are fetching by position in the table, you do not even need loop you just go $specific_person_data = $query_result_array[$i]...
So this now contains all of data about the person at position $i in your data table.
Update for links:
Each persons data can be passed to another page through link like this:
linkadress.php*?var1=X&var2=Y&var3=Z...*
and fetched on the other end with $_POST['var1'], $_POST['var2'] etc.
make sure not to echo or return data directly, but on every post var use strip_tags for security precaution.
Also here is article of mine on the subject of sensitive data handling and soem basic security:
http://metaphorical-lab.com/blog/?p=443

Categories