Maison >développement back-end >tutoriel php >Problèmes courants et solutions dans la pratique des tests unitaires PHP
Problèmes courants avec les tests unitaires PHP : Tests de dépendances externes : utilisation d'un framework moqueur (tel que Mockery) pour créer de fausses dépendances et affirmer leurs interactions. Tests de membres privés : utilisez des API de réflexion telles que ReflectionMethod pour accéder aux membres privés ou utilisez des modificateurs de visibilité de test tels que @protected. Tests d'interaction de base de données : configurez et vérifiez l'état de la base de données à l'aide d'un cadre de test de base de données tel que DbUnit. Tests d'API/service Web externes : utilisez une bibliothèque client HTTP pour simuler les interactions, à l'aide d'un serveur local ou stub dans l'environnement de test.
Questions fréquemment posées sur les tests unitaires PHP
Question 1 : Comment tester unitairement du code avec des dépendances externes ?
Solution : Utilisez un framework moqueur comme Mockery ou Prophecy de PHPUnit qui vous permet de créer de faux objets de dépendance et de faire des assertions sur leurs interactions.
use Prophecy\Prophet; class UserRepoTest extends \PHPUnit\Framework\TestCase { public function testFetchUser(): void { $prophet = new Prophet(); $cache = $prophet->prophesize(Cache::class); $userRepo = new UserRepo($cache->reveal()); $actualUser = $userRepo->fetchUser(1); $cache->get(1)->shouldHaveBeenCalled(); $this->assertEquals($expectedUser, $actualUser); } }
Question 2 : Comment tester une méthode ou une propriété privée ?
Solution : Utilisez des API de réflexion (telles que ReflectionClass
et ReflectionMethod
) qui vous permettent d'accéder aux membres privés. Cependant, cela peut rendre les tests difficiles à maintenir. ReflectionClass
和 ReflectionMethod
),允许你访问私有成员。然而,它可能会使测试难以维护。
另一种解决方案是使用测试特定的可见性修饰符,例如 PHPUnit 的 @protected
@protected
de PHPUnit. class UserTest extends \PHPUnit\Framework\TestCase { public function testPasswordIsSet(): void { $user = new User(); $reflector = new ReflectionClass($user); $property = $reflector->getProperty('password'); $property->setAccessible(true); $property->setValue($user, 'secret'); $this->assertEquals('secret', $user->getPassword()); } }Question 3 : Comment tester l'interaction avec la base de données ?
Solution :
Utilisez un framework de test de base de données tel que DbUnit de PHPUnit ou Doctrine DBAL Assertions qui vous permet de définir et de vérifier l'état de la base de données.use PHPUnit\DbUnit\TestCase; class PostRepoTest extends TestCase { protected function getConnection(): Connection { return $this->createDefaultDBConnection(); } public function testCreatePost(): void { $dataset = $this->createXMLDataSet(__DIR__ . '/initial-dataset.xml'); $this->getDatabaseTester()->setDataSet($dataset); $this->getDatabaseTester()->onSetUp(); $post = new Post(['title' => 'My First Post']); $postRepo->persist($post); $postRepo->flush(); $this->assertTrue($this->getConnection()->getRowCount('posts') === 1); } }Question 4 : Comment tester du code qui s'appuie sur des API ou des services web externes ?
Solution :
Utilisez une bibliothèque client HTTP pour simuler les interactions avec des services externes. Dans un environnement de test, vous pouvez utiliser un serveur local ou stub. 🎜use GuzzleHttp\Client; class UserServiceTest extends \PHPUnit\Framework\TestCase { public function testFetchUser(): void { $httpClient = new Client(); $userService = new UserService($httpClient); $httpClient ->shouldReceive('get') ->with('/users/1') ->andReturn(new Response(200, [], json_encode(['id' => 1, 'name' => 'John Doe']))); $user = $userService->fetchUser(1); $this->assertInstanceOf(User::class, $user); $this->assertEquals(1, $user->getId()); } }
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!