Laravel имеет множество сквозных глубоких отношений

#php #laravel #database #eloquent #relation

Вопрос:

У меня есть многопользовательская настройка, в которой HasMany рабочие пространства арендатора и BelongsToMany учащиеся рабочей области. Как мне создать связь с клиентом, в которой я получаю всех учащихся из всех рабочих пространств в клиенте?

Я взглянул hasManyThrough , но это не решает проблему. Прямо сейчас у меня есть эта функция:

 public function getStudents()
{
    $this->workspaces()->get()->map(function ($workspace) {
        return $workspace->students;
    })->flatten()->unique();
}
 

Но я бы хотел сделать это в отношении вместо приведенного выше кода. Любой совет?

 Tenant :HasMany=> Workspace(tenant_id) :BelongsToMany=> Student(student_workspace table)
 

Заранее спасибо!

Комментарии:

1. Вы видели этот пакет github.com/staudenmeir/eloquent-has-many-deep

2. существует ли промежуточная (сводная) таблица между таблицами «workspaces» и «students» (что-то вроде «student_workspace»)? Я предполагаю, что у вас также должна быть эта сводная таблица, потому что я думаю, что в любом рабочем пространстве может быть несколько учеников, и у каждого ученика может быть несколько рабочих пространств. я прав??

Ответ №1:

Вы могли бы сделать это через join :

 public function students(){
    return Student::select('students.*')
        ->join('student_workspace', 'students.id', '=', 'student_workspace.student_id')
        ->join('workspaces', 'workspaces.id', '=', 'student_workspace.workspace_id')
        ->join('tenants', 'tenants.id', '=', 'workspaces.tenant_id')
        ->where('tenants.id', $this->id);
}
 

Или, как любое обычное отношение, использующее этот пакет: hasManyDeep выполните следующие шаги:

Первый:

 composer require staudenmeir/eloquent-has-many-deep
 

В вашем Workspace файле модели:

 public function students()
{
    return $this->belongsToMany(Student::class, 'student_workspace');
}
 

В вашем Tenant файле модели:

 use StaudenmeirEloquentHasManyDeepHasRelationships;

class Tenant extends Model
{

    use HasFactory, HasRelationships;

    public function students(){
        return $this->hasManyDeepFromRelations($this->workspaces(), (new Workspace)->students());
    }

}
 

Надеюсь, это было бы полезно.