【问题标题】:Troubleshooting "The controller for URI is not callable" error对“URI 的控制器不可调用”错误进行故障排除
【发布时间】:2013-07-30 09:07:06
【问题描述】:

我正在开发 Symfony 2.3,我声明了一个新的 route 和新的 controller,但是当我从浏览器调用这个控制器时我收到此错误:

The controller for URI "/user/1" is not callable. in /dev.mydomain.org/vendor/symfony/symfony/src/Symfony/Component/HttpKernel/Controller/ControllerResolver.php at line 82

这是我的简单路线配置:

user_homepage:
    pattern:  /user
    defaults: { _controller: UserBundle:Default:index }
    
user_show:
    pattern:  /user/{id}
    defaults: { _controller: UserBundle:Default:show }
    requirements:
        id:  \d+

这是我非常简单的控制器

public function showUserAction($id)
{        
    return $this->render('UserBundle:Default:show.html.twig', array());
}

怎么了?

【问题讨论】:

    标签: symfony routes


    【解决方案1】:

    逻辑名称UserBundle:Default:show 指的是UserBunde\Controller\DefaultController::showAction 你有一个方法叫showUserAction

    要么将方法名称更改为showAction,要么将逻辑名称更改为UserBundle:Default:showUser

    【讨论】:

    • 供应商名称我故意省略了。无论如何,它现在有效。非常感谢。今天辛苦了一天。
    • +1 和 facepalm,我忘记了函数名称中的 Action 部分。
    【解决方案2】:

    虽然与给出的示例无关,但如果控制器 Action 不是 public 也可能导致此错误

    【讨论】:

    • 非常感谢您。我改变了我对通过 ajax 调用哪个方法的想法,而另一个方法是私有的,这导致了这个错误。让我难倒了 15 分钟。谢谢=)
    • 谢谢这个答案对我有帮助。 +1
    【解决方案3】:

    您将控制器功能定义为showUserAction,而在定义中您说它是show[Action]

    要么改变你的路线配置

    user_show:
        pattern:  /user/{id}
        defaults: { _controller: UserBundle:Default:showUser }
        requirements:
            id:  \d+
    

    或更改您的控制器签名

    public function showAction($id)
    {
    

    看看有没有帮助

    【讨论】:

      【解决方案4】:

      这里不是这样。但是还有一个相关的问题:

      如果您忘记了“操作”后缀,一切都会起作用。但是当你意识到你忘记了后缀然后添加它时......惊喜!与 OP 相同的错误。

      这里的问题是关于缓存

      Symfony 创建两个用于缓存 url 的文件:

      • AppDevUrlGenerator.php
      • AppDevUrlMatcher.php

      如果您更改操作名称(即添加“操作”后缀),则该缓存信息已过时。

      解决方案

      php app/console cache:clear
      

      【讨论】:

        【解决方案5】:

        经过大量搜索,这对我有用:

        1.- 创建 CRUDController

        // src/Acme/DemoBundle/Controller/CRUDController.php
        
        namespace Acme\DemoBundle\Controller;
        
        use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
        use Sonata\AdminBundle\Controller\CRUDController as Controller;
        use Symfony\Component\HttpFoundation\RedirectResponse;
        use Inter\PimeBundle\Entity\Empresa;
        
        class CRUDController extends Controller
        {
            public function publicarAction($id)
            {
               //code here...
            }
        }
        

        2.- 创建服务

        # app/config/config.yml
        services:
            ebtity.admin.service:
                class: Acme\DemoBundle\Admin\EntityAdmin
                tags:
                    - { name: sonata.admin, manager_type: orm, group: group, label: label }
                arguments:
                    - NULL
                    - Acme\DemoBundle\Entity\Entity
                    - AcmeDemoBundle:EntityAdmin
        

        3.- 为操作按钮创建模板

        {# src/Acme/DemoBundle/Resources/views/CRUD/list__action_publicar.html.twig #}
        
        <a class="btn btn-sm" href="{{ admin.generateObjectUrl('publicar', object) }}">Publicar</a>
        

        4.- 配置路由

        // src/Acme/DemoBundle/Admin/EntityAdmin.php
        
        namespace Acme\DemoBundle\Admin;
        
        // ...
        
        use Sonata\AdminBundle\Route\RouteCollection;
        
        class EntityAdmin extends Admin
        {
             // ...
        
            protected function configureListFields(ListMapper $listMapper)
            {
                $listMapper
                    ->addIdentifier('name')
                    ->add('engine')
                    ->add('rescueEngine')
                    ->add('createdAt')
                    ->add('_action', 'actions', array(
                        'actions' => array(
                            'publicar' => array(
                                'template' => 'AcmeDemoBundle:CRUD:list__action_publicar.html.twig'
                            )
                        )
                    ));
            }
        
            protected function configureRoutes(RouteCollection $collection)
            {
                $collection
                        ->add('publicar', 
                            $this->getRouterIdParameter().'/publicar',
                            array('_controller' => 'AcmeDemoBundle:CRUD:publicar')    
                        );
            }
        }
        

        5.- 清除缓存

        希望对你有帮助

        【讨论】:

          【解决方案6】:

          类似于接受的答案,如果您的控制器被定义为服务,例如(在 YAML 中):

          services:
              user.default:
                  class: \UserBundle\DefaultController
          

          你的路由使用这个控制器服务:

          user_show:
              pattern:  /user/{id}
              defaults: { _controller: user.default:showUserAction }
              requirements:
                  id:  \d+
          

          那么需要将动作方法完整地命名包括Action后缀,否则会报“controller ... is not callable”错误。

          【讨论】:

            【解决方案7】:

            就我而言,我使用的是 symfony 2.

            symfony 的旧版本维护方法命名约定。方法后缀应包含Action字。

            示例:

            在路由yml文件中方法定义是

            docudex_report_make_authorization:
            pattern:  /make-authorization
            defaults: { _controller: DocudexReportBundle:Default:makeAuthorization }
            

            在控制器中方法是

            public function makeAuthorization(){}
            

            因此我得到了错误。

            将方法名称更改为public function makeAuthorizationAction 后,它运行良好。

            【讨论】:

              【解决方案8】:

              我想分享我的经验以及我是如何解决的:

              我正在一个应用程序中导入一个包,其路由是使用注释定义的,并且它们也可以通过以下方式在应用程序中正常导入:

              auth_bundle_routes:
                # loads routes from the given routing file stored in some bundle
                resource: '@XyzAuthBundle/Controller/'
                type:     annotation
              

              但由于我的捆绑控制器是使用服务定义的,Symfony 显示错误:

              URI“/facebook/request-code”的控制器不可调用。 控制器 Xyz\AuthBundle\Controller\FacebookController" 需要 构造函数参数并且不存在于容器中。你是否 忘记定义这样的服务?

              我更新了我的路由包以使用 routing.yaml 文件而不是注释并将控制器称为service::method 语法,然后这个错误就消失了。

              xyz_auth.facebook_request_code:
                path: /facebook/request-code
                controller: xyz_auth.controller.facebook_controller::requestCode
              

              捆绑路由必须使用

              导入
              auth_bundle_routes:
                resource: '@XyzAuthBundle/Resources/config/routing.yaml'
              

              希望这会节省一些人的时间。

              【讨论】:

                【解决方案9】:

                如果您的 env 使用 .env.local.php 并且在未运行 composer dump-env 的情况下将新更改添加到 env 文件中,则可能会发生同样的问题

                【讨论】:

                  【解决方案10】:

                  出现此错误的原因之一是您错过了在控制器的方法名称后添加单词“Action”。如果你认为你的路由没问题,请检查方法名称。

                  【讨论】:

                    猜你喜欢
                    • 1970-01-01
                    • 2016-02-14
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 2018-04-26
                    • 1970-01-01
                    • 1970-01-01
                    相关资源
                    最近更新 更多