Hi there I've got a quick question regarding Doctrine and the difference between merge()
and persist()
I have a NewsBuilder
class:
namespace FantasyPro\DataBundle\Builder;
use FantasyPro\DataBundle\Entity\News;
use FantasyPro\DataBundle\Helpers\DateHelper;
class NewsBuilder
{
/**
* @var DateHelper $dateHelper
*/
private $dateHelper;
public function __construct( DateHelper $dateHelper )
{
$this->dateHelper = $dateHelper;
}
public function buildNews( $currentNews = null, $news)
{
if ( ! $currentNews) { // check if we already have the news stored
$currentNews = new News();
}
$currentNews->setNewsID( $news['NewsID'] );
$currentNews->setTitle( $news['Title'] );
$currentNews->setUpdated( $this->dateHelper->parseDate( $news['Updated'] ) );
$currentNews->setUrl( $news['Url'] );
$currentNews->setContent( $news['Content'] );
$currentNews->setSource( $news['Source'] );
$currentNews->setTermsOfUse( $news['TermsOfUse'] );
$currentNews->setTeam( $news['Team'] );
$currentNews->setPlayerID( $news['PlayerID'] );
return $currentNews;
}
}
this is used by a NewsPersister
Class
This performs a check on my repo using FindByOne()
passing the id of the data i am parsing.
namespace FantasyPro\DataBundle\Persisters;
use Doctrine\ORM\EntityManager;
use FantasyPro\DataBundle\Builder\NewsBuilder;
use FantasyPro\DataBundle\Entity\News;
class NewsPersister {
/**
* @var EntityManager $em
*/
private $em;
/**
* @var NewsBuilder $builder
*/
private $builder;
public function __construct( EntityManager $em, NewsBuilder $builder )
{
$this->em = $em;
$this->builder = $builder;
}
public function Persist($news){
//get the news repository
$repo = $this->em->getRepository( 'DataBundle:News' );
// get the current news from the db
$criteria = array(
'newsID' => $news['NewsID']
);
/**
* @var News $currentNews
*/
$currentNews = $repo->FindOneBy( $criteria );
//todo: use a logger to write this data to file
//build the news entity
$currentNews = $this->builder->buildNews( $currentNews, $news );
//persist the team
$this->em->persist( $currentNews );
}
}
Hers my question: can drop the FindByOne()
statement and simply use $em->merge()
instead of $em->persist()
Am i right in thinking that the $em->merge
sets the entity to either update or insert depending on whether the id exists or not? making my extra call to he repo unnecessary?
no, you can't remove
The difference is what you do with entity after.
Persist takes an entity instance, adds it to persistance context and makes it managed, so all other updates will be managed by entity manager.
Merge will create new instance of entity, copies state from provided entity, and will makes new copy managed, but passed entity won't be managed, so futher changes won't be cached by entity manager
By your example: if you will change persist to merge, then it won't make any difference. So merge will do same job as persist. And usually you should use merge when you have detached entity or unserialized (i.e from cache)