Son bölüme hoşgeldiniz. Bu bölümde Solidity kodlarımızı foundry ile test edeceğiz. Foundry temelleri için şu sayfaya bakabilirsiniz.
Test dosyamız şurada.
Öncelikle Dots.sol dosyamızın bir örneğini oluşturuyoruz. Ve aktörlerimizi basitçe tanımlıyoruz.
Kod adresindeki (hazinemizdeki) parayı takip etmek için kodlarımızı yazıyoruz.
emit log_named_address("Treasury", address(dots));
emit log_named_decimal_uint("Treasury balance is ", address(dots).balance, 18);
Sözleşmenin yaratıcısı olarak oyunu başlatıyoruz.
vm.prank(owner);
dots.startGame(2, 2, 0.1 ether, 0.0001 ether);
startGame fonksiyonuna verdiğimiz değerler ile oyun başlıyor. Dikkat bunu sadece sözleşme owner'ı yapabilir. Bunu düzenleyerek oyunun akışını değiştirebilirsiniz.
Aktörlerimizi ayrıntılı tanınımlama zamanıdır. Emit fonksiyonlarını da yazıyoruz.
assertEq yoluyla temel parametrelerimizi sorguluyoruz.
Mesela;
//testGameIndexNumber
function testGameIndexNumber() public {
assertEq(dots.activeGameIndex(), 0);
}
Oyun indeksi "0" ile başladığı için bu testin sonucunda dots.activeGameIndex()=0 olmalıdır.
Test zamanıdır.
forge test --match testGameIndexNumber
//testCountriesNumber
function testCountriesNumber() public {
assertEq(dots.numberOfCountries(),20);
}
Dots.sol dosyasında 20 üke belirlemiştik. Test edelim.
forge test --match testCountriesNumber
Şİmdi 25 ülke için deneyelim.
//testFailCountriesNumber
function testFailCountriesNumber() public {
assertEq(dots.numberOfCountries(),25);
}
Burada testin adını testFail diye başlatırsanız testin hatalı olduğunu test etmiş olursunuz. Bu testin geçmesi gereklidir çünkü hatalıdır.
Oyunu Alice'e başlattıralım. Başlatamaz değil mi? Hatırlayın startGame'i sadece owner başlatabilirdi.
//testFailStartFunction
function testFailStartFunction() public {
vm.prank(alice);
dots.startGame(1,2,3,4);
}
Şimdi Alice oyuna başlasın ama ödediği para yetersiz olsun.
//testFailInsufficientBasePrice
function testFailInsufficientBasePrice() public {
vm.startPrank(alice);
dots.claimLocation{value: 0.01 ether}(1,1,8);
vm.stopPrank();
}
Neden ? Çünkü her piksel için açılış fiyatını startGame fonksiyonunda(yukarıda) owner 0.1 ether olarak belirlemişti.
Alice şimdi doğruyu yapsın.
//testInsufficientBasePrice
function testInsufficientBasePrice() public {
vm.startPrank(alice);
dots.claimLocation{value: 0.1 ether}(1,1,8);
vm.stopPrank();
}
Şimdi şunu deneyelim. Alice bir piksel alsın. Sonra Bob gelip Alice den alsın.
//testInsufficientPrice
function testInsufficientPrice() public {
vm.startPrank(alice);
dots.claimLocation{value: 0.1 ether}(1,1,8);
vm.stopPrank();
vm.startPrank(bob);
dots.claimLocation{value: 0.2 ether}(1,1,8);
vm.stopPrank();
}
Senaryo aynı fakat Bob, Alice'e aynı fiyatı teklif ediyor. Yakıştı mı Bob ?
//testFailInsufficientPrice
function testFailInsufficientPrice() public {
vm.startPrank(alice);
dots.claimLocation{value: 0.1 ether}(1,1,8);
vm.stopPrank();
vm.startPrank(bob);
dots.claimLocation{value: 0.1 ether}(1,1,8);
vm.stopPrank();
}
Alice x:1 ve y:1 koordinatları için 8 numaralı ülkenin bayrağını alsın.
//testUndefinedCoordinates
function testUndefinedCoordinates() public {
vm.startPrank(alice);
dots.claimLocation{value: 0.1 ether}(1,1,8);
vm.stopPrank();
}
Alice x:1 ve y:20 koordinatları için 8 numaralı ülkenin bayrağını alsın.Alamaz koordinatlarımızda 20 yok.
//testFailUndefinedCoordinates
function testFailUndefinedCoordinates() public {
vm.startPrank(alice);
dots.claimLocation{value: 0.1 ether}(1,20,8);
vm.stopPrank();
}
Alice 25 numaralı ülkenin bayrağını alsın. Alamaz. 20 ülke var.
//testFailUndefinedCountry
function testFailUndefinedCountry() public {
vm.startPrank(alice);
dots.claimLocation{value: 0.1 ether}(1,1,25);
vm.stopPrank();
}
Tüm test kodlarını buradan anlatmam çok sıkıcı olurdu. Gerisi size kalmış. NFT FLAG WAR projesi, Foundry ile nasıl test yapıldığını öğrenmek için mükemmel bir kaynaktır.