Как я могу издеваться над другой моделью, чтобы получить полиморфные отношения? - PullRequest
1 голос
/ 15 мая 2019

У меня есть 3 модели данных, одна из которых расширяет другую:

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Opinion extends Model
{
    public function reactions()
    {
        return $this->morphMany('App\Models\Reaction', 'reactable');
    }

    ...
}
namespace App\Models\Activity;

use App\Models\Opinion;

class ActivityOpinion extends Opinion
{
    ...
}
namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Reaction extends Model
{
    public function reactable()
    {
        return $this->morphTo();
    }

    ...
}

Модель App\Models\Opinion имеет полиморфную связь с моделью App\Models\Reaction.Я могу получить все реакции App\Models\Opinion без проблем, поэтому я знаю, что отношения прекрасно работают.

Мой вопрос: как я могу получить тот же набор реакций из модели App\Models\Activity\ActivityOpinion?Потому что сейчас он ищет App\Models\Activity\ActivityOpinion как отношения, но мне нужно, чтобы он искал App\Models\Opinion.Можно ли издеваться над другой моделью в полиморфных отношениях?

1 Ответ

0 голосов
/ 15 мая 2019

Это связано с тем, что в полиморфных отношениях в сохраненных данных (если оставить значение по умолчанию) тип отношения получает пространство имен класса (своего рода) для указания, какую модель необходимо вернуть. Вот почему, когда вы пытаетесь получить доступ к вашим отношениям reactions() из ActivityOpinion, он будет искать значение App\ActivityOpinion в reactable_type.

Вы можете настроить класс morph для поиска в модели, добавить следующее:

Opinion.php

protected $morphClass = 'reaction';

Этого должно быть достаточно, если нет, добавьте его также в модель ActivityOpinion.


Примечание

Это может привести к ошибкам при попытке поиска результатов с помощью Eloquent. Проверьте этот другой ответ , чтобы устранить это возможное несоответствие.



Обновление

Я только что узнал, что вы могли бы сделать все это еще проще с MorphMap . Из документов:

Пользовательские полиморфные типы

По умолчанию Laravel будет использовать полное имя класса для хранения тип связанной модели. Например, учитывая один ко многим пример выше, где Comment может принадлежать Post или Video, по умолчанию commentable_type будет либо App\Post, либо App\Video, соответственно. Тем не менее, вы можете отделить база данных из внутренней структуры вашего приложения. В этом случае вы может определить «карту морфов», чтобы Eloquent проинструктировал использовать произвольное имя для каждая модель вместо имени класса:

use Illuminate\Database\Eloquent\Relations\Relation;

Relation::morphMap([
    'posts' => 'App\Post',
    'videos' => 'App\Video',
]);

Вы можете зарегистрировать morphMap в функции boot вашего AppServiceProvider или создайте отдельного поставщика услуг, если вы хочу.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...