Tengo un modelo de Subscriber
// Subscriber Model id user_id subscribable_id subscribable_type public function user() { return $this->belongsTo('App\User'); } public function subscribable() { return $this->morphTo(); }
Y un modelo de Topic
// Topic Model public function subscribers() { return $this->morphMany('App\Subscriber', 'subscribable'); }
Y quiero que todos los usuarios pasen por el modelo Subscriber
, para notificarles como
Notification::send($topic->users, new Notification($topic));
// Topic Model public function users() { return $this->hasManyThrough('App\User', 'App\Subscriber'); }
¿Algunas ideas?
// Topic Model public function users() { return $this->hasManyThrough('App\User', 'App\Subscriber', 'subscribable_id') ->where( 'subscribable_type', array_search(static::class, Relation::morphMap()) ?: static::class ); }
Las relaciones polimórficas hasManyThrough
son las mismas que cualquier otra, pero con una restricción adicional en subscribable_type
, que se puede recuperar de la matriz Relation::morphMap()
, o usando el nombre de la clase directamente.
Además del enfoque de Matt, el siguiente código también podría ser otra solución:
//Topic Model public function users() { return $this->belongsToMany(User::class, 'subscribers', 'subscribale_id', 'user_id') ->where('subscribale_type', static::class); }
De esta manera, el Subscriber
se trata como una tabla dinámica y el segundo argumento es el nombre de la tabla para el pivote.
El tercer argumento es el nombre de clave externa del modelo en el que está definiendo la relación, mientras que el cuarto argumento es el nombre de clave externa del modelo al que se está uniendo. Lea más aquí .
Considere la cláusula where
después de belongsToMany
a muchos para filtrar solo el modelo actual.
Lo que buscas no es hasManyThrough
, sino morphedByMany
.
hasManyThrough
es útil cuando tiene A
uno a muchos B
, B
uno a muchos C
, y desea usar A
para obtener muchos C
.
Lo que tiene es una tabla dinámica polimórfica ubicada en el medio entre A
y C
.
// Topic Model public function users() { return $this->morphedByMany('App\User', 'subscribable', 'pivot/subscriber_table_name'); }
Documentos: https://laravel.com/docs/6.x/eloquent-relationships#many-to-many-polymorphic-relations