一个表单中有两个提交按钮

692

我在表单中有两个提交按钮。如何在服务器端确定哪一个被点击了?

23个回答

1021

解决方案 1:
为每个输入框赋予不同的值,但名称保持相同:

<input type="submit" name="action" value="Update" />
<input type="submit" name="action" value="Delete" />

然后在代码中检查哪个被触发:

if ($_POST['action'] == 'Update') {
    //action for update here
} else if ($_POST['action'] == 'Delete') {
    //action for delete
} else {
    //invalid action!
}

这个做法的问题在于您将逻辑绑定到了输入框中用户可见的文本上。


解决方法2:
为每个输入框赋予唯一的名称,然后检查 $_POST 是否存在该输入框:

<input type="submit" name="update_button" value="Update" />
<input type="submit" name="delete_button" value="Delete" />

这段代码中:

if (isset($_POST['update_button'])) {
    //update action
} else if (isset($_POST['delete_button'])) {
    //delete action
} else {
    //no button pressed
}

42
为了国际化的目的,最好使用所选择的答案。 - Robin Green
11
如答案所述,如果您使用上面选择的答案,您可以将表单国际化(即翻译为不同的语言或方言),而不会影响逻辑。如果您使用本答案中的第一选项,则逻辑取决于实际呈现表单的语言。 - Robin Green
2
@RobinGreen: 我认为大多数人会使用第二种逻辑,不是吗? - László Papp
6
i18n代表国际化,其中的数字18指的是第一个字母和最后一个字母之间的18个字母。 - Buttle Butkus
23
楼主没有要求 PHP。 - Rudey
显示剩余9条评论

541
如果您给每个输入框一个名称,被点击的输入框将像任何其他输入框一样被发送。
<input type="submit" name="button_1" value="Click me">

