GV

GeezerVison

The World Wide Web, restored to 800 pixels of glory.

Home|About|Gaming cabinet|Archives|How it works|Starter sites

On this site

  • Sign in
  • ActionsCI/CD and automation
  • CodespacesCloud development environments
  • All Features
  • Documentation
  • Training
  • Certifications
  • Build with Copilot
  • Customize Copilot
  • Integrations
  • Trending repos
  • GitHub Sponsors
  • Developer articles
  • Enterprises

This view

  • Original page
  • New address

GeezerVison is showing github.com — GitHub - tarantool-php/phpunit-extras: A collection of helpers for PHPUnit to ease testing Tarantool libraries.

BranchesTags
Open more actions menu

Latest commit

 

History

59 Commits
59 Commits

Folders and files

NameName
Last commit message
Last commit date
.github
.github
 
 
src
src
 
 
tests
tests
 
 
.gitattributes
.gitattributes
 
 
.gitignore
.gitignore
 
 
.php-cs-fixer.dist.php
.php-cs-fixer.dist.php
 
 
LICENSE
LICENSE
 
 
README.md
README.md
 
 
composer.json
composer.json
 
 
phpunit-extension.xml
phpunit-extension.xml
 
 
phpunit.xml.dist
phpunit.xml.dist
 
 
psalm.xml
psalm.xml
 
 

Repository files navigation

PHPUnit Extras

Quality Assurance Telegram

A collection of helpers for PHPUnit to ease testing Tarantool libraries. It is based on rybakit/phpunit-extras. Please refer to that package for further documentation.

Table of contents

  • Installation
  • Attributes
    • Processors
      • Lua
      • Sql
    • Requirements
  • RequiresIfLua
  • RequiresTarantool
  • Expectations
    • Requests
    • Prepared statements
  • Mocking
  • Testing
  • License

Installation

composer require --dev tarantool/phpunit-extras

Attributes

Besides the attributes provided by the package rybakit/phpunit-extras, the library includes with attributes specific to Tarantool. The easiest way to enable them is by inheriting your test classes from Tarantool\PhpUnit\TestCase:

use Tarantool\Client\Client;
use Tarantool\PhpUnit\TestCase;

final class MyTest extends TestCase
{
    protected function getClient() : Client
    {
        // TODO: Implement getClient() method.
    }
    
    // ...
}

Another option is to register an extension called AttributeExtension:

<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/10.5/phpunit.xsd"
    bootstrap="vendor/autoload.php"
>
    <!-- ... -->

    <extensions>
        <bootstrap class="Tarantool\PhpUnit\Attribute\AttributeExtension" />
    </extensions>
</phpunit>

By default, the extension assumes that the Tarantool server you want to connect to is available on 127.0.0.1:3301. You can customize the default settings by specifying either a DSN string or an array of options as extension configuration values. PHPUnit 10 passes extension parameters as strings, so use the DSN form for options that require numeric or Boolean values (such as socket_timeout):

<extensions>
    <bootstrap class="Tarantool\PhpUnit\Attribute\AttributeExtension">
        <parameter name="dsn" value="tcp://127.0.0.1:3301/?socket_timeout=10" />
    </bootstrap>
</extensions>

or

<extensions>
    <bootstrap class="Tarantool\PhpUnit\Attribute\AttributeExtension">
        <parameter name="uri" value="tcp://127.0.0.1:3301" />
        <parameter name="username" value="tester" />
        <parameter name="password" value="secret" />
    </bootstrap>
</extensions>

Configuration values can also reference environment variables, which might be useful if you need to share the same settings with a Tarantool instance file or any other script:

<extensions>
    <bootstrap class="Tarantool\PhpUnit\Attribute\AttributeExtension">
        <parameter name="dsn" value="tcp://%env(TARANTOOL_HOST)%:%env(TARANTOOL_PORT)%" />
    </bootstrap>
</extensions>

