简体   繁体   English

Laravel 5 如何全局设置 Cache-Control HTTP 标头?

[英]Laravel 5 how to set Cache-Control HTTP header globally?

My Laravel application is returning Cache-Control: no-cache, private HTTP header by default for each site.我的 Laravel 应用程序默认为每个站点返回Cache-Control: no-cache, private HTTP header。 How can I change this behaviour?我怎样才能改变这种行为?

PS: It is not a PHP.ini problem, because changing session.cache_limiter to empty/public does not change anything. PS:这不是 PHP.ini 的问题,因为将session.cache_limiter更改为 empty/public 不会改变任何内容。

Laravel 5.6+ Laravel 5.6+

There's no longer any need to add your own custom middleware.不再需要添加您自己的自定义中间件。

The SetCacheHeaders middleware comes out of the box with Laravel, aliased as cache.headers SetCacheHeaders中间件随 Laravel 开箱即用,别名为cache.headers

The nice thing about this Middleware is that it only applies to GET and HEAD requests - it will not cache POST or PUT requests since you almost never want to do that.这个中间件的好处是它只适用于GETHEAD请求——它不会缓存POSTPUT请求,因为你几乎不想这样做。

You can apply this globally easily by updating your RouteServiceProvider :您可以通过更新您的RouteServiceProvider轻松地全局应用它:

protected function mapWebRoutes()
{
    Route::middleware('web')
        ->middleware('cache.headers:private;max_age=3600') // added this line
        ->namespace($this->namespace)
        ->group(base_path('routes/web.php'));
}

protected function mapApiRoutes()
{
    Route::prefix('api')
        ->middleware('api')
        ->middleware('cache.headers:private;max_age=3600') // added this line
        ->namespace($this->namespace)
        ->group(base_path('routes/api.php'));
}

I don't recommend that though.不过我不建议这样做。 Instead, as with any middleware, you can easily apply to specific endpoints, groups, or within the controller itself, eg:相反,与任何中间件一样,您可以轻松地应用于特定端点、组或控制器本身,例如:

Route::middleware('cache.headers:private;max_age=3600')->group(function() {
    Route::get('cache-for-an-hour', 'MyController@cachedMethod');
    Route::get('another-route', 'MyController@alsoCached');
    Route::get('third-route', 'MyController@alsoAlsoCached');
});

Note that the options are separated by semicolon not comma, and hyphens are replaced by underscores.请注意,选项由分号而不是逗号分隔,连字符由下划线代替。 Also, Symfony only supports a limited number of options :此外,Symfony 仅支持有限数量的选项

'etag', 'last_modified', 'max_age', 's_maxage', 'private', 'public', 'immutable'

In other words you can't simply copy and paste a standard Cache-Control header value, you will need to update the formatting:换句话说,您不能简单地复制和粘贴标准的Cache-Control标头值,您需要更新格式:

CacheControl format:       private, no-cache, max-age=3600
  ->
Laravel/Symfony format:    private;max_age=3600

Laravel 5.5 < Laravel 5.5 <

You can have a global middleware for that.您可以为此拥有一个全局中间件。 something like:就像是:

<?php

namespace App\Http\Middleware;

use Closure;

class CacheControl
{
    public function handle($request, Closure $next)
    {
        $response = $next($request);

        $response->header('Cache-Control', 'no-cache, must-revalidate');
        // Or whatever you want it to be:
        // $response->header('Cache-Control', 'max-age=100');

        return $response;
    }
}

then just register this as a global middleware in the Kernel file:然后只需将其注册为内核文件中的全局中间件:

protected $middleware = [
    ....
    \App\Http\Middleware\CacheControl::class
];

For people that seek a way to write less code, here is another way you can add headers to a response without extra steps.对于寻求编写更少代码的方法的人,这里是另一种无需额外步骤即可向响应添加标头的方法。

In the example above, I created a middleware to prevent routes from being cached in the end user browser.在上面的例子中,我创建了一个中间件来防止路由在最终用户浏览器中被缓存。

<?php

class DisableRouteCache
{
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        return $next($request)->withHeaders([
            "Pragma" => "no-cache",
            "Expires" => "Fri, 01 Jan 1990 00:00:00 GMT",
            "Cache-Control" => "no-cache, must-revalidate, no-store, max-age=0, private",
        ]);
    }
}

Source: Attaching Headers To Responses来源: 将标题附加到响应

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM