İddialar
Aassertions, gerçek bir değerin beklenen bir değerle eşleştiğini iddia etmek için kullanılır. Bunlar
Tester\Assert
'un yöntemleridir.
En doğru iddiaları seçin. Assert::same($a, $b)
, Assert::true($a === $b)
'den daha iyidir çünkü
başarısızlık durumunda anlamlı bir hata mesajı görüntüler. İkinci durumda sadece false should be true
alırız ve $a ve $b değişkenlerinin içeriği hakkında hiçbir şey söylemez.
Çoğu iddia, beklentinin başarısız olması durumunda hata mesajında görünen isteğe bağlı bir
$description
adresine de sahip olabilir.
Örnekler aşağıdaki sınıf takma adının tanımlandığını varsayar:
use Tester\Assert;
Assert::same($expected, $actual, ?string $description=null)
$expected
$actual
ile aynı olmalıdır. PHP operatörü ile aynıdır ===
.
Assert::notSame($expected, $actual, ?string $description=null)
Assert::same()
'un tersidir, bu nedenle PHP operatörü !==
ile aynıdır.
Assert::equal($expected, $actual, ?string $description=null, bool $matchOrder=false, bool $matchIdentity=false)
$expected
$actual
ile aynı olmalıdır. Assert::same()
adresinden farklı olarak, nesne
kimliği, dizilerdeki anahtar çiftleri ⇒ değer sırası ve marjinal olarak farklı ondalık sayılar göz ardı edilir; bunlar
$matchIdentity
ve $matchOrder
adresleri ayarlanarak değiştirilebilir.
Aşağıdaki durumlar equal()
açısından aynıdır, ancak same()
için aynı değildir:
Assert::equal(0.3, 0.1 + 0.2);
Assert::equal($obj, clone $obj);
Assert::equal(
['first' => 11, 'second' => 22],
['second' => 22, 'first' => 11],
);
Ancak, dikkat edin, dizi [1, 2]
ve [2, 1]
eşit değildir, çünkü anahtar ⇒ değer çiftleri
değil, yalnızca değerlerin sırası farklıdır. Dizi [1, 2]
olarak da yazılabilir
[0 => 1, 1 => 2]
ve bu nedenle [1 => 2, 0 => 1]
eşit kabul edilecektir.
Sözde beklentileri $expected
adresinde de kullanabilirsiniz.
Assert::notEqual($expected, $actual, ?string $description=null)
Karşısında Assert::equal()
.
Assert::contains($needle, string|array $actual, ?string $description=null)
$actual
bir dizeyse, $needle
alt dizesini içermelidir. Bir dizi ise, $needle
öğesini
içermelidir (kesinlikle karşılaştırılır).
Assert::notContains($needle, string|array $actual, ?string $description=null)
Karşısında Assert::contains()
.
Assert::hasKey(string|int $needle, array $actual, ?string $description=null)
$actual
bir dizi olmalı ve $needle
anahtarını içermelidir.
Assert::notHasKey(string|int $needle, array $actual, ?string $description=null)
$actual
bir dizi olmalı ve $needle
anahtarını içermemelidir.
Assert::true($value, ?string $description=null)
$value
true
, yani $value === true
olmalıdır.
Assert::truthy($value, ?string $description=null)
$value
doğru olmalıdır, bu nedenle if ($value) ...
koşulunu karşılar.
Assert::false($value, ?string $description=null)
$value
false
, yani $value === false
olmalıdır.
Assert::falsey($value, ?string $description=null)
$value
falsey olmalıdır, bu nedenle if (!$value) ...
koşulunu karşılar.
Assert::null($value, ?string $description=null)
$value
null
, yani $value === null
olmalıdır.
Assert::notNull($value, ?string $description=null)
$value
null
olmamalıdır, bu yüzden $value !== null
.
Assert::nan($value, ?string $description=null)
$value
Bir Numara Değil olmalıdır. NAN testi için yalnızca Assert::nan()
adresini kullanın. NAN
değeri çok spesifiktir ve Assert::same()
veya Assert::equal()
iddiaları tahmin edilemeyecek şekilde
davranabilir.
Assert::count($count, Countable|array $value, ?string $description=null)
$value
adresindeki öğe sayısı $count
olmalıdır. Yani count($value) === $count
ile aynı.
Assert::type(string|object $type, $value, ?string $description=null)
$value
belirli bir tipte olmalıdır. $type
olarak string kullanabiliriz:
array
list
– sıfırdan itibaren sayısal anahtarların artan sırasına göre dizinlenmiş dizibool
callable
float
int
null
object
resource
scalar
string
- sınıf adını veya nesnesini doğrudan geçmelidir.
$value instanceof $type
Assert::exception(callable $callable, string $class, ?string $message=null, $code=null)
$callable
çağrıldığında $class
örneğinin bir istisnası fırlatılmalıdır. Eğer
$message
adresini geçersek, istisnanın mesajı eşleşmelidir. Ve eğer
$code
adresini geçersek, istisnanın kodu aynı olmalıdır.
Örneğin, istisnanın mesajı eşleşmediği için bu test başarısız olur:
Assert::exception(
fn() => throw new App\InvalidValueException('Zero value'),
App\InvalidValueException::class,
'Value is to low',
);
Assert::exception()
atılan bir istisna döndürür, böylece iç içe geçmiş bir istisnayı test
edebilirsiniz.
$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)
$callable
çağrısının beklenen hataları (yani uyarılar, bildirimler, vb.) oluşturup oluşturmadığını
kontrol eder. $type
olarak E_...
sabitlerinden birini belirtiriz, örneğin E_WARNING
. Ve
eğer $message
geçilirse, hata mesajı da kalıpla eşleşmelidir. Örneğin:
Assert::error(
fn() => $i++,
E_NOTICE,
'Undefined variable: i',
);
Geri arama daha fazla hata üretirse, hepsini tam sırayla beklemeliyiz. Bu durumda diziyi $type
adresine
aktarırız:
Assert::error(function () {
$a++;
$b++;
}, [
[E_NOTICE, 'Undefined variable: a'],
[E_NOTICE, 'Undefined variable: b'],
]);
Eğer $type
sınıf adı ise, bu iddia Assert::exception()
ile aynı şekilde
davranır.
Assert::noError(callable $callable)
$callable
işlevinin herhangi bir PHP uyarısı/bildirimi/hatası veya istisnası atmadığını kontrol eder.
Başka bir iddianın olmadığı bir kod parçasını test etmek için kullanışlıdır.
Assert::match(string $pattern, $actual, ?string $description=null)
$actual
$pattern
ile eşleşmelidir. İki çeşit kalıp kullanabiliriz: düzenli ifadeler veya joker
karakterler.
Bir düzenli ifadeyi $pattern
olarak geçirirsek, sınırlandırmak için ~
or #
kullanmalıyız. Diğer sınırlayıcılar desteklenmez. Örneğin, $var
adresinin yalnızca onaltılık basamaklar
içermesi gereken test:
Assert::match('#^[0-9a-f]$#i', $var);
Diğer varyant dize karşılaştırmaya benzer ancak $pattern
adresinde bazı vahşi karakterler
kullanabiliriz:
%a%
satır sonu karakterleri hariç herhangi bir şeyden bir veya daha fazlası%a?%
satır sonu karakterleri dışında herhangi bir şeyden sıfır veya daha fazlası%A%
satır sonu karakterleri de dahil olmak üzere herhangi bir şeyden bir veya daha fazlası%A?%
satır sonu karakterleri de dahil olmak üzere herhangi bir şeyden sıfır veya daha fazlası%s%
satır sonu karakterleri hariç bir veya daha fazla beyaz boşluk karakteri%s?%
satır sonu karakterleri hariç sıfır veya daha fazla beyaz boşluk karakteri%S%
beyaz boşluk hariç bir veya daha fazla karakter%S?%
beyaz boşluk dışında sıfır veya daha fazla karakter%c%
herhangi bir türden tek bir karakter (satır sonu hariç)%d%
bir veya daha fazla rakam%d?%
sıfır veya daha fazla basamak%i%
işaretli tamsayı değeri%f%
kayan nokta sayısı%h%
bir veya daha fazla HEX rakamı%w%
bir veya daha fazla alfanümerik karakter%%
bir % karakteri
Örnekler:
# 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)
Assert::match() ile aynıdır ancak kalıp $file
adresinden yüklenir. Çok uzun
dizeleri test etmek için kullanışlıdır. Test dosyası okunabilir duruyor.
Assert::fail(string $message, $actual=null, $expected=null)
Bu iddia her zaman başarısız olur. Sadece kullanışlıdır. İsteğe bağlı olarak beklenen ve gerçek değerleri geçebiliriz.
Beklentiler
Sabit olmayan elemanlara sahip daha karmaşık yapıları karşılaştırmak istiyorsak, yukarıdaki ifadeler yeterli
olmayabilir. Örneğin, yeni bir kullanıcı oluşturan ve özniteliklerini bir dizi olarak döndüren bir yöntemi test ediyoruz.
Parola karma değerini bilmiyoruz, ancak onaltılık bir dize olması gerektiğini biliyoruz. Ve bir sonraki eleman hakkında
bildiğimiz tek şey, bunun bir nesne olması gerektiğidir DateTime
.
Bu durumlarda, yapıyı kolayca tanımlamak için kullanılabilecek Assert::equal()
ve
Assert::notEqual()
yöntemlerinin $expected
parametresinin içindeki Tester\Expect
'u kullanabiliriz.
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'));
Expect
ile, Assert
ile hemen hemen aynı iddialarda bulunabiliriz. Yani Expect::same()
,
Expect::match()
, Expect::count()
, vb. gibi metotlarımız var. Ek olarak, bunları şu şekilde
zincirleyebiliriz:
Expect::type(MyIterator::class)->andCount(5); # we expect MyIterator and items count is 5
Ya da kendi onaylama işleyicilerini yazabiliriz.
Expect::that(function ($value) {
# return false if expectation fails
});
Başarısız İddialar Soruşturması
Tester, bir iddia başarısız olduğunda hatanın nerede olduğunu gösterir. Karmaşık yapıları
karşılaştırdığımızda, Tester karşılaştırılan değerlerin dökümlerini oluşturur ve bunları output
dizinine kaydeder. Örneğin hayali test Arrays.recursive.phpt
başarısız olduğunda dökümler aşağıdaki gibi
kaydedilecektir:
app/
└── tests/
├── output/
│ ├── Arrays.recursive.actual # actual value
│ └── Arrays.recursive.expected # expected value
│
└── Arrays.recursive.phpt # failing test
Dizinin adını Tester\Dumper::$dumpDir
adresinden değiştirebiliriz.