Laravel Eloquent - Attach VS Sync

Laravel Eloquent - Attach vs Sync

attach():

  • Insert related models when working with many-to-many relations
  • No array parameter is expected

Example:

$user = User::find(1);
$user->roles()->attach(1);

sync():

Similar to the attach() method, the sync() method is used to attach related models. However, the main differences are:

  • sync() accepts an array of IDs to place on the pivot table
  • Secondly, most important, the sync method will delete the data from the pivot table if the model does not exist in the array, and insert only the new items to the pivot table.

Example:

user_role


id user_id role_id
1 12 1
2 12 5
3 12 2
$user = User::find(12);
$user->roles()->sync(array(1, 2, 3));

The above operation will delete:


id user_id role_id
2 12 5

And insert role_id 3 to the table.

user_role table


id user_id role_id
1 12 1
3 12 2
4 12 3

Laravel Eloquent - Attach vs. SyncWithoutDetaching

Let's assume that you have auto-increment primary key id in your pivot table, you will notice:

  1. attach() will add the new records to the pivot table, and pre-existed relations will get fresh ids.
  2. sync() will remove all existed relations and set only provided in current request, with fresh ids too.
  3. syncWithoutDetaching() will not remove all existing relations missing from the one provided in current process, then the pre-existed rows won't get new ids.

Detach vs Sync In Laravel

If you are going to have all of the selected categories then it would probably be better to use sync rather than attach/detach for each.

The equivalent of `syncWithPivotValues` for `attach` method in Laravel 9

You can do something like this:

$user->roles()->attach([
1 => ['active' => true],
2 => ['active' => true],
3 => ['active' => true],
]);

Resource: https://laravel.com/docs/9.x/eloquent-relationships#updating-many-to-many-relationships

If you don't want to repeat ['active' => true] all the time, you can use array_fill_keys like this: array_fill_keys([1, 2, 3], ['active' => true]) so your code will look like:

$user->roles()->attach(array_fill_keys([1, 2, 3], ['active' => true]));

Resource: https://www.php.net/manual/en/function.array-fill-keys.php

SOLVED: Looking for a smarter way to sync and order entries in Laravel/Eloquent pivot table

You can add data to the pivot table while attaching or syncing, like so:


$mediaIds = [
1 => ['sort_order' => 'order_for_1'],
3 => ['sort_order' => 'order_for_3']
];

//[STORE]
$page->media()->attach($mediaIds;

//[UPDATE]
$page->media()->sync($mediaIds);

Laravel: save / attach / sync custom pivot model (belongsToMany)

explanation

the attach method is actually a Model function. so with your withPivot t3.t1 is not a model yet
, when you are accessing with pivot magic method from your relation belongs to many it only return the column

answers

so for your situation, withPivot t3.t1 pivot as Model instance. here the steps

  1. create new PivotModel that extends use Illuminate\Database\Eloquent\Relations\Pivot;
  2. on the your t1Model, add using($classNamespace) to the belongsToMany method, example: belongsToMany()->using(PivotModel::class)
  3. then when t1->getT2s->pivot is already returning Model instance and you can use attach function to that pivot


Related Topics



Leave a reply



Submit