staudenmeir / belongs-to-through

Laravel Eloquent BelongsToThrough relationships
MIT License
1.17k stars 91 forks source link

[Bug] withTrashed not removing the soft delete on the intermediate table #110

Closed ryanmortier closed 1 day ago

ryanmortier commented 2 days ago

Hello,

First off, thanks so much for the package.

I'm running into an issue using this and perhaps my issue is an edge case. I'm simply trying to load a belongsToThrough relationship but for some reason the query is not removing the soft delete scope.

This is my relationship WorkOrder > Equipment > Location A work order belongs to a location through the associated equipment.

WorkOrder

    public function location(): \Znck\Eloquent\Relations\BelongsToThrough
    {
        return $this->belongsToThrough(
            Location::class,
            Equipment::class,
            foreignKeyLookup: [
                Location::class => 'location_id',
                Equipment::class => 'equipment_id',
            ],
            localKeyLookup: [
                Location::class => 'id',
                Equipment::class => 'id',
            ]
        )
            ->withTrashed()
            ->withTrashed(['locations.deleted_at', 'equipment.deleted_at']);
    }

Here is the SQL generated:

SELECT
  top 1 [dbo].[locations].*
FROM
  [dbo].[locations]
  INNER JOIN [maintenance].[equipment] ON [maintenance].[equipment].[location_id] = [dbo].[locations].[id]
WHERE
  [maintenance].[equipment].[id] = '13'
  AND [maintenance].[equipment].[deleted_at] IS NULL

As you can see, the locations soft delete scope is removed but for some reason the equipment soft delete scope isn't removed. I suspect that maybe it has something to do with Equipment being both plural and singular at the same time, thus the table name is just equipment rather than equipments?

Also I saw in issue #51 that you suggested using two ->withTrashed() so that's why that is defined like that.

I also tried just doing:

->withTrashed()
->withTrashed('equipment.deleted_at');
ryanmortier commented 2 days ago

Err I managed to fix this. I tried adding the schema into the withTrashed call and that resolves my issue. I'm not sure if this is intended or not? I'll leave open until you comment.

Solution:

            ->withTrashed()
            ->withTrashed(['maintenance.equipment.deleted_at'])
staudenmeir commented 2 days ago

Hi @ryanmortier, Yeah, in this case you also need to add the schema. Is the schema part of the model's $table property?

ryanmortier commented 1 day ago

Yes, it is. I am explicitly setting the $table property on all my models. E.g. protected $table = 'maintenance.equipment';

staudenmeir commented 1 day ago

The package works with the qualified deleted_at column and that includes the schema in your case: https://github.com/staudenmeir/belongs-to-through/blob/main/src/Relations/BelongsToThrough.php#L124