Symfony2 FosUserBundle is not hydrating User Entity with custom Entity - symfony

I have my own User Entity which extends the Fos one. It is capable of having another Entity attached to it as a manyToOne relationship.
Using the following code inside my own Profile Controller results in this Entity not being added to the User Entity.
$user = $repo->find($user->getId());
All my other custom fields are in place, its just this Entity that is missing. The relationship looks like this
manyToOne:
game_system:
targetEntity: Acme\NameofBundle\Entity\GameSystem
joinColumn:
onDelete: SET NULL
name: game_system_id
referencedColumnName: id
Edit
It's worth noting that the getGameSystem call works inside my main Bundle, NameofBundle.
But it fails inside of MemberBundle, MemberBundle extends FOSUserBundle. The GameSystem Entity is inside NameofBundle while my User is my MemberBundle.
Edit 2
My config.yml
fos_user:
db_driver: orm
firewall_name: main
user_class: Acme\MemberBundle\Entity\User
group:
group_class: Acme\MemberBundle\Entity\User

There seems to be a problem with the line:
$user = $repo->find($user->getId());
which seems redundant
How can you id from user if you haven't fetched user from database yet?
or, if you have already user object you don't need to get it from database.
The following would be more correct and to get the id you want you'd have to make a list with findAll().
$user = $repo->find($id);

Related

doctrine postRemove listener on delete cascade in symfony

I have the entity File that is on the owning side of a oneToMany relation, Document is on the inversed side. There is a cascade deletion, so when Document is deleted, all related File entities are deleted, too.
Now I have an entity listener with a postRemove() method for File. But the event is only fired, when I remove the entity directly, not when its done via cascade deletion.
Is there a solution to trigger the postRemove event with a cascade deletion?
One solution would be to put the postRemove event to Document as well, but that would not be very clean because the document should not care for the File postRemove stuff.
Or I could replace the cascade deletion by a postRemove in Document that removes the File entities piece by piece. But I would like to keep the current cascade.
So, is there a way how I can trigger events within a cascade?
That is my current event code:
File.orm.yml
AppBundle\Entity\File:
type: entity
entityListeners:
AppBundle\EventListener\FileListener:
postRemove: [postRemove]
Listener Class
class FileListener {
public function postRemove(File $file) {
dump($file); die();
}
}
service.yml
file_listener:
class: AppBundle\EventListener\FileListener
arguments: ['%path_image%', '%path_thumb%', '%path_preview%']
tags:
- { name: doctrine.orm.entity_listener }
- { name: doctrine.orm.entity_listener, entity_manager: custom }
Ok I solved it replacing onDelete: cascade by cascade: [remove]. But cascade: [remove] needs to be on the inversed side! So not in File but in Document.
The downside of this solution ist, that the cascade operation is not done by the database but by doctrine itself and that means heavy memory load. Its ok for my structure with only a small collection but should be taken in mind for larger groups.

manyToOne is creating new products

I am trying to implement Sylius Cart Bundle, but every time I add a product to the cart, a new product is created.
This is probably link to my line:
cascade: ["persist", "remove"]
In my YAML File:
Pharmacie\FrontBundle\Entity\CartItem:
type: entity
table: app_cart_item
manyToOne:
produit:
targetEntity: Pharmacie\FrontBundle\Entity\Product
cascade: ["persist", "remove"]
joinColumn:
name: product_id
referencedColumnName: id
But if take it off, I get an error:
A new entity was found through the relationship 'Pharmacie\FrontBundle\Entity\CartItem#produit' that was not configured to cascade persist operations for entity: 3test2. To solve this issue: Either explicitly call EntityManager#persist() on this unknown entity or configure cascade persist this association in the mapping for example #ManyToOne(..,cascade={"persist"})
According to the doctrine doc, this error occurs when you set a new object.
But I am only getting an existing object By ID:
$product = $this->getProductRepository()->find($productId);
$item->setProduit($product); //this generates the error
$item->setUnitPrice(5); //this works fine
I don't understand why it's save as a new object.
If I use merge instead of persist, I get the same error:
A new entity was found through the relationship...
Found it (finally...) !
I had 2 entity manager mixed up. This iw why the doctrine wanted to store it as a new object all the time.
The mistake was in the services.yml file, on a listener.
Maybe it can help someone to look in the good direction.

