代码之家  ›  专栏  ›  技术社区  ›  Gal

如何防止机器人自动填写表格?

  •  97
  • Gal  · 技术社区  · 16 年前

    我试图想出一个足够好的反垃圾邮件机制,以防止自动生成的输入。我读过验证码1+1=?东西工作得很好,但他们也提出了一个额外的步骤,阻碍免费快速使用的应用程序(我不寻找任何类似的请)。

    我试着在我所有的表单中设置一些隐藏的字段 display: none; 但是,我确信可以将脚本配置为跟踪表单字段id,而不填充它。

    你有没有实施/知道一个好的反自动填表方法?有什么东西可以通过HTML和/或服务器端处理无缝地完成,并且(几乎)是防弹的吗(如果没有JS,您可以简单地禁用它)。

    我尽量不依赖会话来实现这一点(例如,计算一个按钮被点击多少次以防止过载)。

    27 回复  |  直到 9 年前
        1
  •  74
  •   Pindatjuh    16 年前

    解决反垃圾邮件的一种容易实现但不容易出错(特别是在“特定”攻击上)的方法是跟踪表单提交和页面加载之间的时间。

    人类输入一个URL,加载页面,在页面完全加载之前等待,向下滚动,阅读内容,决定是否评论/填写表单,需要时间填写表单,然后提交。

    时间上的差异可能很微妙;而如何在没有cookies的情况下跟踪这段时间,则需要某种方式的服务器端数据库。这可能会影响性能。
    你还需要调整阈值时间。

        2
  •  77
  •   Ben Scheirman    16 年前

    其实我发现一个简单的蜜罐田效果不错。大多数机器人都会 每一个

    http://haacked.com/archive/2007/09/11/honeypot-captcha.aspx

    如果您创建了一个文本框,请在javascript中隐藏它,然后验证该值是否正确 空白的 在服务器上,这将淘汰99%的机器人,并且不会导致99%的用户

        3
  •  24
  •   Michael W Moriarty    6 年前

    万一呢- 机器人找不到任何 form

    3个例子:

    1. 使用AJAX插入表单
    <noscript>
      <p class="error">
        ERROR: The form could not be loaded. Please enable JavaScript in your browser to fully enjoy our services.
      </p>
    </noscript>
    
    • 创建 form.html 把你的 形式 内部 <div id="formContainer">

    • 在需要调用该窗体的页面中,使用空 <div id="dynamicForm"></div> $("#dynamicForm").load("form.html #formContainer");

    1. 完全使用JS构建表单

    // THE FORM
    var $form = $("<form/>", {
      appendTo : $("#formContainer"),
      class    : "myForm",
      submit   : AJAXSubmitForm
    });
    
    // EMAIL INPUT
    $("<input/>",{
      name        : "Email", // Needed for serialization
      placeholder : "Your Email",
      appendTo    : $form,
      on          : {        // Yes, the jQuery's on() Method 
        input : function() {
          console.log( this.value );
        }
      }
    });
    
    // MESSAGE TEXTAREA
    $("<textarea/>",{
      name        : "Message", // Needed for serialization
      placeholder : "Your message",
      appendTo    : $form
    });
    
    // SUBMIT BUTTON
    $("<input/>",{
      type        : "submit",
      value       : "Send",
      name        : "submit",
      appendTo    : $form
    });
    
    function AJAXSubmitForm(event) {
      event.preventDefault(); // Prevent Default Form Submission
      // do AJAX instead:
      var serializedData = $(this).serialize();
      alert( serializedData );
      $.ajax({
        url: '/mail.php',
        type: "POST",
        data: serializedData,
        success: function (data) {
          // log the data sent back from PHP
          console.log( data );
        }
      });
    }
    .myForm input,
    .myForm textarea{
      font: 14px/1 sans-serif;
      box-sizing: border-box;
      display:block;
      width:100%;
      padding: 8px;
      margin-bottom:12px;
    }
    .myForm textarea{
      resize: vertical;
      min-height: 120px;
    }
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
    <div id="formContainer"></div>
    1. 输入
    • 机器人喜欢( 喜欢) 俏皮
    <input 
      type="text"
      name="email"
      id="email"
      placeholder="Your email"
      autocomplete="nope"
      tabindex="-1"
    
    They wll be happy to enter some value such as
    `dsaZusil@kddGDHsj.com`
    
    • 使用上述HTML后,您还可以使用CSS不显示输入:
    input[name=email]{ /* bait input */
      /* do not use display:none or visibility:hidden
         that will not fool the bot*/
      position:absolute;
      left:-2000px;
    }
    
    • 既然您的输入对用户不可见,那么在PHP中 $_POST["email"] (没有任何价值)!否则不要提交表格。
    • 另一个输入 喜欢 <input name="sender" type="text" placeholder="Your email"> 之后(!) “机器人诱饵”

    致谢:

    Developer.Mozilla - Turning off form autocompletition
    StackOverflow - Ignore Tabindex

        4
  •  21
  •   Peyman Mohamadpour    9 年前

    我所做的是使用一个隐藏字段,将时间戳放在上面,然后使用PHP将其与服务器上的时间戳进行比较。

    如果它超过15秒(取决于你的表单大小),那就是一个机器人。

        5
  •  17
  •   HawleyTronics    14 年前

    一个非常有效的方法,几乎消除垃圾邮件是有一个文本字段,其中有文本,如“删除此文本,以提交表单!”必须删除该文本才能提交表格。

    在表单验证时,如果文本字段包含原始文本或任何随机文本,则不要提交表单。机器人程序可以读取表单名称并自动填写姓名和电子邮件字段,但不知道是否必须从某个字段中删除文本才能提交。

    我在我们公司的网站上实现了这个方法,它完全消除了我们每天收到的垃圾邮件。真的很管用!

        6
  •  13
  •   Steve    14 年前

    不如创建一个与背景颜色相同的文本字段输入框,但必须保持空白。这将解决机器人读取显示的问题:无

        7
  •  9
  •   handle    8 年前
        8
  •  7
  •   John Himmelman    16 年前

    许多垃圾邮件机器人只是在网络上徘徊的服务器端脚本。您可以通过使用一些javascript在发送表单请求之前对其进行操作(即,基于某个客户机变量设置一个附加字段)来解决其中的许多问题。这不是一个完整的解决方案,可能会导致许多问题(例如,移动设备上没有javascript的用户等),但它可能是攻击计划的一部分。

    下面是一个小例子。。。

    <script>
    function checkForm()
    {
        // When a user submits the form, the secretField's value is changed
        $('input[name=secretField]').val('goodValueEqualsGoodClient');
    
        return true;
    }
    </script>
    
    <form id="cheese" onsubmit="checkForm">
    <input type="text" name="burger">
    
    <!-- Check that this value isn't the default value in your php script -->
    <input type="hidden" name="secretField" value="badValueEqualsBadClient">
    
    <input type="submit">
    </form>
    

    <?php
    
    if ($_REQUEST['secretField'] != 'goodValueEqualsGoodClient')
    {
        die('you are a bad client, go away pls.');
    }
    
    ?>
    

    此外,验证码是伟大的,真的是最好的防御垃圾邮件。

        9
  •  5
  •   Gras Double    11 年前

    我很惊讶还没有人提到这个方法:

    • 提供此图像时放置cookie。


    赞成的意见:

    • 方便用户和开发者
    • 似乎很可靠
    • 没有JavaScript

    欺骗:

    • 添加一个HTTP请求
    • 要求在客户端上启用Cookie


    例如,这个方法被WordPress插件使用 Cookies for Comments .

        10
  •  5
  •   Adam    6 年前

    你不能

    • 垃圾邮件机器人不使用javascript,
    • 你可以跟踪鼠标事件来检测机器人,
    • 他们看不到一个领域是视觉隐藏,
    • 他们不会等一段时间再提交。

    如果你不想要一个用户友好的解决方案, 给他们一个漂亮的 “我是个垃圾邮件发送者” 提交按钮 :

     <input type="submit" name="ignore" value="I am a spammer!" />
     <input type="image" name="accept" value="submit.png" alt="I am not a spammer" />
    

    当然你可以玩两个图像 input[type=image] 按钮,更改每次加载后的顺序、文本替代项、图像内容(及其大小)或 name

     <input type="image" name="random125454548" value="random125454548.png"
          alt="I perfectly understand that clicking on this link will send the
          e-mail to the expected person" />
     <input type="image" name="random125452548" value="random125452548.png"
          alt="I really want to cancel the submission of this form" />
    

    出于可访问性的原因,你必须给出一个正确的文本选择,但我认为对于屏幕阅读器用户来说,长句比被认为是机器人更好。

        11
  •  3
  •   SF.    16 年前

    一个非常简单的方法是提供一些字段,如 <textarea style="display:none;" name="input"></textarea> 并放弃所有已填写此项的答复。

    不管怎样,你不会对来自台湾或印度的实时“机器人”做太多的反对,他们每发布一个链接的报酬是0.03美元,并以此为生。

        12
  •  2
  •   user2643367    13 年前

    它的工作原理是利用大多数html表单处理脚本(我使用FormMail.pl)的电子邮件别名功能,以及一个图形提交“代码”,它可以在最简单的图形程序中轻松创建。其中一个图形包括代码M19P17nH和提示“请在左侧输入代码”。

    当然,人类可以在一瞬间解决这个问题,而不需要所有与reCAPTCHA和类似的、更优雅的方案相关的问题。如果一个垃圾邮件发送者确实对收件人的失败做出了响应,并将图像代码编程到机器人中,那么一旦你意识到机器人已经被硬编码为响应,你就可以很容易地对其进行更改。在使用这种方法的五年中,我从未收到过任何一个使用它的表单的垃圾邮件,也从未收到过任何表单用户的投诉。我确信机器人的OCR功能可以打败它,但是我从来没有在我的任何使用html表单的网站上遇到过这种情况。我还使用了“垃圾邮件陷阱”(隐藏的“来这里”html代码,指向我的反垃圾邮件政策)取得了很好的效果,但他们只有大约90%的有效性。

        13
  •  1
  •   Community Mohan Dere    9 年前

    我在想很多事情:

    1. 正在获取引用url(在本例中应该是来自同一域的url)。。。普通用户在到达联系人窗体之前必须浏览网站: PHP: How to get referrer URL?
    2. 在一个文本字段中填入一些伪文本,以便在服务器端检查它是否被覆盖
    3. 检查浏览器版本: http://chrisschuld.com/projects/browser-php-detecting-a-users-browser-from-php.html ... 很明显,机器人不会使用浏览器,而只是一个脚本。
    4. 使用AJAX逐个发送字段,并检查提交之间的时间差
    5. 在表单之前/之后使用假页面,只是为了发送另一个输入
        14
  •  0
  •   Brian    16 年前

    总而言之,每种解决方案都有其优缺点。你将不得不在用户难以通过反垃圾邮件机制和垃圾邮件机器人数量之间找到一个令人满意的中间值。

        15
  •  0
  •   Nick Allen    16 年前

    Robots不能执行JavaScript,所以您可以使用JavaScript向页面中注入某种隐藏元素,然后在表单提交之前检测到它的存在,但要小心,因为您的一些用户也会禁用JavaScript

    否则我认为你将被迫使用一种形式的客户证明“人性”

        16
  •  0
  •   Thibault Falise    16 年前

    我找到的避免被机器人发送垃圾邮件的最佳解决方案是在表单上使用一个非常简单的问题或字段。

    尝试添加如下字段:

    • 1+1 = ?
    • 复制框中的网站名称

    这些技巧要求用户理解必须在表单上输入的内容,因此很难成为大量bot表单填充的目标。

    但是,在我看来,它比验证码简单得多,填写表单时的开销不超过5秒,从用户的角度来看,这似乎是可以接受的。

        17
  •  0
  •   Pool    16 年前

    有一个 tutorial

        18
  •  0
  •   matthew    16 年前

        19
  •  0
  •   h0mayun    12 年前

    这只是一个想法,我用在我的应用程序,效果很好

    您可以使用javascript或jquery在鼠标移动时创建cookie,并在服务器端检查cookie是否存在,因为只有人类有鼠标,所以cookie只能由他们创建 cookie可以是时间戳,也可以是可验证的令牌

        20
  •  0
  •   CoffeDeveloper    11 年前

    以我的经验,如果表格只是一个“联系”表格,你不需要特别的措施。垃圾邮件通过webmail服务得到适当的过滤(您可以通过服务器脚本跟踪webform请求,以查看哪些内容有效地到达您的电子邮件,当然我假设您有一个好的webmail服务:D)

    顺便说一句,我试着不依赖会话来完成这个任务(比如,如何计算) 多次单击按钮以防止过载)。

    我不认为这是好的,事实上,我想要实现的是接收来自用户的电子邮件,这些用户做了一些特定的操作,因为他们是我感兴趣的用户(例如,用户看了“简历”页,并使用了适当的联系形式)。因此,如果用户做了我想做的事情,我就开始跟踪它的会话并设置一个cookie(我总是设置会话cookie,但当我不启动会话时,它只是一个假装用户有会话的假cookie)。如果用户做了一些不需要的事情,我就不麻烦为他保留一个会话,所以没有过载等。

    另外,广告服务提供某种api(可能已经存在)来查看用户是否“看了广告”,这对我来说也很好,很可能看广告的用户是真正的用户,但如果他们不是真正的好,至少你得到了1个视图,所以没有损失(相信我,广告控制比你一个人能做的任何事情都要复杂)

        21
  •  0
  •   Robidu    10 年前

    实际上是陷阱 显示:无 很有魅力。它有助于将CSS声明移动到包含任何全局样式表的文件中,这将强制垃圾邮件bot也加载这些样式表(直接加载) style=“显示:无;” 声明可能会被spam bot解释,就像文档本身中的本地样式声明一样)。

    这与其他对策相结合,应该会使任何垃圾邮件机器人卸载他们的垃圾毫无意义(我有一个用各种措施保护的留言簿,到目前为止,他们已经落入我的主要陷阱-然而,如果任何机器人绕过这些,还有其他准备触发)。

    我使用的是假表单字段的组合(如果使用的浏览器通常不处理CSS或CSS,则也称为无效字段) 显示:无

    关于验证邮件的一个注意事项:这个步骤是完全可选的,但是当一个人选择实现它时,这个过程必须尽可能容易使用(即,它应该归结为单击包含在电子邮件中的链接),并使相关电子邮件地址在一段时间内被列入白名单,以便在用户希望发表其他帖子时避免后续验证。

        22
  •  0
  •   cookie    10 年前
    1. 我使用一种方法,其中有一个隐藏的文本框。由于机器人解析网站,他们可能会填补它。然后我检查它,如果它是空的,如果它不是网站返回。

    2. 添加电子邮件验证。用户收到一封电子邮件,他需要单击一个链接。否则在一段时间内丢弃该帖子。

        23
  •  0
  •   Harika Y    9 年前

    function formCheck(){
    var timeStart; 
    var timediff;
    
    $("input").bind('click keyup', function () {
        timeStart = new Date().getTime();          
    }); 
     timediff= Math.round((new Date().getTime() - timeStart)/1000);
    
      if(timediff < 3) { 
        //throw a warning or don't submit the form 
      } 
      else submit(); // some submit function
    
    }
    
        24
  •  0
  •   nmit026    8 年前

    随着垃圾邮件机器人和自动浏览器等技术的日益成熟,确定垃圾邮件的来源将变得更加困难。但无论是通过软件发布,还是通过人工发布,或者两者兼而有之,垃圾邮件都是垃圾邮件,因为它的内容。我认为最好的解决方案是通过像Cleantalk或Akismet这样的反垃圾邮件API来运行发布的内容。这是相对便宜和有效的,不困扰用户。在使用API之前,您可以检查表单提交时间和其他传统检查,以查找不太复杂的bot。

        25
  •  0
  •   Michael W Moriarty    6 年前

    您可以尝试通过在Javascript验证之后添加正确的操作atribute来欺骗垃圾邮件机器人。

    HTML格式

    <form id="form01" action="false-action.php">
        //your inputs
        <button>SUBMIT</button>
    </form>
    

    JAVASCRIPT语言

    $('#form01 button').click(function(){
    
       //your Validations and if everything is ok: 
    
        $('#form01').attr('action', 'correct-action.php').on("load",function(){
            document.getElementById('form01').submit()
        });
    })
    

    然后在.attr()之后添加一个“回调”以防止出错。

        26
  •  0
  •   Alex from Jitbit    5 年前

    决定添加另一个答案,抱歉。

    我们使用两种方法的组合:

    1. name="email" (其他答案已经提到)一定要用一种复杂的方式来隐藏它,比如从屏幕上移开或者别的什么。因为机器人可以探测到 display:none
    2. 当用户 clicks focuses 如果你想成为一个标签友好)在一个必填字段(没有提到在其他答案)

    阻止99%的机器人。

    另外,确保只在没有被密码管理器(如LastPass或1Passwor)填充的字段上使用焦点技巧。

    出于同样的原因-在你的蜜罐上标记 autocomplete="false" tabindex="-1"

        27
  •  0
  •   Gray droiddeveloper    5 年前

    用途:

    1. 用IP地址检查窗体到窗体的延迟
    2. 块IP(可选)
        28
  •  -1
  •   MartinWebb    10 年前

    只值我五分钱。 如果这样做的目的是阻止99%的机器人,这听起来很不错,如果99%的机器人不能运行Java脚本,那么最好的解决方案就是不要使用带有post URL提交操作的表单。

    如果表单是通过java脚本控制的,并且java脚本收集表单数据,然后通过HTTP请求发送,那么机器人就不能提交表单。因为submit按钮将使用Java脚本来运行发送表单的代码。