* * * * *
[TOC]
## 简介
Laravel 为 HTTP 请求的生成和输出的检查都提供了非常流畅的 API。例如,你可以查看下面的这个测试用例:
~~~
<?php
namespace Tests\Feature;
use Tests\TestCase;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Foundation\Testing\WithoutMiddleware;
class ExampleTest extends TestCase
{
/**
* 一个基础的测试用例。
*
* @return void
*/
public function testBasicTest()
{
$response = $this->get('/');
$response->assertStatus(200);
}
}
~~~
`get` 方法会创建一个 `GET` 请求来请求你的应用,而 `assertStatus` 方法断言返回的响应是指定的 HTTP 状态码。除了这个简单的断言之外,Laravel 也包含检查响应标头、内容、JSON 结构等各种断言。
### 自定义请求头
您可以使用 `withHeaders` 方法在发送到应用程序之前自定义请求的标头。 你可以添加想要的任何自定义标题:
~~~
<?php
class ExampleTest extends TestCase
{
/**
* 一个基本的功能测试示例。
*
* @return void
*/
public function testBasicExample()
{
$response = $this->withHeaders([
'X-Header' => 'Value',
])->json('POST', '/user', ['name' => 'Sally']);
$response
->assertStatus(200)
->assertJson([
'created' => true,
]);
}
}
~~~
> {tip} 运行测试时,CSRF 中间件会自动禁用。
## Session / 认证
Laravel 提供了几个可在测试时使用 Session 的辅助函数。首先,你需要传递一个数组给 `withSession` 方法来设置 Seesion 数据。这让你在应用程序的测试请求发送之前,先给数据加载 Session 变得简单:
~~~
<?php
class ExampleTest extends TestCase
{
public function testApplication()
{
$response = $this->withSession(['foo' => 'bar'])
->get('/');
}
}
~~~
当然,一般使用 Session 时都是用于维持用户的状态,如认证用户。`actingAs` 辅助函数提供了简单的方式来让指定的用户认证为当前的用户。例如,我们可以使用 [工厂模型](https://www.kancloud.cn/tonyyu/laravel_5_6/786284#_68) 来生成并认证用户:
~~~
<?php
use App\User;
class ExampleTest extends TestCase
{
public function testApplication()
{
$user = factory(User::class)->create();
$response = $this->actingAs($user)
->withSession(['foo' => 'bar'])
->get('/');
}
}
~~~
你也可以通过传递 guard 名称作为 `actingAs` 的第二参数以指定用户通过哪种 guard 来认证:
~~~
$this->actingAs($user, 'api')
~~~
## 测试 JSON API
Laravel 也提供了几个辅助函数来测试JSON API 和它们的相应。例如 `json`, `get`, `post`, `put`, `patch` 和`delete` 可以被用于发送各种 HTTP 动作。你也可以轻松地将数据和请求头传递到这些方法中。让我们写一个 `POST`请求到 `/user` 并断言返回期望的数据来开始使用它们:
~~~
<?php
class ExampleTest extends TestCase
{
/**
* 一个基础的功能测试示例。
*
* @return void
*/
public function testBasicExample()
{
$response = $this->json('POST', '/user', ['name' => 'Sally']);
$response
->assertStatus(200)
->assertJson([
'created' => true,
]);
}
}
~~~
> {tip} `assertJson` 方法将响应转换为数组并且利用 `PHPUnit::assertArraySubset` 来验证给定的数组存在于应用返回的 JSON 响应中。所以,如果 JSON 相应中如果有其他属性,测试仍旧会在给定数组存在的情况下通过。
### 验证完全匹配
如果你想验证应用返回的 JSON **完全** 匹配给定的数组,你应该使用 `assertExactJson` 方法:
~~~
<?php
class ExampleTest extends TestCase
{
/**
* 一个基础的功能测试示例。
*
* @return void
*/
public function testBasicExample()
{
$response = $this->json('POST', '/user', ['name' => 'Sally']);
$response
->assertStatus(200)
->assertExactJson([
'created' => true,
]);
}
}
~~~
## 测试文件上传
进行测试时,这个 `Illuminate\Http\UploadedFile` 类提供了一个可能用来生成虚拟的文件或者图片的 `fake` 方法。它与这个 `Storage` Facade 的 `fake` 方法结合在一起巨大的简化了文件上传的测试。 例如 , 你可能把那两个特征结合起来很容易测试一个头像的上传成功:
~~~
<?php
namespace Tests\Feature;
use Tests\TestCase;
use Illuminate\Http\UploadedFile;
use Illuminate\Support\Facades\Storage;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Foundation\Testing\WithoutMiddleware;
class ExampleTest extends TestCase
{
public function testAvatarUpload()
{
Storage::fake('avatars');
$response = $this->json('POST', '/avatar', [
'avatar' => UploadedFile::fake()->image('avatar.jpg')
]);
// 验证文件已存储 ...
Storage::disk('avatars')->assertExists('avatar.jpg');
// 验证一个文件不存在 ...
Storage::disk('avatars')->assertMissing('missing.jpg');
}
}
~~~
#### 虚拟文件定义
当使用这个 `fake` 方法创建文件时,为了更好地测试你想要的图片尺寸,你也许会设定图片的宽度,高度,以及图片的大小 :
~~~
UploadedFile::fake()->image('avatar.jpg', $width, $height)->size(100);
~~~
此外,在进行创建图片时,你可能使用这个 `create` 方法创建其它任何类型的文件:
~~~
UploadedFile::fake()->create('document.pdf', $sizeInKilobytes);
~~~
## 可用断言
### 响应断言
`Laravel` 为您的 [PHPUnit](https://phpunit.de/) 测试提供了各种常规断言方法。 这些断言可以通过从 `json`, `get`, `post`, `put`, 和 `delete` 测试方法返回的响应来访问:
[assertCookie](#_Cookie_249)
[assertCookieExpired](#_Cookie__257)
[assertCookieMissing](#_Cookie__265)
[assertDontSee](#assertDontSee_273)
[assertDontSeeText](#assertDontSeeText_281)
[assertExactJson](#assertExactJson_289)
[assertHeader](#assertHeader_297)
[assertHeaderMissing](#assertHeaderMissing_305)
[assertJson](#assertJson_313)
[assertJsonFragment](#assertJsonFragment_321)
[assertJsonMissing](#assertJsonMissing_329)
[assertJsonMissingExact](#assertJsonMissingExact_337)
[assertJsonStructure](#assertJsonStructure_345)
[assertJsonValidationErrors](#assertJsonValidationErrors_353)
[assertPlainCookie](#assertPlainCookie_361)
[assertRedirect](#assertRedirect_369)
[assertSee](#assertSee_377)
[assertSeeInOrder](#assertSeeInOrder_385)
[assertSeeText](#assertSeeText_393)
[assertSeeTextInOrder](#assertSeeTextInOrder_401)
[assertSessionHas](#assertSessionHas_409)
[assertSessionHasAll](#assertSessionHasAll_417)
[assertSessionHasErrors](#assertSessionHasErrors_425)
[assertSessionHasErrorsIn](#assertSessionHasErrorsIn_433)
[assertSessionMissing](#assertSessionMissing_441)
[assertStatus](#assertStatus_449)
[assertSuccessful](#assertSuccessful_457)
[assertViewHas](#assertViewHas_465)
[assertViewHasAll](#assertViewHasAll_473)
[assertViewIs](#assertViewIs_481)
[assertViewMissing](#assertViewMissing_489)
#### 断言 Cookie
断言此响应包含给定的 `cookie`:
~~~
$response->assertCookie($cookieName, $value = null);
~~~
#### 断言 Cookie 过期
断言此响应包含给定的 `cookie` 并且其已过期:
~~~
$response->assertCookieExpired($cookieName);
~~~
#### 断言 Cookie 丢失
断言此响应不包含给定的 `cookie`:
~~~
$response->assertCookieMissing($cookieName);
~~~
#### assertDontSee
验证所给的字符串不包含在响应中:
~~~
$response->assertDontSee($value);
~~~
#### assertDontSeeText
验证所给的字符串不包含在响应的文本中:
~~~
$response->assertDontSeeText($value);
~~~
#### assertExactJson
验证响应和所给 JSON 数据完全符合:
~~~
$response->assertExactJson(array $data);
~~~
#### assertHeader
验证所给的头目前在响应中:
~~~
$response->assertHeader($headerName, $value = null);
~~~
#### assertHeaderMissing
验证所给的头目前没有在响应中:
~~~
$response->assertHeaderMissing($headerName);
~~~
#### assertJson
验证响应包含所给的 JSON 数据:
~~~
$response->assertJson(array $data);
~~~
#### assertJsonFragment
验证此响应包含给定的 JSON 片段:
~~~
$response->assertJsonFragment(array $data);
~~~
#### assertJsonMissing
验证此响应不包含给定的 JSON 片段:
~~~
$response->assertJsonMissing(array $data);
~~~
#### assertJsonMissingExact
验证此响应不包含确切的 JSON 片段
~~~
$response->assertJsonMissingExact(array $data);
~~~
#### assertJsonStructure
验证此响应含有给定的 JSON 结构:
~~~
$response->assertJsonStructure(array $structure);
~~~
#### assertJsonValidationErrors
验证此响应有给定键的 JSON 验证错误 :
~~~
$response->assertJsonValidationErrors($keys);
~~~
#### assertPlainCookie
验证此响应包含所给的 cookie 『 加密 』:
~~~
$response->assertPlainCookie($cookieName, $value = null);
~~~
#### assertRedirect
断言响应重定向到指定 URI:
~~~
$response->assertRedirect($uri);
~~~
#### assertSee
断言响应中包含指定字符串:
~~~
$response->assertSee($value);
~~~
#### assertSeeInOrder
断言响应中有序包含指定字符串:
~~~
$response->assertSeeInOrder(array $values);
~~~
#### assertSeeText
断言响应文本中包含指定字符串:
~~~
$response->assertSeeText($value);
~~~
#### assertSeeTextInOrder
断言响应文本中有序包含指定字符串:
~~~
$response->assertSeeTextInOrder(array $values);
~~~
#### assertSessionHas
断言 session 包含数据片段:
~~~
$response->assertSessionHas($key, $value = null);
~~~
#### assertSessionHasAll
断言 session 中存在指定的所有值:
~~~
$response->assertSessionHasAll($key, $value = null);
~~~
#### assertSessionHasErrors
断言 session 中含有指定错误:
~~~
$response->assertSessionHasErrors(array $keys, $format = null, $errorBag = 'default');
~~~
#### assertSessionHasErrorsIn
断言 session 中含有指定错误:
~~~
$response->assertSessionHasErrorsIn($errorBag, $keys = [], $format = null);
~~~
#### assertSessionMissing
断言 session 中不含有指定键:
~~~
$response->assertSessionMissing($key);
~~~
#### assertStatus
断言响应中存在指定状态码:
~~~
$response->assertStatus($code);
~~~
#### assertSuccessful
断言响应中存在成功状态码:
~~~
$response->assertSuccessful();
~~~
#### assertViewHas
断言响应视图中存在指定数据片段:
~~~
$response->assertViewHas($key, $value = null);
~~~
#### assertViewHasAll
断言响应视图中存在指定的所有数据:
~~~
$response->assertViewHasAll(array $data);
~~~
#### assertViewIs
断言响应视图与指定值一致:
~~~
$response->assertViewIs($value);
~~~
#### assertViewMissing
断言响应视图缺少一个绑定的数据:
~~~
$response->assertViewMissing($key);
~~~
### 认证断言
`Laravel` 为您的 [PHPUnit](https://phpunit.de/) 测试提供了多种身份认证相关的断言:
| 方法 | 描述 |
| --- | --- |
| `$this->assertAuthenticated($guard = null);` | 断言此用户已被认证 |
| `$this->assertGuest($guard = null);` | 断言此用户未被认证 |
| `$this->assertAuthenticatedAs($user, $guard = null);` | 断言给定的用户被认证 |
| `$this->assertCredentials(array $credentials, $guard = null);` | 断言给定的凭证有效 |
| `$this->assertInvalidCredentials(array $credentials, $guard = null);` | 断言给定的凭证无效 |
本文章首发在
- 前言
- 翻译说明
- 发行说明
- 升级指南
- 贡献导引
- 入门指南
- 安装
- 配置信息
- 文件夹结构
- Homestead
- Valet
- 部署
- 核心架构
- 请求周期
- 服务容器
- 服务提供者
- Facades
- Contracts
- 基础功能
- 路由
- 中间件
- CSRF 保护
- 控制器
- 请求
- 响应
- 视图
- URL
- Session
- 表单验证
- 错误
- 日志
- 前端开发
- Blade 模板
- 本地化
- 前端指南
- 编辑资源 Mix
- 安全相关
- 用户认证
- Passport OAuth 认证
- 用户授权
- 加密解密
- 哈希
- 重置密码
- 综合话题
- Artisan 命令行
- 广播系统
- 缓存系统
- 集合
- 事件系统
- 文件存储
- 辅助函数
- 邮件发送
- 消息通知
- 扩展包开发
- 队列
- 任务调度
- 数据库
- 快速入门
- 查询构造器
- 分页
- 数据库迁移
- 数据填充
- Redis
- Eloquent ORM
- 快速入门
- 模型关联
- Eloquent 集合
- 修改器
- API 资源
- 序列化
- 测试相关
- 快速入门
- HTTP 测试
- 浏览器测试 Dusk
- 数据库测试
- 测试模拟器
- 官方扩展包
- Cashier 交易工具包
- Envoy 部署工具
- Horizon
- Scout 全文搜索
- Socialite 社会化登录