【问题标题】:Prevent resubmit form after click "back" button单击“返回”按钮后防止重新提交表单
【发布时间】:2011-12-06 13:10:10
【问题描述】:

我有 2 页:

page1.php:
- 有一个带有文本框和“提交”按钮的表单。例如:<form name="frm_register" action="page1.php" method="post">

- 将文本框的值存储到数据库的 php 和 mysql 代码。将值提交到数据库后,Javascript 会将页面重定向到php2.php。例如:

$query = "INSERT INTO traceuser (username) VALUES ('{$username}')";
$result = mysql_query($query, $connection);
echo '<script language="javascript">window.location="page2.php";</script>';

page2.php
- mysql 从数据库中检索数据并显示在此页面上。

问题: 当我按下“返回”按钮时,浏览器会弹出一条警告消息,提示表单将被重新提交。单击“返回”按钮时如何防止重新提交表单?我需要清除page1.php的缓存吗?如何用 php 或 javascript 或 ajax 做到这一点?


更新 1: 感谢您将 javascript window.location="page2.php" 替换为 php header('Location: home2.php'); 的答案。它解决了 80% 的问题。剩下的 20% 问题如下所示:
    if (strtotime($_SESSION['servertime']) < time()-3){ //10800 = 3 hours 3600 = 1 hour
                if (($username != "") AND ($username != $_SESSION[username])){
                    $_SESSION['servertime'] = $servertime; 
                    $_SESSION['username'] = $username;
                    $query = "INSERT INTO traceuser (username) VALUES ('{$username}')";
                    $result = mysql_query($query20, $connection);
                    header('Location: page2.php');
                    exit;
                } else {
                    echo "same name"; //problem here
                }
            }else{
                echo "submit multiple data too fast"; //problem here too.
            }
   }

执行以下步骤时会出现问题:
1)用户提交数据成功,跳转到page2.php查看记录。
2) 用户点击“返回”按钮,跳转回page1.php。
3) 用户提交数据失败,停留在page1.php。 (因为太快或同名)
4)用户提交数据成功,跳转到page2.php查看记录。
5) 用户点击“返回”按钮,但浏览器显示警告信息“表单将被重新提交”。

问题出在第3步。第3步没有运行header('Location: page2.php');,没有跳转到page2.php。所以它会导致第 5 步显示警告消息。如何解决这个问题?


更新 2: 我已经找到了解决 20% 问题的解决方案,效果很好。我使用session['error123'] 来决定是否要显示错误消息“同名”。如果成功将数据提交到数据库或成功跳转到 page2.php,我将杀死 session['error123']。我还使用header('Location: page1.php'); 重定向到自己的页面(同一页面),以使页面忘记以前的表单提交。代码示例:
if ($_SESSION['error123'] == "toofast"){
    echo $_SESSION['error123'] ;
}elseif ($_SESSION['error123'] == "samename"){
    echo $_SESSION['error123'] ;
}

if (strtotime($_SESSION['servertime']) < time()-3){ //10800 = 3 hours 3600 = 1 hour
                if (($username != "") AND ($username != $_SESSION['username'])){
                    $_SESSION['username'] = $username;
                    $query = "INSERT INTO traceuser (username) VALUES ('{$username}')";
                    $result = mysql_query($query20, $connection);
                    $_SESSION['error123'] = "aa";
                    header('Location: http://localhost/plekz/page2.php');
                    exit;
                } else {
                    $_SESSION['error123'] = "samename";
                    header('Location: http://localhost/plekz/page1.php');
                    exit;
                }
            }else{
                $_SESSION['error123'] = "toofast";
                header('Location: http://localhost/plekz/page1.php');
                    exit;
            }
        }
    }

注意:您需要通过&lt;?php ob_start();?&gt; 缓冲输出,因为$_SESSION 不能放在header() 之前。 Buffer会停止包括session在内的所有输出,让header()先发送输出。

【问题讨论】:

  • 您的问题中剩下的 20% 与 I am confused about PHP Post/Redirect/Get 相同,请参阅此 tutorial,第 2 节。绝不允许重新提交表单.
  • @hakre,您建议的解决方案是将提交表单数据的脚本与接收和处理该数据的脚本分开,对吗?如果我这样做,我的 page1.php 必须负责两个任务: 1) 如果 $_Get['success']!=true,则在页面上显示带有文本框和提交按钮的表单,如果 $_Get[ 则必须显示所有记录'成功']==真。如果显示记录必须依赖于 php if else 语句,那么我需要通过 php echo 包装显示记录的 html 代码。将所有html包装在php echo中将是很多工作...... omg。

标签: php javascript mysql


【解决方案1】:

而不是

echo '&lt;script language="javascript"&gt;window.location="page2.php";&lt;/script&gt;';

您应该在提交后使用 header() 函数来重定向您的用户。

所以在伪代码中,

