Nette Documentation Preview

syntax
Assertions
**********

.[perex]
As afirmações são usadas para afirmar que um valor real corresponde a um valor esperado. Eles são métodos do `Tester\Assert`.

Escolha as afirmações mais precisas. É melhor `Assert::same($a, $b)` do que `Assert::true($a === $b)` porque exibe uma mensagem de erro significativa em caso de falha. No segundo caso, obtemos apenas `false should be true` e não diz nada sobre o conteúdo das variáveis $a e $b.

A maioria das afirmações também pode ter um `$description` opcional que aparece na mensagem de erro se a expectativa falhar.

Os exemplos assumem que a seguinte classe está definida:

```php
use Tester\Assert;
```


Assert::same($expected, $actual, string $description=null) .[method]
--------------------------------------------------------------------
`$expected` deve ser o mesmo que `$actual`. É o mesmo que o operador de PHP `===`.


Assert::notSame($expected, $actual, string $description=null) .[method]
-----------------------------------------------------------------------
Ao contrário de `Assert::same()`, então é o mesmo que o operador PHP `!==`.


Assert::equal($expected, $actual, string $description=null, bool $matchOrder=false, bool $matchIdentity=false) .[method]
------------------------------------------------------------------------------------------------------------------------
`$expected` deve ser o mesmo que `$actual`. Ao contrário de `Assert::same()`, a identidade do objeto, a ordem dos pares de chaves => valor em arrays e números decimais marginalmente diferentes são ignorados, o que pode ser alterado através da configuração `$matchIdentity` e `$matchOrder`.

Os seguintes casos são idênticos do ponto de vista de `equal()`, mas não para `same()`:

```php
Assert::equal(0.3, 0.1 + 0.2);
Assert::equal($obj, clone $obj);
Assert::equal(
	['first' => 11, 'second' => 22],
	['second' => 22, 'first' => 11],
);
```

Entretanto, tenha cuidado, a matriz `[1, 2]` e `[2, 1]` não são iguais, porque apenas a ordem dos valores é diferente, não a chave => pares de valores. A matriz `[1, 2]` também pode ser escrito como `[0 => 1, 1 => 2]` e, portanto `[1 => 2, 0 => 1]` serão considerados iguais.

