仅在kernel.terminate事件之后返回响应

我对kernel.terminate理解是在响应返回给客户端触发。

在我的testing艰难中,这似乎并不是这样。 如果我把一个sleep(10)放在kernel.terminate调用的函数中。 浏览器也等待10秒钟。 处理似乎在响应发送之前发生。

我有以下configuration:

 calendar: class: Acme\CalendarBundle\Service\CalendarService arguments: [ @odm.document_manager, @logger, @security.context, @event_dispatcher ] tags: - { name: kernel.event_subscriber } 

我的订阅者类别:

 class CalendarService implements EventSubscriberInterface { public static function getSubscribedEvents() { return array( 'kernel.terminate' => 'onKernelTerminate' ); } public function onKernelTerminate() { sleep(10); echo "hello"; } } 

UPDATE

这似乎与Symfony不发送Content-Length标题有关。 如果我生成了,响应正确返回。

 // app_dev.php ... $kernel = new AppKernel('dev', true); $kernel->loadClassCache(); $request = Request::createFromGlobals(); $response = $kernel->handle($request); // --- START EDITS --- $size = strlen($response->getContent()); $response->headers->set('Content-Length', $size); $response->headers->set('Connection', 'close'); // ---- END EDITS ---- $response->send(); $kernel->terminate($request, $response); 

这个问题原来是非常具体的我的设置(Nginx,PHP-FCGI,Symfony)。

造成这个问题的原因有很多:

  1. Symfony不包含Content-Length也不包含Connection: close标题
  2. PHP-FCGI不支持fastcgi_finish_request功能
  3. Nginx缓存来自PHP-FCGI的响应,因为Gzip处于打开状态

解决方案是从PHP-FCGI切换到PHP-FPM,以获得对fastcgi_finish_request支持。 Symfony在执行内核终止逻辑之前内部调用它,从而明确地关闭连接。

解决这个问题的另一种方法是关闭Nginx上的Gzip,但这对我来说不是一个真正的选择。