[TOC]
# 响应
## 创建响应
### 字符串 & 数组
```
Route::get('/', function () {
return 'Hello World';
});
// 框架会自动将数组转化为一个 JSON 响应
Route::get('/', function () {
return [1, 2, 3];
});
```
>[success] 提示:从路由或控制器返回`Eloquent 集合`也会被自动转化为 JSON 响应。
### Response 对象
```
Route::get('home', function () {
return response('Hello World', 200)
->header('Content-Type', 'text/plain');
});
```
### 添加响应头
```
return response($content)
->header('Content-Type', $type)
->header('X-Header-One', 'Header Value')
->header('X-Header-Two', 'Header Value');
return response($content)
->withHeaders([
'Content-Type' => $type,
'X-Header-One' => 'Header Value',
'X-Header-Two' => 'Header Value',
]);
```
### 缓存控制中间件
Laravel 内置了一个`cache.headers`中间件,可以用来快速地为路由组设置`Cache-Control`头信息。如果在指令集中声明了`etag`,Laravel 会自动将 ETag 标识符设置为响应内容的 MD5 哈希值
```
Route::middleware('cache.headers:public;max_age=2628000;etag')->group(function() {
Route::get('privacy', function () {
// ...
});
Route::get('terms', function () {
// ...
});
});
```
### 添加 Cookies 到响应
```
// 模板设置cookie
return response()->view('welcome')->cookie('name', 'value', $minutes);
return response()->view('welcome')->withCookie('name', 'value', $minutes);
// 设置 Cookies ,名称、值、过期时间等,与`setcookie`方法的参数类似
return response($content)
->header('Content-Type', $type)
->cookie('name', 'value', $minutes [, $path, $domain, $secure, $httpOnly]);
// Cookie 队列,`queue`方法接受一个`Cookie`实例或者创建实例所需的参数
Cookie::queue(Cookie::make('name', 'value', $minutes));
Cookie::queue('name', 'value', $minutes);
// 生成 Cookie 实例
$cookie = cookie('name', 'value', $minutes);
return response('Hello World')->cookie($cookie);
```
### 删除 Cookie
```
$cookie = Cookie::forget('name' [, $path, $domain]);
return response()->view('welcome')->cookie($cookie);
return response()->view('welcome')->cookie('name', null, -2628000 [, $path, $domain]);
```
### Cookies & 加密
默认情况下,Laravel 生成的所有 Cookie 都是经过加密和签名,因此不能被客户端修改或读取。 如果你想要应用程序生成的部分 Cookie 不被加密,那么可以使用在`app/Http/Middleware`目录中`App\Http\Middleware\EncryptCookies`中间件的`$except`属性。
```
/**
* 不需要被加密的cookies名称
*
* @var array
*/
protected $except = [
'cookie_name',
];
```
## 重定向
```
// 全局辅助函数
Route::get('dashboard', function () {
return redirect('home/dashboard');
});
// 表单提交失败后退之前页面
// 由于该功能利用了会话控制,需要确保调用 back 函数的路由使用 web中间件组 或所有 Session中间件
Route::post('user/profile', function () {
//验证请求
return back()->withInput();
});
```
### 重定向到命名路由
如果调用不带参数的辅助函数`redirect`时,会返回`Illuminate\Routing\Redirector`实例。这个实例允许你调用`Redirector`上的任何方法。
```
return redirect()->route('login');
// 对于具有以下 URI 的路由: profile/{id}
return redirect()->route('profile', ['id' => 1]);
// 通过 Eloquent 模型填充参数,自动从模型提取ID
return redirect()->route('profile', [$user]);
```
如果要自定义这个路由参数的默认参数值,需要重写模型实例上的 getRouteKey 方法
```
public function getRouteKey()
{
return $this->slug;
}
```
### 跳转到控制器 Action
```
return redirect()->action('HomeController@index');
// 参数设置
return redirect()->action(
'UserController@profile', ['id' => 1]
);
```
### 跳转到外部域名
```
// 创建不带有任何额外的 URL 编码、有效性校验和检查的`RedirectResponse`实例
return redirect()->away('https://www.google.com');
```
### 带有传送 Session 值的跳转
```
Route::post('user/profile', function () {
// Update the user's profile...
return redirect('dashboard')->with('status', 'Profile updated!');
});
// 跳转后前台显示
@if (session('status'))
<div class="alert alert-success">
{{ session('status') }}
</div>
@endif
```
### 带有 Cookie 的跳转
```
// 使用全局辅助函数
return redirect('test')->cookie('name', 'value', 1);
return redirect('test')->withCookie('name', 'value', 1);
// 使用 Redirect Facades
return Redirect::to('test')->cookie('name', 'value', 1);
return Redirect::route('test')->withCookie('name', 'value', 1);
// 使用 withCookies 设置多个 Cookie
$cookie1 = cookie('name1', 'value1', 1);
$cookie2 = cookie('name2', 'value2', 1);
return Redirect::action('IndexController@test')->withCookies([$cookie1, $cookie2]);
```
## 其它的响应类型
### 视图响应
```
// 控制响应状态和头信息
return response()
->view('hello', $data, 200)
->header('Content-Type', $type);
// 如果不需要传递自定义的 HTTP 状态码和自定义头信息,可以使用全局 view 辅助函数。
return view('hello', $data);
```
### JSON 响应
```
return response()->json([
'name' => 'Abigail',
'state' => 'CA'
]);
```
### JSONP 响应
```
return response()
->json(['name' => 'Abigail', 'state' => 'CA'])
->withCallback($request->input('callback'));
```
### 文件下载
```
// 注意:Symfony HttpFoundation 要求下载的文件有一个 ASCII 文件名。
return response()->download($pathToFile);
// 第二个参数为用户下载文件的文件名,第三个参数为 HTTP 头信息数组
return response()->download($pathToFile, $name, $headers);
// 下载后删除文件
return response()->download($pathToFile)->deleteFileAfterSend();
// 流下载,字符串响应转换为下载响应,不需要写入磁盘
return response()->streamDownload(function () {
echo GitHub::api('repo')
->contents()
->readme('laravel', 'laravel')['contents'];
}, 'laravel-readme.md' [, $headers]);
```
### 文件响应
```
// 直接在浏览器显示图片或PDF等
return response()->file($pathToFile);
return response()->file($pathToFile, $headers);
```
## 响应宏
自定义在路由或控制器中复用的响应
```
// `macro`方法接受一个名称作为第一个参数,闭包函数作为的第二个参数。
<?php
namespace App\Providers;
use Illuminate\Support\ServiceProvider;
use Illuminate\Support\Facades\Response;
class ResponseMacroServiceProvider extends ServiceProvider
{
/**
* 注册应用程序的响应宏
*
* @return void
*/
public function boot()
{
Response::macro('caps', function ($value) {
return Response::make(strtoupper($value));
});
}
}
// 响应宏的闭包在`ResponseFactory`实现类或辅助函数`response`中调用宏名称的时候被执行
return response()->caps('foo');
```
- 入门指南
- 安装
- 部署
- 基础功能
- 路由
- 中间件
- CSRF 保护
- 控制器
- 请求
- 响应
- 视图
- URL
- Session
- 表单验证
- 错误
- 日志
- 前端开发
- Blade 模板
- 本地化
- 脚手架
- 编译资源 Mix
- 安全相关
- 用户认证
- API 认证
- 综合话题
- 命令行
- 广播
- 缓存
- 集合
- 事件
- 文件存储
- 辅助函数
- 邮件发送
- 消息通知
- 扩展包开发
- 队列
- 任务调度
- 数据库
- 快速入门
- 查询构造器
- 分页
- 数据库迁移
- 数据填充
- Redis
- Eloquent ORM
- 快速入门
- 速查表
- Artisan
- Auth
- Blade
- Cache
- Collection
- Composer
- Config
- Container
- Cookie
- DB
- Environment
- Event
- File
- Helper
- Input
- Lang
- Log
- Model
- Pagination
- Queue
- Redirect
- Request
- Response
- Route
- SSH
- Schema
- Security
- Session
- Storage
- String
- URL
- UnitTest
- Validation
- View