Mysql
 sql >> Database >  >> RDS >> Mysql

laravel eloquente ordina per relazione

Secondo le mie conoscenze, carico desideroso with metodo eseguire la seconda query. Ecco perché non puoi ottenere ciò che desideri con il caricamento ansioso with metodo.

Penso di usare join metodo in combinazione con metodo di relazione è la soluzione. La seguente soluzione è completamente testata e funziona bene.

// 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();
}

Quindi puoi chiamare $user->sortedChannels('desc') per ottenere l'elenco dei canali ordina per risposte created_at attributo.

Per condizioni come canali (che può avere o meno risposte), usa semplicemente leftJoin metodo.

public function sortedChannels($orderBy)
    {
        return $this->channels()
                ->leftJoin('replies', 'channel.id', '=', 'replies.channel_id')
                ->orderBy('replies.created_at', $orderBy)
                ->get();
    }

Modifica:

Se vuoi aggiungere groupBy metodo alla query, devi prestare particolare attenzione al tuo orderBy clausola. Perché in Sql natura, Group By clausola eseguita prima di Order By clausola. Vedi in dettaglio questo problema su questa domanda sull'overflow dello stack .

Quindi se aggiungi groupBy metodo, devi usare orderByRaw metodo e dovrebbe essere implementato come il seguente.

return $this->channels()
                ->leftJoin('replies', 'channels.id', '=', 'replies.channel_id')
                ->groupBy(['channels.id'])
                ->orderByRaw('max(replies.created_at) desc')
                ->get();