Symfony:表单包含可选的附加表单 - >如何正确提交和保留

问题描述 投票:0回答:2

我在Symfony项目中为一个页面使用了两种表单类型。我这样做是为了让用户在创建新文档form type的两个选项之间做出决定

如何构建页面:有几个文本字段要填写。它们都属于我的DocumentCreateType,并且还包括您可以在图片中看到的选择的右侧部分(手动选择IATA)。我的第二种表单类型(UploadProfileType)包含相同的三个下拉列表和一个附加的下一个(市场,渠道1和产品),但在选择的左侧站点(使用上传配置文件)。

因此,根据用户选择的内容,只需提交DocumentCreateType,或者必须提交和保留两种表单类型。

如何在Controller中使用它?到目前为止,我的控制器看起来像这样,但它没有正确持久化数据

  $upForm = $this->createForm(UploadProfileType::class, $document, array('user' => $currentuser));
    $form = $this->createForm(DocumentCreateType::class, $document);

      $form->handleRequest($request);
     $upForm->handleRequest($request); 

    if ($form->isSubmitted() && $form->isValid())
    {
    ...
    }

上传配置文件和IATA之间选择的ChoiceType看起来像是由javascript处理:

  $builder

        ->add('use_upload_profile', ChoiceType::class, array(
                  'choices' => array(
                      true => 'label.use_upload_profile',
                      false => 'label.select_iatas_manually'
                  ),
                  'mapped' => false,
                  'expanded' => true,
                  'label' => false,
                  'data' => true,
                  'translation_domain' => 'Documents'))

            ;
          }

提前致谢

forms symfony types controller submit
2个回答
0
投票

多种形式

在HTTP中,您只能在请求中提交一个表单。

为每个表单提交创建一个端点,您只需提交一个表单。

创建文档A - > createADocumentAction()

创建文档B - > createBDocumentAction()

一切形式与一切

如果您将表单调用到一组数据但所有内容都通过单个请求进行提交,则应创建一个Symfony From(Type),其中包含您计划提交的两个symfony表单的所有数据。


0
投票

您不能同时提交两个表格,它可以是一个或另一个。所以我建议你创建两种不同的形式:

  • 当选择“使用上传配置文件”时,将提交第一个
  • 当选择“手动选择IATA”时,将提交第二个

在每个表单中,您都需要提交所有数据。如果要避免FormType中的重复代码,可以创建自定义表单类型(不与实体关联):

<?php
// src/AppBundle/Form/Custom/CustomFormType.php

namespace AppBundle\Form\Custom;

use Symfony\Component\Form\Extension\Core\Type\FormType;

class CustomFormType
{
    /**
     * Create the 'upload profile' custom form (not associated to a class)
     * 
     * @param type $formFactory
     * @param type $defaultData
     * @return type
     */
    public function createUploadProfileCustomForm($formFactory, $defaultData)
    {
        /* Create the 'upload profile' form (not associated to a class) */
        $form = $formFactory->createBuilder(FormType::class, $defaultData, array());

        $this->addMarkets($form);
        $this->addChannel1($form);
        $this->addProducts($form);

        /* Add whatever other field necessary */
        $form->add(...);

        /* Return the form */
        return $form->getForm();
    }

    /**
     * Create the 'select IATA manually' custom form (not associated to a class)
     * 
     * @param type $formFactory
     * @param type $defaultData
     * @return type
     */
    public function createSelectIATAManuallyCustomForm($formFactory, $defaultData)
    {
        /* Create the 'select IATA manually' form (not associated to a class) */
        $form = $formFactory->createBuilder(FormType::class, $defaultData, array());

        $this->addMarkets($form);
        $this->addChannel1($form);
        $this->addProducts($form);

        /* Add whatever other field necessary */
        $form->add(...);

        /* Return the form */
        return $form->getForm();
    }

    protected function addMarkets($form)
    {
        $form->add('markets', ...
            /* To complete */
        );
    }

    protected function addChannel1($form)
    {
        $form->add('channel1', ...
            /* To complete */
        );
    }

    protected function addProducts($form)
    {
        $form->add('products', ...
            /* To complete */
        );
    }
}

要在控制器中处理这两种形式:

/* Create the 'upload profile' form (not associated to a class) */
$defaultDataUP = array(...);
$customFormTypeUP = new CustomFormType();
$formUploadProfile = $customFormTypeUP->createUploadProfileCustomForm($this->get('form.factory'), $defaultDataUP);
$formUploadProfile ->handleRequest($request);

/* Create the 'select IATA manually' form (not associated to a class) */
$defaultDataSM = array(...);
$customFormTypeSM = new CustomFormType();
$formSelectManually = $customFormTypeSM->createSelectIATAManuallyCustomForm($this->get('form.factory'), $defaultDataSM);
$formSelectManually ->handleRequest($request);

/* If the user selected 'upload profile' and submitted the associated form */
if ($formUploadProfile->isSubmitted() && $formUploadProfile->isValid()) {

    /* Do some action, persist to database, etc. */

    /* Then redirect the user */
    return new RedirectResponse(...);
}
/* Else, if the user selected 'select manually' and submitted the associated form */
elseif ($formSelectManually->isSubmitted() && $formSelectManually->isValid()) {

    /* Do some action, persist to database, etc. */

    /* Then redirect the user */
    return new RedirectResponse(...);
}

/* Render the page, don't forget to pass the two forms in parameters */
return $this->render('yourPage.html.twig', array(
    'form_upload_profile' => $formUploadProfile->createView(),
    'form_select_iata_manually' => $formSelectManually->createView(),
    /* Add other parameters you might need */
));

然后,使用JavaScript,根据选择的单选按钮,您可以显示第一个表单(带有自己的提交按钮)或第二个表单(也有自己的提交按钮)。

© www.soinside.com 2019 - 2024. All rights reserved.