在 page.php 操作 page1.php 上单击提交 page1.php 向数据库调用提交数据

header('Location: http://example.com/page2.php');

这应该可以防止您的点击返回问题

【讨论】:

  • 您好,您的解决方案解决了 80% 的问题,我确实更新了我的问题以向您展示其余 20% 的问题,请教我如何解决。谢谢。
  • @BenSwinburne:任何 HTTP 标头在冒号后都需要一个空格 (SP)。位置标头需要绝对 URI。保重。
  • @hakre 我的示例使用绝对 URI... 方案、主机名和 abs 路径以及单个空格。你的评论是什么意思?
  • @BenSwinburne:只是想让您知道我编辑您的答案(已修复),以便您了解它。就是这样;)
  • @zac1987:只有它适用于你并不意味着它适用于每个浏览器。因为这不是微不足道的,所以有一个标准,其中定义了所有这些标头,并写下了应该如何使用这些标头。它通常称为 RFC,例如您使用的是 HTTP 1/1 位置:w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.30
【解决方案2】:

您可以通过实现Post-Redirect-Get (PRG Pattern) 来防止重新提交。

如果你有 http_redirect 函数,可能只是一行:

http_redirect("page2.php");

而不是你的 javascript echo。

如果不是,那是两行:

header("Location: http://example.com/page2.php");
exit;

example.com 替换为站点的您的主机名。

相关:Back button re-submit form data ($_POST); I am confused about PHP Post/Redirect/Get

【讨论】:

  • 您好,您的解决方案解决了 80% 的问题,我确实更新了我的问题以向您展示其余 20% 的问题,请教我如何解决。谢谢。
  • 谢谢。已经找到了两种不同的解决方案。谢谢你的建议:)
【解决方案3】:

一种方法是通过 Ajax 将表单数据提交到远程脚本,如果查询返回成功,您可以跳转到“谢谢”页面。 所以用户可以点击返回按钮并且“重新加载”请求不会弹出。

希望这个想法对你有帮助

【讨论】:

  • 点击“返回”按钮后,page1.php 将再次运行ajax 代码而无需点击“提交”按钮,因为page1.php 有缓存......所以我认为ajax 也不能解决问题...
【解决方案4】:

您可以通过 Ajax 调用来代替吗?表单上没有任何动作,提交时会调用一个 Ajax 函数。 Ajax 调用将执行查询并提供响应(您可以只回显结果),然后您可以根据结果提供动态反馈。你永远不会离开这个页面。

<form id="thisForm">
...form input fields...
<input type="button" onclick="return submitForm('thisForm')"/>
</form>

function submitForm(formId) {
    $.ajax( {
        type: "post",
        url: 'page2.php',
        data: $('#' + formId + ' input').serialize(),
        ... any other Ajax parameters...,
        success: function(data) {
        }
    });
    return false;
}

【讨论】:

  • 顺便说一句,当进行 Ajax 调用时,您永远不会离开页面(例如 page1.php),因此后退按钮只会将您带到 page1.php 之前的位置。页面刷新也不会再次执行 Ajax 调用。
  • 从你的代码中,你建议我不要离开page1.php页面,但我需要在page2.php上显示记录/数据,这意味着我需要离开page1.php然后去到 page2.php。这不是一个注册系统,所以请不要误解它。用户在 page1.php 上提交数据后,用户必须重定向到 page2.php。还有其他解决方案吗?
  • 我已经看到onlick功能了!!如果刷新页面,该功能将不会再次调用,直到再次单击该按钮。非常感谢!我认为您的回答将解决我的问题。我现在要测试它。谢谢。
  • 您可以将数据从 page2 返回到 Ajax 调用(从 page2 完成需要执行的操作后),然后在您仍在 page1 时动态呈现数据。如果您返回一个表的数据,您可以使用 jQuery 将该信息放入 page1 上的一个空 DIV 中。
  • Ajax 有很多内容。如果你想使用 jQuery 之类的库,可以查看:api.jquery.com/jQuery.post
【解决方案5】:

在用户单击后退按钮时显示为离线的页面中添加此代码:

<?php
 session_start();
 header_remove("Expires");
 header_remove("Cache-Control");
 header_remove("Pragma");
 header_remove("Last-Modified");
?>

【讨论】:

    【解决方案6】:

    创建一个如图所示的会话here

    您应该使用会话并从每个页面验证用户,您会惊讶于 SESSION 的工作原理!太棒了!

    【讨论】:

    • 请包含一个简短的示例,而不是简单地链接到另一个网站,因为链接可能会随着时间的推移而失效。
    猜你喜欢
    • 2018-02-21
    • 2013-02-20
    • 2011-10-15
    • 2017-12-13
    • 1970-01-01
    • 2015-12-30
    • 2019-06-24
    • 2016-03-23
    • 1970-01-01
    相关资源
    最近更新 更多