Symfony PageEntity->getByPath() or PageController->getByPath()? - symfony

I would like to return the page Entity from the method: getByPath($path). I just would like to know where this method should be in the script. Inside the controller or inside the entity class?
In my opinion the entity "Page" shouldn't have a function called "getByPath()" since an entity should only contain database information of one entity, which can be get or set by getters and setters. And this "getByPath" function is not just a getter or setter it requires me to run the entitymanager within the entity. Am I right?
So am I right that I should make a PageController and create the "getByPath()" (which will return the page object) function there? Or would anyone create that function inside the entity class?
I would like to know what the nicest way is to accomplish this.
Thanks in advance.

You should put that function inside a custom repository for the Page entity
While the Entities are the objects you are storing, the Repository is the class that provides methods to access/load those objects, eg when you call $em->getRepository('Entities\Page')->find($page_id);, you call the find() method on your Page repository and it's its job to find it for you.
Doctrine provides a default repository for each entity (with the various find*() methods, ...), but you can provide a custom one where you can add your own method, such as getByPath().
Symfony 2 - Database and Doctrine - Custom Repository Classes
Doctrine 2 - Custom repository

Related

Possible to use Entity getters in custom repository?

I am in need of grabbing a few fields of an entity, running them through some processing, and returning the processed data. I am wondering if it is possible to call the getters of the Entity for which the custom repository is being built inside that custom repository? The only way I thought of so far seems like it would create an infinite loop by calling the entity's repository, which would include a call to the very custom repository being used as well.
I can write the actual queries, but I figured it it would be cleaner to access the data through existing methods, then why not?
Update: So I built a method in the custom repository that I pass the entity object to that I want to work with. Seems a little weird that I would have to pass the entity to it's own custom repository so that it would know what to act on, but I can't seem to find any other way. So in my Controller right now I am calling the entity, then calling up the repository for the entity, and passing the previously called entity to the repository. Is that right?
$user = $this->get('security.context')->getToken()->getUser();
$user_repository = $this->getDoctrine()->getRepository('AppBundle:User');
$profiles = $user_repository->getAllUsersProfiles($user);
It turns out I had the whole concept of Custom Repositories incorrect. I was using them to store methods that would pull out data relevant to the entity, but only relevant in the sense that the entity was being used to filter something else.
Prior to this epiphany my User Custom Repository had methods like getAllUsersProfiles($user) and getAllUsersCampaigns($user). My previously incorrect understanding was that because the User entity was the thing that was central to filtering the Profiles and Campaigns, that these belonged in the User Custom Repository.
What I have now come to understand is that getAllUserProfiles($user) belongs in the Profiles Custom Repository, and would be more appropriately named getAllByUser($user). Now when I need to use it, I pull up the Profiles Repository and call the appropriate method:
$profile_repository = $this->getDoctrine()->getRepository('AppBundle:Profile');
$all_profiles = $profile_repository->getAllByUser($user);

Doctrine custom repository methods and unmanaged entities

I've got custom entity repository (let's say CategoryRepository) that returns Doctrine entities. I also have newly created entity (let's say Product) that I want to persist.
Product is related to Category and, in that case, Product is the owning side of the relationship so I've got following code:
$category = $categoryRepository->customGetCategory($someCriteria);
$product = new Product();
$product->setCategory($category);
$em->persist($product);
and result is
[Doctrine\ORM\ORMInvalidArgumentException]
A new entity was found through the relationship
'Acme\SomethingBundle\Entity\Product#category' that was not configured
to cascade persist operations for entity: blahblah. 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"})
For now I'm aware that all entities returned by custom repository methods using \Doctrine\ORM\Query::getResult() method where Query object is returned by EntityManager::createQuery($dql) factory method are detached by default. So I've got entity returned by repository that exists in database and I can't find a way for doctrine to have it managed just like any entity returned by f. ex. $repository->findBy() method.
Could anyone point me in right direction with this? I'd really like to solve that, it's killing me.
This is probably one of the top 5 Doctrine questions asked. Just difficult to search for. Could try searching on the error message.
The problem is that Category::setProduct is never being called. Update your Product entity with:
class Product
{
public function setCategory($category);
{
$this->category = $category;
$category->setProduct($this); // *** Add this
}
}

Symfony doctrine:generate:entities How to find is and has methods

I have an entity called Member with a boolen property called "active". When I generate the getters and setters with doctrine:generate:entities I get the methods getActive() and setActive(). Now I rename the getter to isActive. When I now call doctrine:generate:entities on this entity again, the process generates a new method getActive as he does not find the method isActive.
Is there a way to tell it to search for is and has getter methods too?
No, this is not possible at the moment. You can vote for this feature here: http://www.doctrine-project.org/jira/browse/DDC-2287. However it is not recommended to use the "doctrine:generate:entities"-command to update entities. The command was built to generate the entities for the first time and not to update them. You should maintain your entities with your ide.

Accessing Symfony2 global parameter in entity class

I have a value stored in my parameters.ini file, and I need to access it during the prepersist method of my model.
Normally I use $this->container->getParameter('value');, but the container is not available in the entity.
Is there a way to get parameters within an entity class?
P.S. The value is an API key for a service I am pulling info from during prepersist. Best practice is to keep keys/passwords in parameters.ini
Best practice is to use a service to persist your entity. This one would inject the container and set your parameter when you call your updateMyEntity() service method.
Inside your controller (or whatever you want):
$user = new User('foo');
$user->setSomeProperty('bar');
$userService->update($user);
Inside the UserService:
public function update(User $user) {
$user->setSomeParameter($this->container->getParameter('value'));
$this->em->persist($user);
}
In addition to Florent's answer, Entities are meant to be purely data objects. They should not know about any other variables or services within your application. I'm more curious about why your entity needs to know anything about an API key that is system-wide. With very little background information, I'd say you should rethink what you are trying to do.
You need a service to interact with the API, ideally configured through the container. I don't see what that has to do with an entity.

Handling both EntityRepository and QueryBuilder for PagerBundle in Symfony2 and Doctrine

The PagerBundle is a very useful bundle for handling pagination in Symfony2. However, it provides
the adapter DoctrineOrmAdapter for Doctrine2 based on QueryBuilder.
Then, one should create a specific query with the QueryBuilder inside each controller. This approach will bring to the need of defining ad hoc functions that can be used inside the controllers, as well as possible problem when the table schema change. In fact, the correct approach is to use the user-defined EntityRepository, which contains all the useful queries for the Doctrine Entity.
Each call to the EntityRepository should return the result of a query, not a Query object or a QueryBuilder object.
So, how do you suggest to handle this problem?
PS: Please, don't answer that I can return a QueryBuilder by the functions of the entity repository. It is trivial!

Resources