Once the attributes are configured, you can start using them:

Processors

Lua

Allows executing Lua code before running a test.

Example:

use Tarantool\PhpUnit\Attribute\Lua;

#[Lua("tube:put('kick_me')")]
#[Lua('tube:bury(0)')]
public function testKickReleasesBuriedTask() : void
{
    // ...
}

SQL

Allows executing SQL statements before running a test (requires Tarantool 2.0+).

Example:

use Tarantool\PhpUnit\Attribute\Sql;

#[Sql('DROP TABLE IF EXISTS foobar')]
#[Sql('CREATE TABLE foobar (id INTEGER PRIMARY KEY, name VARCHAR(50))')]
#[Sql("INSERT INTO foobar VALUES (1, 'A'), (2, 'B')")]
public function testExecuteQueryFetchesAllRows() : void
{
    // ...
}

Requirements

Requirements allow skipping tests based on preconditions.

RequiresIfLua

Here, <condition> is an arbitrary Lua expression that should evaluate to a Boolean value.

Example:

use Tarantool\PhpUnit\Attribute\RequiresIfLua;

#[RequiresIfLua("box.session.user() ~= 'guest'")]
public function testChangeUserPassword() : void
{
    // ...
}

RequiresTarantool

Here, <version-constraint> uses a version constraint format similar to Composer's. For details on supported formats, please see the Composer documentation.

Example:

use Tarantool\PhpUnit\Attribute\RequiresTarantool;

#[RequiresTarantool('^2.3.2')]
public function testPrepareCreatesPreparedStatement() : void
{
    // ...
}

If you're interested in how to create and register your own attributes and requirements, please refer to the rybakit/phpunit-extras README.

Expectations

Requests

To test that your code sends (or does not send) certain requests, the following methods are available:

  • TestCase::expect<REQUEST_NAME>RequestToBeCalled(int $count) : void
  • TestCase::expect<REQUEST_NAME>RequestToBeCalledAtLeast(int $count) : void
  • TestCase::expect<REQUEST_NAME>RequestToBeCalledAtMost(int $count) : void
  • TestCase::expect<REQUEST_NAME>RequestToBeCalledOnce() : void
  • TestCase::expect<REQUEST_NAME>RequestToBeCalledAtLeastOnce() : void
  • TestCase::expect<REQUEST_NAME>RequestToBeCalledAtMostOnce() : void
  • TestCase::expect<REQUEST_NAME>RequestToBeNeverCalled() : void
  • TestCase::expectNoRequestToBeCalled() : void

where <REQUEST_NAME> is the name of the request, for example Call, Insert, etc. These methods are part of the Tarantool\PhpUnit\TestCase class, but they can also be enabled through a trait:

use PHPUnit\Framework\TestCase;
use PHPUnitExtras\Expectation\Expectations as BaseExpectations;
use Tarantool\Client\Client;
use Tarantool\PhpUnit\Expectation\RequestExpectations;

final class MyTest extends TestCase
{
    use BaseExpectations;
    use RequestExpectations;

    protected function getClient() : Client
    {
        // TODO: Implement getClient() method.
    }

    /**
     * @after
     */
    protected function verifyTestCaseExpectations() : void
    {
        $this->verifyExpectations();
    }

    // ...
}

Example:

public function testGetSpaceIsCached() : void
{
    $this->client->flushSpaces();

    $this->expectSelectRequestToBeCalledOnce();
    $this->client->getSpace('test_space');
    $this->client->getSpace('test_space');
}

Prepared statements

In order to assert prepared statement allocations, use the Tarantool\PhpUnit\Expectation\PreparedStatementExpectations trait, which contains the following methods:

  • expectPreparedStatementToBe<TYPE>(int $count) : void
  • expectPreparedStatementToBe<TYPE>AtLeast(int $count) : void
  • expectPreparedStatementToBe<TYPE>AtMost(int $count) : void
  • expectPreparedStatementToBe<TYPE>Once() : void
  • expectPreparedStatementToBeNever<TYPE>() : void
  • expectPreparedStatementToBe<TYPE>AtLeastOnce() : void
  • expectPreparedStatementToBe<TYPE>AtMostOnce() : void

