Sometimes you just get some content in form of a byte stream and you want to make a file out of it and download it.
Here is a short tutorial on how to do this with a StreamedResponse in Symfony2 and how you can write a functional test to validate the basics for the action.
Step 1 would be to write the test:
1 2 3 4 5 6 7 8 9 10 11 |
/** * @test */ public function canDownloadFile() { $crawler = $this->client->request('GET', '/reports/download/1'); $this->assertEquals(200, $this->client->getResponse()->getStatusCode(), 'Wrong status code'); $this->assertEquals('application/pdf', $this->client->getResponse()->headers->get('Content-Type'), 'Wrong content type'); $this->assertContains('yourFilename.pdf', $this->client->getResponse()->headers->get('Content-Disposition'), 'Wrong filename'); } |
Now all the tests should be very red, so it is the right time implementing the controller. I don’t show how to set up the route for that, just how the controller looks like.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
/** * @param \Symfony\Component\HttpFoundation\Request $request * @param int $pdfReportId * * @return \Symfony\Component\Form\Form|\Symfony\Component\HttpFoundation\Response */ public function downloadAction(Request $request, $pdfReportId) { $this->initRepositories(); $report = $this->reportRepository->findById($pdfReportId); $response = new StreamedResponse( function () use ($report) { echo base64_decode($report->getFileContent()); }); $response->headers->set('Content-Type', 'application/pdf'); $response->headers->set('Cache-Control', ''); $response->headers->set('Content-Length', strlen($report->getFileContent())); $response->headers->set('Last-Modified', gmdate('D, d M Y H:i:s')); $contentDisposition = $response->headers->makeDisposition(ResponseHeaderBag::DISPOSITION_ATTACHMENT, 'yourFilename.pdf'); $response->headers->set('Content-Disposition', $contentDisposition); $response->prepare($request); return $response; } |
At the place where I call $report->getFileContent you can also use a buffer to read for example a large file.