#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());
}
}
Надеюсь, это было бы полезно.