pitchart/phlunit

PHP流畅断言

dev-master 2021-03-25 10:49 UTC

README

Build Status Scrutinizer Code Quality Code Coverage

Phlunit: PHP Fluent Unit Testing

Check::that(tdd())->with($phlunit)->isAnInstanceOf(Awesomeness::class);

phpunit的流畅断言。

为什么?

Phlunit将使您的测试

  • 易于编写:只需输入Check::that($sut),让自动完成引导您。
  • 易于阅读:非常接近纯英文,使非技术人员更容易阅读测试代码。
  • 易于调试:每个失败的检查都会抛出一个带有清晰消息状态的异常,以便于您的TDD体验。
  • 更不易出错:不再混淆"预期"和"实际"值的顺序。

安装

composer require --dev pitchart/phlunit

编写检查

像往常一样编写测试用例和测试方法,只需切换到Check::that()来编写您的断言

use Pitchart\Phlunit\Check;

$integers = [1, 2, 3, 4, 5, 42];
Check::that($integers)->contains(2, 3, 42);


$heroes = "Batman and Robin";
Check::that($heroes)
    ->startsWith("Batman")
    ->contains("Robin")
;

// Collection checks
Check::that([0, 1, 2])
    ->isACollectionOf('integer')
    ->hasElementAt(1)
    ->and->hasNoElementAt(12)
    ->hasLength(3)
    ->hasNotLength(12)
    ->contains(1, 2)
    ->isSubsetOf(0, 1, 2, 3, 4)
    ->containsNoDuplicateItem()
;

// PSR-7 ResponseInterface checks
$response = (new Response(200))
    ->withHeader('xxx-header', 'xxx-header-value')
    ->withBody(Utils::streamFor('{"name": "Batman", "city": "Gotham City"}'))
;

Check::that($response)
    ->asJson()
        ->matchesSchema(['type' => 'object', 'required' => ['name'], 'properties' => ['name' => ['type' => 'string']]]);

Phlunit为以下类型和类提供检查

  • 字符串、布尔值、整数、浮点数、数组
  • xml和json格式
  • 可迭代对象
  • 可调用对象
  • Throwable
  • ResponseInterface (PSR-7)
  • DateTimeInterface

语法糖

使用that()andThat()方法提高可读性

Check::thatCall([$spiderman, 'saveGotham'])->with('batman', 'superman')
    ->throws(\LogicException::class)
    ->that()->isDescribedBy("Sorry, we are not in the same univers!");

Check::that($batman->getFirstname())->isEqualTo('Bruce')
    ->andThat($batman->getLastname())->isEqualTo('Wayne');

需要更多检查吗?

使用自定义约束

编写自定义phpunit约束,并通过is()has()isNot()hasNot()方法使用它们

class CustomConstraint extends Constraint
{
    //...
}

Check::that($sut)->is(new CustomConstraint());

创建自定义Check类

class CustomClassCheck implements FluentCheck
{
    //...
}

// Register your custom checks for dedicated classes in phpunit's bootstrap file
Check::registerChecksFor(Custom::class, CustomClassChecks::class);

//
Check::that(Check::that(new Custom))->isAnInstanceOf(CustomClassChecks::class);

测试数据构建器

Phlunit提供了一种简单且可扩展的方法来实现测试数据构建器模式

这是推荐的用法,以不破坏流畅体验

use Pitchart\Phlunit\Builder;

class HeroBuilder extends Builder
{
    protected function __construct(array $arguments)
    {
        parent::__construct(Hero::class, $arguments);
    }
    
    public function build(): Hero
    {
        return $this->buildInstance();
    }
    
    public static function create(): self
    {
        return new self([
            'name' => 'Batman',
            'firstname' => 'Bruce',
            'lastname' => 'Wayne',
        ]);
    }
    
    public static function batman(): self
    {
        return self::create();
    }
}

// Use it in your test cases:
$batman = HeroBuilder::batman()->build();

$superman = HeroBuilder::create()
    ->withName('Superman')
    ->andFirstname('Clark')
    ->andLastname('Kent')
    ->build()
;

期望异常

Phlunit提供了一种流畅的方式来期望您的代码抛出异常,使用Expect

use Pitchart\Phlunit\Expect;

public function test_an_exception_is_thrown()
{
    Expect::after($this)
        ->anException(\InvalidArgumentException)
        ->describedBy('An exception message')
        ->havingCode(42);
    
    // Act
}

致谢

此软件包主要受到NFluentAssertJ的启发。

感谢Bruno Boucard的启发。

许可证

MIT许可证