2012-04-07 10 views
6

Tengo un repositorio en el que intento configurar el almacenamiento en caché de resultados. Solo he podido encontrar un solo ejemplo en línea sobre cómo hacer esto ... pero cuando implemento el ejemplo en uno de mis repositorios, aparece un error. Estoy usando APC para el almacenamiento en caché y he habilitado el caché de consultas para usar APC en mi archivo config.yml. He asignaron 512M a APC y su único usando 50M actualmente (23M de esto es por esta única entrada de caché fallado)¿Cómo especifico el caché de resultados de la consulta en un repositorio symfony2?

Aquí está el repositorio de código que tengo:

class AchievementRepository extends EntityRepository 
{ 
    function findAchievementsByCategory($categoryObj) 
    { 
     $em=$this->getEntityManager()->createQuery("SELECT a FROM FTWGuildBundle:Achievement a where a.category=:category order by a.title") 
      ->setParameter('category',$categoryObj); 
     $em->useResultCache(true,3600,'findAchievementsByCategory'); 
     $result=$em->getResult(); 
     return $result; 
    } 
} 

Y cuando este se ejecuta consigo el siguiente error

Notice: apc_store() [<a href='function.apc-store'>function.apc-store</a>]: &quot;type&quot; returned as member variable from __sleep() but does not exist in /data/www/ftw2/Symfony/vendor/doctrine-common/lib/Doctrine/Common/Cache/ApcCache.php line 80 

Cuando miro en mi archivo apc.php para ver lo que se almacena en caché, encuentro mi entrada de caché en la sección caché de usuario con un valor almacenado de

Fatal error: Nesting level too deep - recursive dependency? in /data/www/localhost/apc.php on line 1000 

¿Alguien me puede dar alguna indicación sobre dónde me he equivocado?

Hay un par de columnas en esta entidad que son ManyToOne, ¿tengo que desactivar la carga lenta en esta consulta para que esto funcione? ¿Si es así, cómo? EDIT: activar la carga ansiosa añadiendo, fetch = "ansiosos" por mi mapeo ManyToOne ... no hay manzanas :(

editar # 2: respondió - código de la clase de trabajo (nota, todas las propiedades de la clase de entidad (Logro) han sido cambiados para proteger)

class AchievementRepository extends EntityRepository 
{ 
    function findAchievementsByCategory($categoryObj) 
    { 
     $em=$this->getEntityManager()->createQuery("SELECT a FROM FTWGuildBundle:Achievement a where a.category=:category order by a.title") 
      ->setParameter('category',$categoryObj); 
     $em->useResultCache(true,3600,'findAchievementsByCategory'); 
     $result=$em->getArrayResult(); 
     return $result; 
    } 
} 

Respuesta

3

cuando Doctrina caché una entidad, que guarda el estado serializado de la misma. el problema es que las propiedades privadas (la visibilidad por defecto cuando se genera por la doctrina) no pueden ser serializados. para Arregle esto, tiene que proteger las propiedades de su entidad. Más información: http://doctrine-orm.readthedocs.org/en/2.0.x/reference/working-with-objects.html#merging-entities

La otra cosa es a know issue que está (finalmente) corregido en la versión 2.2 de Doctrine, que estará en Symfony 2.1. Si no puede actualizar por algún motivo, la única forma de guardar asociaciones en caché es usar getArrayResult en lugar de rellenar entidades.

+0

Gracias! Actualicé para usar propiedades protegidas y cambié mi getResult() a getArrayResult() y ahora almacena en caché correctamente. – Chris

+0

@Chris, ¿cómo se evaluó si el resultado se almacenó en caché? – cbacelar

+0

@cbacelar - un par de formas 1) Use el depurador de consultas, renderice una página y vea cuántas consultas se ejecutan. Verá sus consultas no almacenadas en caché aquí. Actualiza la página y verás que las consultas en caché no se ejecutan. 2) Compruebe las estadísticas en su caché (memcached, apc, etc.) para ver si hay más datos o más registros en la memoria caché. apc tiene una interfaz agradable que puede instalar para permitirle ver cada entidad en caché (incluyendo clave, valor y estadísticas) – Chris

Cuestiones relacionadas