【问题标题】:What happens if you try to redirect before a form submit?如果您在表单提交之前尝试重定向会发生什么?
【发布时间】:2013-08-19 08:10:54
【问题描述】:

我在我正在开发的网站中遇到了这个奇怪的代码,但我不明白我所看到的行为是如何发生或为什么发生的。

<input type="submit" value="Save" onclick="document.location.href='http://www.google.com'" />

(更改了 href;它实际上指向与表单操作相同的 URL)。

因为onclick 事件在表单提交之前触发,我希望这段代码将页面重定向到 Google.com,从而停止执行页面并且从不提交表单。或者可能重定向到 Google.com,但仍然完成提交表单。

但是发生的情况似乎是重定向被完全忽略了,并且无论如何都会提交表单。为什么会这样?
我确认onclick 事件触发得很好;我将重定向移动到一个函数中,并在onclick 中调用了该函数。该函数在提交之前被调用得很好,但重定向似乎被忽略了。

【问题讨论】:

  • 我知道 return false 会阻止提交,在这种情况下重定向确实会发生。但是为什么在这种情况下不会发生重定向?是什么阻止了它?
  • 您能否在jsfiddle 中重新生成此内容并告诉我们您正在使用哪个浏览器进行测试?
  • 我最近遇到了同样的问题。您可以改用 并在按钮的操作事件代码的末尾附加someform.submit()。或者,您可以覆盖 onsubmit 表单属性或相应的提交事件处理程序。

标签: javascript html forms redirect submit


【解决方案1】:

我刚刚在不同的浏览器中测试了这种行为,所有浏览器都给出了相同的结果,这是我的结论:

<!-- submit button inside form -->
<form method="post">
    <input type="submit" value="submit" /> <!-- onclick = submitted to same page -->
    <input type="submit" value="submitNredirect" onclick="document.location.href='http://www.google.com';" /> <!-- onclick = submitted to same page, ignored redirect -->
</form>
<!-- submit button without form -->
<input type="submit" value="submit" /> <!-- onclick = no submit or redirect occur -->
<input type="submit" value="submitNredirect" onclick="document.location.href='http://www.google.com';" /> <!-- onclick = redirect -->

如您所知,javascript 是线性的,它执行首先出现的代码行。假设我们有这个表格:

<form id="myform" method="post" onsubmit="alert('onsubmit');">
    <input id="mybtn" type="submit" value="submit" onclick="alert('onclick');" />
</form>
<script>
    $(document).ready(function() {
        $('#mybtn').bind('click', function() {
            alert('bind click');
        });
        $('#myform').bind('submit', function() {
            alert('bind submit');
        });
        // onclick > bind click > onsubmit > bind submit
    });
</script>

单击按钮时,首先发生绑定到按钮的事件(“单击”事件),然后发生绑定到表单的事件(“提交”事件)。 结果如下:

  1. 警报:点击
  2. 警报:绑定点击
  3. 警报:提交时
  4. 警报:绑定提交
  5. 表单提交

如果您在任何函数中包含任何重定向代码,重定向将被忽略并发生提交,我相信 javascript 会用表单发布过程覆盖document.location.href,“表单提交”就像一个隐含/隐藏的行脚本末尾的代码,如果您在某些时候不return false;,则会执行此隐式/隐藏行。

我不是专家,但这是我经过一些测试后所理解的。如果我错了,请纠正我。

编辑:如果我们在每个函数中包含document.location.href 会怎样?像这样:

<form id="myform" method="post" onsubmit="document.location.href='http://www.onsumbit.com';">
    <input id="mybtn" type="submit" value="submit" onclick="document.location.href='http://www.onclick.com';" />
</form>
<script>
    $(document).ready(function() {
        $('#mybtn').bind('click', function() {
            document.location.href='http://www.bindclick.com';
            return false;
        });
        $('#myform').bind('submit', function() {
            document.location.href='http://www.bindsumbit.com';
        });
    });
</script>

“href”的字符串值的状态变化如下(但在脚本末尾执行重定向):

  1. document.location.href = 'http://www.onclick.com';
  2. document.location.href = 'http://www.bindclick.com';
  3. document.location.href = 'http://www.onsubmit.com';
  4. document.location.href = 'http://www.bindsubmit.com';
  5. document.location.href = '/'; // 表单提交
  6. javascript,根据“href”字符串值进行重定向

但我们在#2 之后有return false;,这意味着将对“http://www.bindclick.com”进行重定向

