教条:QueryBuilder vs createQuery?

在学说中,您可以通过两种方式创buildDQL:

EntityManager :: createQuery

$query = $em->createQuery('SELECT u FROM MyProject\Model\User u WHERE u.id = ?1'); 

QueryBuilder

 $qb->add('select', 'u') ->add('from', 'User u') ->add('where', 'u.id = ?1') ->add('orderBy', 'u.name ASC'); 

我不知道有什么区别,应该使用哪一个?

  1. DQL更容易阅读,因为它非常类似于SQL。 如果您不需要根据一组参数更改查询,则这可能是最佳select。

  2. 查询生成器是构build查询的api,因此如果需要dynamic构build查询,比如遍历一组参数或filter,查询生成器就更容易。 你不需要做任何string操作来build立你的查询,如连接,分割或其他。

查询生成器只是,可以说,接口来创build查询…它应该更舒适的使用,它没有只有add()方法,但也有像(),和Where(),from()等方法但是最后,它只是像在createQuery()方法中使用的那样组成查询语句。

更高级的查询生成器的使用示例:

 $em->createQueryBuilder() ->from('Project\Entities\Item', 'i') ->select("i, e") ->join("i.entity", 'e') ->where("i.lang = :lang AND e.album = :album") ->setParameter('lang', $lang) ->setParameter('album', $album); 

他们有不同的目的:

  • 当你知道你的完整查询时,DQL更容易使用。
  • 查询生成器是聪明的,当你必须build立你的查询基于一些条件,循环等

主要区别是调用方法的开销。 你的第一个代码示例(createQuery)只是为了简单起见,只是一个方法调用,而queryBuilder却是4.在所有事情结束时,它们都归结为一个必须执行的string,第一个例子是你给它的string,另一个你用多个链接的方法调用来构build它。

如果你正在寻找一个相对于另一个的理由,这是一个风格问题,看起来更可读。 对我而言,我大多数时候都喜欢queryBuider,它为查询提供了定义好的部分。 另外,在过去,当你需要的时候可以很容易地添加条件逻辑。

使用查询生成器时,可能会更容易进行unit testing。 假设您有一个存储库,可以根据复杂的条件列表查询一些数据。 而且您要确保如果将特定条件传递到存储库中,则会在查询中添加其他一些条件。 在DQL的情况下,你有两个select:

1)使用灯具并testing与DB的真实交互。 我觉得有点麻烦和ununitestish。

2)检查生成的DQL代码。 这可能会让你的testing太脆弱了。

使用QueryBuilder,你可以用模拟来代替它,并validation带有所需参数的“andWhere”方法被调用。 当然,如果您的查询很简单并且不依赖任何参数,这些注意事项是不适用的。