I have two tables in mysql: a master table called "grants" and a child table called "goals". Grants has an id field as well as a bunch of others and goals has a goal name and a grant_id to link it to the grants table.
On the html form, the user can add or edit as many goals as they wish (I'm using Javascript to add new inputs). The form also gets any previous goals added and adds them to the form.
<div id="goals">
<?php
$goals = getGoalsById($_GET['id']);
if (empty($goals)) echo "<p>Goal 1: <input type='text' size='40' name='goals[]' /></p>";
else {
$i = 1;
foreach($goals as $goal) {
echo "<p>Goal {$i}: <input type='text' size='40' name=\"goals[{$goal['id']}]\" value=\"{$goal['goal']}\" /></p>";
$i++;
}
}
?>
</div>
<input type="button" value="Add goal" onClick="addInput('goals')" />
When I submit the form, I have the following statement to insert or update the goals:
foreach($goals as $key=>$goal) {
$sql_goals_add[] = "INSERT INTO goals (id, goal, grant_id) VALUES ($key,:goalnew,$grant_id) ON DUPLICATE KEY UPDATE goal = :goalupdate";
foreach ($sql_goals_add AS $sql_goal) {
$stmt_goal = $DBH->prepare($sql_goal);
$stmt_goal->bindValue(':goalnew', $goal, PDO::PARAM_STR);
$stmt_goal->bindValue(':goalupdate', $goal, PDO::PARAM_STR);
}
$stmt_goal->execute();
}
This works fine for updating existing goals as the key that is passed is the id that is in the goal table. However, the problem I run into is when they have new goals, the $goals array that gets passed from the form always starts at 0 and therefore the insert query tries to use 0, 1, 2, etc as the insert id. I'd rather have it automatically choose the next available id in the goals table.
I have tried to auto-populate what I think could be the new goal id's, but this is a bad idea as multiple people may hit the site as once and it could overlap. Any help is appreciated!
I’m going to make a few assumptions for this process to work for you.
The form in the case of a new entry is blank .
In the case of an update the form is populated from the database as
it stands.
On update the form is redisplayed from the database with a note at
the top that says the update has happened.
This is not bank data or hyper critical fault intolerant data. Which
for your application I don’t think it is. It is a form for
processing administrative data.
The Post process I suggest is a follows.
I suggest split up your insert process a little.
Insert/update into the master table. If it is an insert, grab the record Id from the crated row for use as your external key for the goals table.
Delete all entries from your goals table related to the external key. This will run even if there is no entry yet and will clear all goals should there be any. Literally rip out all rows and do a fresh insert.
Loop through the goals part of the post array using the master table’s record id as the external key for insertion. It is damn hard to keep track of the original goal record IDs for update. Because you cleared the table you don't worry with it as that data is in the post also. If the person edits the wording of a goal you don’t need to detect that to see if the goal needs updating as they are all reentered at once.
Display the form again with data pulled from the database. If there is an error and you output the result back into the form the user can always update again if there is a fault in the update process after the data is cleared from the goals table. The user will see the problem and try again if data is lost.
Again not how I handle bank data but for the form with an infinite number of goals that can be tacked on this is the easiest solution I have found.
Best of luck
So, after having the discussion over in G+, I ended up splitting things out:
1) Rename the arrays that are passed to goalsNew and goalsExisting
2) Changing the function to parse each array separately so it will perform an insert on new entries, but an update on existing entries. Below is the completed code, in case anyone cares. :)
<div id="goals">
<?php
$goals = getGoalsById($_GET['id']);
if (empty($goals)) echo "<p>Goal 1: <input type='text' size='40' name='goalsNew[]' /></p>";
else {
$i = 1;
foreach($goals as $goal) {
echo "<p>Goal {$i}: <input type='text' size='40' name=\"goalsExisting[{$goal['id']}]\" value=\"{$goal['goal']}\" /></p>";
$i++;
}
}
?>
</div>
And here is the function that does it all (and I renamed it dealingWithChildren from dealingWithGoals because this is going to be used for multiple child tables, but also because a new father should have a function called dealingWithChildren!
function dealWithChildren($childType, $childNew, $childExisting, $grant_id) {
$fieldName = substr($childType, 0, -1);
dbConnect();
global $DBH;
try {
// If there are no children at all, delete them all
if(empty($childNew) && empty($childExisting)) {
$sql_child_delete = "DELETE FROM $childType WHERE grant_id = $grant_id";
$stmt_child = $DBH->prepare($sql_child_delete);
$stmt_child->execute();
}
// If the user removed a child, delete those children
if(!empty($childExisting)) {
$sql_child_delete = "DELETE FROM $childType WHERE grant_id = $grant_id AND id NOT IN (";
$i = 0;
$len = sizeof($childExisting);
foreach($childExisting as $key=>$child) {
$sql_child_delete .= $key;
if ($len > 1 && $i < $len-1) $sql_child_delete .= ",";
$i++;
}
$sql_child_delete .= ")";
$stmt_del_child = $DBH->prepare($sql_child_delete);
$stmt_del_child->execute();
}
// If a user added any children
if(!empty($childNew)) {
foreach($childNew as $key=>$child) {
$sql_child_add[] = "INSERT INTO $childType ($fieldName, grant_id) VALUES (:childnew,$grant_id)";
foreach ($sql_child_add AS $sql_child) {
$stmt_child = $DBH->prepare($sql_child);
$stmt_child->bindValue(':childnew', $child, PDO::PARAM_STR);
}
$stmt_child->execute();
}
}
// If a user updated any children
if(!empty($childExisting)) {
foreach($childExisting as $key=>$child) {
$sql_child_update[] = "UPDATE $childType SET $fieldName = :childupdate WHERE id = $key";
foreach ($sql_child_update AS $sql_child) {
$stmt_child = $DBH->prepare($sql_child);
$stmt_child->bindValue(':childupdate', $child, PDO::PARAM_STR);
}
$stmt_child->execute();
}
}
} catch (PDOException $f) {
echo 'Database query failure: ' . $f->getMessage();
//exit;
}
dbDisconnect();
}
Related
I am coding a discography tool for a music database.
Artists are able to insert tracks, singles, EPs, and albums all into separate tables on the database.
Having tracks be in their own separate table allows the same tracks to be attached to multiple singles, EPs and albums while only requiring there to be one record for that track in the database.
Which means individual track pages can have an automatically generated list of links back to the Singles, EPs and albums that they appear on. Making navigating the database through the website a much smoother experience.
I have come to the point where I am coding a tool to attach any existing tracks in the database for a given artist onto an album page.
I am using another table in the database called 'trackconnections' to create the relational links between the track ids from the track table and the album id from the album table, with an additional column called albumtracknum available to be able to output the tracks in the right order when queried on the album page.
The code for the tool is behind a button labelled 'Attach existing track(s) to album'. The code for this tool is as follows:
if (isset($_POST['attachexistingtracktoalbum-submit'])) {
require "includes/db_connect.pdo.php";
$artistid = $_POST["artistid"];
$albumid = $_POST["albumid"];
echo '<strong>Select each track you would like to add to this album below and type in the track number you want it to have on the album in the box underneith the name of each selected track.</strong><br><br>';
$stmt = $pdo->query("SELECT * FROM track WHERE artist_id = '$artistid'
order by trackname");
while ($row = $stmt->fetch())
{
echo '<form action="includes/attachexistingtracktoalbum.inc.php" method = "post">';
echo '<div class="checkbox">';
echo '<label>';
echo "<input type='checkbox' name='trackid[]' value='".$row['id']."' />";
echo '<span class="cr"><i class="cr-icon glyphicon glyphicon-ok"></i></span>';
echo ' '.$row['trackname'];
echo '</label>';
echo "<br><label for='albumtracknum'>Track number:</label><br>
<input type='text' name='albumtracknum[]'>
<input type='hidden' name='albumid[]' value='".$albumid,"'>
<br><br>";
echo '</div>';
}
?>
<input type="hidden" name="albumidforreturn" value="<?php echo $albumid;?>">
<button type="submit" name="attachexistingtracktoalbum-submit">Attach track(s) to album</button>
<?php }
else {
header("Location: /index.php");
exit();
}?>
(NB: The post data here is not sanitised for the sql query as it has been passed along in a hidden form from the original album page)
This generates a page with all track names for the current artist available on a list with checkboxes, with each track name being followed by a data entry box to enter the track number for the album being added to.
Submission of the form then hands off to the following include code:
if (isset($_POST['attachexistingtracktoalbum-submit'])) {
require "db_connect.pdo.php";
$albumid = implode(',',$_POST['albumid']);
$trackid = implode(',',$_POST['trackid']);
$albumtracknum = implode(',',$_POST['albumtracknum']);
$albumidforreturn = $_POST['albumidforreturn'];
// echo 'albumid: '.$albumid.'<br>';
// echo 'trackid: '.$trackid.'<br>';
// echo 'albumtracknum: '.$albumtracknum.'<br>';
$sql = "INSERT INTO trackconnections (albumid, trackid, albumtracknum) VALUES (?,?,?);";
$stmt= $pdo->prepare($sql);
$stmt->execute([$albumid,$trackid,$albumtracknum]);
header("Location: ../albumdetail.php?albumid=$albumidforreturn");
exit();
}
else {
header("Location: ../index.php");
exit();
}
(NB: The commented out echos are there to test what the output is from the previous form)
The 2 problems I am having are that my 'Attach existing tracks to album' form submit:
1. Passes on too much data.
The generated form should only pass on the track ids, album number, and track numbers that have had their checkboxes ticked. For insertion into the 'trackconnections' table.
Instead it narrows down the ticked checkbox track ids only and then creates comma separated values for every available track to select, rather than just those actually selected.
Which leads to annoying outputs such as the following when passing on data from form to include:
albumid: 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4
trackid: 30,14
albumtracknum: ,2,3,,,,,,,,,,,,,,,,,,,,,
Where it should only read as:
albumid: 4,4
trackid: 30,14
albumtracknum: 2,3
Having too much data get passed through means that the row inserts won't be correct on multiple INSERTS once I do get this working, as they won't align with one another in the correct order.
2. The include only INSERTS 1 row to the 'trackconnections' table.
It seems I am misunderstanding how to add multiple rows to the database with my code here.
As having multiple checkboxes ticked on my 'Attach existing tracks to album' form only inserts 1 single row to the database on submission of the form each time.
Consistently the only track that gets added to the 'trackconnections' table is the first track with its checkbox ticked and, because of issue no. 1 above, the albumtracknum is always 0 unless I type a number into the first albumtracknum box on the available checklist.
I need to make tweaks to this code so that both problem 1 and 2 are addressed together, meaning that ticking the checkboxes & adding track numbers into each box following the track names actually adds multiple rows to the database along with their corresponding album track numbers.
I hope someone can help.
EDIT TO SHOW REFINED AND WORKING CODE:
New code for checkbox and textbox sections -
if (isset($_POST['attachexistingtracktoalbum-submit'])) {
require "includes/db_connect.pdo.php";
$artistid = $_POST["artistid"];
$albumid = $_POST["albumid"];
echo '<strong>Select each track you would like to add to this album below and type in the track number you want it to have on the album in the box underneith the name of each selected track.</strong><br><br>';
$stmt = $pdo->query("SELECT * FROM track WHERE artist_id = '$artistid'
order by trackname");
echo '<form action="includes/attachexistingtracktoalbum.inc.php" method = "post">';
while ($row = $stmt->fetch())
{
echo '<div class="checkbox">';
echo '<label>';
echo "<input type='checkbox' name='trackid[]' value='".$row['id']."' />";
echo '<span class="cr"><i class="cr-icon glyphicon glyphicon-ok"></i></span>';
echo ' '.$row['trackname'];
echo '</label>';
echo "<br><label for='albumtracknumber'>Track number:</label><br>
<input type='text' name='albumtracknumber_".$row['id']."'>
<input type='hidden' name='albumid[]' value='".$albumid,"'>
<br><br>";
echo '</div>';
}
?>
<input type="hidden" name="albumidforreturn" value="<?php echo $albumid;?>">
<button type="submit" name="attachexistingtracktoalbum-submit">Attach track(s) to album</button>
</form>
<?php }
else {
header("Location: /index.php");
exit();
}
New code for the include INSERT processing -
if (isset($_POST['attachexistingtracktoalbum-submit'])) {
require "db_connect.pdo.php";
$albumid = implode(',',$_POST['albumid']);
$trackid = implode(',',$_POST['trackid']);
$albumidforreturn = $_POST['albumidforreturn'];
foreach($_POST['trackid'] as $trackidloop) {
$albumtracknum = $_POST["albumtracknumber_{$trackidloop}"];
$sql = "INSERT INTO trackconnections (albumid, trackid, albumtracknum) VALUES (?,?,?);";
$stmt= $pdo->prepare($sql);
$stmt->execute([$albumid,$trackidloop,$albumtracknum]);
}
header("Location: ../albumdetail.php?albumid=$albumidforreturn");
exit();
}
else {
header("Location: ../index.php");
exit();
}
This isn't an entire solution but I see some problems:
You are looping through tracks and creating a new form for each one. The first problem is , you are missing the closing form tag. I guess the browser is automatically creating one, when it sees the next form start tag. ?? That's why you only get one single posted checkbox.
I would put all the track checkboxes into a single form. Then the posted trackid[] array will contain all the checked items.
[EDIT after your comment: The hidden fields albumid[] post the entire array, whereas the trackid[] checkboxes only post the actual checked boxes (HTML spec).
Instead of having albumid[], You could put the trackID and albumID together for the checkbox value, then parse them apart when you handle the post:
$value = $row['id']. ',' . $row['albumid'];
echo "<input type='checkbox' name='trackid[]' value='".$value."' />";
ALSO, the SQL, "INSERT INTO (..) .. VALUES (...) " only inserts one row.
It's easy to do that SQL in a loop for all the checked boxes.
foreach($_POST['trackid'] as $value) {
// parse the $value...
// SQL Insert...
}
EDIT 2: From my own comment:
Like hidden fields, input (text) field arrays also post the entire array (with empty values for blank inputs). (Again, this is not a PHP thing, it's a web browser standard to only post checked checkboxes and radio buttons. But ALL text and hidden INPUTs are posted.) So in your example, you need to code a mechanism to know which textbox goes with each checkbox. Quick and dirty...You could add a row index (0,1,2,3...) as another comma-separated number in your checkbox values, then you'll have the index into the posted textbox array. Alternatively, you could name the textboxes ' .. name="textinput_' . $row['trackid'] . '" ...' (not an array), then upon post, read them in your foreach loop with
$val = $_POST["textinput_{$trackid}"];
I have a problem here with break and loops things in php.I have an input type, if I give the id 2 for ex, if there is 2 in db then only "You liked this url already" should be appear.This works. If I give then id 3 it says "Data added".Good for now.But if I enter again id 3 it says:
Data added!You liked this url already
and a new value of 3 is posting in the db.How to avoid this? Here is my function:
<form method="post">
Url id: <input type="text" name="urlid" id="urlid">
<input type="submit" name="givelikes" value="Give Likes">
<br />
<br />
</form>
<?php
if(isset($_POST['givelikes'])){
$urlid = $_POST['urlid'];
$con = mysqli_connect('localhost','root','root', 'db');
$user = $_SESSION['sess_user'];
$query=mysqli_query($con,"SELECT likes FROM users WHERE user='".$user."'");
$row = mysqli_fetch_array($query);
$array = explode(" ", $row['likes']);
foreach ($array as $value) {
echo $value;
echo $urlid;
if($value == $urlid){
echo "You liked this url already";
break;
}
else{
$array = $row['likes'];
$array .= " ";
$array .= "$urlid";
$query = ("Update users set likes = '".$array."' where user = '".$user."'");
if(mysqli_query($con,$query)){
echo "Data added!";
}
else{
echo "ERROR: Could not able to execute sql: " . mysqli_error($con);
}
}
}
}
?>
Currently you're looping through all "likes" and comparing them. So the sequence of steps is like this:
Enter 2
No likes yet, so the data is added
Enter 2
Loop over likes, find 2, data was already added
Enter 3
Loop over likes, find 2, not match so data is added
Enter 3
Loop over likes, find 2, not match so data is added
Continue looping, find 3, data was already added
Correcting this is going to involve changing your design a bit. Right now you have one de-normalized record with a string of space-delimited "likes". Normalize your data. Have one record per "like". And instead of constantly updating a single record, insert new records.
Then when you want to see if a "like" already exists, you can use a WHERE clause. Something like this:
SELECT * FROM users WHERE user=? AND like=?
(Note: This is using query parameters as a prepared statement. This is highly recommended. Your current code is wide open to SQL injection.)
If any record is found at all, then the item was "already liked" and you can output the message. If no record was found, INSERT a new one for that "like".
No need for a loop.
I'm having a bunch of features table in MySQL DB in my PHP project. I'm fetching through php and creating a table with textboxes named by column name and id of record in photos table using code:
functions.php Code:
function m_html_editPhotos($id) {
$result = "<table class=\"tabelka\" id=\"tbl_photos\"><thead><tr><th>Miniaturka</th><th>Duże zdjęcie</th></tr></thead><tbody>";
$mysqli = m_db_Init();
$qry = "SELECT ID, Img_Min, Img_Nrm FROM tbl_Zdjecie WHERE ID_Grzyb = ?";
if($stmt = $mysqli -> prepare($qry)) {
$stmt -> bind_param("i", $id);
mysqli_stmt_bind_result($stmt, $img_id, $img_min, $img_nrm);
$stmt->execute();
$i =0;
while (mysqli_stmt_fetch($stmt)) {
$i = $i+1;
$result .= "<tr><td><!--<label>Link do miniaturki:<label>--><input type=\"text\" class=\"required\" name=\"photo[$i][min]\" value=$img_min></td><td><!--<label>Link do zdjęcia pełnego rozmiaru:</label>--><input type=\"text\" class=\"required\" name=\"photo[$i][nrm]\" value=$img_nrm></td><td style=\"display:none;\"><input type=\"text\" name=\"photo[$i][id]\" value=$img_id /></td></tr>";
}
$stmt -> close();
}
mysqli_close($mysqli);
$result .= "</tbody></table><div class=\"link\" onclick=\"AddPhotoEditRow();\">Dodaj kolejne zdjęcie</div>";
return $result;
}
Now what I'd like is to edit photos table iterating through each row of generated as above table with textboxes for thumbnail_url (img_min) and full size link (img_nrm)
Additionally I'd like to add new ones to the table from dynamically created rows by function AddPhotoEditRow();
functions.js Code:
function AddPhotoEditRow(){
$('#tbl_photos > tbody:last').append('<tr><td><input type="text" name="photo[0][min]"></td><td><input type="text" name="photo[0][nrm]"></td><td style=\"display:none;\"><input type=\"text\" name=\"photo[0][id]\" value=\"0\" /></td></tr>');
}
edit.php Code:
include 'functions.php';
if(isset($_POST["change"])) m_db_updateAllFeatures($_GET["id"]);
if (m_db_isAdmin("")){
if (!isset($_GET["id"]) || !is_numeric($_GET["id"]))
header("Location: ../index.php");
else {
if (isset($_POST["Nazwa_PL"]))
m_db_UpdateName("PL", $_GET["id"],$_POST["Nazwa_PL"]);
if (isset($_POST["Nazwa_Lac"]))
m_db_UpdateName("Lac", $_GET["id"],$_POST["Nazwa_Lac"]);
render_edit_body();
}
}
I'd like to iterate somehow through photos links and update existing records by parsing textbox names passed through $_POST, additionally would be good to insert new photo links (that with id=0). I'm setting new rows' id to 0 because I need to distinguish if I'm inserting to table, or updating, right? I've assumed that all 0-indexed fields should be added, rest of them should be inserted. I might have my conception wrong, if there is a better way to do full functionality to that table "control" then I'm very open to suggestions.
You've got the basics, except
$('#tbl_photo snip snip name="photo[0][min]"> snip snip snip
^---
the 0 should not be hardcoded. You're telling php to create an array of 'photo' values in the $_POST array, but then you force the index keys to be 0 for all entries, causing later ones to overwrite earlier ones.
Keep a count in Javascript as to how many of these fields you've inserted, and use that count to increment the index key, e.g.
$('#tbl_photo snip snip name="photo[' + i + '][min]"> snip snip snip
instead, where i is the field count. Then it's a simple matter of:
foreach($_POST['photo'] as $i => $photo) {
echo $photo['min'];
}
to get that min value for each photo field.
If you use 0 for all newly created HTML elements, the PHP $_POST will contains just the information of the last item.
This is my solution using the same approach as yours with a bit of modification, supposed that we have a form wrap outside out loop and an array named $data contains the seeding information:
PHP code to create the table
// the $data array contains a list of picture object, these object will be updated later.
foreach($data as $num => $row)
{
echo "<tr>\n";
echo sprintf("<td><input type='text' name='name[%d]' value='%s' /></td>\n", $num, $row['name']);
echo "</tr>\n";
}
echo "<tr><td>\n";
echo "<a id='add-item'>Add new item</a>\n";
echo "<input type="hidden" name='num-created' value='0' />";
echo "</td></tr>\n"
JavaScript code to add new element (using jQuery)
$(document).ready(function(){
$('#add-item').click(function(){
var currentCreatedNum = $("input[name=num-created]").val() * 1;
var html = "<tr>";
html += "<td><input type='text' name='newname["+ (currentCreatedNum + 1) +"]' value='' /></td>";
html += "</tr>";
$("input[name=num-created]").val(currentCreatedNum + 1);
});
});
The PHP code to manipulate the POST request
# check contrains ...
# update old records
foreach($_POST['name'] as $id => $name)
{
// get information of existing item and update this record
}
# create new record
foreach($_POST['newname'] as $order => $name)
{
// get information of new item and create a new record
}
As you can see, the name attribute of manual created elements must be different from the existing one.
If I'm understanding, you're wanting to access each dynamically created table item? You can do this by simply creating a dynamic array. As each new TD element (or whatever element) is generated, make the name like name=Something[] (with empty brackets). This will automatically assign each item generated as a member of the array called "Something". You can of course generate key values through a counter as well.
Here's a simplified example from a project I did, where an "Update" button (not shown here) posts back to the same page:
echo "<td class='grid'>
<input type='checkbox' name='chkDel[]' />
</td>";
Then the PHP would be as follows:
if (isset($_POST['chkDel'])) {
// Make a MySQL Connection
$con = mysql_connect(host,user,pwd) or die(mysql_error());
mysql_select_db("db_name");
$rows = 0;
foreach($_POST['chkDel'] as $chkdel) {
//query to delete post
$delQuery = "DELETE FROM table WHERE ".$chkdel;
//run the query
mysql_query($delQuery) or die(mysql_error());
//Get rows affected
$i = mysql_affected_rows();
$rows = $rows + $i;
}
mysql_close($con);
}
Is that what you're looking for?
I am trying to update a row in a mysql database. To do this, I would use a simple query like this:
"UPDATE `contactinfo` SET `Company` = 'Google', WHERE `id` = '1';"
The problem is that the database is dynamic and users can add columns at any time. So I do not know the names of the columns. To find the names and create a form to post to the page that will actually do the mysql work uses this code:
<?php
$result = mysql_query("select * from contactinfo WHERE `id` = '".$rid."';");
if (!$result) {
die('Query failed: ' . mysql_error());
}
$i = 0;
while ($i < mysql_num_fields($result)) {
$meta = mysql_fetch_field($result, $i);
if (!$meta) {
echo "ERROR";
}
$name = $meta->name;
$r = mysql_fetch_array(mysql_query("select * from contactinfo WHERE `id` = '".$rid."';"));
$content = $r[$name];
if($name != 'id') {
echo "<tr><td align='center'><div align='left'>Edit ".$name."</div></td></tr>";
echo "<tr><td align='center'><input type='text' value='" . $content . "' /></td></tr>";
}
$i++;
}
mysql_free_result($result);
?>
This creates a nice little table with input boxes that allow the user to edit the content of the row that has been selected. The row id number($rid) is used to identify which row needs to be changed.
My question is, how can I get the new content for the row from the posted form and create a query to update it? I can't seem to figure out how to dynamically get the names of the form as well as the new content to the write the query.
If any clarification is needed just let me know and all help is appreciated.
Thanks.
The easiest way is to name the fields in the form exactly how the name of the fields in the database are.
Lets say you have this form
<form action="">
<input name="field[firstname]">
<input name="field[lastname]">
<input name="field[address]">
</form>
You should probably be able to create the form based on the fields names too, you are probably already doing this.
In the file that processes the response you can do something like this:
foreach($_POST['field'] as $field_name => $field_value) {
$sql_str[] = "{$field_name} = '{$field_value}'";
}
This just goes through the 'field' array that comes from post and puts the proper update text into another array.
Then just do a
mysql_query("UPDATE contactinfo SET ".implode(',', $sql_str)." WHERE `id` = '".$rid."';")
To put it into the database.
What you can do is add a column in the database with a bit flag and if the user is new or old, the flag will reflect it.
that way you can update the user to say if it is new or old.
hope this helps.
You might do well to investigate whether there is an ORM framework that you could use.
Anyway, the simplest way to do what you want is to pass the name of the field in the INPUT field.
$content = AddSlashes($content); // You may need HTMLEntities() here
$field = <<<FIELD
<input type="text" value="$content" />
FIELD;
Also, another useful trick to employ is to either supply an array of "protected" fields, or specify a prefix that makes the field unchangeable. For example, you almost certainly do not want a user to be able to change the primary keys.
So you could generate the form with
if ('id' == $meta->name or 'pk' == $meta->name or (0 === strpos($meta->name, 'pk_')))
{
// This is a primary key field
$html .= <<<PKFIELD
<input type="hidden" name="{$meta->name}" value="{$contents}" />
PKFIELD;
continue;
}
if (0 === strpos($meta->name, 'hf_'))
{
// hidden field, ignored (can't be changed)
continue;
}
if (0 === strpos($meta->name, 'ro_'))
{
// read-only field, shown but without even the name
$html .= <<<ROFIELD
<input type="text" readonly="readonly" class="readonly" value="{$contents}" />
ROFIELD;
continue;
}
Or you could use a fixed-size prefix and an array of templates:
$fieldtpls = array(
'pk_' => '<input type="hidden" name="{NAME}" value="{VALUE}" />',
'ta_' => '<textarea name="{NAME}">{VALUE}</textarea>',
'ro_' => '<input type="text" value="{VALUE}" readonly="readonly" />',
);
then you analyze each field and apply a default unless a known prefix is used.
Your users would then have to name the fields accordingly. Another possibility is to allow for a "meta-table" to hold the type and handling of each table and field, but in that case you would need to complicate a bit the user interface by creating a sort of "admin editor" for the Meta table:
table field type rw parameters
users name text yes
users id hidden no
users role text no
users notes area yes class:"widearea"
...and that way be dragons ORM frameworks.
Need a little help...
I have a basic html table with text field form in last column and a hidden field on each row of the web table. The data in this table is extracted out of a table in the database.
I want my users to be able to update one field in the database (a score) using this web form (page).
I have a hidden web form component on each row that contains the unique id of the record in the database for each row in the web page table.
I was attempting to create code that would update the entire list of entries on the web form, even if the user is not updating that particular field. (The values of the scores field are populated into the web form at the creation of the table. So if you did not update any scores, but hit the submit button, it would update the database table with the same values.)
Here’s my code: (abbreviated to save bytes…)
<?php
//Do all the database connection stuff up front
if (isset($_POST[‘score’]))
{
$student_id = $_POST[‘student_id’];
$score = $_POST['score'];
$n = count($score);
$i = 0;
echo "You have updated these student scores on this assignment. \r\n" .
"<ol>";
while ($i < $n)
{
echo "<hr><P>{$score[$i]} \r\n";
echo "<hr><P>{$student_id[$i]} \r\n";
$qry = "UPDATE assignments SET score = ".$score[$i]." WHERE student_id = " .$student_id[$i]. '"';
$result=#mysql_query($qry);
$i++;
}
}
if($result) {
header("location: member-index.php");
exit();
}else {
die("Query failed");
}
?>
Am I on the right track? Is there a better way to do what I’m attempting? All suggestions and ideas welcome!
Thank you in advance!
i'm guessing you are using
<input name="scores[]"/>
why not echo the unique id into the input name?
<input name="score[<?php echo $unique_id ?>]" />
this means in the loop, the $i would be the unique id (one less variable and less HTML).
and please use mysql_real_escape_string() when working with DB transactions. I know it's an example code but please don't forget that
Besides that, yes, you are on the right track