128
请确保按钮的名称正确!例如,“button-1”将无法使用。这可能会为某些人节省大量麻烦,所以请记住这一点。 - pdolinaj
28
通常,表单中的所有输入都会随表单一起发送。由于只有在单击按钮时才提交按钮的值,因此您必须搜索这些预定义名称的表单值。我认为另一个答案(https://dev59.com/xXRB5IYBdhLWcg3wtJCF#21778226)更合理,它涉及将它们全部赋予相同的名称,但是不同的值。然后,您只需在已知的单个表单字段名称下获取该值。这也使得很明显,对于给定的输入名称,只有一个值(被单击的值)将被发送,就像单选按钮的工作原理一样(相同的名称,不同的值)。 - Triynko
10
如@Triynko在那个答案的评论中所说,这种方法更适合国际化。例如,如果页面是用西班牙语渲染的,按钮的文本可能会不同。因此,在代码逻辑中依赖于该按钮的文本将在这种情况下出现问题。按名称操作更安全,因为它是一个不显示给用户的值,因此可以更多地将其视为“私有”变量而不是向用户发送的消息。 - sfarbota
2
澄清@sfarbota的评论:Parrot答案中显示的第一个解决方案存在问题,因为它依赖于测试用户可见值。这是可疑的-当更改用户可见单词时会导致代码崩溃,被认为是“脆弱”的。Parrot答案中显示的第二个解决方案很好-它与此解决方案相同。Parrot的第二个解决方案还显示了相应的编写代码,因此比此解决方案更有用。 - ToolmakerSteve
5
查看Leo的答案,以获取使用属性formaction的HTML5更新解决方案。或者查看kiril的答案,了解如何使用户可见的HTML与发送到浏览器的值独立,从而解决国际化问题。 - ToolmakerSteve
如果你使用javascript FormData来提交表单,请注意:默认情况下,它不包括提交按钮的名称/值。但是你可以自己添加 - djvg

168

现在有一种新的HTML5方法,即formaction属性:

<button type="submit" formaction="/action_one">First action</button>
<button type="submit" formaction="/action_two">Second action</button>

显然,这在Internet Explorer 9及更早版本中无法工作,但对于其他浏览器,您应该没问题(请参见:w3schools.com HTML <button> formaction Attribute)。

个人而言,我通常使用JavaScript远程提交表单(以获得更快的感知反馈),并以此方法作为备份。在这两种方法之间,唯一未覆盖的人是JavaScript已禁用的Internet Explorer 9之前的版本。

当然,如果您基本上是在服务器端执行相同的操作,而不管按下哪个按钮,这可能是不合适的,但通常如果有两个用户端可用的操作,则它们也将映射到两个服务器端操作。

正如Pascal_dher在评论中指出的那样,此属性也适用于<input>标记。


2
还可用于“input”标签。根据w3schools的说法:使用button标签时,不同的浏览器可能会提交不同的值:http://www.w3schools.com/tags/tag_button.asp - Pascal_dher
3
提示给 Rails 用户:如果你的表单是使用 form_tag 创建的,添加这个属性是不起作用的。唯一让它起作用的方式是切换到 form_for 并使用 f.submit formaction: 'your_path' - fgblomqvist
6
formaction 属性定义在提交表单时使用的URL。如果指定了 formaction,将会覆盖表单元素上定义的 action 属性。该属性仅适用于类型为 "submit" 的按钮。 - akinuri
不同的表单操作意味着不同的URL路径。如果您想在一个“视图”中处理表单,可能会有点麻烦。 - djvg

152
<form>
    ...
    <button type="submit" name="action" value="update">Update</button>
    <button type="submit" name="action" value="delete">Delete</button>
</form>

按钮内的 HTML(例如 ..>更新<..)是用户看到的内容;由于提供了 HTML,因此value 不可见;它只会发送到服务器。这样就不会有国际化和多个显示语言方面的不便(在前一种解决方案中,按钮的标签也是发送到服务器的值)。


16
浏览器的行为显然有所不同;有些会提交value属性,而另一些则会提交标签之间的字符串...因此对于这个问题要小心。 - Jeroen Dierckx
1
我认为提供的代码片段是完全支持的(http://www.w3schools.com/tags/att_button_type.asp)。 - kiril
2
@kiril 那个链接中的代码片段使用了两种不同类型的<button>submitreset。请注意,reset并不会提交任何内容,它只是重置表单。因此,Jeroen的论点仍然成立。 - fizruk
8
好的,你是正确的。接下来,我查看了HTML5 W3C工作草案。引用如下:
value属性为元素在表单提交时的值。元素的值是其value属性的值(如果有),否则为空字符串。
注:只有当按钮本身被用于启动表单提交时,按钮(及其值)才会包含在表单提交中。
- kiril
11
哪些浏览器会提交标签之间的文本?输入框或按钮只应该提交"value"属性。按钮可以在其标签之间包含任何内容,包括图像或其他HTML标记。这正是使用按钮而不是输入元素的全部意义,并且你试图暗示浏览器将把所有内容都作为值转储?绝不可能。 - Triynko
显示剩余6条评论

37

这个非常容易进行测试:

<form action="" method="get">
    <input type="submit" name="sb" value="One">
    <input type="submit" name="sb" value="Two">
    <input type="submit" name="sb" value="Three">
</form>

把它放在一个HTML页面中,点击按钮,然后查看URL。


10
在这里使用GET是不太好的做法,应尽可能使用POST。 - Syncrossus
12
@Syncrossus 这是为了测试目的。 - Etienne Martin

32

使用 HTML 属性 formaction(第五行):

<form action="/action_page.php" method="get">
    First name: <input type="text" name="fname"><br>
    Last name: <input type="text" name="lname"><br>
    <button type="submit">Submit</button><br>
    <button type="submit" formaction="/action_page2.php">Submit to another page</button>
</form>

4
这类似于Leo之前的回答 - ToolmakerSteve
@ToolmakerSteve - 但是用户已经点赞了。你自己决定吧!! - Love Putin Not War

22
<form>
    <input type="submit" value="Submit to a" formaction="/submit/a">
    <input type="submit" value="submit to b" formaction="/submit/b">    
</form>

HTML5 功能。最近的网页浏览器上完美运行,谢谢! - Stephane Lallemagne
2
请注意:这似乎与Leo早期的回答相同,只是它显示了使用input标签而不是button标签。 - ToolmakerSteve

18

处理多个提交按钮的最佳方法是在服务器脚本中使用switch case语句。

<form action="demo_form.php" method="get">

    Choose your favorite subject:

    <button name="subject" type="submit" value="html">HTML</button>
    <button name="subject" type="submit" value="css">CSS</button>
    <button name="subject" type="submit" value="javascript">JavaScript</button>
    <button name="subject" type="submit" value="jquery">jQuery</button>
</form>

服务器代码/服务器脚本 - 您提交表单的位置:

文件demo_form.php

<?php
    switch($_REQUEST['subject']) {

        case 'html': // Action for HTML here
                     break;

        case 'css': // Action for CSS here
                    break;

        case 'javascript': // Action for JavaScript here
                           break;

        case 'jquery': // Action for jQuery here
                       break;
    }
?>

来源: W3Schools.com


是的,你必须对ActionScript(服务器端脚本技术)有所了解。您可以使用任何脚本/文件来处理提交的数据,例如PHP、ASP、JSP等。<form action="demo_form.php" method="get"> - Shailesh Sonare
好的。这让人困惑,因为还有一种名为ActionScript的编程语言。你应该说:“服务器端代码”或“服务器端脚本”而不是使用原文中的用词。 - Civilian
我从来不知道按钮还能这样用。 - William Isted
提交页面通常使用 method="POST" 方法。 - Daleman
出现了一个错误,它说: C:\xampp\htdocs\Test-1\index.php中未定义数组键“subject” - MJ DLS

12

也许这里提供的解决方案在2009年起作用,但我测试过了所有受欢迎的答案,没有一个在任何浏览器中都能正常工作。

唯一有效的解决方案是这个(但我认为它有点丑陋):

<form method="post" name="form">
    <input type="submit" value="dosomething" onclick="javascript: form.action='actionurl1';"/>
    <input type="submit" value="dosomethingelse" onclick="javascript: form.action='actionurl2';"/>
</form>

2
为什么不直接使用 formaction="actionurl1" 呢?你不需要 JavaScript。 - rybo111
3
IE9浏览器(相对仍被广泛使用)不支持 formaction - LdiCO
1
@inaliaghle 确实,这大约是用户的1% - 这取决于项目的目标对象。大约有1%的用户不使用JavaScript。 - rybo111
1
对于未来的读者:在这个答案中使用JavaScript没有任何问题,这是一项有用的技能。另一方面,更高投票的答案也可以正常工作-忽略这个答案的引导语句。如果由于某种原因您无法让其他答案正常工作,请将您的完整代码发布为SO问题,解释发生了什么(或未发生),并询问您做错了什么。 - ToolmakerSteve

12

如何在一个表单中为多个提交按钮设置formaction:

 <input type="submit" name="" class="btn action_bg btn-sm loadGif" value="Add Address" title="" formaction="/addAddress"> 
 <input type="submit" name="" class="btn action_bg btn-sm loadGif" value="update Address" title="" formaction="/updateAddress"> 

这个不可理解。例如,“You formaction”是什么意思?是否缺少单词?请通过编辑(更改)您的答案来回复,而不是在评论中回复(不要包含“Edit:”,“Update:”或类似内容 - 答案应该看起来像是今天写的)。 - Peter Mortensen
1
@PeterMortensen,“formaction”代表“表单操作”,是一种替换默认表单操作的属性。如果您没有为提交按钮声明“formaction”,则表单将使用其默认路由。如果您声明了,它将使用特定路由。您可以在此处阅读更多信息:https://www.w3schools.com/tags/att_input_formaction.asp - Luís Henriques

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,