通过FormType删除集合的元素

时间:2018-04-20 13:40:22

标签: php jquery symfony symfony-3.4

我正在使用Symfony 3.4.7。我使用3个链接的entites,文章,类别,ArticlesCategories。 ArticlesCategories是关系表。

要管理文章及其关系articleCategories,我使用我添加到FormType ArticlesType的类CollectionType。

在我的显示中,我添加并删除了一篇关于articlesCatégroies的文章。

这是实体的代码文章:

/**
* Articles
*
* @ORM\Table(name="articles")
* @ORM\Entity(repositoryClass="AppBundle\Repository\ArticlesRepository")
* @UniqueEntity("codeArticle", message="Déjà utilisé")
*/
class Articles
{

public function __construct()
{
    $this->articlesCategories = new ArrayCollection();
}

/**
 * @var string
 *
 * @ORM\Column(name="code_article", type="string", length=10)
 * @ORM\Id
 */
private $codeArticle;

//... other variables

/**
 * @var ArticlesCategories
 *
 * @ORM\OneToMany(targetEntity="AppBundle\Entity\ArticlesCategories", mappedBy="codeArticle", cascade={"persist", "remove"}, orphanRemoval=true)
 */
private $articlesCategories;

// other getters and setters 

/**
 * Add articlesCategorie
 *
 * @param ArticlesCategories $articleCategorie
 *
 * @return Articles
 */
public function addArticlesCategorie(ArticlesCategories $articleCategorie){
    $this->articlesCategories[] = $articleCategorie;
    $articleCategorie->setCodeArticle($this);

    return $this;
}

/**
 * remove articlesCategorie
 *
 * @param ArticlesCategories $articlesCategorie
 */
public function removeArticlesCategorie(ArticlesCategories $articlesCategorie){
    $this->articlesCategories->removeElement($articlesCategorie);
}

public function setArticlesCategories($articlesCategories){
    $this->articlesCategories = $articlesCategories;
    return $this;
}

/**
 * Get articlesCategories
 *
 * @return Collection
 */
public function getArticlesCategories(){
    return $this->articlesCategories;
}
}

这是实体ArticleCategories的代码:

/**
 * ArticlesCategories
 *
 * @ORM\Table(name="articles_categories", uniqueConstraints={@ORM\UniqueConstraint(name="unique_codeArticle_codeCategorie", columns={"code_article_id", "code_categorie_id"})})
 * @ORM\Entity(repositoryClass="AppBundle\Repository\ArticlesCategoriesRepository")
 * @UniqueEntity(fields={"codeArticle", "codeCategorie"}, message="Cette relation est déjà enregistré")
 */
class ArticlesCategories
{
    /**
     * @var int
     *
     * @ORM\Column(name="id", type="integer")
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="AUTO")
     */
    private $id;

    /**
     * @var string
     *
     * @ORM\ManyToOne(targetEntity="AppBundle\Entity\Articles", inversedBy="articlesCategories", cascade={"remove"})
     * @ORM\JoinColumn(referencedColumnName="code_article", nullable=false)
     */
    private $codeArticle;

    /**
     * @var string
     *
     * @ORM\ManyToOne(targetEntity="AppBundle\Entity\Categories", cascade={"remove"})
     * @ORM\JoinColumn(referencedColumnName="reference", nullable=false)
     */
    private $codeCategorie;

    /**
     * @var string
     *
     * @ORM\Column(name="critere_rech_1", type="string", length=45, nullable=true)
     */
    private $critereRech1;

    //... getters and setters
}

这是我的表格ArticleType:

的代码
class ArticlesType extends AbstractType
{
    /**
     * {@inheritdoc}
     */
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ->add('codeArticle')
            //...autres attributs
            ->add('articlesCategories', CollectionType::class, array(
                'entry_type' => ArticlesCategoriesType::class,
                'allow_add' => true,
                'allow_delete' => true,
                'prototype' => true,
                'label' => 'categories',
                'attr' => array('class' => 'collection-articlesCategories'),
                'auto_initialize' => true,
                'by_reference' => false
            ));
    }
}

这是我想要编辑文章时调用的操作:

