繁体   English   中英

Symfony2 FOSRESTBundle REST API返回PDF

[英]Symfony2 FOSRESTBundle REST API to return PDF

我在里面制作了一个Bundle和一个REST控制器。 “index”方法以JSON格式返回数组,没关系:

MyBundle /控制器/原料药/休息/ BaconController.php

class BaconController extends Controller implements ClassResourceInterface
{
    /**
     * @var Request $request
     * @return array
     * @Rest\View
     */
    public function cgetAction(Request $request)
    {
        $mediaType = $request->attributes->get('media_type');
        $format = $request->getFormat($mediaType);
        my_dump($format);

        return array(
             array("id" => 1, "title" => "hello",),
             array("id" => 2, "title" => "there",),
        );
    }
}

MyBundle /资源/配置/ API / routing_rest.yml

my_api_rest_bacon:
    type: rest
    resource: "MyBundle:Api/Rest/Bacon"
    name_prefix: api_rest_bacon_
    prefix: /my/bacon

所以,此时JSON结果完全返回:

mysite.com/app_dev.php/api/my/bacon/bacons.json

返回我的数组。

但现在我需要让我的控制器生成带有数据的PDF。 所以我希望它在我打电话时返回PDF文件:

mysite.com/app_dev.php/api/my/bacon/bacons.pdf

我发现了一些半手册: RSS视图处理程序RSS config.ynal带有答案的CSV问题 并尝试做类似的事情:

我添加了这些行

Symfony的/应用/配置/ config.yml

framework:
    [...some old stuff here...]
    request:
        formats:
            pdf: 'application/pdf'

fos_rest:
    body_converter:
        enabled:              true
    format_listener:
        rules:
            # Prototype array
            -
                # URL path info
                path:                 ~
                # URL host name
                host:                 ~
                prefer_extension:     true
                fallback_format:      html
                priorities:           [html,json]
            -
                path:                 ~
                host:                 ~
                prefer_extension:     true
                fallback_format:      pdf
                priorities:           [pdf]
    view:
        # @View or @Template
        view_response_listener: force #true
        formats:
            json: true
            pdf: true
            xls: true
            html: false
        templating_formats:
            pdf: false
            xls: false
        mime_types: {'pdf': ['application/pdf']}
    routing_loader:
        default_format: html
    param_fetcher_listener: true
    body_listener: true
    allowed_methods_listener: true

services:
    my.view_handler.pdf:
        class: Lobster\MyBundle\View\PdfViewHandler
    my.view_handler:
        parent: fos_rest.view_handler.default
        calls:
            - ['registerHandler', [ 'pdf', [@my.view_handler.pdf, 'createResponse'] ] ]

MyBundle /查看/ PdfViewHandler.php

namespace Lobster\MyBundle\View;

use FOS\RestBundle\View\View;
use FOS\RestBundle\View\ViewHandler;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;

class PdfViewHandler
{
    public function createResponse(ViewHandler $handler, View $view, Request $request, $format)
    {
        my_dump('pdf createResponse started');

        $pdf = "some pdf";

        return new Response($pdf, 200, $view->getHeaders());
    }
}

所以现在我打电话的时候

mysite.com/app_dev.php/api/my/bacon/bacons.pdf

我看到一个错误An Exception was thrown while handling: Format html not supported, handler must be implemented ,我的函数my_dump保存到文件格式的文件信息:它是html ,而不是pdf

此外, pdf createResponse无法正常工作。 为什么?

所以我找到了解决方案(我将介绍如何启用2种输出格式:PDF和XLS):

1)不需要config.yml这一部分:

framework:
    [...some old stuff here...]
    request:
        formats:
            pdf: 'application/pdf'

2) fos_rest.format_listener在第config.yml应该是这样的:

format_listener:
    rules:
        -
            path:                 '^/api/my/bacon.*\.xls$'
            host:                 ~
            prefer_extension:     false
            fallback_format:      json
            priorities:           [xls, json]
        -
            path:                 '^/api/my/bacon.*\.pdf$'
            host:                 ~
            prefer_extension:     false
            fallback_format:      json
            priorities:           [pdf, json]
        -
            path:                 ~
            host:                 ~
            prefer_extension:     true
            fallback_format:      html
            priorities:           [html,json]

3)需要在config.yml中将service部分添加到fos_rest

fos_rest:
[...]
    service:
        view_handler: my.view_handler

4) config.yml services根部分应该是这样的

services:
    my.view_handler.xls:
        class: Lobster\MyBundle\View\XlsViewHandler
    my.view_handler.pdf:
        class: Lobster\MyBundle\View\PdfViewHandler
    my.view_handler:
        parent: fos_rest.view_handler.default
        calls:
            - ['registerHandler', ['xls', [@my.view_handler.xls, 'createResponse'] ] ]
            - ['registerHandler', ['pdf', [@my.view_handler.pdf, 'createResponse'] ] ]

就是这样。 现在它完美无缺

如果文件具有不同的数据内容,那么Controller也可以自己生成文件,并在BinaryFileResponse中返回结果。

  • 无需更改任何配置
  • _format可用于选择所需的文件格式
  • 所有代码都驻留在控制器内(以及与特定格式gen相关的一些服务),因此添加新内容或更改现有需要在少量文件中进行更改。

暂无
暂无

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

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