Currently I'm working on a large form with dynamic number of input fields, it can get extremely large (above 3k variables or more) and it causes problems with 'max_input_vars' option.
I'm looking for a workaround for this issue (I'm not interested in increasing the value of 'max_input_vars' option), so currently I'm trying to join all form fields values into single field (using jQuery serialize() method) and then recreate the variables on the server side.
This is what I have so far:
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Workaround for max_input_vars</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
</head>
<body>
<?php
if($_SERVER["REQUEST_METHOD"]==="POST" && !empty($_POST["data"])) {
$vars = explode("&", $_POST["data"]);
$data = array();
foreach($vars as $var) {
parse_str($var, $variable);
assign_var($_POST, $variable);
}
echo "<pre>";
var_dump($_POST);
echo "</pre>";
}
function assign_var(&$target, $var) {
$key = key($var);
if(is_array($var[$key]))
assign_var($target[$key], $var[$key]);
else {
if($key==0)
$target[] = $var[$key];
else
$target[$key] = $var[$key];
}
}
?>
<form id="myForm" method="POST">
<input type="text" name="var_1" value="<?php echo htmlentities("double quote: \"hello\"");?>"/><br/>
<input type="text" name="var_2" value="<?php echo htmlentities("single quote: 'hello'");?>"/><br/>
<input type="text" name="var_3" value="<?php echo htmlentities("text with & ampersant");?>"/><br/>
<input type="text" name="var_4" value="<?php echo htmlentities("animals");?>"/><br/>
<input type="text" name="matrix[]" value="1"/><br/>
<input type="text" name="matrix[]" value="2"/><br/>
<input type="text" name="matrix[]" value="3"/><br/>
<input type="text" name="matrix[]" value="4"/><br/>
<input type="text" name="matrix[]" value="5"/><br/>
<input type="text" name="matrix[]" value="6"/><br/>
<input type="text" name="matrix[]" value="7"/><br/>
<input type="text" name="var_5" value="abc"/><br/>
<input type="text" name="var_6" value="bcd"/><br/>
<input type="text" name="var_7" value="cde"/><br/>
<input type="text" name="var_8" value="def"/><br/>
<input type="text" name="multi_matrix[colors][]" value="red"/><br/>
<input type="text" name="multi_matrix[colors][]" value="blue"/><br/>
<input type="text" name="multi_matrix[colors][]" value="green"/><br/>
<input type="text" name="multi_matrix[weight][]" value="75"/><br/>
<input type="text" name="multi_matrix[weight][]" value="83"/><br/>
<input type="text" name="multi_matrix[weight][]" value="62"/><br/>
<input type="text" name="multi_matrix[height][]" value="170"/><br/>
<input type="submit" value="Send">
</form>
<style>
input {
margin: 5px 0;
}
</style>
<script type="text/javascript">
(function(){
$(function(){
$("#myForm").submit(function(event) {
var $this = $(this);
var data = $this.serialize();
$this.find("input, textarea, select, button").remove();
$this.append("<input type='hidden' class='data' name='data'/>");
$this.find("input.data").val(data);
});
});
})(jQuery);
</script>
</body>
</html>
As you can see, I'm intercepting the submit event and replace all form fields with single 'data' field. On PHP side I'm using explode() and pars_str() methods to recreate the variable, lastly I want to put the variable into $_POST array, so I created simple recursive function that can handle simple values and multidimensional associative arrays.
The result is a $_POST array filled with form values, as if the form was submitted normally.
What do you think about above method ? Maybe there's a much simpler solution to the problem that I hadn't noticed earlier ? If not, are there any options to improve the above code ? Are there any negative side effects of the above solution ?
Thanks in advance !
I need assistance in taking the next step in inserting data entered into a dynamically-generated form. I have looked for a number of days at other similar questions and am still missing a piece.
Here is my HTML form (minus error trapping/validations):
<form id="form" name="form" method="post" action="recipeaddsubmit.php">
<table id="myTable">
<tr>
<td width="10%">Amount</td>
<td width="10%">Measure</td>
<td width="35%">Ingredient</td>
</tr>
<tr>
<td valign="top">
<input type="text" name="Amt1" id="Amt1" size="1" />
<input type="text" name="Amt2" id="Amt2" size="1" />
</td>
<td valign="top">
<select name="Measure" id="Measure">
<option>Cup</option>
<option>Ounce</option>
</select>
</td>
<td valign="top">
<input type="text" name="Ing" id="Ing" size="40" />
</td>
</tr>
</table>
<button type="button" onclick="displayResult()">Insert new row</button>
<input type="submit" name="button" id="button" value="Submit" />
</form>
Here is the javascript in my header:
<script>
function displayResult()
{
var table=document.getElementById("myTable");
var row=table.insertRow(-1);
var cell1=row.insertCell(0);
var cell2=row.insertCell(1);
var cell3=row.insertCell(2);
cell1.innerHTML="<input type='text' name='Amt1' id='Amt1' size='1' />
<input type='text' name='Amt2' id='Amt2' size='1' />";
cell2.innerHTML="<select name='Measure' id='Measure'> <option>Cup</option>
<option>Ounce</option></select>";
cell3.innerHTML="<input type='text' name='Ing' id='Ing' size='40' />";
}
</script>
And here is my attempted/partial mysqli insert statement (checkInput is a self-created validation function I have used before without issue):
$amt1 = checkInput($_POST['Amt1']);
$amt2 = checkInput($_POST['Amt2']);
$measure = checkInput($_POST['Measure']);
$ing = checkInput($_POST['Ing']);
$ingAddQuery ="INSERT INTO Ingredient (Amt1, Amt2, Measure, Ing)
VALUES ({$amt1}, {$amt2}, {$measure}, {$ing})";
mysqli_query($mysqli,$ingAddQuery);
if (!mysqli_query($mysqli,$ingAddQuery))
{
die('Error: ' . mysqli_error());
}
What I don't understand is how to incorporate a foreach loop in terms of how to increment for a certain number of rows; I understand the concept but not the application in this case.
Thank you for your assistance!
change the name from amt1 to amt1[] and etcetera...
so
<input type="text" name="Amt1[]" id="Amt1[]" size="1" />
When you submit the form,
$_POST['Amt1']; //is an array
will be an array, so you could do
$Amt1Array = $_POST['Amt1'];
foreach($Amt1Array => $Amt1){
//do stuff here
}
Better yet you can index the array using the js to create names like...
<input type="text" name="Amt1[0]" id="Amt1[0]" size="1" />
<input type="text" name="Amt2[0]" id="Amt2[0]" size="1" />
<input type="text" name="Amt1[1]" id="Amt1[1]" size="1" />
<input type="text" name="Amt2[1]" id="Amt2[1]" size="1" />
Then in the PHP you could
$Amt1Array = $_POST['Amt1'];
$Amt2Array = $_POST['Amt2'];
foreach($Amt1Array as $key => $Amt1Value){
$Amt2Value = $Amt2Array[$key];
//do stuff with rows
}
I have a suggestion.
Why don't u create a hidden input type.
<input type="hidden" name="cellCount" value="0" />
Each time u insert a new row, change value of this hidden field. This will not show on browser. This hidden element will also get submit when u submit form. this can be retrieved on server by $_POST["cellCount"].
Hope this will help u.
I have an HTML input form that is being sent as a PHP_SELF and then stored on a MySQL table. The input field is dynamically controlled with JS. There are 4 inputs: number (text), amount (int), Approval (text), and Date (text). There inputs are all arrays when they are sent to the PHP file via POST. They're stored in a MySQL table with column fields as: ID (primary key), num (text(4)), amnt (decimal(8,2)), app (text(10)), and date (varchar(10)). I'm getting three significant errors when I try to run the page.
If a number such a 0125 is entered in the number field on the form, it is stored as 125 in the MySQL table. This is regardless of the fact that the field is being stored as a text string.
The Approval field works perfectly fine when only integers are entered, however, when only text or a combination of text and numbers is inserted, the MySQL query produces the following error: Error: Unknown column 'aft859' in 'field list'. For example, when 853234 is entered, everything goes through fine, but when aft859 is entered, the error is produced.
When a date is entered, it gets inputted into the MySQL table as a decimal value. For example, a date of 08/07/2012 is saved as '0.00056802'.
I have checked every line to make sure that nothing is being converted in the PHP or HTML process, and I've echoed every line to make sure that the values are being handled properly. After much debugging, I'm lead to believe that the following two sections might be causing my problem:
//Check To See If User Has Already Created Table
$sql = "CREATE TABLE IF NOT EXISTS $tablename_cc (
ID int NOT NULL AUTO_INCREMENT,
PRIMARY KEY(ID),
cc_num TEXT(4),
cc_amnt DECIMAL(8,2),
cc_app TEXT(10),
cc_date VARCHAR(10)
);";
or it might be this:
if (!mysql_query('INSERT INTO ' .$tablename_cc. '(cc_num, cc_amnt, cc_app, cc_date) VALUES '.implode(',',$pairs)))
die('Error: ' . mysql_error());
else
echo '<strong>', "Your information have been submitted and will be added to your account upon approval.", '</strong>', "</br>", "</br>", "</br>";
I'm not too familiar with PHP, HTML, or MySQL (this is my first program ever), and I'm not sure if I've missed something. I tried to check all quotes and make sure they were right. I'm running all this in Wordpress, just in case that's culprit. Here is my code in its entirety for reference:
<?php
if(isset($_POST['submit']))
{
//Get Current User Login
global $current_user;
$current_user = wp_get_current_user();
$ulog = $current_user->user_login;
$tablename_cc = "cc_".$ulog;
//Check To See If User Has Already Created Table
$sql = "CREATE TABLE IF NOT EXISTS $tablename_cc (
ID int NOT NULL AUTO_INCREMENT,
PRIMARY KEY(ID),
cc_num TEXT(4),
cc_amnt DECIMAL(8,2),
cc_app TEXT(10),
cc_date VARCHAR(10)
);";
mysql_query($sql);
$cc_num = $_POST['cc_num'];
$cc_amnt = $_POST['cc_amnt'];
$cc_app = $_POST['cc_app'];
$cc_date = $_POST['cc_date'];
$items = array_map(null,$cc_num,$cc_amnt,$cc_app,$cc_date);
$pairs = array();
foreach ($items as $sub) {
if(implode(',', $sub) != ",,,")
$pairs[] = '('.implode(',', $sub).')';
}
echo implode(',',$pairs);
if (!mysql_query('INSERT INTO ' .$tablename_cc. '(cc_num, cc_amnt, cc_app, cc_date) VALUES '.implode(',',$pairs)))
die('Error: ' . mysql_error());
else
echo '<strong>', "Your information has been submitted and will be added to your account upon approval.", '</strong>', "</br>", "</br>", "</br>";
}
?>
<!--raw-->
<html>
<head>
<title></title>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js"></script>
<script src="jquery.maskedinput.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function() {
$('#btnAdd').click(function() {
var num = $('.ccinput').length; // how many "duplicatable" input fields we currently have
var newNum = new Number(num + 1); // the numeric ID of the new input field being added
// create the new element via clone(), and manipulate it's ID using newNum value
var newElem = $('#input' + num).clone().attr('id', 'input' + newNum);
// insert the new element after the last "duplicatable" input field
$('#input' + num).after(newElem);
// enable the "remove" button
$('#btnDel').attr('disabled','');
$("*#date").mask("99/99/9999");
// business rule: you can only add 20 names
if (newNum == 20)
$('#btnAdd').attr('disabled','disabled');
});
$('#btnDel').click(function() {
var num = $('.ccinput').length; // how many "duplicatable" input fields we currently have
$('#input' + num).remove(); // remove the last element
// enable the "add" button
$('#btnAdd').attr('disabled','');
// if only one element remains, disable the "remove" button
if (num-1 == 1)
$('#btnDel').attr('disabled','disabled');
});
$("*#date").mask("99/99/9999");
});
</script>
</head>
<body>
Please fill in your information in the form below and press submit. If you need to add more, please click the "Add" button at the bottom of the form. You may enter a maximum of 20 at a time. Leave all unused fields blank.
<form method="post" action="<?php echo htmlentities($PHP_SELF); ?>">
<fieldset>
<legend>Information:</legend>
<div id="input1" class="ccinput">
# (last 4 digits): <input id="cnum" type="text" name="cc_num[]" maxlength="4" size="4" /> CC Amount: <input id="camnt" type="int" name="cc_amnt[]" /> Approval Code: <input id="appr" type="text" name="cc_app[]" maxlength="10" size="10" /> Date: <input id="date" type="text" name="cc_date[]" /> </br>
</div>
<div id="input2" class="ccinput">
# (last 4 digits): <input id="cnum" type="text" name="cc_num[]" maxlength="4" size="4" /> CC Amount: <input id="camnt" type="int" name="cc_amnt[]" /> Approval Code: <input id="appr" type="text" name="cc_app[]" maxlength="10" size="10" /> Date: <input id="date" type="text" name="cc_date[]" /> </br>
</div>
<div id="input3" class="ccinput">
# (last 4 digits): <input id="cnum" type="text" name="cc_num[]" maxlength="4" size="4" /> CC Amount: <input id="camnt" type="int" name="cc_amnt[]" /> Approval Code: <input id="appr" type="text" name="cc_app[]" maxlength="10" size="10" /> Date: <input id="date" type="text" name="cc_date[]" /> </br>
</div>
<div id="input4" class="ccinput">
# (last 4 digits): <input id="cnum" type="text" name="cc_num[]" maxlength="4" size="4" /> CC Amount: <input id="camnt" type="int" name="cc_amnt[]" /> Approval Code: <input id="appr" type="text" name="cc_app[]" maxlength="10" size="10" /> Date: <input id="date" type="text" name="cc_date[]" /> </br>
</div>
<div id="input5" class="ccinput">
# (last 4 digits): <input id="cnum" type="text" name="cc_num[]" maxlength="4" size="4" /> CC Amount: <input id="camnt" type="int" name="cc_amnt[]" /> Approval Code: <input id="appr" type="text" name="cc_app[]" maxlength="10" size="10" /> Date: <input id="date" type="text" name="cc_date[]" /> </br>
</div>
<div>
<input type="button" id="btnAdd" value="Add" />
<input type="button" id="btnDel" value="Remove" />
</div>
</fieldset>
<input type="submit" value="Submit" name="submit" />
</form>
</body>
</html>
<!--/raw-->
The reason your text values are being truncated (losing leading zeros) is because you're inserting them as numbers and MySQL is dropping the leading zero, and the dates are becoming decimals is because you're inserting them as equations and MySQL is evaluating them.
The reason for this is this line:
$pairs[] = '('.implode(',', $sub).')';
None of the values are surrounded by quotes. You can fix this with:
$pairs = '("'.implode('","', $sub).'")';
Then, you're using implode() again on the already imploded list on the line:
if (!mysql_query('INSERT INTO ' .$tablename_cc. '(cc_num, cc_amnt, cc_app, cc_date) VALUES '.implode(',',$pairs)))
Update this line to:
if (!mysql_query('INSERT INTO ' .$tablename_cc. '(cc_num, cc_amnt, cc_app, cc_date) VALUES ' .$pairs . ))
if (!mysql_query('INSERT INTO ' .$tablename_cc. '(cc_num, cc_amnt, cc_app, cc_date) VALUES '.implode(',',$pairs)))
You need to wrap the input values in apostrophes; otherwise, they'll be treated as numbers - that's why you get the Unknown column error and the date is treated as a sum and not a date.
if (!mysql_query("INSERT INTO " .$tablename_cc. " (cc_num, cc_amnt, cc_app, cc_date) VALUES '".implode("','",$pairs) . "'"))
I think that will do it.
I have a sort of complex php,html script that I am using to create an interactive design. I am using a repeat table and i am basically cloning the contents of a particular table row and appending it to the end of the table. When I select a certain option in the select menu, the corresponding textfields get updated with the correct values. However cloned rows misbehave
What I'm asking is if there is a way to make this fields also change values. Here is the various code
Code for adding/cloning a row. Please note the id details is the id of a table row
$("#addrow1").click(function(){
//alert("It works");
//$('#description tr:last').after('<tr>...</tr>');
$('#details').clone().appendTo('#dailyexpense');
});
Code for changing the textfield and textbox values
$("#cities").live('change',function(){
var cityrates = $("#cities :selected").val();
var brkfstrates = (0.2 * cityrates).toFixed(1);
$("#brkfasttxt").val(brkfstrates);
$("#brkfastchk").val(brkfstrates);
var lunchrates = (0.3 * cityrates).toFixed(1);
$("#lunchtxt").val(lunchrates);
$("#lunchchk").val(lunchrates);
var dinnerrates = (0.3 * cityrates).toFixed(1);
$("#dinnertxt").val(dinnerrates);
$("#dinnerchk").val(dinnerrates);
var incdntlrates = (0.2 * cityrates).toFixed(1);
$("#incidentltxt").val(incdntlrates);
$("#incidentlchk").val(incdntlrates);
});
My table row code for the one that gets loaded by the browser
<tr id="details">
<td><label for="date"></label>
<input style="background-color:#CCC;" type="text" name="date" id="date" /></td>
<td><label for="cities"></label>
<select name="cities" id="cities" style="background-color:#CCC; width:220px;">
<?php
foreach($country as $makassi1){
$selectcities = "SELECT City, Country, Rate FROM perdiem_rates WHERE Country = '$makassi1'";
$checkcity = mysql_query($selectcities)or die(mysql_error());
$countcities = mysql_num_rows($checkcity);
while($row=mysql_fetch_assoc($checkcity))
{
$countries = ($row['Country']);
$names =($row['City']) ;
$rate =($row['Rate']) ;
$ratess=$countries."-".$names
?>
<option id="cityoptrates" value="<?php echo $rate; ?>">
<?php echo $ratess; ?>
</option>
<?php
}
}
?>
</select></td>
<td><input name="brkfastchk" type="checkbox" class="chkbox" id="brkfastchk" />
<label for="brkfasttxt"></label>
<input style="background-color:#CCC;" name="brkfasttxt" type="text" id="brkfasttxt" size="5" readonly="readonly" />
<label for="brkfastchk"></label></td>
<td><input type="checkbox" name="lunchchk" id="lunchchk" class="chkbox" />
<label for="lunchtxt"></label>
<input style="background-color:#CCC;" name="lunchtxt" type="text" id="lunchtxt" size="5" readonly="readonly" />
<label for="lunchchk"></label></td>
<td><input type="checkbox" name="dinnerchk" id="dinnerchk" class="chkbox" />
<label for="dinnertxt"></label>
<input style="background-color:#CCC;" name="dinnertxt" type="text" id="dinnertxt" size="5" readonly="readonly" />
<label for="dinnerchk"></label></td>
<td><input type="checkbox" name="incidentlchk" id="incidentlchk" class="chkbox" />
<label for="incidentltxt"></label>
<input style="background-color:#CCC;" name="incidentltxt" type="text" id="incidentltxt" size="5" readonly="readonly" />
<label for="incdntchk"></label></td>
<td colspan="2"><label for="daily_totals"></label>
<input style="background-color:#CCC;" name="daily_totals" type="text" id="daily_totals" size="5" /></td>
</tr>
As per the above my textfield value changing code works perfectly with the first initial row. The cloned rows don't work. The only one which works on the cloned rows is the select menu for selecting the cities. Help needed. Open to suggestions and improvements.
link to actual code in jsfiddle http://jsfiddle.net/NAafu/10/
In your case maybe you should also clone the events:
$('#details').clone(true).appendTo('#dailyexpense');
as stated in the documentation of clone()
EDIT - The problem perhaps is that you are using an id selector ($("#cities").live) which returns only one element. Ids should be unique on the page you should use a class instead
I'm trying to upload a form to the database, that uses the same field names, as part of a CMS.
This is the form (I have used JQuery to multiply the div the number of options per product):
<form method="post" enctype="multipart/form-data" action="testing.php">
<div class="OptExtra1">
<h3>Additional Option</h3>
<label for="RESAddType">File type (i.e. “CD” or “Download”)</label>
<input name="RESAddType[]" type="text" id="RESAddType" size="48" class="FW" />
<label for="RESAddTitle">File title (i.e. “Boxed Set of 4 CDs”)</label>
<input name="RESAddTitle[]" type="text" id="RESAddTitle" size="48" class="FW" />
<label for="RESAddFType">File format (As “MP3” // “WORD” // “PDF”)</label>
<input name="RESAddFType[]" type="text" id="RESAddFType" size="48" class="FW" />
<label for="RESAddPrice">File price (Enter as “6.99” – <strong>NO “£” SIGN!</strong>)</label>
<input name="RESAddPrice[]" type="text" id="RESAddPrice" size="48" class="FW" />
<label for="RESAddFName">File name</label>
<input name="RESAddFName[]" type="text" id="RESAddFName" size="48" class="FW" />
<label for="RESAddTxt">File text</label>
<textarea name="RESAddTxt[]" id="RESAddTxt" cols="70" rows="50" class="mceAdvanced"></textarea>
<label for="RESAddSample">File text</label>
<textarea name="RESAddSample[]" id="RESAddSample" cols="70" rows="50" class="mceVSimple"></textarea>
<input type="button" value="Add another option" class="SubmitButton" onclick="inserter()" />
<hr />
</div>
<p><input type="submit" name="submit" value="Add Resource" class="SubmitButton"/><input type="hidden" name="RESCatCode" value="2" /><input type="hidden" name="RESCatSubCode" value="5" /><input type="hidden" name="submitted" value="true" /></p>
and this is what I have so far for the PHP
if(isset($_POST['submitted'])){
$RESCode = 100;
$RESAddType = $_POST['RESAddType'];
$RESAddTitle = htmlentities($_POST['RESAddTitle'], ENT_QUOTES);
$RESAddFType = $_POST['RESAddFType'];
$RESAddPrice = $_POST['RESAddPrice'];
$RESAddFName = $_POST['RESAddFName'];
$RESAddTxt = mysql_real_escape_string($_POST['RESAddTxt']);
$RESAddSample = mysql_real_escape_string($_POST['RESAddSample']);
for ($i=0; $i < count($_POST['RESAddType']); $i++) {
$OptionQuery = mysql_query ("INSERT INTO ResAdd (RESAddCode, RESCode, RESAddType, RESAddTitle, RESAddFType, RESAddPrice, RESAddFName, RESAddTxt, RESAddSample) VALUES ('', '".$RESCode."', '".$RESAddType."', '".$RESAddTitle."', '".$RESAddFType."', '".$RESAddPrice."', '".$RESAddFName."', '".$RESAddTxt."', '".$RESAddSample."');");
}
header("Location: welcome.php");
exit;
}
It kind of worked, but is just putting in the word "array" into the database. Also the htmlentities and mysql_real_escape_string posts don't upload anything to the database.
Any ideas please?
You've forgotten something :)
$OptionQuery = mysql_query ("INSERT INTO ResAdd (RESAddCode, RESCode, RESAddType, RESAddTitle, RESAddFType, RESAddPrice, RESAddFName, RESAddTxt, RESAddSample) VALUES ('', '".$RESCode[$i]."', '".$RESAddType[$i]."', '".$RESAddTitle[$i]."', '".$RESAddFType[$i]."', '".$RESAddPrice[$i]."', '".$RESAddFName[$i]."', '".$RESAddTxt[$i]."', '".$RESAddSample[$i]."');");
Look at all these $i in the code above. If you don't use them, the script will try to use the entire array (and trying to print or save an array as a string always results in printing "Array").
P.S.I've edited my answer. Sorry for the previous one, I've misunderstood the code and posted a wrong answer.
You need to looping
$cnt=count($_POST['RESAddType']);
for ($counter=0; $counter < $cnt; $counter++)
{
$_POST['RESAddType'][$counter]// to access the value
$_POST['RESAddPrice'][$counter]//
//create your query here
}