class ArticlesController extends Controller
{
    /**
     * Displays a form to edit an existing article entity.
     *
     * @Route("/edit/{codeArticle}", name="articles_edit", defaults={"codeArticle" = null} )
     * @Method({"GET", "POST"})
     */
    public function editAction(Request $request, Articles $article = null)
    {
        if($article != null){
            /*$em = $this->getDoctrine()->getManager();
            $article = $em->getRepository('AppBundle:Articles')->find($id_article);*/
            $deleteForm = $this->createDeleteForm($article);
            $editForm = $this->createForm('AppBundle\Form\ArticlesType', $article);
            $editForm->handleRequest($request);

            if ($editForm->isSubmitted() && $editForm->isValid()) {
                // récupère tous les articles même ceux qui viennent d'être ajouter par la fonction JS add
                $articlesCategories = $article->getArticlesCategories();
                dump($articlesCategories);
                foreach($articlesCategories as $ac){
                    // si l'article est null
                    if($ac->getCodeArticle() == null){
                        // on attribue à la relation articleCategorie l'article que l'on modifi
                        $ac->setCodeArticle($article);
                    }

                }
                $this->getDoctrine()->getManager()->flush();
            }

            return $this->render('articles/edit.html.twig', array(
                'article' => $article,
                'edit_form' => $editForm->createView(),
                'delete_form' => $deleteForm->createView(),
            ));
        }
        else{
            return $this->forward('AppBundle:articles:new', [
                    'message' => 'Pour éditer un article il faut d\'abord l\'afficher.'
                ]
            );
        }
    }
}

我在Twig视图上显示表单。 我使用Jquery添加和删除关系ArticlesCategories的形式。 这就是我的文章与其集合的形式: My display 我遇到的问题是,当我添加关系并点击“Editer”时,我可以看到关系是在我的数据库中创建的。但是当我删除一个关系并点击“Editer”时,我可以看到我的关系没有删除数据库。

我不知道我的错误在哪里。

我希望我很清楚。 谢谢你的帮助。

[编辑] 这是我的观点:

    {% extends 'articles/gerer.html.twig' %}
{% import 'articles/fields.html.twig' as formMacros %}

{% block contenu %}
    {{ form_start(delete_form) }}
    <input type="submit" value="Supprimer">
    {{ form_end(delete_form) }}

    {{ form_start(edit_form) }}

        {{ form_label(edit_form.codeArticle, "Référence article") }}
        {{ form_errors(edit_form.codeArticle) }}
        {{ form_widget(edit_form.codeArticle, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.description, "Description") }}
        {{ form_errors(edit_form.description) }}
        {{ form_widget(edit_form.description, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.ecotaxe) }}
        {{ form_errors(edit_form.ecotaxe) }}
        {{ form_widget(edit_form.ecotaxe, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.qteMaxCde) }}
        {{ form_errors(edit_form.qteMaxCde) }}
        {{ form_widget(edit_form.qteMaxCde, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.publication) }}
        {{ form_errors(edit_form.publication) }}
        {{ form_widget(edit_form.publication, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.designation) }}
        {{ form_errors(edit_form.designation) }}
        {{ form_widget(edit_form.designation, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.taxonomie) }}
        {{ form_errors(edit_form.taxonomie) }}
        {{ form_widget(edit_form.taxonomie, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.referenceStock) }}
        {{ form_errors(edit_form.referenceStock) }}
        {{ form_widget(edit_form.referenceStock, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.articleRegroupement) }}
        {{ form_errors(edit_form.articleRegroupement) }}
        {{ form_widget(edit_form.articleRegroupement, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.articleAssocie1) }}
        {{ form_errors(edit_form.articleAssocie1) }}
        {{ form_widget(edit_form.articleAssocie1, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.articleAssocie2) }}
        {{ form_errors(edit_form.articleAssocie2) }}
        {{ form_widget(edit_form.articleAssocie2, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.articleAssocie3) }}
        {{ form_errors(edit_form.articleAssocie3) }}
        {{ form_widget(edit_form.articleAssocie3, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.seuilDegressif) }}
        {{ form_errors(edit_form.seuilDegressif) }}
        {{ form_widget(edit_form.seuilDegressif, {'attr': {'class': 'form-control'}}) }}

        {{ form_label(edit_form.tauxDegressif) }}
        {{ form_errors(edit_form.tauxDegressif) }}
        {{ form_widget(edit_form.tauxDegressif, {'attr': {'class': 'form-control'}}) }}

    <div class="row well well-sm js-collection-articles-categories-wrapper" data-prototype="{{ formMacros.printCategorieRow(edit_form.articlesCategories.vars.prototype)|e('html_attr') }}"
         data-index="{{ edit_form.articlesCategories|length }}">
        <div class="col-lg-12 col-md-12 col-sm-12 col-xs-12">
            Catégories
        </div>
        {% for ac in  edit_form.articlesCategories %}
            {{ formMacros.printCategorieRow(ac) }}
        {% endfor %}
        <a href="#" class="js-collection-articles-categories-add">
            <span class="fa fa-plus-circle"> Ajouter une catégorie</span>
        </a>
    </div>
    <input type="submit" value="Modifier" />

    {{ form_end(edit_form) }}
{% endblock %}
{% block javascripts %}
    {{ parent() }}
