0

I'm developing a site using Zend Framework 2 where the client wanted to be able to export some data to an Excel file. For this I went with PHPExcel, and I got it working on my local computer, where I run Apache2.

<?php
        //Create a writer for Excel
        $objWriter = new PHPExcel_Writer_Excel2007($objPHPExcel);

        // Get the data from php://output
        // https://stackoverflow.com/questions/16551375/phpexcel-in-zend2-controller
        ob_flush();
        ob_start();
        $objWriter->save('php://output');
        $excelOutput = ob_get_clean();

        //Get a new response object
        $response = new \Zend\Http\Response();

        //Set headers for the response object
        $response->getHeaders()
            ->addHeaderLine('Last-Modified: ' . gmdate("D, d M Y H:i:s") . ' GMT')
            ->addHeaderLine('Cache-Control: no-store, no-cache, must-revalidate')
            ->addHeaderLine('Cache-Control: post-check=0, pre-check=0')
            ->addHeaderLine('Pragma: no-cache')
            ->addHeaderLine('Content-Type', 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet')
            ->addHeaderLine('Content-Disposition: attachment;filename="report.xlsx"');

        //Set the content for the response object
        $response->setContent($excelOutput);

        return $response;
?>

The problem is that when I uploaded the project to my production server, running Nginx with a pretty standard setup using PHP-FPM, the Excel file isn't sent using the correct headers. It seems like they are overwritten with "text/html" which makes the browser show some garbled characters instead of making the file available for download.

I followed this (PHPExcel in Zend2 Controller) question for getting the content into a variable.

I can't figure out why this is happening, are the headers set differently using PHP on Apache2 than running Nginx with PHP-FPM?


Update: Returned headers

Apache on local computer:

HTTP/1.1 200 OK
Date: Sun, 11 May 2014 11:24:09 GMT
Server: Apache/2.4.4 (Win32) OpenSSL/0.9.8y PHP/5.4.19
X-Powered-By: PHP/5.4.19
Expires: Thu, 19 Nov 1981 08:52:00 GMT
Cache-Control: post-check=0, pre-check=0
Pragma: no-cache
Last-Modified: Sun, 11 May 2014 11:24:09 GMT
Content-Disposition: attachment;filename="report.xlsx"
Content-Length: 6551
Keep-Alive: timeout=5, max=100
Connection: Keep-Alive
Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet

Nginx headers:

HTTP/1.1 200 OK
Server: nginx/1.1.19
Date: Sun, 11 May 2014 11:14:18 GMT
Content-Type: text/html
Transfer-Encoding: chunked
Connection: keep-alive
Vary: Accept-Encoding
X-Powered-By: PHP/5.3.10-1ubuntu3.11
Expires: Thu, 19 Nov 1981 08:52:00 GMT
Cache-Control: no-store, no-cache, must-revalidate, post-check=0, pre-check=0
Pragma: no-cache
Content-Encoding: gzip
Community
  • 1
  • 1
fhugas
  • 392
  • 1
  • 10
  • 1
    Can you dump the headers from both your Apache env and your nginx one? – Jurian Sluiman May 11 '14 at 11:22
  • I added the headers from both environments now. – fhugas May 11 '14 at 11:36
  • 1
    See pastie, I cannot reproduce your case: http://pastie.org/9165934. The provided code returns the provided headers. I guess it's not this part of the code, but rather an nginx setting or some difference based on your environment (php version, fw version etc). – Jurian Sluiman May 11 '14 at 12:40
  • I tried your pastie code and got the correct headers as well. This led me onto another track and I managed to solve the problem. It was the first initial ob_flush() that was the root to this issue. Why this affected nginx and not apache is beyond my understanding. Thank you for your time helping me out with this one. :) – fhugas May 11 '14 at 13:38

0 Answers0