phpunit:如何在测试之间传递值?

时间:2015-08-09 23:24:04

标签: class phpunit

我真的碰到了这堵砖墙。如何在phpunit中的测试之间传递类值?

测试1 - >设定值,

测试2 - >读取值

这是我的代码:

class JsonRpcBitcoinTest extends PHPUnit_Framework_TestCase
{
    public function setUp(){
        global $configRpcUser, $configRpcPass, $configRpcHost, $configRpcPort;

        $this->bitcoindConn = new JsonRpcBitcoin($configRpcUser, $configRpcPass, $configRpcHost, $configRpcPort);
        $this->blockHash = '';
    }

    /**
    * @depends testCanAuthenticateToBitcoindWithGoodCred
    */
    public function testCmdGetBlockHash()
    {   
        $result = (array)json_decode($this->bitcoindConn->getblockhash(20));
        $this->blockHash = $result['result'];
        $this->assertNotNull($result['result']);
    }

    /**
    * @depends testCmdGetBlockHash
    */
    public function testCmdGetBlock()
    {   
        $result = (array)json_decode($this->bitcoindConn->getblock($this->blockHash));
        $this->assertEquals($result['error'], $this->blockHash);
    }
}

testCmdGetBlock()未获得应在$this->blockHash中设置的testCmdGetBlockHash()的值。

非常感谢帮助理解错误。

4 个答案:

答案 0 :(得分:32)

在测试之前始终调用setUp()方法,因此即使您在两个测试之间设置了依赖关系,setUp()中设置的任何变量都将被覆盖。 PHPUnit数据传递的工作方式是从一个测试的返回值到另一个测试的参数:

class JsonRpcBitcoinTest extends PHPUnit_Framework_TestCase
{
    public function setUp()
    {
        global $configRpcUser, $configRpcPass, $configRpcHost, $configRpcPort;

        $this->bitcoindConn = new JsonRpcBitcoin($configRpcUser, $configRpcPass, $configRpcHost, $configRpcPort);
        $this->blockHash = '';
    }


    public function testCmdGetBlockHash()
    {   
        $result = (array)json_decode($this->bitcoindConn->getblockhash(20));
        $this->assertNotNull($result['result']);

        return $result['result']; // the block hash
    }


    /**
     * @depends testCmdGetBlockHash
     */
    public function testCmdGetBlock($blockHash) // return value from above method
    {   
        $result = (array)json_decode($this->bitcoindConn->getblock($blockHash));
        $this->assertEquals($result['error'], $blockHash);
    }
}

因此,如果您需要在测试之间保存更多状态,请在该方法中返回更多数据。我猜想PHPUnit令人烦恼的原因是不鼓励依赖测试。

See the official documentation for details

答案 1 :(得分:7)

您可以在函数中使用静态变量... PHP烦人地与所有实例共享类方法的静态变量......但是在这个cas中它可以帮助:p

protected function &getSharedVar()
{
    static $value = null;
    return $value;
}

...

public function testTest1()
{
    $value = &$this->getSharedVar();

    $value = 'Hello Test 2';
}


public function testTest2()
{
    $value = &$this->getSharedVar();

    // $value should be ok
}

注意:这不是好方法,但如果您在所有测试中都需要一些数据,它会有所帮助......

答案 2 :(得分:0)

这对我来说在所有测试中都很好:$ this-> varablename

class SignupTest extends TestCase
{
    private $testemail = "registerunittest@company.com";
    private $testpassword = "Mypassword";
    public $testcustomerid = 123;
    private $testcountrycode = "+1";
    private $testphone = "5005550000";

    public function setUp(): void
    {
        parent::setUp();
    }

    public function tearDown(): void 
    {
        parent::tearDown();
    }

    public function testSignup()
    {
        $this->assertEquals("5005550000", $this->testphone;
    }
}

答案 3 :(得分:0)

另一种选择是使用静态变量。

这里是一个示例(用于Symfony 4功能测试):     

namespace App\Tests\Controller\Api;

use Symfony\Bundle\FrameworkBundle\Test\WebTestCase;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Hautelook\AliceBundle\PhpUnit\RefreshDatabaseTrait;
use Symfony\Component\HttpFoundation\AcceptHeader;

class BasicApiTest extends WebTestCase
{
    // This trait provided by HautelookAliceBundle will take care of refreshing the database content to a known state before each test
    use RefreshDatabaseTrait;

    private $client = null;

    /**
     * @var string
     */
    private const APP_TOKEN = 'token-for-tests';

    /**
     * @var string
     */
    private static $app_user__email = 'tester+api+01@localhost';

    /**
     * @var string
     */
    private static $app_user__pass = 'tester+app+01+password';

    /**
     * @var null|string
     */
    private static $app_user__access_token = null;

    public function test__Authentication__Login()
    {
        $this->client->request(
            Request::METHOD_POST,
            '/api/login',
            [],
            [],
            [
                'CONTENT_TYPE' => 'application/json',
                'HTTP_App-Token' => self::APP_TOKEN
            ],
            '{"user":"'.static::$app_user__email.'","pass":"'.static::$app_user__pass.'"}'
        );
        $response = $this->client->getResponse();

        $this->assertEquals(Response::HTTP_OK, $response->getStatusCode());

        $content_type = AcceptHeader::fromString($response->headers->get('Content-Type'));
        $this->assertTrue($content_type->has('application/json'));

        $responseData = json_decode($response->getContent(), true);
        $this->assertArrayHasKey('token', $responseData);

        $this->static = static::$app_user__access_token = $responseData['token'];
    }

    /**
     * @depends test__Authentication__Login
     */
    public function test__SomeOtherTest()
    {
        $this->client->request(
            Request::METHOD_GET,
            '/api/some_endpoint',
            [],
            [],
            [
                'CONTENT_TYPE' => 'application/json',
                'HTTP_App-Token' => self::APP_TOKEN,
                'HTTP_Authorization' => 'Bearer ' . static::$app_user__access_token
            ],
            '{"user":"'.static::$app_user__email.'","pass":"'.static::$app_user__pass.'"}'
        );
        $response = $this->client->getResponse();

        $this->assertEquals(Response::HTTP_OK, $response->getStatusCode());

        $content_type = AcceptHeader::fromString($response->headers->get('Content-Type'));
        $this->assertTrue($content_type->has('application/json'));
        //...
    }
}