我有两个模型
项目:
protected $fillable = [
'code',
'name',
'uom'
];
public function recipe()
{
return $this->belongsTo('App\Recipe');
}
食谱:
protected $fillable = [
'recipecode',
'itemcode',
'qty'
];
public function item()
{
return $this->hasMany('App\Item');
}
在迁移中,我有:
public function up()
{
Schema::table('recipes', function (Blueprint $table) {
$table->foreign('itemcode')->references('code')->on('items');
});
}
在RecipesController中,我有:
public function index()
{
$recipes = Recipe::all()->sortBy('recipecode');
$items = Item::all();
return view ('recipe.index', compact('recipes', 'items'));
}
我想在视图中查看配方代码,项目代码以及项目名称,项目数量等。
@foreach($recipes as $recipe)
<tr>
<td>{{ $recipe->recipecode }}</td> // this works
<td>{{ $recipe->itemcode }}</td> // this works
<td>{{ $recipe->item->name }}</td> // this doesn't work
<td>{{ $recipe->item->uom }}</td> // this doesn't work
<td>{{ $recipe->item->qty }}</td> // this doesn't work
</tr>
@endforeach
我应该怎么做才能从Items表中看到“名称”和“ uom”列?我认为关系有问题...
答案 0 :(得分:0)
首先,$recipe->item->name
不能按预期工作,因为$recipe->item
是App\Item
的集合,而不是App\Item
模型实例。那是因为您已将关系设置为“ hasMany”
第二,请阅读有关eager loading的更多信息。您现在正在做的是多个查询。这就是N + 1,对于您要查询数据库以获取项目的每个配方。您不需要这样做,因为它根本没有性能。使用Recipe::with('item')->sortBy('recipecode')->get()
。
现在,请记住,$recipe->item
不是单个项目,而是属于该食谱的项目的集合。您可能需要在表上花一点时间才能显示一份食谱的多个项目。
答案 1 :(得分:0)
由于您使用的是hasMany
,因此必须在命名函数中遵循命名约定
public function items()
{
return $this->hasMany('App\Item');
}
在RecipesController中,您可以渴望加载。
$recipes = Recipe::with('items')->sortBy('recipecode')->get();
在此处阅读文档:https://laravel.com/docs/master/eloquent-relationships
也可以在刀片中显示
@foreach($recipes as $recipe)
<tr>
<td>{{ $recipe->recipecode }}</td> // this works
<td>{{ $recipe->itemcode }}</td> // this works
@foreach($recipe->items as $item)
<td>{{ $item->name }}</td>
@endforeach
</tr>
@endforeach
答案 2 :(得分:0)
其他答案分享了为什么您不能直接使用$recipe->item
的原因。但是,我认为数据库设计中存在更大的错误。
您设计的数据库具有一对多关系。例如,一个食谱有很多项目。但是,一项只有一种配方的相反说法似乎是错误的。您可以用一项烹饪许多食谱。即你可以用鸡肉做炸鸡和咖喱鸡。
数据库设计应该是这样的,
recipes: code, name, uom
items: code, name
item_recipe: item_code, recipe_code, qty