【讨论】:

  • @LoSauer 我知道,我只是使用 jQuery 进行测试,因为问题不在于代码,而在于 javascript 的行为方式
  • 我明白了。但这与 JavaScript 或其“线性”无关。它是关于如何在特定的浏览器实现中设置处理程序以及 input[type=submit] 的事件冒泡。一种选择是覆盖这些处理程序...
  • @LoSauer 我会说如果提交是唯一的问题,请参考这个链接echoecho.com/htmlforms12.htm 这解释了更多.. input[type=submit] 是将事件绑定到任何的 jQuery/javaScript 代码类型为提交的输入标签。您可以忽略这些步骤,然后在删除 jQuery 后行为也将按照相同的顺序进行。我希望这会让事情变得清楚:)
  • @MarmiK,@evilReiko。这篇文章有几个缺陷: *) 使用包装库来调查特定的浏览器行为是有缺陷的。 *) 设置document.location.href 来表达观点是有严重缺陷的,除非你设置了锚点。 *) 未回答为什么,但仅列出了事件层次结构
  • 如果我没看错,听起来这实际上很清楚地回答了“为什么”的问题。因为设置 document.location.href 实际上并没有立即进行重定向;相反,它只会在处理完页面后导致 Javascript 重定向。事实上,我只是通过在重定向之前和之后发出警报来测试这一点。我收到了两个警报,然后它重定向了。这似乎证实了答案所说的。谢谢!
【解决方案2】:
<form action="http://www.yahoo.com" method="get">
<input type="submit" value="Save" onclick="document.location.href='http://www.google.com'" />
</form>

单击“保存”按钮,我发现取决于您将被定向到 Yahoo (Chrome) 的浏览器,除非您将 return false 添加到 onclick 事件。在 IE 10 上,您会被定向到 Google。

我认为编写浏览器的人必须回答这个问题。

【讨论】:

    【解决方案3】:

    我认为这是一个值得商榷的问题,

    我会从行为方面来回答,

    表单的默认方法是GET,因此按下提交按钮表单将获取数据。 来源Old Post

    但如果您在 document.location.href="http://www.google.com" 中包含 e.preventDefault()

    现在,如果链接是index.html,本地索引页面会根据网站地址调用,因为你已经删除了原始链接,无法判断为什么最初使用这些!!!? ??

    我可以在你的问题中说运行这段代码,

    <form onsubmit="javascript:alert('Form Submit called '+ this.method);">
        <input type=submit value=Submit onclick="javascript:document.location.href='http://www.google.com';alert('Button Submit');" />
    </form>
    

    这将清除流的调用。因为 document.location.href 永远不会使用这个改变..

    在更改 href alert(document.location.href); 后使用此代码,这将为您提供未更改的位置。

    也许阻止默认行为可能会改变这一点,但这不是你代码的一部分..

    我希望这会让事情更清楚。

    【讨论】:

      【解决方案4】:

      您所观察的是HTMLInputElement 的处理程序的默认和继承行为,除非被覆盖。

      解决方案:

      请改用HTML5 button type-submit Element,所有现代浏览器都应该能够正确处理它。

      <form action="/" method="post" onsubmit="alert('submit event')">
        <input type="text" name="someinput" value="100">
        <button type="submit" onclick="alert('button onclick handled before form-submit')">submit</button>
      </form>
      

      说明:

      您没有提供特定的浏览器,但您可能正在使用 WebKit,它与 onsubmit / onclick 事件层次结构 before 存在问题。

      在项目的代码站点上,您可以搜索实现各种 HTMLElement 的代码。
      例如,搜索onsubmit 将导致Webkit onsubmit-event bubbling test

      解决此事件冒泡问题的一种方法是使用button 并将其呈现为“提交”,方法是找到其封闭表单并通过函数(HTMLFormElement-instance).submit() 提交。

      另一种方法是更改​​表单的提交处理程序,这应该是您要查找的内容。

      <form action="/" method="post" accept-charset="utf-8" id="myform3"
         onsubmit="event.stopPropagation(); event.cancelBubble = true;">
         A form with the default Browser submit-handler overwritten:
         <br>
         <input type="text" name="someinput" value="100">
         <input type="submit" name="commit" value="Submit" 
           onclick="alert('will alert first and submit later  using the browser default submit handler.');">
       </form>
      

      所有案例都在这个fiddle中演示。

      干杯!

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2019-01-01
        • 2018-11-05
        • 2021-05-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-08-03
        • 2011-06-21
        相关资源
        最近更新 更多