fields - query builder cakephp 3
Cómo filtrar por condiciones para los modelos asociados? (1)
Utilice Query :: matching () o Query :: innerJoinWith ()
Al realizar consultas desde la tabla de Contacts
, lo que está buscando es Query::matching()
o Query::innerJoinWith()
, no (solo) Query::contain()
.
Consulte Libro de cocina> Acceso a la base de datos y ORM> Creador de consultas> Filtrado por datos asociados
Aquí hay un ejemplo usando sus tablas:
$this->Contacts
->find()
->matching(''Users'', function(/Cake/ORM/Query $q) {
return $q->where([''Users.id'' => 1]);
});
Esto agregará automáticamente las uniones requeridas + condiciones a la consulta generada.
Apunte a la mesa de unión
En caso de que tenga una configuración manual de muchas a muchas asociaciones a través de hasMany
y belongsTo
, puede orientar directamente la tabla de unión:
$this->Contacts
->find()
->matching(''ContactsUsers'', function(/Cake/ORM/Query $q) {
return $q->where([''ContactsUsers.user_id'' => 1]);
});
Incluir contenciones
En caso de que realmente desee que todas las asociaciones sean devueltas en sus resultados también, simplemente siga usando contain()
también
$this->Contacts
->find()
->contain(''Users'')
->matching(''Users'', function(/Cake/ORM/Query $q) {
return $q->where([''Users.id'' => 1]);
});
Eso contendría a todos los usuarios que pertenecen a un contacto.
En los casos en que tienes múltiples coincidencias y quisieras contener solo esas coincidencias, también deberías filtrar la contención. En este ejemplo, no tiene mucho sentido, ya que solo habría una coincidencia, pero en otras situaciones podría ser útil, por ejemplo, si quisieras hacer coincidir todos los contactos que tienen usuarios activos, y recuperar los contactos, incluidos todos los usuarios activos asociados:
$this->Contacts
->find()
->contain([''Users'' => function(/Cake/ORM/Query $q) {
return $q->where([''Users.active'' => true]);
}])
->matching(''Users'', function(/Cake/ORM/Query $q) {
return $q->where([''Users.active'' => true]);
});
Asociaciones profundas
También puede orientar asociaciones más profundas de esa manera, mediante el uso de la sintaxis de ruta notada por puntos conocida de Query::contain()
, por ejemplo, si también tiene una asociación de Users hasOne Xyz
, puede filtrar por Xyz.id
usando
->matching(''Users.Xyz'', function(/Cake/ORM/Query $q) {
return $q->where([''Xyz.id'' => 1]);
})
Seleccione de la otra mesa en su lugar
Con estas asociaciones y sus requisitos simples, también podría consultar fácilmente desde el otro lado, es decir, a través de la tabla Users
y usar solo Query::contain()
para incluir los contactos asociados, como
$this->Users
->find()
->contain(''Contacts'')
->where([
''Users.id'' => 1
])
->first();
Todos los contactos se pueden encontrar en la propiedad de contacts
las entidades.
Tengo una asociación belongsToMany en Usuarios y Contactos.
Me gustaría encontrar los contactos del usuario dado. Necesitaría algo como
$this->Contacts->find()->contain([''Users'' => [''Users.id'' => 1]]);
El libro de cocina habla sobre dar condiciones para contener, métodos de búsqueda personalizados y cantar a través de la clave de asociación, pero no descubrí cómo juntarlos.