<script>
    jQuery(document).ready(function () {
        var $wrapper = $('.js-collection-articles-categories-wrapper');

        $wrapper.on('click', '.js-remove-articles-categories', function (e) {
            e.preventDefault();

            $(this).closest('.js-collection-articles-categories-item')
                .fadeOut()
                .remove();
        })

        $wrapper.on('click', '.js-collection-articles-categories-add', function (e) {
            e.preventDefault();

            var prototype = $wrapper.data('prototype');

            var index = $wrapper.data('index');

            var newForm = prototype.replace(/__name__/g, index);

            $wrapper.data('index', index + 1);

            $(this).before(newForm);
        })
    });
</script>
{% endblock %}

我使用form_theme来显示我的集合的元素,这是代码:

{% import _self as formMacros %}
    {% macro printCategorieRow(ac) %}
        <div class="js-collection-articles-categories-item">

            {{ form_errors(ac) }}
            <div class="col-lg-2 col-md-2 col-sm-2 col-xs-6">
                {{ form_label(ac.codeCategorie) }}
                {{ form_widget(ac.codeCategorie, {'attr': {'class': 'select_articles_categories'}}) }}
            </div>

            <div class="col-lg-10 col-md-10 col-sm-10 col-xs-12">
                <a href="#" class="js-remove-articles-categories pull-right">
                    <span class="fa fa-close">Supprimer une catégorie</span>
                </a>
                <table class="table">
                    <tr>
                        <th>Critères</th>
                        <th>Valeurs</th>
                    </tr>
                    <tr id="new_article_table_critere1">
                        <td><div id="critere1">{{ form_label(ac.critereRech1) }}</div></td>
                        <td>{{ form_widget(ac.critereRech1, {'attr': {'class': 'form-control'}}) }}</td>
                    </tr>
                    <tr id="new_article_table_critere2">
                        <td><div id="critere2">{{ form_label(ac.critereRech2) }}</div></td>
                        <td>{{ form_widget(ac.critereRech2, {'attr': {'class': 'form-control'}}) }}</td>
                    </tr>
                    <tr id="new_article_table_critere3">
                        <td><div id="critere3">{{ form_label(ac.critereRech3) }}</div></td>
                        <td>{{ form_widget(ac.critereRech3, {'attr': {'class': 'form-control'}}) }}</td>
                    </tr>
                    <tr id="new_article_table_critere4">
                        <td><div id="critere4">{{ form_label(ac.critereRech4) }}</div></td>
                        <td>{{ form_widget(ac.critereRech4, {'attr': {'class': 'form-control'}}) }}</td>
                    </tr>
                </table>
            </div>
        </div>
    {% endmacro %}

1 个答案:

答案 0 :(得分:0)

在您的实体中进行以下更改,&#39;文章&#39;。

注意:不要忘记为&#39; codeArticle&#39;添加一个setter函数(例如:setcodeArticle())。在您的实体中,&#39; ArticlesCategories&#39;

public function removeArticlesCategorie(ArticlesCategories $articlesCategorie){
    $this->articlesCategories->removeElement($articlesCategorie);
    $articlesCategorie->setcodeArticle(null);
}