Сохранение обратной стороны отношения «многие ко многим» - PullRequest
0 голосов
/ 25 мая 2018

Я пытаюсь сделать возможным сохранение отношения на обратной стороне отношения.Я знаю, что это невозможно в Doctrine, но я нашел разные статьи, которые показывают такую ​​возможность.Проблема в том, что описанный способ не работает для меня.

Моя исходная база:

У меня есть две сущности в отношении многие ко многим.

// Widget.php

/**
* @ORM\ManyToMany(targetEntity="App\Entity\Layout", mappedBy="widgets", cascade={"persist"})
*/
private $layouts;

// Layout.php

/**
* @ORM\ManyToMany(targetEntity="App\Entity\Widget", inversedBy="layouts", cascade={"persist"})
*/
private $widgets;

У меня есть для обеих сущностей метод получения, установки и добавления и удаления.Они выглядят так (оба одинаково):

public function setLayouts(ArrayCollection $layouts) {
    $this->layouts->clear();
    foreach ($layouts as $layout) {
        $this->addLayout($layout);
    }
    return $this;
}

public function getLayouts() {
    return $this->layouts;
}

public function addLayout(Layout $layout) {
    if ($this->layouts->contains($layout)) {
        return $this;
    }
    $this->layouts->add($layout);
    $layout->addWidget($this);
    return $this;
}

public function removeLayout(Layout $layout) {
    if (!$this->layouts->contains($layout)) {
        return $this;
    }
    $this->layouts->removeElement($layout);
    $layout->removeWidget($this);
    return $this;
}

Так что моя сторона - это макет в этом случае.Кроме того, у меня есть FormTypes для обеих сущностей:

class LayoutType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options) {
        $builder->add('widgets', EntityType::class, [
            'required' => true,
            'class' => Widget::class,
            'multiple' => true,
        ]);
...

class WidgetType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options) {
        $builder->add('layouts', EntityType::class, [
            'required' => false,
            'class' => Layout::class,
            'multiple' => true,
            'by_reference' => false,
        ]);
...

И, наконец, мой контроллер (контроллер компоновки выглядит одинаково):

public function postAction(Request $request) {
    $widget = new Widget();

    $formFactory = $this->container->get('form.factory');
    $form = $formFactory->createNamed('', WidgetType::class, $widget, ['method' => 'POST']);
    $form->handleRequest($request);

    if (!$form->isValid()) {
        return View::create($form, Response::HTTP_BAD_REQUEST);
    }

    $em = $this->getDoctrine()->getManager();
    $em->persist($widget);
    $em->flush();

    return View::create($widget);
...

Возможное решение:

Я использую форму Symfony для всех моих сущностей, поэтому должна быть возможность добавить 'by_reference' => false в конкретное поле.Я нашел это решение, например, здесь: https://afilina.com/doctrine-not-saving-manytomany Как вы видите выше, я уже добавил опцию.

Моя проблема:

Первая сторона, сохранениеМакет и добавление виджетов к нему, отлично работает.Но другая сторона, сохраняющая виджет и добавляющая макеты к нему, не работает.Почему это так?Я использую последнюю версию Smyfony (4.0.10).В этом ли проблема?

Спасибо за помощь!

...