使用 Docker 进行 PHP 集成测试:完整指南

面向初学者的在线Python训练器

轻松学习Python,无需理论负担。在浏览器中直接解决带自动检查的实践任务,无需安装任何东西。

开始课程

引言:为什么在Docker中进行PHP集成测试是必备技能



现代PHP应用程序的开发很少局限于单台服务器。数据库、缓存(Redis、Memcached)、消息队列(RabbitMQ)、外部API——所有这些都需要验证组件间的交互。单元测试(unit tests)虽然能隔离代码,但无法保证类A通过真实数据库与类B正确协作。这时就需要集成测试的介入。



传统方法的问题在于环境配置。开发者需要花费数小时搭建MySQL、配置权限、安装PHP扩展。Docker可以一劳永逸地解决这个问题。本文将详细讲解如何使用Docker和Docker Compose组织PHP应用的集成测试。您将获得现成的配置文件、代码示例以及优化建议。



1. 为PHP测试配置Docker环境



1.1. 基础项目结构



假设我们有一个基于Symfony或Laravel的简单PHP应用(任何框架都适用)。在项目根目录创建docker-compose.yml文件:



version: '3.8'

services: php: build: . volumes: - .:/var/www/html environment: - DATABASE_URL=mysql://test_user:test_pass@db:3306/test_db depends_on: - db

db: image: mysql:8.0 environment: MYSQL_ROOT_PASSWORD: root_pass MYSQL_DATABASE: test_db MYSQL_USER: test_user MYSQL_PASSWORD: test_pass ports: - "3307:3306" # 映射到非标准端口,避免与本地数据库冲突

test_runner: image: php:8.2-cli volumes: - .:/var/www/html working_dir: /var/www/html entrypoint: ["vendor/bin/phpunit"] depends_on: - db - php


关键要点:

  • test_runner服务使用独立的PHP CLI容器——这样可以将测试执行与主应用隔离。
  • 数据库以纯净模式启动。每次运行测试时我们都可以重建数据库。
  • MySQL端口映射到3307,避免干扰开发者的本地数据库。


1.2. PHP应用的Dockerfile



为主服务php创建Dockerfile:



FROM php:8.2-fpm

RUN docker-php-ext-install pdo_mysql mysqli

COPY --from=composer:latest /usr/bin/composer /usr/bin/composer

WORKDIR /var/www/html

COPY . .

RUN composer install --no-interaction --prefer-dist


这个镜像将同时用于开发和测试。必须安装pdo_mysql扩展——否则涉及数据库的测试将会失败。



2. 使用PHPUnit编写集成测试



2.1. PHPUnit基础配置



确保已通过Composer安装PHPUnit。phpunit.xml文件需要指向测试数据库:



<?xml version="1.0" encoding="UTF-8"?><phpunit bootstrap="vendor/autoload.php">    <php>        <env name="DATABASE_URL" value="mysql://test_user:test_pass@db:3306/test_db" />        <env name="APP_ENV" value="test" />    </php>    <testsuites>        <testsuite name="Integration">            <directory>tests/Integration</directory>        </testsuite>    </testsuites></phpunit>


2.2. 集成测试示例:数据库操作



假设我们有一个用户仓库(User Repository)。编写测试验证保存和查询功能:



<?php

namespace App\\Tests\\Integration;

use App\\Entity\\User;use App\\Repository\\UserRepository;use Doctrine\\ORM\\EntityManagerInterface;use Symfony\\Bundle\\FrameworkBundle\\Test\\KernelTestCase;

class UserRepos

博客

书籍推荐