Symfony2和Doctrine $ em->持续VS $ em->合并

时间:2015-04-30 16:40:26

标签: symfony merge doctrine persist

您好,我有一个关于学说的快速问题以及merge()persist()之间的区别

我有一个NewsBuilder课程:

  • 这需要一个新闻实体,并检查它是否存在于 数据库,如果是,它将实体的值设置为数据 传递并返回实体。
  • 如果它不存在,则会创建一个新的新闻实体设置数据和
    返回实体

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;
    }
}

这是由NewsPersister

使用的

这会使用FindByOne()传递我正在解析的数据的ID来检查我的存储库。

    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 );
        }
    }

我的问题:可以删除FindByOne()语句,只需使用$em->merge()代替$em->persist()

我是否正确地认为$em->merge将实体设置为更新或插入,具体取决于id是否存在?我额外打电话给他回购不必要吗?

1 个答案:

答案 0 :(得分:12)

不,你无法删除

不同之处在于您对实体的影响。

Persist接受实体实例,将其添加到持久性上下文并使其受管理,因此所有其他更新将由实体管理器管理。

合并将创建实体的新实例,从提供的实体复制状态,并将管理新副本,但不会管理传递的实体,因此实体管理器不会缓存进一步的更改

通过你的例子:如果你将坚持更改为合并,那么它将没有任何区别。因此合并将持续做同样的工作。通常,当你有分离的实体或未序列化的(即来自缓存)时,你应该使用merge