2017-12-04 13 views
1

2つのモデル間の関係を設定する方法があるので、hasMany関係をロードするときにbelongsTo関係が自動的に呼び出し元/親に設定されますか?Laravelで2ウェイ関係を作る方法

製品のセーブ・トリガーを使用して注文の新しいコピーをロードしたときに、各製品の新しいコピーを使用して、忘れてしまう問題に遭遇しました。 オーダーに100個の製品があり、オーダー - >製品 - >オーダー - >製品をループしようとすると、合計10100個の製品で101個のオーダーがロードされました。

解決方法の1つは、setRelation()を使用してコントローラのループ内でbelongsTo関係を設定することでした。

モデルからその関係を設定する方法があれば、私は好きです。

<?php 
class Order extends Model { 
    public function products() { 
     return $this->hasMany(Product::class); 
    } 

    public function updateTotals() { 
     foreach ($this->products as $product) { 
      // code 
     } 
     $this->save(); 
    } 
} 

class Product extends Model { 
    public function order() { 
     return $this->belongsTo(Order::class); 
    } 

    public static function boot() { 
     parent::boot(); 
     static::updated(function (Product $product) { 
      $product->order->updateTotals(); 
     }); 
    } 
} 

class OrderController extends Controller { 
    public function postView(UserOrderSaveRequest $request) { 
     $order = $request->getOrder(); 
     foreach ($order->products as $product) { 
      $product->setRelation('order', $order); 
      // code 
      $product->save(); 
     } 
    } 
} 

アップデート1: 私は答えをテストするために使用されるテスト

// tinker function to fetch the first order 
$o = Order(); 

// load 2 products 
$o->products[0]; 
$o->products[1]; 

// Set relation 
$o->products[0]->setRelation('order', $o); 
$o->products[1]->setRelation('order', $o); 

// load 2 products orders 
$o->products[0]->order; 
$o->products[1]->order; 

// Test 1 (true if setRelation was used) 
// (false in @Bilal Maqsood answer) 
$o === $o->products[0]->order; 

// Test 2 (true if setRelation was used) 
// (true in @Bilal Maqsood answer) 
$o->products[1]->order === $o->products[0]->order; 

// Test 3 (false?) 
$o->products[1]->order->products[0] === $o->products[0]->order->prodcuts[0] 
+0

あなたは多対多の関係について話していますか? –

+0

1対多の、hasMany()とbetlongsTo()を使用したもう片方はありません –

+0

$ order-> products-> orderは$ orderと同じオブジェクトで、メモリ内の別のコピーではありません。メモリ指数を食べる –

答えて

1

class Product extends Model { 

    protected $with = ['order']; 

    public function order() { 
     return $this->belongsTo(Order::class); 
    } 

} 

のようなあなたが製品モデルコード$withプロパティの負荷更新のために定義された関係製品の各レコード。

+1

"with"を追加すると、メモリ内の注文コピーの数が101から2に減少します。さらに、setRelation()バージョンでは1つしか得られませんが、より良いものになります。 –

関連する問題