-
Notifications
You must be signed in to change notification settings - Fork 43
Description
I am extending my User entity with an attribute using a ManyToMany association.
In my example I use "costCenters" but you can think of it as the already existing "roles" attribute.
User entity:
/**
* @var \Doctrine\Common\Collections\Collection
* @ORM\ManyToMany(targetEntity="Application\Entity\Role")
* @ORM\JoinTable(name="user_role_linker",
* joinColumns={@ORM\JoinColumn(name="user_id", referencedColumnName="id")},
* inverseJoinColumns={@ORM\JoinColumn(name="role_id", referencedColumnName="id")}
* )
*/
protected $roles;
/**
* @var \Doctrine\Common\Collections\Collection
* @ORM\ManyToMany(targetEntity="Application\Entity\CostCenter")
* @ORM\JoinTable(name="user_costCenter",
* joinColumns={@ORM\JoinColumn(name="user_id", referencedColumnName="user_id")},
* inverseJoinColumns={@ORM\JoinColumn(name="costCenter_id", referencedColumnName="id")}
* )
*/
private $costCenters;
public function getCostCenters() {
return $this->costCenters;
}
public function setCostCenters($costCenters) {
$this->costCenters = $costCenters;
}
Extending the form in my _Module.php_:
public function onBootstrap($e)
{
$app = $e->getParam('application');
// $em is a Zend\EventManager\SharedEventManager
$em = $app->getEventManager()->getSharedManager();
$em->attach('ZfcUserAdmin\Form\EditUser', 'init', function($e) {
// $form is a ZfcUser\Form\Register
$form = $e->getTarget();
$sm = $form->getServiceManager();
$om = $sm->get('Doctrine\ORM\EntityManager');
#$form->setHydrator(new \DoctrineORMModule\Stdlib\Hydrator\DoctrineEntity($om, 'Application\Entity\User'));
$form->add(array(
'name' => 'costCenters',
'type' => 'DoctrineModule\Form\Element\ObjectMultiCheckbox',
'options' => array(
'label' => 'Access to costcenters',
'object_manager' => $om,
'target_class' => 'Application\Entity\CostCenter',
'property' => 'id',
),
));
});
}
I already inserted some rows in my database and the edit form is populated correctely with these existing costcenters.
When editing and saving I get these warnings / errors:
Warning: spl_object_hash() expects parameter 1 to be object, string given in /vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php on line 1375*
exception 'Doctrine\ORM\ORMException' with message 'Found entity of type on association Application\Entity\User#costCenters, but expecting Application\Entity\CostCenter' in /vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php:783
I think the configuration of entities and form are correct. It looks like the method to update the user entity in Service/User.php l. 78 ff. causes a problem:
// first, process all form fields
foreach ($data as $key => $value) {
if ($key == 'password') continue;
$setter = $this->getAccessorName($key);
if (method_exists($user, $setter)) call_user_func(array($user, $setter), $value);
}
My posted value for costCenters will be an array of strings including the IDs.
It looks like the entity manager will ony receive these strings since it doesn't know they have to be "hydrated" to find the related objects / entities.
Normally I would bind the object to Zend_Form and then a hydrator will do this in order to correctely persist the entity, e.g.:
$id = /*(int)*/ $this->params('id', null);
$em = $this->getEntityManager();
$timeDataStatus = $em->find('Application\Entity\TimeDataStatus', $id);
$formManager = $this->serviceLocator->get('FormElementManager');
$form = $formManager->get('CreateTimeDataStatus');
$form->bind($timeDataStatus);
$request = $this->getRequest();
if ($request->isPost()) {
$form->setData($request->getPost());
if ($form->isValid()) {
$em->persist($timeDataStatus);
$em->flush();
}
}
Since saving multiple roles will probably be a use case for future admin forms can we achieve a solution here?