HTTP 響應(yīng)
基礎(chǔ)響應(yīng)
所有的路由和控制器都應(yīng)該返回某種響應(yīng)發(fā)送回給用戶的瀏覽器,laravel提供了多種不同的方式來返回響應(yīng)。最基本的響應(yīng)就是簡單的在路由或控制器中返回字符串:
Route::get('/', function () {
return 'Hello World';
});
這里返回的字符串會被laravel自動的轉(zhuǎn)換為HTTP響應(yīng)發(fā)送出去.
響應(yīng)對象
大多數(shù)時候,路由或者控制器的行為都應(yīng)該返回Illuminate\Http\Response
實例或者view
。Response
實例允許你便利的對響應(yīng)頭和響應(yīng)的狀態(tài)進行定制化.一個Response
實例繼承自Symfony\Component\HttpFoundation\Response
類,該類提供了多種方法來生成一個HTTP響應(yīng):
use Illuminate\Http\Response;
Route::get('home', function () {
return (new Response($content, $status))
->header('Content-Type', $value);
});
laravel也提供了便利的response
全局幫助函數(shù):
Route::get('home', function () {
return response($content, $status)
->header('Content-Type', $value);
});
所有可以使用的
Response
實例的方法,你可以查看 API 文檔 和 Symfony API文檔.
附加響應(yīng)頭
Response
實例的大多數(shù)方法都是允許進行鏈式調(diào)用的坦刀,你可以使用鏈式調(diào)用來流利的構(gòu)建響應(yīng)。例如,你可以使用header
方法去添加多種響應(yīng)頭在其被發(fā)送到用戶客戶端之前:
return response($content)
->header('Content-Type', $type)
->header('X-Header-One', 'Header Value')
->header('X-Header-Two', 'Header Value');
或者你可以使用withHeaders
方法來通過指定的數(shù)組添加請求頭到響應(yīng):
return response($content)
->withHeaders([
'Content-Type' => $type,
'X-Header-One' => 'Header Value',
'X-Header-Two' => 'Header value'
]);
添加cookie到響應(yīng)
Response
實例的cookie
可以簡單的追加cookie信息到響應(yīng)鲤遥。例如沐寺,你可以使用cookie
方法來生成cookie并附加到響應(yīng)中:
return response($content)
->header('Content-Type', $type)
->cookie('name', 'value');
cookie
方法允許你添加額外的參數(shù)來進一步定制化你的cookie屬性:
->cookie($name, $value, $minutes, $path, $domain, $secure, $httpOnly)
默認的,laravel中所有的cookie都是經(jīng)過簽證加密的,所以客戶端的用戶是沒辦法修改或者解讀的.所以如果你想在生成某些cookie時盖奈,禁用默認的加密混坞,你需要在App\Http\Middleware\EncreyptCookies
中間件的$except
屬性中進行追加:
protected $except = [
'cookie_name'
];
其它響應(yīng)類型
幫助方法response
也可以用來便利的生成其它類型的響應(yīng)實例,如果你使用response
幫助方法不傳遞任何參數(shù)卜朗,那么它會返回一個實現(xiàn)了Illuminate\Contracts\Routing\ResponseFactory
contract的實例拔第。該契約提供了多種有用的方法來生成響應(yīng).
視圖響應(yīng)
如果你想控制響應(yīng)的響應(yīng)頭與狀態(tài),并且你也需要返回一個視圖作為響應(yīng)的內(nèi)容场钉,那么你可以使用view
方法:
return response()
->view('hello', $data)
->header('Content-Type', $type);
當然蚊俺,如果你并不需要定制化響應(yīng)的狀態(tài)或者響應(yīng)頭,那么你可以直接使用全局幫助方法view
逛万。
JSON響應(yīng)
json
方法會自動的設(shè)置響應(yīng)頭的Content-Type
為application/json
,以及使用json_encode
方法將提供的數(shù)組轉(zhuǎn)換為JSON:
return response()->json(['name' => 'Abigail', 'state' => 'CA']);
如果你想要生成jsonp
的響應(yīng)泳猬,那么你可以使用json
方法然后附加setCallback
方法:
return response()
->json(['name' => 'Abigail', 'state' => 'CA'])
->setCallback($request->input('callback'));
文件下載
download
方法可以在返回一個強制用戶端瀏覽器進行下載指定路徑文件的響應(yīng)。download
方法也允許傳遞第二個參數(shù)作為瀏覽器下載時的文件名,你也可以傳遞http響應(yīng)頭數(shù)組作為第三個參數(shù):
return response()->download($pathToFile);
return response()->download($pathToFile, $name, $headers);
注意:Symfony HttpFoundation需要被下載的文件有一個ASCII文件名
文件響應(yīng)
file
方法允許你在瀏覽器直接顯示image或pdf類型的文件來代替直接下載宇植。該方法接收文件路徑作為第一個參數(shù)得封,也可以接收HTTP響應(yīng)頭數(shù)組作為第二個參數(shù):
return response()->file($pathToFile);
return response()->file($pathToFile, $headers);
重定向
重定向響應(yīng)是一個Illuminate\Http\RedirectResponse
類的實例,它包含了所有重定向到指定URI所需要的響應(yīng)頭信息指郁。laravel提供了多種方式去生成重定向?qū)嵗?最簡單的方式莫過于使用全局幫助方法redirect
:
Route::get('dashboard', function () {
return redirect('home/dashboard');
});
有時候你需要將用戶重定向到上一次請求的地址忙上,那么你可以使用全局幫助方法back
。因為這里用到了session闲坎,所以你必須要保證你的路由使用了session中間件疫粥,默認的laravel的路由都被包裹在web
路由組中,web
中間件組中已經(jīng)包含了session中間件:
Route::post('user/profile', function () {
// Validate the request...
return back()->withInput();
});
重定向至命名路由
當你使用redirect
方法而不傳遞任何參數(shù)時腰懂,laravel將返回Illuminated\Routing\Redirector
的一個實例梗逮,該實例允許你使用一些方法來處理重定向信息,例如,為了生成重定向到命名路由绣溜,你可以使用route
方法:
return redirect()->route('login');
如果命名路由也含有參數(shù)慷彤,那么你可以傳遞第二個參數(shù)到route
方法:
return redirect()->route('profile', ['id' => 1]);
如果你需要重定向的路由是使用Eloquent
模型的id
作為參數(shù)識別的路由,那么你可以直接在route
方法中傳遞用戶實例,它會自動被解析到id:
return redirect()->route('profile', [$user]);
重定向至控制器行為
你也可以生成重定向信息到控制器的某個行為.你可以簡單的通過action
方法傳遞控制器名稱和控制器行為來做到這些.你應(yīng)該注意怖喻,你并不需要特別的指出控制器的全部命名空間,因為laravel的RouteServiceProvider
已經(jīng)自動的設(shè)置了默認的命名空間:
return redirect()->action('HomeController@index');
當然底哗,如果你的控制器行為也接收其他的參數(shù),你同樣可以在action
方法中傳遞第二個參數(shù):
return redirect()->action('UserController@profile', ['id' => 1]);
重定向并閃存session
你可以通過RedirectResponse
實例的鏈式調(diào)用來做到在生成重定向信息的同時閃存seession數(shù)據(jù)锚沸,這在執(zhí)行行為之后存儲消息狀態(tài)的場景尤其有用:
Route::post('user/profile', function () {
// Update the user's profile...
return redirect('dashboard')->with('status', 'profile updated');
});
當然跋选,在用戶重定向到新頁面時,你是可以訪問到閃存的會話信息的咒吐,例如,在blade模板中,你可以這么使用:
@if (session('status'))
<div class="alert alert-success">
{{ session('status')}}
</div>
@endif
響應(yīng)宏
如果你想自定義某種可復(fù)用的響應(yīng)恬叹,你可以使用Response
facade的 macro
方法或者提供Illuminate\Contracts\Routing\ResponseFactory
的一個實現(xiàn):
<?php
namespace App\Providers;
use Response;
use Illuminate\Support\ServiceProvider;
class ResponseMacroServiceProvider extends ServiceProvider {
public function boot() {
Response::macro('caps', function ($value) {
return Response::make(strtoupper($value));
});
}
}
macro
方法接收一個別名作為第一個參數(shù)候生,接收一個閉包作為第二個參數(shù)。閉包會在訪問ResponseFactory
實現(xiàn)的實例的動態(tài)屬性macro
別名時執(zhí)行绽昼,或者通過全局幫助方法response
:
return response()->caps('foo');