简体   繁体   English

如何在Laravel 5中正确使用TerminableMiddleware?

[英]How to use TerminableMiddleware in Laravel 5 correctly?

I'm experimenting with TerminableMiddleware in Laravel 5, to try and understand it and see what can be achieved, once the HTTP request has been answered. 我正在使用Laravel 5中的TerminableMiddleware进行实验,以尝试理解它,并了解一旦HTTP请求得到答复,可以实现的目标。 My thinking is that it was something like : 我的想法是:

http://php.net/manual/en/function.fastcgi-finish-request.php http://php.net/manual/en/function.fastcgi-finish-request.php

Though I put together a test here, and I can see the request is held open till the Terminable has finished. 尽管我在这里进行了测试,但可以看到请求一直处于打开状态,直到Terminable完成。 My thinking is that it would of sent the response and closed the connection. 我的想法是,它将发送响应并关闭连接。 Or does it rely on fastcgi_finish_request() being installed ? 还是依赖于fastcgi_finish_request()的安装?

Am I trying to use it in the wrong way ? 我是否试图以错误的方式使用它?

<?php namespace App\Http\Middleware;

    use Illuminate\Contracts\Routing\TerminableMiddleware;

    use Closure;

    class MyTestMiddleware implements TerminableMiddleware {


    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        $response = $next($request);

        $response->setContent("OK " . time());

        return $response;
    }

    public function terminate($request, $response)
    {

        $fp = fopen('/tmp/deleteme', "w");

        for ($i = 0; $i < 100000 ; $i++)
        {
           fputs($fp, $this->generateRandomString(400) . "\n");
        }

        fclose($fp);
    }

    private function generateRandomString($length = 10)
    {
        $characters = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
        $charactersLength = strlen($characters);
        $randomString = '';
        for ($i = 0; $i < $length; $i++)
        {
            $randomString .= $characters[rand(0, $charactersLength - 1)];
        }

        return $randomString;
    }
}

The terminate() method is called in the end of your public/index.php file: 在您的public / index.php文件的末尾调用Terminate()方法:

$kernel = $app->make(Illuminate\Contracts\Http\Kernel::class);

$response = $kernel->handle(
    $request = Illuminate\Http\Request::capture()
);

$response->send();

$kernel->terminate($request, $response);

The $response object is an instance of Symfony\\Component\\HttpFoundation\\Response, which current implementation of send() method is: $ response对象是Symfony \\ Component \\ HttpFoundation \\ Response的一个实例,send()方法的当前实现是:

public function send()
{
    $this->sendHeaders();
    $this->sendContent();

    if (function_exists('fastcgi_finish_request')) {
        fastcgi_finish_request();
    } elseif ('cli' !== PHP_SAPI) {
        static::closeOutputBuffers(0, true);
    }

    return $this;
}

So the answer is Yes, it relies on fastcgi_finish_request being installed. 因此答案是肯定的,它依赖于fastcgi_finish_request的安装。 In fact, it tries to call it if exists. 实际上,它尝试调用它(如果存在)。 If not, it'll just output your response content and run the terminate() method while the connection is open. 如果没有,它将仅输出您的响应内容,并在连接打开时运行Terminate()方法。

If you need to do something heavier after the connection is closed, you should implement it using Laravel's Queues instead. 如果您需要在关闭连接后执行更重的操作,则应改为使用Laravel的Queues来实现它。

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

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