从 php 脚本填充表单并发送它

Posted

技术标签:

【中文标题】从 php 脚本填充表单并发送它【英文标题】:populate form from php script and send it 【发布时间】:2016-03-28 01:03:07 【问题描述】:

我在网上搜索,一无所获。

在网站上,有一个电子邮件地址的输入框。我想用电子邮件地址填写此字段并发送表格。 我找到了这段代码:

$postdata = http_build_query(
array(
    'email' => 'youremailaddress'
)
); 
$opts = array('http' =>
array(
    'method'  => 'POST',
    'header'  => 'Content-type: application/x-www-form-urlencoded',
    'content' => $postdata
)
);

$context  = stream_context_create($opts);

$result = file_get_contents('http://example.com/submit.php', false, $context);

但在我的情况下,操作文件是当前页面本身,并且 url 被重写。所以当我这样输入网址时:

$result = file_get_contents('http://example.com/login.html', false, $context);
var_dump($result);

我得到了页面,但没有发送表单

【问题讨论】:

你是否在目标站点验证了请求类型是POST,并且唯一的字段是email(具体来说,没有CSRF token)? 也许试试 Goutte? packagist.org/packages/fabpot/goutte 【参考方案1】:

您可能需要查看 Selenium Webdriver 和 PHPUnit 来完成此任务。即使提交 URL 每次更改,您也应该能够轻松填写并提交。这是一个如何工作的示例:

<?php

class phproTest extends PHPUnit_Extensions_Selenium2TestCase

        protected function setUp()
        
                // Which browser to use
                $this->setBrowser('firefox');
                // The base URL
                $this->setBrowserUrl('http://example.com/');
        

        public function testContactFormExists()
        
                $this->url( 'http://example.com/login.html' );

                $email = $this->byName( 'sender_email' );
                $submit = $this->byName( 'submit_button' );

                $this->assertEquals( '', $email->value() );
                $this->assertEquals( 'Submit', $submit->value() );
        

        public function testSubmitToSelf()
        
                // set the url
                $this->url( 'contact' );

                // create a form object for reuse
                $form = $this->byId( 'contact_form' );

                // get the form action
                $action = $form->attribute( 'action' );

                // check the action value
                $this->assertEquals( 'http://example.com/login.html', $action );
                // fill in the form field values
                $this->byName( 'sender_email' )->value( 'youremailhere' );

                // submit the form
                $form->submit();
        

?>

看起来很多,但一旦你把它分解,它并没有那么糟糕。通过使用此方法,您将使用实际的浏览器(在本例中为 firefox)来填写并提交表单。这将加载和处理创建唯一提交 URL 所需的 javascript,具体取决于表单的创建方式。

【讨论】:

【参考方案2】:

一个可能对您有用的选项是 Fabien Potencier 编写的 Goutte,用于提交表单。

packagist 的示例代码:

$crawler = $client->request('GET', 'http://github.com/');
$crawler = $client->click($crawler->selectLink('Sign in')->link());
$form = $crawler->selectButton('Sign in')->form();
$crawler = $client->submit($form, array('login' => 'fabpot', 'password' => 'xxxxxx'));
$crawler->filter('.flash-error')->each(function ($node) 
    print $node->text()."\n";
);

在 Packagist 上获取它:https://packagist.org/packages/fabpot/goutte

【讨论】:

以上是关于从 php 脚本填充表单并发送它的主要内容,如果未能解决你的问题,请参考以下文章

PHP:从表单中获取电子邮件并在单击按钮时发送它

带有双引号的 JAVASCRIPT var 到 PHP 并返回用于自动填充

无法从网站表单填充 wampserver 数据库?

有人可以将来自不同主机的表单数据发送到我的 PHP 脚本,该脚本将获取的数据插入 MySQL 吗?如果是这样,我们如何保护它?

Bootstrap HTML + MySQL PHP 表单安全性

如何以在 php 中作为字符串回显的形式填充单选按钮?