测试

Windows下安装 phpunit

  • 下载对应的 PHAR 文件,比如我就下载的就是 7.0 版本的 https://phar.phpunit.de/phpunit-7.0.phar
  • 将下载好的文件放在一个目录,比如 C:\bin 可以重命名为 phpunit.phar
  • C:\bin 添加到系统环境变量中
  • 打开 cmd 命令行
cd C:\bin
echo @php "%~dp0phpunit.phar" %* > phpunit.cmd
exit
  • 再次打开一个命令行,输入 phpunit --version 应该能看到版本信息,就表示安装成功了,开始用起来吧

单元测试

tests/Unit

这个比较简单,都是一些简单的单元测试,看文档即可,可以在 PHPStorm 中直接点击这个运行进行测试即可

如下图所示

功能测试

tests/Feature

功能测试,接口测试,主要发起一个接口请求来断言返回的数据等

测试代码

<?php
/**
 * phpunit 中文文档
 * https://phpunit.readthedocs.io/zh_CN/latest/assertions.html#assertarrayhaskey
 */

namespace Tests\Feature;

use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Facades\Storage;
use Tests\TestCase;

use Illuminate\Http\UploadedFile;


class ExampleTest extends TestCase {
    public $url = '/phpunit/index?test=';

    public function testBasic() {
        // 发起一个 get 请求
        $response = $this->get('/api/test/index?type=12&name=舒孝元');

        // 自定义请求头
        $response->withHeaders(['X-Header' => 'shuxiaoyuan']);

        // 打印 header  头
        $response->dumpHeaders();

        // 打印响应主体
        $response->dump();
    }

    /**
     * 测试响应状态码是否正常
     */
    public function testBasicExample() {
        $url = $this->url . '1';
        $response = $this->get($url);

        /**
         * assertOk:返回状态码是否是 200
         * assertSuccessful:断言响应状态码是否介于200-300之间
         * assertNotFound:断言响应状态码是否是 404
         * assertForbidden:断言响应状态码是否是 403
         */
        $response->assertNotFound();
    }

    /**
     * 测试是否包含给定的字符串
     */
    public function testSeeText() {
        $url = $this->url . '1';
        $response = $this->get($url);

        /**
         * 都是判断是否有包含给定的字符串
         * assertSeeText:会将响应实体转化为纯文本进行判断,即将 HTML 标签过滤掉。
         */
        $response->assertSee('shuxiaoyuan');
        $response->assertSeeText('name');
    }

    /**
     * 测试上传文件
     */
    public function testFileUpload() {
        $url = $this->url . '2';

        // 伪造目录,目录在:storage/framework/testing/disks/photos
        Storage::fake('photos');

        /**
         * 伪造上传图片
         *
         * UploadedFile::fake()->create() 方法伪造其他类型的文件
         */
//        $photo = UploadedFile::fake()->image('picture.jpg');
        $photo = UploadedFile::fake()->create('teset.pdf');


        $this->post($url, [
            'photo' => $photo
        ]);

        // 断言文件是否上传成功
        Storage::disk('photos')->assertMissing('teset.pdf');
    }

    /**
     * 测试 JSON API
     * assertStatus:断言返回状态码
     * assertJson:断言返回 JSON 数据中是否包含给定数据
     * assertJsonMissing:断言返回 JSON 数据中不包含给定键
     * assertJsonCount:断言给定键值下数据项的个数
     * assertJsonFragment:断言 JSON 数据中是否包含给定片段
     * assertJsonStructure:断言返回 JSON 响应是否包含给定的数据结构;
     * assertExactJson:断言返回 JSON 响应是否与期望数据完全一致;
     * assertJsonMissingExact:断言返回 JSON 响应是否包含给定的完整 JSON 片段;
     * assertJsonValidationErrors:断言 JSON 响应包含给定键对应的 JSON 格式验证错误信息;
     * assertJsonMissingValidationErrors:与 assertJsonValidationErrors 方法相对。
     */
    public function testJsonApi() {
        $url = $this->url . '1';

        $response = $this->json('GET', $url);

        // 断言接口响应状态码是否是200
        $response->assertStatus(200)
            // 断言返回 JSON 数据中是否包含给定数据
                 ->assertJson([
                                  'name' => 'shuxiaoyuan',
                                  'age'  => 18
                              ])
            // 断言返回 JSON 数据中不包含给定键
                 ->assertJsonMissing([
                                         'test' => '不包含这个'
                                     ])
            // 断言给定键值下数据项的个数
                 ->assertJsonCount(4)
            // 断言 JSON 数据中是否包含给定片段
                 ->assertJsonFragment([
                                          'age' => 18
                                      ]);
    }
}


接口逻辑代码

<?php

/**
 * 请提供简单说明
 *
 * User: 舒孝元
 * Date: 2020/9/18 10:13
 * Mail: sxy@shuxiaoyuan.com
 * Website: https://www.shuxiaoyuan.com
 */


namespace App\Http\Controllers\Test;


use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Storage;

class UnitController extends Controller {
    public function index(Request $request) {
        $test = $request->input('test', '');
        if (!$test) {
            return outErrcode('1000', '缺少必要参数,啥参数,不告诉你');
        }
        $rc = new \ReflectionClass(self::class);
        if ($rc->hasMethod('test' . $test)) {
            $name = $rc->getMethod('test' . $test)->name;
            return $this->$name($request);
        } else {
            return outErrcode('1000', '没有找到相应的类型');
        }
    }

    private function test1(Request $request) {
        $data = [
            'name' => 'shuxiaoyuan',
            'age'  => 18,
            'sex'  => '男',
            'test' => '随便写点'
        ];

        return $data;
    }

    private function test2(Request $request) {
        $file = $request->file('photo');
        return Storage::putFile('images', $file);
    }
}

浏览器测试