首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >Symfony4,如何正确处理缺失的表单域?(在$this->propertyAccessor->setValue中无异常)

Symfony4,如何正确处理缺失的表单域?(在$this->propertyAccessor->setValue中无异常)
EN

Stack Overflow用户
提问于 2019-02-22 05:52:38
回答 1查看 833关注 0票数 0

我有一个Task实体,它有两个必填的、不可为空的字段:

  • title
  • dueDatetime

和表单来创建任务。表单由外部脚本通过带有application/x-www-form-urlencodedPOST调用(所以没有json或任何花哨的东西),所以我使用标准symfony来处理它。

问题是我不能控制脚本,如果脚本忘记了其中一个参数,symfony4会在我有时间检查表单是否有效之前,直接在handleRequest步骤抛出一个异常。这导致了丑陋的响应500。

我的问题是:如何避免这种情况?对我来说,最好的方法就是像以前一样继续使用"form->isValid()“,但如果有其他标准的方法来处理,也没问题。

注意:如果我不必将实体的setter设置为接受空值,这将是最好的

我得到的异常是:

应为"DateTimeInterface“类型的参数,但给出了"NULL”类型。

在供应商/symfony/property中-访问/PropertyAccessor.php::throwInvalidArgumentException (第153行)

在vendor/symfony/form/Extension/Core/DataMapper/PropertyPathMapper.php->setValue中(第85行)

在供应商/symfony/form/form.php->mapFormsToData中(第622行)

在vendor/symfony/form/Extension/HttpFoundation/HttpFoundationRequestHandler.php->submit中(第108行)

在供应商/symfony/form/form.php->handleRequest(第492行) 中

重现错误的卷曲:

代码语言:javascript
复制
curl -d 'title=foo' http://127.0.0.1:8080/users/api/tasks

代码:

实体:

代码语言:javascript
复制
class Task
{


    /**
     * @ORM\Id()
     * @ORM\GeneratedValue()
     * @ORM\Column(type="bigint")
     */
    private $id;

    /**
     * @Assert\NotNull()
     * @Assert\NotBlank()
     * @ORM\Column(type="string", length=500)
     */
    private $title;
    /**
     *
     * @ORM\Column(type="datetimetz")
     */
    private $dueDatetime;

    public function getDueDatetime(): ?\DateTimeInterface
    {
        return $this->dueDatetime;
    }

    public function setDueDatetime(\DateTimeInterface $dueDatetime): self
    {
        $this->dueDatetime = $dueDatetime;
        return $this;
    }

    public function setTitle($title)
    {
        $this->title = $title;
        return $this;
    }

    public function getTitle()
    {
        return $this->title;
    }

}

表格

代码语言:javascript
复制
class TaskType extends AbstractType                                                                                     
{                                                                                                                       
    public function buildForm(FormBuilderInterface $builder, array $options)                                            
    {                                                                                                                   
        $builder                                                  
            ->add('title')                                                                                                                                                   
            ->add('dueDatetime')
        ;
    }
    public function configureOptions(OptionsResolver $resolver)
    {
        $resolver->setDefaults(['data_class' => Task::class]);
    }
}

控制器:

代码语言:javascript
复制
class TaskController extends AbstractController
{
   /**
     * @Route(
     *   "/users/api/tasks",
     *   methods={"POST"},
     *   name="user_api_create_task"
     * )
     */
    public function apiCreateTask(Request $request)
    {
        $task = new Task();;

        // the use of createNamed with an empty string is just so that
        // the external scripts don't have to know about symfony's convention
        $formFactory = $this->container->get('form.factory');
        $form = $formFactory->createNamed(
            '',
            TaskType::class,
            $task
        );
        $form->handleRequest($request); // <-- this throw exception

        // but this code should handle this no ? 
        if (!$form->isSubmitted() || !$form->isValid()) {
            return new JsonResponse([], 422);
        }
        $entityManager = $this->getDoctrine()->getManager();
        $entityManager->persist($task);
        $entityManager->flush();


        return new JsonResponse();
    }
}
EN

回答 1

Stack Overflow用户

发布于 2020-05-06 18:20:37

您需要允许可以为空的参数(带"?")在方法setDueDatetime中

代码语言:javascript
复制
public function setDueDatetime(?\DateTimeInterface $dueDatetime): self
{
    $this->dueDatetime = $dueDatetime;
    return $this;
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/54816792

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档