Según mi conocimiento, carga ansiosa with
el método ejecuta la segunda consulta. Es por eso que no puedes lograr lo que quieres con carga ansiosa with
método.
Creo que usar join
método en combinación con método de relación es la solución La siguiente solución está completamente probada y funciona bien.
// In User Model
public function channels()
{
return $this->belongsToMany('App\Channel', 'channel_user')
->withPivot('is_approved');
}
public function sortedChannels($orderBy)
{
return $this->channels()
->join('replies', 'replies.channel_id', '=', 'channel.id')
->orderBy('replies.created_at', $orderBy)
->get();
}
Luego puede llamar a $user->sortedChannels('desc')
para obtener la lista de canales ordenar por respuestas created_at
atributo.
Para condiciones como canales (que puede o no tener respuestas), simplemente use leftJoin
método.
public function sortedChannels($orderBy)
{
return $this->channels()
->leftJoin('replies', 'channel.id', '=', 'replies.channel_id')
->orderBy('replies.created_at', $orderBy)
->get();
}
Editar:
Si desea agregar groupBy
método a la consulta, debe prestar especial atención a su orderBy
cláusula. Porque en Sql naturaleza, Group By
la cláusula se ejecuta primero antes de Order By
cláusula. Consulte los detalles de este problema en esta pregunta de desbordamiento de pila
.
Entonces, si agrega groupBy
método, tienes que usar orderByRaw
y debe implementarse de la siguiente manera.
return $this->channels()
->leftJoin('replies', 'channels.id', '=', 'replies.channel_id')
->groupBy(['channels.id'])
->orderByRaw('max(replies.created_at) desc')
->get();