Search code examples
polymorphismrelationshiplaravel-9

Laravel 9 morphTo with custom column names


In the Laravel 9 docs on Relations -> Morphs, it says:

"Key Conventions If necessary, you may specify the name of the "id" and "type" columns utilized by your polymorphic child model. If you do so, ensure that you always pass the name of the relationship as the first argument to the morphTo method. Typically, this value should match the method name, so you may use PHP's FUNCTION constant:

/**
 * Get the model that the image belongs to.
 */
public function imageable()
{
    return $this->morphTo(__FUNCTION__, 'imageable_type', 'imageable_id');
}

"

In my app, the table columns are "kind" and "item_id"

According to this documentation, it seems this should work in my Upload model:

public function uploadable()
    {
        return $this->morphTo(__FUNCTION__, 'kind', 'item_id');
    }

My Product model has:

public function documents()
    {
        return $this->morphMany(Upload::class, 'uploadable');
    }

However when I call my $model->documents() function, I get this SQL error:

"SQLSTATE[42S22]: Column not found: 1054 Unknown column 'uploads.uploadable_id' in 'where clause' (SQL: select * from uploads where uploads.uploadable_id in (5467) and uploads.uploadable_type = App\Models\Product and uploads.deleted_at is null)"

So it seems that the function is not even working.


Solution

  • This is the code that ended up working.

    In Product model:

    public function documents()
        {
            return $this->morphMany(Upload::class, 'uploadable', 'kind', 'item_id');
        }
    

    In Upload model:

    public function uploadable()
        {
            return $this->morphTo('uploadable', 'id', 'kind');
        }
    

    It seems perhaps that this is a bug?