FOSRestBundle:控制器必须返回给定的响应(Array())

Posted

技术标签:

【中文标题】FOSRestBundle:控制器必须返回给定的响应(Array())【英文标题】:FOSRestBundle: The controller must return a response (Array()) given 【发布时间】:2014-01-08 10:44:09 【问题描述】:

我从 FOSRestBundle 开始。我已经添加了这个路由配置:

//Sermovi/Bundle/APIBundle/Resources/config/routing.yml    
sermovi_api_homepage:
        type: rest
        resource: Sermovi\Bundle\APIBundle\Controller\DefaultController

//app/config/routing.yml     
sermovi_api:
    type: rest
    prefix:   /api
    resource: "@SermoviAPIBundle/Resources/config/routing.yml"

还有这个 config.yml

fos_rest:
    routing_loader:
        default_format: json
    view:
        view_response_listener: true

sensio_framework_extra:
    view:
        annotations: false

还有这个控制器:

namespace Sermovi\Bundle\APIBundle\Controller;

use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use FOS\RestBundle\Controller\FOSRestController;
use Symfony\Component\HttpFoundation\Response;


class DefaultController extends FOSRestController

    public function getArticlesAction()
    
        $em = $this->getDoctrine()->getManager();

        $entity = $em->getRepository('SermoviManagementBundle:Transaction')->find(776);

        return array(
            'entity' => $entity
        );
    

我收到了这个错误:

["message":"控制器必须返回一个响应(Array(entity => 对象(Sermovi\Bundle\ManagementBundle\Entity\Transaction)) 给定)。","class":"LogicException","trace":["namespace":"","short_class":"","class":"","type":"","function" :"","file":"/home/tirengarfio/workspace/sermovi/app/bootstrap.php.cache","line":2855,"args":[],"namespace":"Symfony\Component \HttpKernel","short_class":"HttpKernel","class":"Symfony\Component\HttpKernel\HttpKernel","type":"->","function":"handleRaw","file":"/home /tirengarfio/workspace/sermovi/app/bootstrap.php.cache","line":2817,"args":[["object","Symfony\Component\HttpFoundation\Request"],["string","1 "]],"命名空间":"Symfony\Component\HttpKernel","short_class":"HttpKernel","class":"Symfony\Component\HttpKernel\HttpKernel","type":"->","函数":"句柄","文件":"/home/tirengarfio/workspace/sermovi/app/bootstrap.php.cache","line":2946,"args":[["object","Symfony\Component \HttpFoundation\Request"],["string","1"],["boolean",true]],"namespace":"Symfony\Component\HttpKernel\DependencyInjection","short_class":"ContainerAwareHttpKernel", "class":"Symfony\Component\HttpKernel\Dependen cyInjection\ContainerAwareHttpKernel","type":"->","function":"handle","file":"/home/tirengarfio/workspace/sermovi/app/bootstrap.php.cache","line":2247 ,"args":[["object","Symfony\Component\HttpFoundation\Request"],["string","1"],["boolean",true]],"namespace":"Symfony\ Component\HttpKernel","short_class":"Kernel","class":"Symfony\Component\HttpKernel\Kernel","type":"->","function":"handle","file":"/主页/tirengarfio/workspace/sermovi/web/app_dev.php","line":28,"args":[["object","Symfony\Component\HttpFoundation\Request"]]]]

编辑:

“可以”我在下面做这样的事情吗?或者因为 FOSRestBundle 正在使用 JMSSerializerBundle 我不应该这样做?

$serializedEntity = $this->container->get('serializer')->serialize($entity, 'json');
return new Response($serializedEntity);

【问题讨论】:

我必须说,您试图实现的目标应该是捆绑包以零配置工作的唯一方法。 FOSRestBundle 完全不符合最小惊喜原则。 【参考方案1】:

有几种方法可以使用 FOSRestBundle 设置控制器。你这样做的方式,你必须返回一个视图。这是 github 上的一个 rest 控制器的链接,可能会对您有所帮助。 LiipHelloBundle 有一个例子。

另外,我发现在我的控制器中使用ClassResourceInterface 是最简单的。这样,我返回一个数组,它自己处理所有的序列化。它还使用您的控制器名称来生成必要的路由,因此我不必手动定义任何路由。这是我设置控制器的首选方式。请参阅文档条目here 了解其工作原理。

如果您最终使用了ClassResourceInterface,请务必为每个操作添加以下注释,这样您返回的数组就会被正确序列化:

use FOS\RestBundle\Controller\Annotations as Rest;
//.....

/**
* @Rest\View()
*/
public function cgetAction() 

您甚至可以通过设置控制器的方式来做到这一点,但我之前没有尝试过。让我们知道您是否这样做并且可行。

更新

对于那些可能对使用 FOSRestBundle 而不使用 ClassResourceInterface 感兴趣的人,问题中控制器操作的问题是它不返回视图。这应该在行动中起作用:

class DefaultController extends FOSRestController

    public function getArticlesAction()
    
        $em = $this->getDoctrine()->getManager();

        $entity = $em->getRepository('SermoviManagementBundle:Transaction')->find(776);
        $statusCode = 200;

        $view = $this->view($entity, $statusCode);
        return $this->handleView($view);
    

【讨论】:

如何注入服务(例如 Doctrine)以与 ClassResourceInterface 一起使用?有了这个,你有我的投票。就此而言,文档确实无法提供完整的示例。干杯 @tishma 我很确定你可以像往常一样使用上下文感知方法获得 Doctrine,所以$this->getDoctrine() 抱歉,应该说“容器感知”,而不是上下文感知。

以上是关于FOSRestBundle:控制器必须返回给定的响应(Array())的主要内容,如果未能解决你的问题,请参考以下文章

FOSRestbundle、JMS Serializer 和 SonataMediaBundle 返回图像的公共 url

控制器必须返回一个响应(给定 null)。您是不是忘记在控制器的某处添加 return 语句?请

如何将从服务器获得的响应发送到电子邮件?

带有 RESTful 身份验证的 Symfony2 应用程序,使用 FOSRestBundle 和 FOSUserBundle

无法使用 FOSRestBundle

无法使用 Symfony 5 安装 FOSRestBundle