I have a simple HTML script:
<form action="" method="post">
<input type="text" name="amount">
<?php echo $amountError; ?>
<input type="submit">
</form>
And I display errors using this:
<?
$amount = $_POST['amount'];
if ($_SERVER['REQUEST_METHOD'] == 'POST') {
if (empty($_POST['amount'])) {
$amountError = 'Empty amount';
} else {
header("Location: apmoketi.php");
}
?>
In the apmoketi.php file there is only one line
echo $amount = $_POST['amount'];
However, when I'm trying to display data in the apmoketi.php page, I don't get the value of the $amount variable using action="", but using action="apmoketi.php" I can get it but my PHP code doesn't checking for any errors, why?
A call to header("Location: apmoketi.php"); makes the browser follow the specified URL as another, completely separate request. This new request doesn't have access to the POST data of the previous one.
Your options:
use include so apmoketi.php has access to the variables of the current script
use sessions to preserve data between requests
use a query parameter to carry the value over:
header('Location: apmoketi.php?amount=' . urlencode($amount));
When you redirect to header("Location: apmoketi.php");, the variables are no longer in $_POST[] so you need to set a session variable before you redirect:
$_SESSION['amount'] = $amount;
the way i do it is i have a folder called action with subfiles in there lets say the file called file2 in this file all the php action happens.
and in the root of my folder i have another file called file1 and in here theres the html and now how i would do it is
<form action="action/file2.php" method="post">
<input type="text" name="amount">
<?php echo $amountError; ?>
<input type="submit">
</form>
Related
I think that this problem occurs often on a web application development. But I'll try to explain in details my problem.
I'd like to know how to correct this behavior, for example, when I have a block of code like this :
<?
if (isset($_POST['name'])) {
... operation on database, like to insert $_POST['name'] in a table ...
echo "Operation Done";
die();
}
?>
<form action='page.php' method='post' name="myForm">
<input type="text" maxlength="50" name="name" class="input400" />
<input type="submit" name="Submit" />
</form>
When the form gets submitted, the data get inserted into the database, and the message Operation Done is produced. Then, if I refreshed the page, the data would get inserted into the database again.
How this problem can be avoided? Any suggestion will be appreciated :)
Don't show the response after your create action; redirect to another page after the action completes instead. If someone refreshes, they're refreshing the GET requested page you redirected to.
// submit
// set success flash message (you are using a framework, right?)
header('Location: /path/to/record');
exit;
Set a random number in a session when the form is displayed, and also put that number in a hidden field. If the posted number and the session number match, delete the session, run the query; if they don't, redisplay the form, and generate a new session number. This is the basic idea of XSRF tokens, you can read more about them, and their uses for security here: http://en.wikipedia.org/wiki/Cross-site_request_forgery
Here is an example:
<?php
session_start();
if (isset($_POST['formid']) && isset($_SESSION['formid']) && $_POST["formid"] == $_SESSION["formid"])
{
$_SESSION["formid"] = '';
echo 'Process form';
}
else
{
$_SESSION["formid"] = md5(rand(0,10000000));
?>
<form action="<?php echo htmlspecialchars($_SERVER["PHP_SELF"]); ?>" method="post">
<input type="hidden" name="formid" value="<?php echo htmlspecialchars($_SESSION["formid"]); ?>" />
<input type="submit" name="submit" />
</form>
<?php } ?>
I ran into a similar problem. I need to show the user the result of the POST. I don't want to use sessions and I don't want to redirect with the result in the URL (it's kinda secure, I don't want it accidentally bookmarked). I found a pretty simple solution that should work for the cases mentioned in other answers.
On successfully submitting the form, include this bit of Javascript on the page:
<script>history.pushState({}, "", "")</script>
It pushes the current URL onto the history stack. Since this is a new item in history, refreshing won't re-POST.
UPDATE: This doesn't work in Safari. It's a known bug. But since it was originally reported in 2017, it may not be fixed soon. I've tried a few things (replaceState, etc), but haven't found a workaround in Safari. Here are some pertinent links regarding the issue:
Safari send POST request when refresh after pushState/replaceState
https://bugs.webkit.org/show_bug.cgi?id=202963
https://github.com/aurelia/history-browser/issues/34
Like this:
<?php
if(isset($_POST['uniqid']) AND $_POST['uniqid'] == $_SESSION['uniqid']){
// can't submit again
}
else{
// submit!
$_SESSION['uniqid'] = $_POST['uniqid'];
}
?>
<form action="page.php" method="post" name="myForm">
<input type="hidden" name="uniqid" value="<?php echo uniqid();?>" />
<!-- the rest of the fields here -->
</form>
I think it is simpler,
page.php
<?php
session_start();
if (isset($_POST['name'])) {
... operation on database, like to insert $_POST['name'] in a table ...
$_SESSION["message"]="Operation Done";
header("Location:page.php");
exit;
}
?>
<html>
<body>
<div style='some styles'>
<?php
//message here
echo $_SESSION["message"];
?>
</div>
<form action='page.php' method='post'>
<!--elements-->
</form>
</body>
</html>
So, for what I needed this is what works.
Based on all of the above solutions this allows me to go from a form to another form, and to the n^ form , all the while preventing the same exact data from being "saved" over and over when a page is refreshed (and the post data from before lingers onto the new page).
Thanks to those who posted their solution which quickly led me to my own.
<?php
//Check if there was a post
if ($_POST) {
//Assuming there was a post, was it identical as the last time?
if (isset($_SESSION['pastData']) AND $_SESSION['pastData'] != $_POST) {
//No, Save
} else {
//Yes, Don't save
}
} else {
//Save
}
//Set the session to the most current post.
$_session['pastData'] = $_POST;
?>
We work on web apps where we design number of php forms. It is heck to write another page to get the data and submit it for each and every form. To avoid re-submission, in every table we created a 'random_check' field which is marked as 'Unique'.
On page loading generate a random value and store it in a text field (which is obviously hidden).
On SUBMIT save this random text value in 'random_check' field in your table. In case of re-submission query will through error because it can't insert the duplicate value.
After that you can display the error like
if ( !$result ) {
die( '<script>alertify.alert("Error while saving data OR you are resubmitting the form.");</script>' );
}
No need to redirect...
replace die(); with
isset(! $_POST['name']);
, setting the isset to isset not equal to $_POST['name'], so when you refresh it, it would not add anymore to your database, unless you click the submit button again.
<?
if (isset($_POST['name'])) {
... operation on database, like to insert $_POST['name'] in a table ...
echo "Operation Done";
isset(! $_POST['name']);
}
?>
<form action='page.php' method='post' name="myForm">
<input type="text" maxlength="50" name="name" class="input400" />
<input type="submit" name="Submit" />
</form>
This happen because of simply on refresh it will submit your request again.
So the idea to solve this issue by cure its root of cause.
I mean we can set up one session variable inside the form and check it when update.
if($_SESSION["csrf_token"] == $_POST['csrf_token'] )
{
// submit data
}
//inside from
$_SESSION["csrf_token"] = md5(rand(0,10000000)).time();
<input type="hidden" name="csrf_token" value="
htmlspecialchars($_SESSION["csrf_token"]);">
I think following is the better way to avoid resubmit or refresh the page.
$sample = $_POST['submit'];
if ($sample == "true")
{
//do it your code here
$sample = "false";
}
I have couple of identical HTML pages which take user input and with PHP I save the input on text files. As it's always the same I would like to apply the same PHP on every html page. So my question is if there is a way to redirect to the next html page but not through PHP, so that the PHP can be reusable for all the pages?
Because if I add onclick="window.location.href='/main2.html' then the PHP is not fired up or if I change action="main2.html" then again the PHP is not included. Or if I add header("Location: main2.html"); then it cannot really be applied to all the html pages, as it goes main.html -> main2.html -> main3.html etc.
HTML 1:
<form method="post" action="process.php">
<input type="text" name="address" required>
<input type="submit" value="Submit" id="intro">
</form>
HTML 2:
<form method="post" action="process.php">
<input type="text" name="address" required>
<input type="submit" value="Submit" >
</form>
PHP:
<?php
$myfile = fopen("text.txt", "a+");
$address = $_POST['address'].";";
fwrite($myfile, $address);
//header("Location: main2.html");
fclose($myfile);
?>
Thank you in advance!
Although you don't want to use PHP, it can make this pretty simple for you. You can use the session variable in PHP to track the user, the entries he has made and even allow them to go back and forward.
You can read more on it here.
You can redirect the user based on the session counter or the source from where the call is made and direct them accordingly to the next page. This makes your code scalable as well.
So you code will be something like this:
session_start();
if( isset( $_SESSION['counter'] ) ) {
$_SESSION['counter'] += 1;
}else {
$_SESSION['counter'] = 1;
}
$newURL = "HTMLPage".$_SESSION['counter']."html";
header('Location: '.$newURL);
The above code will redirect the user to the next page. PS: You will have to handle the case for your last html page.
I want to use back option on php without losing the form data.
I've tried this way;
if ($username==""){
echo 'Please fill. <input type="button" value="Back" onClick="history.back()">';
} else{
$doaction;
}
And this way;
$url= $_SERVER['HTTP_REFERER'];
if ($username==""){
echo "Please fill.";
header("refresh: 2; url=$url");
}
else{
$doaction;
}
On both ways I lose my data. How can I make this better?
This worked for me and using ob_start(); (in PHP below) needs to be included, otherwise it will throw an error, such as:
PHP Warning: Cannot modify header information - headers already sent by (output started)
Use the following exactly as shown, then modify to suit later.
Using Sessions is a way to achieve this. Each field will re-appear in the input boxes, if they were filled.
HTML form (form.php)
<?php
session_start();
?>
<form method="post" action="submitted.php">
<p>
<label for='name'>Your Name:</label>
<br>
<input type="text" name="username" value="<?php echo isset($_SESSION['username']) ? $_SESSION['username'] : '' ?>">
</p>
<p>
<label for='name'>Email:</label>
<br>
<input type="text" name="email" value="<?php echo isset($_SESSION['email']) ? $_SESSION['email'] : '' ?>">
</p>
<input type="submit" name="submit" value="Submit">
<br>
</form>
PHP (submitted.php)
<?php
ob_start();
session_start();
$_SESSION['username'] = $_POST['username'];
$_SESSION['email'] = $_POST['email'];
$url= $_SERVER['HTTP_REFERER'];
$username=$_POST['username'];
$email=$_POST['email'];
// use this one below, if you want to check more than one field
// if (empty($_POST['username']) || empty($_POST['email']) ){
if (empty($_POST['username'])){
echo "Fill in all fields.";
header("refresh: 2; url=$url");
}
else{
echo "OK, redirecting back to show fields are showing, or not.";
header("refresh: 2; url=$url");
}
Your approach reloads the formular, so the webserver will send a clean form to the client. If you want a prefilled form you will have to use a PHP script which knows the formerly filled in values and creates a prefilled form.
In the code you have used, (assuming you have a form further up) there is no data being passed between the pages because nothing is telling the script to transfer the data between that page and it's destination.
In your first example, history.back() simply tells the browser to go back to the last page viewed before the current one. In your second example, your header line essentially just tells the browser to go back to the previous page after two seconds.
To keep data between page transfers, without any further knowledge of what you're doing, I would suggest using JavaScript to fetch your form data and pass it into a URL used in a window.location call (forming a GET request with your form data in it), OR by using javascript to set a cookie containing the data input before you tell the browser to switch page.
In the first solution, you could then use php's $_GET global to access your form data.
In the second solution, you could use javascript to re-populate the form on page load (or at will)
I can pass values form one page to another but I need to pass value like this,
Page 1:
Page4.php
Page3.php
I need to pass the value in a text field in the Page1.php to a text field in Page2.php, since the form is not directly redirectly to page2, I am unable to pass the value, I tried session, form post method and few other methods but I am yet to succeed.
I would be very happy if you can help me with the code or some suggestions.
Thanks!
Edit..........
I found the answer, thanks for the help, it was actually a careless mistake on my part, I used $_post instead of $_session.
Its working now.
Thanks for the help.
Use something like this:
page1.php
<?php
session_start();
$_SESSION['myValue']=3; // You can set the value however you like.
?>
Any other PHP page:
<?php
session_start();
echo $_SESSION['myValue'];
?>
A few notes to keep in mind though: You need to call session_start() BEFORE any output, HTML, echos - even whitespace.
You can keep changing the value in the session - but it will only be able to be used after the first page - meaning if you set it in page 1, you will not be able to use it until you get to another page or refresh the page.
The setting of the variable itself can be done in one of a number of ways:
$_SESSION['myValue']=1;
$_SESSION['myValue']=$var;
$_SESSION['myValue']=$_GET['YourFormElement'];
And if you want to check if the variable is set before getting a potential error, use something like this:
if(!empty($_SESSION['myValue'])
{
echo $_SESSION['myValue'];
}
else
{
echo "Session not set yet.";
}
Solution using just POST - no $_SESSION
page1.php
<form action="page2.php" method="post">
<textarea name="textarea1" id="textarea1"></textarea><br />
<input type="submit" value="submit" />
</form>
page2.php
<?php
// this page outputs the contents of the textarea if posted
$textarea1 = ""; // set var to avoid errors
if(isset($_POST['textarea1'])){
$textarea1 = $_POST['textarea1']
}
?>
<textarea><?php echo $textarea1;?></textarea>
Solution using $_SESSION and POST
page1.php
<?php
session_start(); // needs to be before anything else on page to use $_SESSION
$textarea1 = "";
if(isset($_POST['textarea1'])){
$_SESSION['textarea1'] = $_POST['textarea1'];
}
?>
<form action="page1.php" method="post">
<textarea name="textarea1" id="textarea1"></textarea><br />
<input type="submit" value="submit" />
</form>
<br /><br />
Go to page2
page2.php
<?php
session_start(); // needs to be before anything else on page to use $_SESSION
// this page outputs the textarea1 from the session IF it exists
$textarea1 = ""; // set var to avoid errors
if(isset($_SESSION['textarea1'])){
$textarea1 = $_SESSION['textarea1']
}
?>
<textarea><?php echo $textarea1;?></textarea>
WARNING!!! - This contains no validation!!!
I think that this problem occurs often on a web application development. But I'll try to explain in details my problem.
I'd like to know how to correct this behavior, for example, when I have a block of code like this :
<?
if (isset($_POST['name'])) {
... operation on database, like to insert $_POST['name'] in a table ...
echo "Operation Done";
die();
}
?>
<form action='page.php' method='post' name="myForm">
<input type="text" maxlength="50" name="name" class="input400" />
<input type="submit" name="Submit" />
</form>
When the form gets submitted, the data get inserted into the database, and the message Operation Done is produced. Then, if I refreshed the page, the data would get inserted into the database again.
How this problem can be avoided? Any suggestion will be appreciated :)
Don't show the response after your create action; redirect to another page after the action completes instead. If someone refreshes, they're refreshing the GET requested page you redirected to.
// submit
// set success flash message (you are using a framework, right?)
header('Location: /path/to/record');
exit;
Set a random number in a session when the form is displayed, and also put that number in a hidden field. If the posted number and the session number match, delete the session, run the query; if they don't, redisplay the form, and generate a new session number. This is the basic idea of XSRF tokens, you can read more about them, and their uses for security here: http://en.wikipedia.org/wiki/Cross-site_request_forgery
Here is an example:
<?php
session_start();
if (isset($_POST['formid']) && isset($_SESSION['formid']) && $_POST["formid"] == $_SESSION["formid"])
{
$_SESSION["formid"] = '';
echo 'Process form';
}
else
{
$_SESSION["formid"] = md5(rand(0,10000000));
?>
<form action="<?php echo htmlspecialchars($_SERVER["PHP_SELF"]); ?>" method="post">
<input type="hidden" name="formid" value="<?php echo htmlspecialchars($_SESSION["formid"]); ?>" />
<input type="submit" name="submit" />
</form>
<?php } ?>
I ran into a similar problem. I need to show the user the result of the POST. I don't want to use sessions and I don't want to redirect with the result in the URL (it's kinda secure, I don't want it accidentally bookmarked). I found a pretty simple solution that should work for the cases mentioned in other answers.
On successfully submitting the form, include this bit of Javascript on the page:
<script>history.pushState({}, "", "")</script>
It pushes the current URL onto the history stack. Since this is a new item in history, refreshing won't re-POST.
UPDATE: This doesn't work in Safari. It's a known bug. But since it was originally reported in 2017, it may not be fixed soon. I've tried a few things (replaceState, etc), but haven't found a workaround in Safari. Here are some pertinent links regarding the issue:
Safari send POST request when refresh after pushState/replaceState
https://bugs.webkit.org/show_bug.cgi?id=202963
https://github.com/aurelia/history-browser/issues/34
Like this:
<?php
if(isset($_POST['uniqid']) AND $_POST['uniqid'] == $_SESSION['uniqid']){
// can't submit again
}
else{
// submit!
$_SESSION['uniqid'] = $_POST['uniqid'];
}
?>
<form action="page.php" method="post" name="myForm">
<input type="hidden" name="uniqid" value="<?php echo uniqid();?>" />
<!-- the rest of the fields here -->
</form>
I think it is simpler,
page.php
<?php
session_start();
if (isset($_POST['name'])) {
... operation on database, like to insert $_POST['name'] in a table ...
$_SESSION["message"]="Operation Done";
header("Location:page.php");
exit;
}
?>
<html>
<body>
<div style='some styles'>
<?php
//message here
echo $_SESSION["message"];
?>
</div>
<form action='page.php' method='post'>
<!--elements-->
</form>
</body>
</html>
So, for what I needed this is what works.
Based on all of the above solutions this allows me to go from a form to another form, and to the n^ form , all the while preventing the same exact data from being "saved" over and over when a page is refreshed (and the post data from before lingers onto the new page).
Thanks to those who posted their solution which quickly led me to my own.
<?php
//Check if there was a post
if ($_POST) {
//Assuming there was a post, was it identical as the last time?
if (isset($_SESSION['pastData']) AND $_SESSION['pastData'] != $_POST) {
//No, Save
} else {
//Yes, Don't save
}
} else {
//Save
}
//Set the session to the most current post.
$_session['pastData'] = $_POST;
?>
We work on web apps where we design number of php forms. It is heck to write another page to get the data and submit it for each and every form. To avoid re-submission, in every table we created a 'random_check' field which is marked as 'Unique'.
On page loading generate a random value and store it in a text field (which is obviously hidden).
On SUBMIT save this random text value in 'random_check' field in your table. In case of re-submission query will through error because it can't insert the duplicate value.
After that you can display the error like
if ( !$result ) {
die( '<script>alertify.alert("Error while saving data OR you are resubmitting the form.");</script>' );
}
No need to redirect...
replace die(); with
isset(! $_POST['name']);
, setting the isset to isset not equal to $_POST['name'], so when you refresh it, it would not add anymore to your database, unless you click the submit button again.
<?
if (isset($_POST['name'])) {
... operation on database, like to insert $_POST['name'] in a table ...
echo "Operation Done";
isset(! $_POST['name']);
}
?>
<form action='page.php' method='post' name="myForm">
<input type="text" maxlength="50" name="name" class="input400" />
<input type="submit" name="Submit" />
</form>
This happen because of simply on refresh it will submit your request again.
So the idea to solve this issue by cure its root of cause.
I mean we can set up one session variable inside the form and check it when update.
if($_SESSION["csrf_token"] == $_POST['csrf_token'] )
{
// submit data
}
//inside from
$_SESSION["csrf_token"] = md5(rand(0,10000000)).time();
<input type="hidden" name="csrf_token" value="
htmlspecialchars($_SESSION["csrf_token"]);">
I think following is the better way to avoid resubmit or refresh the page.
$sample = $_POST['submit'];
if ($sample == "true")
{
//do it your code here
$sample = "false";
}