symfony2 doctrine:generate:CRUD error

I am new to symfony2 framework. I have a mysql db that I have prior to installing symfony. So I was able to generate schema based on the db.
I am trying to generate the CRUD controller for one of the tables. This is a user table and the primary key is UserId. However, when I run doctrine:generate:CRUD, I get the following error
The CRUD generator expects the entity object has a primary key field named "id" with a getId() method.
Do I have to have Id as the PK identifier? is that the best practice? All my PKs for the tables are defined by tablenameid.
I have the get method for the User entity class as getUserid().
How can I let the CRUD generator know that?
Thanks
I don't think it has to be 'id' as PK identifier. I think there might be some error in your entity.
/** #Id #Column(type="integer") #GeneratedValue */
private $userid;
YML File:
Bundle\BundleBundle\Entity\Example:
type: entity
table: Example
fields:
userid:
id: true
type: integer
generator:
strategy: AUTO

Symfony 2 Querying Doctrine-mapped objects

I am experiencing an issue when querying for information across objects in my controller. Please let me know if I need to expand on the information provided (I changed the names of the objects to be more clear outside of context).
I have a oneToOne Bidirectional Mapping across two entities that are in separate bundles.
Object 1:
oneToOne:
person:
targetEntity: Program\PersonBundle\Entity\Person
fetch: EAGER
inversedBy: group
joinColumn:
name: id
referencedColumnName: id
Object 2:
oneToOne:
group:
targetEntity: Program\GroupBundle\Entity\Group
mappedBy: person
fetch: EAGER
I have the appropriate variables in each of the Entity.php files for each object. My question is regarding accessing this information in my controller. When I try to access information across the bundles, it doesn't grab it on the first call. However, when I call it again, it grabs the information properly. Does anyone know why this is? Isn't 'fetch: EAGER' supposed to solve that issue?
$em = $this->getDoctrine()->getEntityManager();
$personsRepository = $em->getRepository("PersonBundle:Person");
foreach($persons as $person)
{
$person->getGroup()->getName(); // This doesn't return anything
$person->getGroup()->getName(); // This returns the group name....
}
Thanks in advance!

Doctrine OneToOne incorrectly? generating a UNIQUE INDEX

SchemaTool is generating unique index for associations that are OneToOne. I believe this is incorrect.
Section 6.6 of the Associations manual page at Doctrine shows an example of a OneToOne for a Product has one Shipping. This is shown to generate the Product table:
CREATE TABLE Product (
id INT AUTO_INCREMENT NOT NULL,
shipping_id INT DEFAULT NULL,
PRIMARY KEY(id)
) ENGINE = InnoDB;
However, with the same code for my entity User has one Organisation, my User table SQL is generated as
CREATE TABLE User (
id INT AUTO_INCREMENT NOT NULL,
organisation_id INT DEFAULT NULL,
UNIQ_3B978F9FA7F43455 (organisation_id),
PRIMARY KEY(id)
) ENGINE = InnoDB;
This prevents me adding 2 users with the same Organisation. Not correct.
I additinally tried to be verbose with the unique JoinColumn annotation param.
#JoinColumn(name="organisation_id", referencedColumnName="id", unique="false")
Any ideas? I can't seem to find anything at all about this.
Thanks
If One organisation has Many Users and Many Users have One and only one organisation then it's not a One-to-One association.
One-to-One associations have to be unique.
Your association is ManyToOne on the User side and OneToMany on the organisation side.
User.php
/**
* #ManyToOne(targetEntity="Organisation")
*/
private $organisation;
Organisation.php
use Doctrine\Common\Collections\ArrayCollection;
/**
* #OneToMany(targetEntity="User", mappedBy="organisation")
*/
private $users;
function __construct() {
$this->users = new ArrayCollection();
}
Maybe a YML version could help someone else starting with doctrine/symfony. Here is my version of it:
User.orm.yml
manyToOne:
organisation:
targetEntity: Organisation
joinColumn:
name: organisation_id
referencedColumnName: id
Organisation.orm.yml
oneToMany:
users:
targetEntity: User
mappedBy: organisation
joinColumn:
name: organisation_id
referencedColumn: id
Hope it helps.

Resources