Formulaire Symfony avec héritage de table de classe Doctrine (CTI)
Dans une question précédente, je demande comment gérer les formulaires volumineux, le résultat était l'héritage de table unique (STI) ou CTI, mappage d'héritage . J'ai choisi pour CTI.
Maintenant, je traite de la façon de créer le formulaire avec CTI. Un aperçu rapide du type ou de la relation qu'il y a.
Chacun inspection
peut en avoir un ou plusieurs surfaces
. Chaque surface est constituée de plusieurs entités sous, comme: surface_leakage
, surface_tension
ou surface_slope
. Comme vous pouvez le voir, surface
le CTI avec des sous-entités. Certains champs se chevauchent (mettez-les dans parent), d'autres pas (mettez-les dans child). Mais à la fin j'ai besoin d'un formulaire avec tous les champs regroupés par surfaces puis par enfant (peut-être Bootrap collapse).
L'établissement de la relation n'était pas si difficile, mais l'utiliser dans une forme est difficile et je ne sais pas comment je pourrais gérer cela. Voir ci-dessous le code avec dans le code deux approuches
<?php
class Inspection
{
/**
* @OneToMany(targetEntity="App\Entity\Surface", mappedBy="inspection")
*/
protected $surfaces; } /** * @Entity * @InheritanceType("JOINED") * @DiscriminatorColumn(name="discr", type="string") * @DiscriminatorMap({"surface" = "Surface", "surface_leagage" = "SurfaceLeakage", ...}) */ class Surface { protected $inpection;
protected $description; } class SurfaceLeakage extends Surface { protected $leakageLevel;
}
// .. other child classes (SurfaceTension, SurfaceSlope, ...)
class InspectionType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
// ...
$builder->add('surfaces', CollectionType::class, [ 'entry_type' => SurfaceType::class, ]); } } // Approach 1, where each child is added to the SurfaceType // with this approach data should be mapped false // This approach ensures that I only have to call SurfaceType once and all fields are loaded, but // could not make this work with data from DB through CIT. // Also this method does not allow me to add field description (from parent) to all childTypes class SurfaceType extends AbstractType { public function buildForm(FormBuilderInterface $builder, array $options) { $builder->add('leakage', SurfaceLeakageType::class, array('mapped' => false));
$builder->add('tension', SurfaceTensionType::class, array('mapped' => false)); // ... } public function configureOptions(OptionsResolver $resolver): void
{
$resolver->setDefaults([ 'data_class' => Surface::class, ]); } } class SurfaceLeakageType extends AbstractType { } // Approach 2, where each childFormType could extend SurfaceType, like below but how to call/create the // form and handling the data. // With this approuch i could parent fields to the child class SurfaceLeakageType extends SurfaceType { public function buildForm(FormBuilderInterface $builder, array $options) { $builder->add('description', TextareaType::class); // field from parent or ...
parent::buildForm($builder, $options);
$builder->add('leakageLevel', IntegerType::class); // own field
// ...
}
}
Ensuite, il y a la forme inherit_data
// Approach 3, inherit data, now each child should add this as a field like below,
// but how the only thing I'm doing on InspectionType build Surfaces as collection so
// i think inherit data also doesn't work
class SurfaceType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options): void { $builder->add('description', TextareaType::class);
}
public function configureOptions(OptionsResolver $resolver): void { $resolver->setDefaults([
'inherit_data' => true,
]);
}
}
class SurfaceLeakageType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
// inherit fields
$builder->add('leakage', SurfaceType::class, [ 'data_class' => SurfaceLeakage::class, ]); $builder->add('leakageLevel', IntegerType::class); // own field
}
}
J'espère que quelqu'un pourrait m'aider
Réponses
Je pense que vous recherchez des formes polymorphes. Vérifiez cet ensemblehttps://github.com/infinite-networks/InfiniteFormBundle