2010-01-16 11 views
7

En general, es mejor hacer una sola consulta frente a muchas consultas para un objeto determinado. Digamos que tengo un montón de objetos 'hijo', cada uno con un 'padre'. Consigo todos los objetos 'hijo':Acceso a la clave del objeto relacionado sin recuperar el objeto en App Engine

sons = Son.all() 

Entonces, me gustaría llegar a todos los padres de ese grupo de hijos. Yo:

father_keys = {} 
for son in sons: 
    father_keys.setdefault(son.father.key(), None) 

entonces puedo hacer:

fathers = Father.get(father_keys.keys()) 

Ahora, esto supone que son.father.key() en realidad no ir a buscar el objeto. ¿Estoy equivocado en esto? Tengo un montón de código que supone que object.related_object.key() en realidad no busca el objeto relacionado desde el almacén de datos.

¿Estoy haciendo esto bien?

Respuesta

10

Puede encontrar la respuesta estudiando las fuentes de appengine.ext.db en la descarga de las fuentes del SDK de App Engine, y la respuesta es, no, no hay ninguna cubierta especial que necesite: el método __get__ (línea 2887 en el fuentes para el SDK 1.3.0 del descriptor ReferenceProperty se invoca antes de saber si .key() o cualquier otra cosa se invocará más tarde en el resultado, por lo que simplemente no tiene la oportunidad de hacer la optimización que desea.

Sin embargo, ver la línea 2929: Método get_value_for_datastorequé hacen exactamente lo que quieres!

En concreto, en lugar de son.father.key(), utilice Son.father.get_value_for_datastore(son) y que debe estar mucho más feliz como resultado ;-).

+1

Kick ass answer. Mi aplicación acaba de obtener 10 veces más rápido y más barato: D –

+0

@Sudhir, me alegro de que haya ayudado, ¡gracias por informarme que lo hizo! -) –

+0

Hablando de eso, ¿los objetos se almacenan en caché cuando se recuperan de la tienda? Entonces, si hiciera Father.get (all_keys) en el controlador, ¿intentaría el tiempo de ejecución obtenerlos nuevamente en la plantilla si solo estoy imprimiendo a los hijos con sus padres? –

1

Prefiero recorrer los hijos y obtener las claves de los padres usando son.parent_key().

parent_key()

devuelve la clave de la entidad matriz de esta instancia, o Ninguno si este caso no tiene un padre.

Since all the path is saved in the instance's key, teóricamente, no hay necesidad de golpear la base de datos de nuevo para obtener la clave de los padres.

Después de eso, es posible obtener todas las instancias de los padres a la vez usando db.get().

get (teclas)

Obtiene la entidad o entidades de la tecla o teclas dado, de cualquier modelo.

Argumentos:

claves Un objeto clave o una lista de objetos clave.

Si se proporciona una clave, el valor de retorno es una instancia de la clase de modelo apropiada de o None si no existe la entidad con la clave especificada. Si se proporciona una lista de claves , el valor de retorno es una lista correspondiente de instancias del modelo , con valores None cuando no existe ninguna entidad para una clave correspondiente.

Cuestiones relacionadas