S
S
sts2019-01-06 20:51:13
symfony
sts, 2019-01-06 20:51:13

How to create a many to many form in Symfony 4, with the ability to select associative data?

I can't figure out how to create a form in symphony 4 in which, when adding/updating products, I could add/remove categories for the edited product. The many to many association.
I have two entities Product and Category with a relation table product_category. The code below is shortened for simplicity
Product entity:

<?php

namespace App\Entity;

use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Validator\Constraints as Assert;

/**
 * @ORM\Entity(repositoryClass="App\Repository\ProductRepository")
 */
class Product
{
    /**
     * @ORM\Id()
     * @ORM\GeneratedValue()
     * @ORM\Column(type="integer")
     */
    private $id;
    /**
     * @ORM\ManyToMany(targetEntity="App\Entity\Category", inversedBy="products")
     */
    private $category;
    
    public function __construct()
    {
        $this->category = new ArrayCollection();
    }

    public function getId(): ?int
    {
        return $this->id;
    }

    /**
     * @return Collection|Category[]
     */
    public function getCategory(): Collection
    {
        return $this->category;
    }

    public function addCategory(Category $category): self
    {
        if (!$this->category->contains($category)) {
            $this->category[] = $category;
        }

        return $this;
    }

    public function removeCategory(Category $category): self
    {
        if ($this->category->contains($category)) {
            $this->category->removeElement($category);
        }

        return $this;
    }
}

category entity:
<?php

namespace App\Entity;

use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping as ORM;

/**
 * @ORM\Entity(repositoryClass="App\Repository\CategoryRepository")
 */
class Category
{
    /**
     * @ORM\Id()
     * @ORM\GeneratedValue()
     * @ORM\Column(type="integer")
     */
    private $id;

    /**
     * @ORM\ManyToMany(targetEntity="App\Entity\Product", mappedBy="category")
     */
    private $products;

    public function __construct()
    {
        $this->products = new ArrayCollection();
    }
    /**
     * @return Collection|Product[]
     */
    public function getProducts(): Collection
    {
        return $this->products;
    }

    public function addProduct(Product $product): self
    {
        if (!$this->products->contains($product)) {
            $this->products[] = $product;
            $product->addCategory($this);
        }

        return $this;
    }

    public function removeProduct(Product $product): self
    {
        if ($this->products->contains($product)) {
            $this->products->removeElement($product);
            $product->removeCategory($this);
        }

        return $this;
    }
}

And the corresponding tables:
create table product
(
    id               int auto_increment        primary key
);

create table category
(
    id      int auto_increment        primary key
);

And the link table:
create table product_category
(
    product_id  int,
    category_id int 
)

As a result, no matter how I tried, the maximum that turned out was to make a form in which I can only update the category NAME when updating the product. But I can't figure out how to remove or add a new category to a product. Of course, in separate forms, both products and categories are successfully processed.
Who can suggest something or give a link to a working example? Off docs read, and did everything according to them, which led me to the result of the possibility of changing the category name in the product form. Google hasn't been much help on this issue either.

Answer the question

In order to leave comments, you need to log in

2 answer(s)
A
Alexander, 2019-01-06
@stunoff

In short, symfony does not have the form type you need.
There is EntityType , which works with already created records in the table and allows you to link existing categories to a product, but you won’t be able to create new categories by editing a product.
PS Although no, I'm lying. What you need: A collection of forms .

G
guyasyou, 2019-11-07
@guyasyou

I myself tried to solve my similar problem through the Form Collection. - it didn't work out... Then I found a solution through transformers
in the demo blog from Symfony , which is much clearer, as for me. See how tags are read and saved there.
I implemented selectors with multiple in this way - everything is fine, and it reads and saves!

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question