where <TYPE> is either Allocated or Deallocated.

Example:

public function testCloseDeallocatesPreparedStatement() : void
{
    $stmt = $this->client->prepare('SELECT ?');

    $this->expectPreparedStatementToBeDeallocatedOnce();
    $stmt->close();
}

To enable all the expectation methods above at once, use the Tarantool\PhpUnit\Expectation\Expectations trait, or extend the Tarantool\PhpUnit\TestCase class.

Mocking

The library provides several helper classes to create test doubles for the Tarantool Client to avoid sending real requests to the Tarantool server. To make these objects easier to create, add the TestDoubleClient trait to your test class:

use PHPUnit\Framework\TestCase;
use Tarantool\PhpUnit\Client\TestDoubleClient;

final class MyTest extends TestCase
{
    use TestDoubleClient;

    // ...
}

If your test cases extend the Tarantool\PhpUnit\TestCase class, this step is not needed because the trait is already included in that class.

A dummy client object can be created as follows:

public function testFoo() : void
{
    $dummyClient = $this->createDummyClient();

    // ...
}

To simulate specific scenarios, such as establishing a connection to a server or returning specific responses in a specific order from the server, use the facilities of the TestDoubleClientBuilder class. For example, to simulate the PING request:

use Tarantool\Client\Request\PingRequest;
use Tarantool\PhpUnit\TestCase;

final class MyTest extends TestCase
{
    public function testFoo() : void
    {
        $mockClient = $this->getTestDoubleClientBuilder()
            ->shouldSend(new PingRequest())
            ->build();

        // ...
    }

    // ...
}

Another example, sending two EVALUATE requests and returning a different response for each:

use Tarantool\Client\RequestTypes;
use Tarantool\PhpUnit\Client\TestDoubleFactory;
use Tarantool\PhpUnit\TestCase;

final class MyTest extends TestCase
{
    public function testFoo() : void
    {
        $mockClient = $this->getTestDoubleClientBuilder()
            ->shouldSend(
                RequestTypes::EVALUATE, 
                RequestTypes::EVALUATE
            )->willReceive(
                TestDoubleFactory::createResponseFromData([2]),
                TestDoubleFactory::createResponseFromData([3])
            )->build();
    
        // ...
    }

    // ...
}

The above example can be simplified to:

$mockClient = $this->getTestDoubleClientBuilder()
    ->shouldHandle(
        RequestTypes::EVALUATE,
        TestDoubleFactory::createResponseFromData([2]),
        TestDoubleFactory::createResponseFromData([3])
    )->build();

Besides, the builder allows setting custom Connection and Packer instances:

$stubClient = $this->getMockClientBuilder()
    ->willUseConnection($myConnection)
    ->willUsePacker($myPacker)
    ->build();

Testing

Before running tests, the development dependencies must be installed:

composer install

Then, to run all the tests:

vendor/bin/phpunit
vendor/bin/phpunit -c phpunit-extension.xml

License

The library is released under the MIT License. See the bundled LICENSE file for details.

About

A collection of helpers for PHPUnit to ease testing Tarantool libraries.

Topics

phpunitphpunit-assertionsphpunit-extensionphpunit-extrasphpunit-utiltarantool

Resources

Readme
MIT license
Activity
Custom properties

Stars

2 stars

Watchers

2 watching

Forks

1 fork
Report repository

Releases

Sponsor this project

Packages

Used by

Contributors

Languages

You are visitor 01402503 — GeezerVison does not store the pages you look up.
Best viewed with Netscape Navigator 4.7 or Internet Explorer 6 at 800×600. No cookies required.