"Unable to guess how to get a Doctrine instance from the request information for parameter "person_id" 同时将此参数添加到 arguments
"Unable to guess how to get a Doctrine instance from the request information for parameter "person_id" while adding this parameter to arguments
我在 symfony 4 "Unable to guess how to get a Doctrine instance from the request information for parameter "person_id" 中遇到错误,我已经尝试过我在 Whosebug 上找到的相关问题的选项,但他们都建议用@paramconverter 解决这个问题,但这方法与@route有关,我认为这不是我需要的。
控制器中的代码如下:
/**
* @Route("/skill/new/", name="new_skill")
* Method({"GET", "POST"})
* @param Request $request
* @param Person $person_id
* @return \Symfony\Component\HttpFoundation\RedirectResponse|Response
*/
public function new(Request $request, Person $person_id) {
$skill = new Skill();
$form = $this->createFormBuilder($skill)
->add('name', TextType::class, array('attr' => array('class' => 'form-control')))
->add('level', TextareaType::class, array(
'attr' => array('class' => 'form-control')
))
->add('save', SubmitType::class, array(
'label' => 'Create',
'attr' => array('class' => 'btn btn-primary mt-3')
))
->getForm();
$form->handleRequest($request);
if($form->isSubmitted() && $form->isValid()) {
$skill = $form->getData();
$entityManager = $this->getDoctrine()->getManager();
$person = $entityManager->getRepository(Person::class)->find($person_id);
$person->addSkill($skill);
$entityManager->persist($skill);
$entityManager->persist($person);
$entityManager->flush();
return $this->redirectToRoute('skill_list');
}
return $this->render('main/new.html.twig', array(
'form' => $form->createView()
));
}
来自 Person 实体
class Person
{
/**
* @ORM\Id()
* @ORM\GeneratedValue()
* @ORM\Column(type="integer")
*/
private $id;
/**
* @ORM\Column(type="string", length=255)
*/
private $name;
/**
* @ORM\OneToMany(targetEntity="App\Entity\Skill", mappedBy="person")
*/
private $skills;
public function __construct()
{
$this->skills = new ArrayCollection();
}
public function getId(): ?int
{
return $this->id;
}
public function getName(): ?string
{
return $this->name;
}
public function setName(string $name): self
{
$this->name = $name;
return $this;
}
/**
* @return Collection|Skill[]
*/
public function getSkills(): Collection
{
return $this->skills;
}
public function addSkill(Skill $skill): self
{
if (!$this->skills->contains($skill)) {
$this->skills[] = $skill;
$skill->setPerson($this);
}
return $this;
}
public function removeSkill(Skill $skill): self
{
if ($this->skills->contains($skill)) {
$this->skills->removeElement($skill);
// set the owning side to null (unless already changed)
if ($skill->getPerson() === $this) {
$skill->setPerson(null);
}
}
return $this;
}
}
使用@paramconverter,我在路由中写了 id param,如 " * @Route("/skill/new/{id}", name="new_skill",但他给出了另一个错误 "No route found for "获取/skill/new
我想要实现的是,当我创建新技能时,它会绑定到具有特定 ID 的特定人员,因此我进行了 ManyToOne 关联。因此,当我在路线“/person/{{ person.id }}”时,我需要为这个特定的 id 添加技能,而不是每个人。
我想我在函数参数上写了 person_id 是个错误,否则它在 entitymanager 中找不到这个参数。我该如何解决?
问题出在路由定义和方法签名中。 Symfony 无法推断它应该获取哪个 Person $person_id
。如果你想让它成为一个实体,你应该为 id 分配一个 url 参数,例如
@Route("/skill/new/{person_id}", name="new_skill")
这会将 URL 从 http://example.com/skill/new to http://example.com/skill/new/123 更改为 123
是您要为其获取 Person
对象的 ID。现在你的 URL 中必须有一个 person id,否则路线将不匹配(正如你已经注意到的那样)。您可以通过更改方法签名使其成为可选的:
/**
* @Route("/skill/new/{person_id}", name="new_skill")
* Method({"GET", "POST"})
* @param Request $request
* @param Person $person_id
* @return \Symfony\Component\HttpFoundation\RedirectResponse|Response
*/
public function new(Request $request, Person $person_id = null) {
通过允许 $person_id
为 null,url 参数应该是可选的,因此您应该能够使用 http://example.com/skill/skill/new or http://example.com/skill/skill/new/123.
如果您不想要该实体,而只想通过一种方式从 URL 中选择性地获取它,而无需明确指定路由参数,您可以稍微更改一下代码:
/**
* @Route("/skill/new", name="new_skill")
* Method({"GET", "POST"})
* @param Request $request
* @param Person $person_id
* @return \Symfony\Component\HttpFoundation\RedirectResponse|Response
*/
public function new(Request $request) {
$person_id = $request->query->get('person_id');
...
如果您现在使用现有的 URL 并添加一个 URL 参数,它将在您的操作中读取,例如http://example.com/skill/new?person_id=1234 会将 $person_id
设置为 1234。当您未指定参数时,它将为空。
Symfony 也有调试命令,可以帮助您检查有哪些路由以及它们是否匹配:
bin/console debug:router
bin/console router:match /skill/new
我在 symfony 4 "Unable to guess how to get a Doctrine instance from the request information for parameter "person_id" 中遇到错误,我已经尝试过我在 Whosebug 上找到的相关问题的选项,但他们都建议用@paramconverter 解决这个问题,但这方法与@route有关,我认为这不是我需要的。
控制器中的代码如下:
/**
* @Route("/skill/new/", name="new_skill")
* Method({"GET", "POST"})
* @param Request $request
* @param Person $person_id
* @return \Symfony\Component\HttpFoundation\RedirectResponse|Response
*/
public function new(Request $request, Person $person_id) {
$skill = new Skill();
$form = $this->createFormBuilder($skill)
->add('name', TextType::class, array('attr' => array('class' => 'form-control')))
->add('level', TextareaType::class, array(
'attr' => array('class' => 'form-control')
))
->add('save', SubmitType::class, array(
'label' => 'Create',
'attr' => array('class' => 'btn btn-primary mt-3')
))
->getForm();
$form->handleRequest($request);
if($form->isSubmitted() && $form->isValid()) {
$skill = $form->getData();
$entityManager = $this->getDoctrine()->getManager();
$person = $entityManager->getRepository(Person::class)->find($person_id);
$person->addSkill($skill);
$entityManager->persist($skill);
$entityManager->persist($person);
$entityManager->flush();
return $this->redirectToRoute('skill_list');
}
return $this->render('main/new.html.twig', array(
'form' => $form->createView()
));
}
来自 Person 实体
class Person
{
/**
* @ORM\Id()
* @ORM\GeneratedValue()
* @ORM\Column(type="integer")
*/
private $id;
/**
* @ORM\Column(type="string", length=255)
*/
private $name;
/**
* @ORM\OneToMany(targetEntity="App\Entity\Skill", mappedBy="person")
*/
private $skills;
public function __construct()
{
$this->skills = new ArrayCollection();
}
public function getId(): ?int
{
return $this->id;
}
public function getName(): ?string
{
return $this->name;
}
public function setName(string $name): self
{
$this->name = $name;
return $this;
}
/**
* @return Collection|Skill[]
*/
public function getSkills(): Collection
{
return $this->skills;
}
public function addSkill(Skill $skill): self
{
if (!$this->skills->contains($skill)) {
$this->skills[] = $skill;
$skill->setPerson($this);
}
return $this;
}
public function removeSkill(Skill $skill): self
{
if ($this->skills->contains($skill)) {
$this->skills->removeElement($skill);
// set the owning side to null (unless already changed)
if ($skill->getPerson() === $this) {
$skill->setPerson(null);
}
}
return $this;
}
}
使用@paramconverter,我在路由中写了 id param,如 " * @Route("/skill/new/{id}", name="new_skill",但他给出了另一个错误 "No route found for "获取/skill/new
我想要实现的是,当我创建新技能时,它会绑定到具有特定 ID 的特定人员,因此我进行了 ManyToOne 关联。因此,当我在路线“/person/{{ person.id }}”时,我需要为这个特定的 id 添加技能,而不是每个人。
我想我在函数参数上写了 person_id 是个错误,否则它在 entitymanager 中找不到这个参数。我该如何解决?
问题出在路由定义和方法签名中。 Symfony 无法推断它应该获取哪个 Person $person_id
。如果你想让它成为一个实体,你应该为 id 分配一个 url 参数,例如
@Route("/skill/new/{person_id}", name="new_skill")
这会将 URL 从 http://example.com/skill/new to http://example.com/skill/new/123 更改为 123
是您要为其获取 Person
对象的 ID。现在你的 URL 中必须有一个 person id,否则路线将不匹配(正如你已经注意到的那样)。您可以通过更改方法签名使其成为可选的:
/**
* @Route("/skill/new/{person_id}", name="new_skill")
* Method({"GET", "POST"})
* @param Request $request
* @param Person $person_id
* @return \Symfony\Component\HttpFoundation\RedirectResponse|Response
*/
public function new(Request $request, Person $person_id = null) {
通过允许 $person_id
为 null,url 参数应该是可选的,因此您应该能够使用 http://example.com/skill/skill/new or http://example.com/skill/skill/new/123.
如果您不想要该实体,而只想通过一种方式从 URL 中选择性地获取它,而无需明确指定路由参数,您可以稍微更改一下代码:
/**
* @Route("/skill/new", name="new_skill")
* Method({"GET", "POST"})
* @param Request $request
* @param Person $person_id
* @return \Symfony\Component\HttpFoundation\RedirectResponse|Response
*/
public function new(Request $request) {
$person_id = $request->query->get('person_id');
...
如果您现在使用现有的 URL 并添加一个 URL 参数,它将在您的操作中读取,例如http://example.com/skill/new?person_id=1234 会将 $person_id
设置为 1234。当您未指定参数时,它将为空。
Symfony 也有调试命令,可以帮助您检查有哪些路由以及它们是否匹配:
bin/console debug:router
bin/console router:match /skill/new