Error: Call to a member function get() on a non-object 500 Internal Server Error - FatalErrorException (Symfony)
Error: Call to a member function get() on a non-object 500 Internal Server Error - FatalErrorException (Symfony)
我是 Mac 和 Symfony 的新手,如果我缺少任何基本知识,我深表歉意
基本上是尝试使用 php class 创建表单,下面是
<?php
namespace TeamRock\ApplicationBundle\entity;
class Person{
protected $email;
protected $fullname;
public function getEmail(){
return $this->$email;
}
public function setEmail($email){
return $this->$email;
}
public function getFullname(){
return $this ->$fullname;
}
public function setFullname($fullname){
return $this -> $fullname;
}
}
?>
然后我有我的class
<?php
namespace TeamRock\ApplicationBundle\form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
class personType extends AbstractType{
public function buildForm(FormBuilderInterface $builder, array $options){
$builder->add ('email','email')->add ('name','text')->add('submit','submit');
}
public function getName(){
return 'person';
}
}
?>
然后在主控制器上
<?php
namespace TeamRock\ApplicationBundle\Controllers\Calvin;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use TeamRock\ApplicationBundle\entity\Person;
use TeamRock\ApplicationBundle\form\PersonType;
class Homepage
{
public function __invoke(Request $request)
{
$person = new person();
$form = $this->createForm(new PersonType(), $person);
return new Response("Hello, world!", Response::HTTP_OK, array('form'=>$form->createView()));
}
}
?>
我不断收到的错误是
Attempted to call method "createForm" on class "TeamRock\ApplicationBundle\Controllers\Calvin\Homepage".
500 Internal Server Error - UndefinedMethodException
感谢任何帮助,正如我所说,我是 php 和 symfony 的新手,它的学习曲线很大,因此感谢任何帮助或指点
我一直在看这些人的视频,仅供参考 Andrew Perkins Symfony Tutorials
再次感谢您的提前帮助!
如何使用控制器作为服务?文档始终是一个很好的起点:http://symfony.com/doc/current/cookbook/controller/service.html
在这个问题的例子中,控制器使用的 createForm 方法恰好定义在:
namespace Symfony\Bundle\FrameworkBundle\Controller;
use Symfony\Component\DependencyInjection\ContainerAware;
class Controller extends ContainerAware
{
public function createForm($type, $data = null, array $options = array())
{
return $this->container->get('form.factory')->create($type, $data, $options);
}
如您所见,createForm 方法依赖于容器对象来访问form.factory 对象。容器是如何注入的?
namespace Symfony\Component\DependencyInjection;
abstract class ContainerAware implements ContainerAwareInterface
{
protected $container;
public function setContainer(ContainerInterface $container = null)
{
$this->container = $container;
}
因此我们需要调用 $controller->setContainer。如果我们以正常方式使用控制器(即不作为服务),那么 setContainer 会在 Symfony\Component\HttpKernel\HttpKernel::handleRaw() 方法中被调用。但是由于我们将控制器定义为服务,因此我们需要注入容器:
# services.yml
homepage__controller:
class: Whatever\Homepage
calls:
- [setContainer, ['@service_container']]
因此,将 setContainer 调用添加到您的服务定义应该会为您提供工作代码。尽管将 createView 直接添加到您的响应中可能不会为您提供所需的结果。肯定不会给你html。但那是另一回事了。
真正的问题当然是为什么要费心将控制器定义为服务。在几乎所有情况下,答案都是不应该。它曾经被推荐用于第三方捆绑包,但现在不再那么多了。如果您查看 FOSUserBundle 控制器,您会看到相当多的重复代码,只是因为它们盲目地遵循控制器作为服务规则。
有时候它是有道理的。我尽量让控制器保持苗条,只注入实际需要的服务。在这个问题中,控制器唯一需要的服务是表单工厂,因此它应该是唯一注入的服务。而且你不应该再扩展基本控制器 class.
class HomepageController
{
private $formFactory;
public function setFormFactory($formFactory)
{
$this->formFactory = $formFactory;
}
public function __invoke(Request $request)
{
$person = new Person();
$form = $this->formFactory->create(new PersonType(), $person);
return new Response("Hello, world!", Response::HTTP_OK, array('form'=>$form->createView()));
}
}
services.yml
my__controller:
class: Whatever\HomepageController
calls:
- [setFormFactory, ['@form.factory']]
我喜欢使用 setter 注入而不是为这些标准服务构造注入。我为我自己的自定义服务保存构造。但是你当然可以使用参数:['@form.factory'] 如果你愿意的话。
最后,如果您只是学习框架以及 PHP OOP,那么只需按照文档中的示例进行操作即可。有很多东西可以学习,而无需陷入这些兔子洞。
我是 Mac 和 Symfony 的新手,如果我缺少任何基本知识,我深表歉意
基本上是尝试使用 php class 创建表单,下面是
<?php
namespace TeamRock\ApplicationBundle\entity;
class Person{
protected $email;
protected $fullname;
public function getEmail(){
return $this->$email;
}
public function setEmail($email){
return $this->$email;
}
public function getFullname(){
return $this ->$fullname;
}
public function setFullname($fullname){
return $this -> $fullname;
}
}
?>
然后我有我的class
<?php
namespace TeamRock\ApplicationBundle\form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
class personType extends AbstractType{
public function buildForm(FormBuilderInterface $builder, array $options){
$builder->add ('email','email')->add ('name','text')->add('submit','submit');
}
public function getName(){
return 'person';
}
}
?>
然后在主控制器上
<?php
namespace TeamRock\ApplicationBundle\Controllers\Calvin;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use TeamRock\ApplicationBundle\entity\Person;
use TeamRock\ApplicationBundle\form\PersonType;
class Homepage
{
public function __invoke(Request $request)
{
$person = new person();
$form = $this->createForm(new PersonType(), $person);
return new Response("Hello, world!", Response::HTTP_OK, array('form'=>$form->createView()));
}
}
?>
我不断收到的错误是
Attempted to call method "createForm" on class "TeamRock\ApplicationBundle\Controllers\Calvin\Homepage".
500 Internal Server Error - UndefinedMethodException
感谢任何帮助,正如我所说,我是 php 和 symfony 的新手,它的学习曲线很大,因此感谢任何帮助或指点
我一直在看这些人的视频,仅供参考 Andrew Perkins Symfony Tutorials
再次感谢您的提前帮助!
如何使用控制器作为服务?文档始终是一个很好的起点:http://symfony.com/doc/current/cookbook/controller/service.html
在这个问题的例子中,控制器使用的 createForm 方法恰好定义在:
namespace Symfony\Bundle\FrameworkBundle\Controller;
use Symfony\Component\DependencyInjection\ContainerAware;
class Controller extends ContainerAware
{
public function createForm($type, $data = null, array $options = array())
{
return $this->container->get('form.factory')->create($type, $data, $options);
}
如您所见,createForm 方法依赖于容器对象来访问form.factory 对象。容器是如何注入的?
namespace Symfony\Component\DependencyInjection;
abstract class ContainerAware implements ContainerAwareInterface
{
protected $container;
public function setContainer(ContainerInterface $container = null)
{
$this->container = $container;
}
因此我们需要调用 $controller->setContainer。如果我们以正常方式使用控制器(即不作为服务),那么 setContainer 会在 Symfony\Component\HttpKernel\HttpKernel::handleRaw() 方法中被调用。但是由于我们将控制器定义为服务,因此我们需要注入容器:
# services.yml
homepage__controller:
class: Whatever\Homepage
calls:
- [setContainer, ['@service_container']]
因此,将 setContainer 调用添加到您的服务定义应该会为您提供工作代码。尽管将 createView 直接添加到您的响应中可能不会为您提供所需的结果。肯定不会给你html。但那是另一回事了。
真正的问题当然是为什么要费心将控制器定义为服务。在几乎所有情况下,答案都是不应该。它曾经被推荐用于第三方捆绑包,但现在不再那么多了。如果您查看 FOSUserBundle 控制器,您会看到相当多的重复代码,只是因为它们盲目地遵循控制器作为服务规则。
有时候它是有道理的。我尽量让控制器保持苗条,只注入实际需要的服务。在这个问题中,控制器唯一需要的服务是表单工厂,因此它应该是唯一注入的服务。而且你不应该再扩展基本控制器 class.
class HomepageController
{
private $formFactory;
public function setFormFactory($formFactory)
{
$this->formFactory = $formFactory;
}
public function __invoke(Request $request)
{
$person = new Person();
$form = $this->formFactory->create(new PersonType(), $person);
return new Response("Hello, world!", Response::HTTP_OK, array('form'=>$form->createView()));
}
}
services.yml
my__controller:
class: Whatever\HomepageController
calls:
- [setFormFactory, ['@form.factory']]
我喜欢使用 setter 注入而不是为这些标准服务构造注入。我为我自己的自定义服务保存构造。但是你当然可以使用参数:['@form.factory'] 如果你愿意的话。
最后,如果您只是学习框架以及 PHP OOP,那么只需按照文档中的示例进行操作即可。有很多东西可以学习,而无需陷入这些兔子洞。