0

我正在构建一个 ZF2+Doctrine2 Web 应用程序,并且我已经在我的实体存储库中实现了缓存。

public function findActive()
{
    $query = $this->_em->createQueryBuilder();
    $query->select('r')
        ->from('Admin\Entity\Brands', 'r')
        ->where('r.deleted = false')
        ->orderBy('r.name', 'ASC');
    return $query->getQuery()
        ->useResultCache(true, 7200, 'brands_find_active')
        ->getResult();;
}

我一直无法弄清楚如何为查找查询注入缓存逻辑。

就像我有一个带有 role_id 的用户表,它链接到角色表并且我执行了一个getRole()->getRoleName()调用。这会导致对角色表进行额外的 sql 查询。如何缓存整个查询/递归?

4

1 回答 1

2

简单地说,你不能。Doctrine 为延迟加载执行“魔术”查询。例如,如果您加载用户,则不会自动查询角色。只有当你调用$user->getRole()角色时才会被查询。

这种行为需要所谓的代理模式。您代码中的用户不是Admin\Entity\User对象,而是从您的用户扩展而来的 Doctrine 类。代理还拥有实体管理器的一个实例,因此它可以在您调用时查询角色getRole()。因为如果是这个代理,就很难序列化和反序列化 php 对象。

由于这种模式,你永远无法很好地缓存 Doctrine 实体。您还一直在代理和关系方面遇到麻烦。加载它们的唯一方法__wakeup()是不加载相关实体并确保.

如果你只使用Doctrine caches会容易得多。您可以使用 ZF2 DoctrineModule 在配置中使用以下代码配置 Doctrine 缓存:

'doctrine' => array(
    'configuration' => array(
        'orm_default' => array(
            'metadata_cache'    => 'apc',
            'query_cache'       => 'apc',
            'result_cache'      => 'apc',
        ),
    ),
),

如果您需要为 apc 缓存提供命名空间(例如,您在一台服务器上有多个站点)通过此配置设置命名空间:

'doctrine' => array(
    'cache' => array(
        'apc' => array(
            'namespace' => 'my-namespace',
        ),
    ),
),
于 2013-09-24T13:03:09.040 回答