Afelip
Afelip

Reputation: 61

How to add(create) object in symfony within unique id?

I have table rows with created employees. Every employee has unique ID. When user clicks on employee, he can add a new skill for this employee with name and level fields. I wrote the code that successfully creates employees and show it, but I don't know how to add skill to unique ID, that it was represented just for one specific user, not all of them.

I made two tables with doctrine - Person and Skill, as well as two controllers for them. Also, I made assotiations ManyToOne, so that one employee could have multiple skills.

Entity for Skill

class Skill
{
  /**
 * @ORM\Id()
 * @ORM\GeneratedValue()
 * @ORM\Column(type="integer")
 */
private $id;

/**
 * @ORM\ManyToOne(targetEntity="App\Entity\Person", inversedBy="skills")
 * @ORM\JoinColumn(nullable=false)
 */
private $person;
/**
 * @ORM\Column(type="string", length=255)
 */
private $name;
/**
 * @ORM\Column(type="string", length=255)
 */
private $level;
public function getId(): ?int
{
    return $this->id;
}

public function getPerson(): ?Person
{
    return $this->person;
}

public function setPerson(?Person $person): self
{
    $this->person = $person;

    return $this;
}
public function getName(): ?string
{
    return $this->name;
}

public function setName(string $name): self
{
    $this->name = $name;

    return $this;
}
public function getLevel(): ?string
{
    return $this->level;
}

public function setLevel(string $level): self
{
    $this->level = $level;

    return $this;
}

}

Entity for Person

class Person
{
/**
 * @ORM\Id()
 * @ORM\GeneratedValue()
 * @ORM\Column(type="integer")
 */
private $id;

/**
 * @ORM\Column(type="string", length=255)
 */
private $name;

/**
 * @ORM\OneToMany(targetEntity="App\Entity\Skill", mappedBy="person")
 */
private $skills;

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

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

public function getName(): ?string
{
    return $this->name;
}

public function setName(string $name): self
{
    $this->name = $name;

    return $this;
}

/**
 * @return Collection|Skill[]
 */
public function getSkills(): Collection
{
    return $this->skills;
}

public function addSkill(Skill $skill): self
{
    if (!$this->skills->contains($skill)) {
        $this->skills[] = $skill;
        $skill->setPerson($this);
    }

    return $this;
}

public function removeSkill(Skill $skill): self
{
    if ($this->skills->contains($skill)) {
        $this->skills->removeElement($skill);
        // set the owning side to null (unless already changed)
        if ($skill->getPerson() === $this) {
            $skill->setPerson(null);
        }
    }

    return $this;
}

}

Function that shoud create/add new skill to employee

 /**
 * @Route("/skill/new", name="new_skill")
 * Method({"GET", "POST"})
 */
public function new(Request $request) {
    $skill = new Skill();
    $form = $this->createFormBuilder($skill)
        ->add('name', TextType::class, array('attr' => array('class' => 'form-control')))
        ->add('level', TextareaType::class, array(
            'attr' => array('class' => 'form-control')
        ))
        ->add('save', SubmitType::class, array(
            'label' => 'Create',
            'attr' => array('class' => 'btn btn-primary mt-3')
        ))
        ->getForm();
    $form->handleRequest($request);
    if($form->isSubmitted() && $form->isValid()) {
        $skill = $form->getData();
        $entityManager = $this->getDoctrine()->getManager();
        $entityManager->persist($skill);
        $entityManager->flush();
        return $this->redirectToRoute('skill_list');
    }
    return $this->render('main/new.html.twig', array(
        'form' => $form->createView()
    ));
}

Upvotes: 0

Views: 847

Answers (2)

Theva
Theva

Reputation: 948

You will have to persist($person) as well

You will have to fetch the Person and set him to Skill before your flush

/**
 * @Route("/skill/new", name="new_skill")
 * Method({"GET", "POST"})
 */
public function new(Request $request) {
    $personId = $request->request->get('person_id'); //POST data
    $person = $entityManager->getRepository(Person::class)
          ->find($personId);
    $skill = new Skill();
    $skill->setPerson($person);
    $form = $this->createFormBuilder($skill)
      /// add fields
        ->getForm();
    $form->handleRequest($request);
    if ($form->isSubmitted() && $form->isValid()) {
    /// $skill = $form->getData();
        $entityManager = $this->getDoctrine()->getManager();
        $entityManager->persist($skill);
        $entityManager->flush();

        return $this->redirectToRoute('skill_list');
    }

    return $this->render('main/new.html.twig', array(
        'form' => $form->createView()
    ));
}

Upvotes: 1

Berthol Yvano
Berthol Yvano

Reputation: 336

In your case, you delegate a technique to a person that is not really correct. Since when you want to add this technique to another person, it will send you an error. The preferable in this situation is a ManyToMany. Otherwise you can always create an associative class to retrieve the identifiers of the two classes.

Upvotes: 0

Related Questions