Você também pode usar as chamadas [expectativas |#expectations] em `$expected`.


Assert::notEqual($expected, $actual, string $description=null) .[method]
------------------------------------------------------------------------
Oposto a `Assert::equal()`.


Assert::contains($needle, string|array $actual, string $description=null) .[method]
-----------------------------------------------------------------------------------
Se `$actual` for um fio, ele deve conter o substrato `$needle`. Se for uma matriz, deve conter o elemento `$needle` (é comparado estritamente).


Assert::notContains($needle, string|array $actual, string $description=null) .[method]
--------------------------------------------------------------------------------------
Oposto a `Assert::contains()`.


Assert::hasKey(string|int $needle, array $actual, string $description=null) .[method]{data-version:2.4}
-------------------------------------------------------------------------------------------------------
`$actual` deve ser uma matriz e deve conter a chave `$needle`.


Assert::notHasKey(string|int $needle, array $actual, string $description=null) .[method]{data-version:2.4}
----------------------------------------------------------------------------------------------------------
`$actual` deve ser uma matriz e não deve conter a chave `$needle`.


Assert::true($value, string $description=null) .[method]
--------------------------------------------------------
`$value` deve ser `true`, portanto `$value === true`.


Assert::truthy($value, string $description=null) .[method]
----------------------------------------------------------
`$value` deve ser verdadeira, portanto satisfaz a condição `if ($value) ...`.


Assert::false($value, string $description=null) .[method]
---------------------------------------------------------
`$value` deve ser `false`, portanto `$value === false`.


Assert::falsey($value, string $description=null) .[method]
----------------------------------------------------------
`$value` deve ser falso, por isso satisfaz a condição `if (!$value) ...`.


Assert::null($value, string $description=null) .[method]
--------------------------------------------------------
`$value` deve ser `null`, portanto `$value === null`.


Assert::notNull($value, string $description=null) .[method]
-----------------------------------------------------------
`$value` não deve ser `null`, portanto `$value !== null`.


Assert::nan($value, string $description=null) .[method]
-------------------------------------------------------
`$value` não deve ser um número. Use apenas o `Assert::nan()` para testes NAN. O valor do NAN é muito específico e as afirmações `Assert::same()` ou `Assert::equal()` podem se comportar de forma imprevisível.


Assert::count($count, Countable|array $value, string $description=null) .[method]
---------------------------------------------------------------------------------
O número de elementos em `$value` deve ser `$count`. Portanto, o mesmo que `count($value) === $count`.


Assert::type(string|object $type, $value, string $description=null) .[method]
-----------------------------------------------------------------------------
`$value` deve ser de um determinado tipo. Como `$type`, podemos usar cordel:
- `array`
- `list` - matriz indexada em ordem ascendente de chaves numéricas a partir de zero
- `bool`
- `callable`
- `float`
- `int`
- `null`
- `object`
- `resource`
- `scalar`
- `string`
- nome da classe ou objeto deve então passar diretamente `$value instanceof $type`


Assert::exception(callable $callable, string $class, string $message=null, $code=null) .[method]
------------------------------------------------------------------------------------------------
Em `$callable` deve ser lançada uma exceção de instância `$class`. Se passarmos `$message`, a mensagem da exceção deve [coincidir |#assert-match]. E se passarmos `$code`, o código da exceção deve ser o mesmo.

Por exemplo, este teste falha porque a mensagem da exceção não corresponde:

```php
Assert::exception(
	fn() => throw new App\InvalidValueException('Zero value'),
	App\InvalidValueException::class,
	'Value is to low',
);
```

O `Assert::exception()` retorna uma exceção lançada, para que você possa testar uma exceção aninhada.

```php
$e = Assert::exception(
	fn() => throw new MyException('Something is wrong', 0, new RuntimeException),
	MyException::class,
	'Something is wrong',
);

Assert::type(RuntimeException::class, $e->getPrevious());
```


Assert::error(string $callable, int|string|array $type, string $message=null) .[method]
---------------------------------------------------------------------------------------
Verifica se a invocação `$callable` gera os erros esperados (ou seja, avisos, avisos, etc.). Como `$type`, especificamos uma das constantes `E_...`, por exemplo `E_WARNING`. E, se passar `$message`, a mensagem de erro também deve [corresponder |#assert-match] ao padrão. Por exemplo:

```php
Assert::error(
	fn() => $i++,
	E_NOTICE,
	'Undefined variable: i',
);
```

Se a ligação de retorno gera mais erros, devemos esperar todos eles na ordem exata. Neste caso, passamos a matriz em `$type`:

```php
Assert::error(function () {
	$a++;
	$b++;
}, [
	[E_NOTICE, 'Undefined variable: a'],
	[E_NOTICE, 'Undefined variable: b'],
]);
```

.[note]
Se `$type` é nome de classe, esta afirmação se comporta da mesma forma que `Assert::exception()`.


Assert::noError(callable $callable) .[method]
---------------------------------------------
Verifica se a função `$callable` não lança nenhum aviso/notificação/erro ou exceção em PHP. É útil para testar um pedaço de código onde não há outra asserção.


Assert::match(string $pattern, $actual, string $description=null) .[method]
---------------------------------------------------------------------------
`$actual` Devemos corresponder a `$pattern`. Podemos utilizar duas variantes de padrões: expressões regulares ou wildcards.

Se passarmos uma expressão regular como `$pattern`, devemos usar `~` or `#` para delimitá-la. Outros delimitadores não são suportados. Por exemplo, teste onde `$var` deve conter apenas dígitos hexadecimais:

```php
Assert::match('#^[0-9a-f]$#i', $var);
```

A outra variante é semelhante à comparação de cordas, mas podemos usar alguns chars selvagens em `$pattern`:

- `%a%` um ou mais de qualquer coisa, exceto os caracteres de fim de linha
- `%a?%` zero ou mais de qualquer coisa, exceto os caracteres de fim de linha
- `%A%` um ou mais de qualquer coisa, incluindo os caracteres de fim de linha
- `%A?%` zero ou mais de qualquer coisa, incluindo os caracteres de fim de linha
- `%s%` um ou mais caracteres de espaço branco, exceto os caracteres de fim de linha
- `%s?%` zero ou mais caracteres de espaço branco, exceto os caracteres de fim de linha
- `%S%` um ou mais caracteres, exceto o espaço branco
- `%S?%` zero ou mais caracteres, exceto para o espaço branco
- `%c%` um único personagem de qualquer tipo (exceto para o final da linha)
- `%d%` um ou mais dígitos
- `%d?%` zero ou mais dígitos
- `%i%` valor inteiro assinado
- `%f%` número do ponto flutuante
- `%h%` um ou mais dígitos do HEX
- `%w%` um ou mais caracteres alfanuméricos
- `%%` um % de caráter

Exemplos:

```php
# Again, hexadecimal number test
Assert::match('%h%', $var);

# Generalized path to file and line number
Assert::match('Error in file %a% on line %i%', $errorMessage);
```


Assert::matchFile(string $file, $actual, string $description=null) .[method]
----------------------------------------------------------------------------
A afirmação é idêntica a [Assert::match() |#assert-match] mas o padrão é carregado a partir de `$file`. É útil para testes de cordas muito longas. Os arquivos de teste podem ser lidos.


Assert::fail(string $message, $actual=null, $expected=null) .[method]
---------------------------------------------------------------------
Esta afirmação sempre falha. É apenas útil. Opcionalmente, podemos passar os valores esperados e reais.


Expectativas .[#toc-expectations]
---------------------------------
Se quisermos comparar estruturas mais complexas com elementos não-constantes, as afirmações acima podem não ser suficientes. Por exemplo, testamos um método que cria um novo usuário e devolve seus atributos como uma matriz. Não sabemos o valor do hash da senha, mas sabemos que ela deve ser uma string hexadecimal. E a única coisa que sabemos sobre o próximo elemento é que ele deve ser um objeto `DateTime`.

Nestes casos, podemos usar o `Tester\Expect` dentro do parâmetro `$expected` dos métodos `Assert::equal()` e `Assert::notEqual()`, que podem ser usados para descrever facilmente a estrutura.

```php
use Tester\Expect;

Assert::equal([
	'id' => Expect::type('int'),                   # we expect an integer
	'username' => 'milo',
	'password' => Expect::match('%h%'),            # we expect a string matching pattern
	'created_at' => Expect::type(DateTime::class), # we expect an instance of the class
], User::create(123, 'milo', 'RandomPaSsWoRd'));
```

Com `Expect`, podemos fazer quase as mesmas afirmações que com `Assert`. Portanto, temos métodos como `Expect::same()`, `Expect::match()`, `Expect::count()`, etc. Além disso, podemos encadeá-los como:

```php
Expect::type(MyIterator::class)->andCount(5);  # we expect MyIterator and items count is 5
```

Ou, podemos escrever os próprios responsáveis pelas asserções.

```php
Expect::that(function ($value) {
	# return false if expectation fails
});
```


Investigação de Assertions Failed .[#toc-failed-assertions-investigation]
-------------------------------------------------------------------------
O Tester mostra onde está o erro quando uma asserção falha. Quando comparamos estruturas complexas, o Tester cria despejos de valores comparados e os salva no diretório `output`. Por exemplo, quando o teste imaginário `Arrays.recursive.phpt` falha, os lixões serão salvos da seguinte forma:

```
app/
└── tests/
	├── output/
	│   ├── Arrays.recursive.actual    # actual value
	│   └── Arrays.recursive.expected  # expected value
	│
	└── Arrays.recursive.phpt          # failing test
```

Podemos mudar o nome do diretório por `Tester\Dumper::$dumpDir`.

Assertions

As afirmações são usadas para afirmar que um valor real corresponde a um valor esperado. Eles são métodos do Tester\Assert.

Escolha as afirmações mais precisas. É melhor Assert::same($a, $b) do que Assert::true($a === $b) porque exibe uma mensagem de erro significativa em caso de falha. No segundo caso, obtemos apenas false should be true e não diz nada sobre o conteúdo das variáveis $a e $b.

A maioria das afirmações também pode ter um $description opcional que aparece na mensagem de erro se a expectativa falhar.

Os exemplos assumem que a seguinte classe está definida:

use Tester\Assert;

Assert::same($expected, $actual, string $description=null)

$expected deve ser o mesmo que $actual. É o mesmo que o operador de PHP ===.

Assert::notSame($expected, $actual, string $description=null)

Ao contrário de Assert::same(), então é o mesmo que o operador PHP !==.

Assert::equal($expected, $actual, string $description=null, bool $matchOrder=false, bool $matchIdentity=false)

$expected deve ser o mesmo que $actual. Ao contrário de Assert::same(), a identidade do objeto, a ordem dos pares de chaves ⇒ valor em arrays e números decimais marginalmente diferentes são ignorados, o que pode ser alterado através da configuração $matchIdentity e $matchOrder.

Os seguintes casos são idênticos do ponto de vista de equal(), mas não para same():

Assert::equal(0.3, 0.1 + 0.2);
Assert::equal($obj, clone $obj);
Assert::equal(
	['first' => 11, 'second' => 22],
	['second' => 22, 'first' => 11],
);

Entretanto, tenha cuidado, a matriz [1, 2] e [2, 1] não são iguais, porque apenas a ordem dos valores é diferente, não a chave ⇒ pares de valores. A matriz [1, 2] também pode ser escrito como [0 => 1, 1 => 2] e, portanto [1 => 2, 0 => 1] serão considerados iguais.

Você também pode usar as chamadas expectativas em $expected.

Assert::notEqual($expected, $actual, string $description=null)

Oposto a Assert::equal().

Assert::contains($needle, string|array $actual, string $description=null)

Se $actual for um fio, ele deve conter o substrato $needle. Se for uma matriz, deve conter o elemento $needle (é comparado estritamente).

Assert::notContains($needle, string|array $actual, string $description=null)

Oposto a Assert::contains().

Assert::hasKey(string|int $needle, array $actual, string $description=null)

$actual deve ser uma matriz e deve conter a chave $needle.

Assert::notHasKey(string|int $needle, array $actual, string $description=null)

$actual deve ser uma matriz e não deve conter a chave $needle.

Assert::true($value, string $description=null)

$value deve ser true, portanto $value === true.

Assert::truthy($value, string $description=null)

$value deve ser verdadeira, portanto satisfaz a condição if ($value) ....

Assert::false($value, string $description=null)

$value deve ser false, portanto $value === false.

Assert::falsey($value, string $description=null)

$value deve ser falso, por isso satisfaz a condição if (!$value) ....

Assert::null($value, string $description=null)

$value deve ser null, portanto $value === null.

Assert::notNull($value, string $description=null)

$value não deve ser null, portanto $value !== null.

Assert::nan($value, string $description=null)

$value não deve ser um número. Use apenas o Assert::nan() para testes NAN. O valor do NAN é muito específico e as afirmações Assert::same() ou Assert::equal() podem se comportar de forma imprevisível.

Assert::count($count, Countable|array $value, string $description=null)

O número de elementos em $value deve ser $count. Portanto, o mesmo que count($value) === $count.

Assert::type(string|object $type, $value, string $description=null)

$value deve ser de um determinado tipo. Como $type, podemos usar cordel:

  • array
  • list – matriz indexada em ordem ascendente de chaves numéricas a partir de zero
  • bool
  • callable
  • float
  • int
  • null
  • object
  • resource
  • scalar
  • string
  • nome da classe ou objeto deve então passar diretamente $value instanceof $type

Assert::exception(callable $callable, string $class, string $message=null, $code=null)

Em $callable deve ser lançada uma exceção de instância $class. Se passarmos $message, a mensagem da exceção deve coincidir. E se passarmos $code, o código da exceção deve ser o mesmo.

Por exemplo, este teste falha porque a mensagem da exceção não corresponde:

Assert::exception(
	fn() => throw new App\InvalidValueException('Zero value'),
	App\InvalidValueException::class,
	'Value is to low',
);

O Assert::exception() retorna uma exceção lançada, para que você possa testar uma exceção aninhada.

$e = Assert::exception(
	fn() => throw new MyException('Something is wrong', 0, new RuntimeException),
	MyException::class,
	'Something is wrong',
);

Assert::type(RuntimeException::class, $e->getPrevious());

Assert::error(string $callable, int|string|array $type, string $message=null)

Verifica se a invocação $callable gera os erros esperados (ou seja, avisos, avisos, etc.). Como $type, especificamos uma das constantes E_..., por exemplo E_WARNING. E, se passar $message, a mensagem de erro também deve corresponder ao padrão. Por exemplo:

Assert::error(
	fn() => $i++,
	E_NOTICE,
	'Undefined variable: i',
);

Se a ligação de retorno gera mais erros, devemos esperar todos eles na ordem exata. Neste caso, passamos a matriz em $type:

Assert::error(function () {
	$a++;
	$b++;
}, [
	[E_NOTICE, 'Undefined variable: a'],
	[E_NOTICE, 'Undefined variable: b'],
]);

Se $type é nome de classe, esta afirmação se comporta da mesma forma que Assert::exception().

Assert::noError(callable $callable)

Verifica se a função $callable não lança nenhum aviso/notificação/erro ou exceção em PHP. É útil para testar um pedaço de código onde não há outra asserção.

Assert::match(string $pattern, $actual, string $description=null)

$actual Devemos corresponder a $pattern. Podemos utilizar duas variantes de padrões: expressões regulares ou wildcards.

Se passarmos uma expressão regular como $pattern, devemos usar ~ or # para delimitá-la. Outros delimitadores não são suportados. Por exemplo, teste onde $var deve conter apenas dígitos hexadecimais:

Assert::match('#^[0-9a-f]$#i', $var);

A outra variante é semelhante à comparação de cordas, mas podemos usar alguns chars selvagens em $pattern:

  • %a% um ou mais de qualquer coisa, exceto os caracteres de fim de linha
  • %a?% zero ou mais de qualquer coisa, exceto os caracteres de fim de linha
  • %A% um ou mais de qualquer coisa, incluindo os caracteres de fim de linha
  • %A?% zero ou mais de qualquer coisa, incluindo os caracteres de fim de linha
  • %s% um ou mais caracteres de espaço branco, exceto os caracteres de fim de linha
  • %s?% zero ou mais caracteres de espaço branco, exceto os caracteres de fim de linha
  • %S% um ou mais caracteres, exceto o espaço branco
  • %S?% zero ou mais caracteres, exceto para o espaço branco
  • %c% um único personagem de qualquer tipo (exceto para o final da linha)
  • %d% um ou mais dígitos
  • %d?% zero ou mais dígitos
  • %i% valor inteiro assinado
  • %f% número do ponto flutuante
  • %h% um ou mais dígitos do HEX
  • %w% um ou mais caracteres alfanuméricos
  • %% um % de caráter

Exemplos:

# Again, hexadecimal number test
Assert::match('%h%', $var);

# Generalized path to file and line number
Assert::match('Error in file %a% on line %i%', $errorMessage);

Assert::matchFile(string $file, $actual, string $description=null)

A afirmação é idêntica a Assert::match() mas o padrão é carregado a partir de $file. É útil para testes de cordas muito longas. Os arquivos de teste podem ser lidos.

Assert::fail(string $message, $actual=null, $expected=null)

Esta afirmação sempre falha. É apenas útil. Opcionalmente, podemos passar os valores esperados e reais.

Expectativas

Se quisermos comparar estruturas mais complexas com elementos não-constantes, as afirmações acima podem não ser suficientes. Por exemplo, testamos um método que cria um novo usuário e devolve seus atributos como uma matriz. Não sabemos o valor do hash da senha, mas sabemos que ela deve ser uma string hexadecimal. E a única coisa que sabemos sobre o próximo elemento é que ele deve ser um objeto DateTime.

Nestes casos, podemos usar o Tester\Expect dentro do parâmetro $expected dos métodos Assert::equal() e Assert::notEqual(), que podem ser usados para descrever facilmente a estrutura.

use Tester\Expect;

Assert::equal([
	'id' => Expect::type('int'),                   # we expect an integer
	'username' => 'milo',
	'password' => Expect::match('%h%'),            # we expect a string matching pattern
	'created_at' => Expect::type(DateTime::class), # we expect an instance of the class
], User::create(123, 'milo', 'RandomPaSsWoRd'));

Com Expect, podemos fazer quase as mesmas afirmações que com Assert. Portanto, temos métodos como Expect::same(), Expect::match(), Expect::count(), etc. Além disso, podemos encadeá-los como:

Expect::type(MyIterator::class)->andCount(5);  # we expect MyIterator and items count is 5

Ou, podemos escrever os próprios responsáveis pelas asserções.

Expect::that(function ($value) {
	# return false if expectation fails
});

Investigação de Assertions Failed

O Tester mostra onde está o erro quando uma asserção falha. Quando comparamos estruturas complexas, o Tester cria despejos de valores comparados e os salva no diretório output. Por exemplo, quando o teste imaginário Arrays.recursive.phpt falha, os lixões serão salvos da seguinte forma:

app/
└── tests/
	├── output/
	│   ├── Arrays.recursive.actual    # actual value
	│   └── Arrays.recursive.expected  # expected value
	│
	└── Arrays.recursive.phpt          # failing test

Podemos mudar o nome do diretório por Tester\Dumper::$dumpDir.