产品类型(movie, Book)有不同的字段,最好将它们存储在数据库的哪个位置?



我使用的是Laravel Eloquent。我有一个产品表,其中的字段包括标题、描述、价格和product_type_id作为每个产品所属的类型,因此产品类型可以是"Book"或"Movie"。一个产品只能属于一种类型。

现在图书和电影产品都需要存储不同的属性,对于图书,我需要存储'作者','num_of_pages'等,对于电影,我需要存储'导演','运行时'等。

这些不是动态属性,它们对于每个类型都是固定的,所以没有自定义字段。

我可以将所有这些"属性"作为列存储在产品表上,但这将意味着大量的空字段。理想情况下,我希望将它们存储在各自的属性表中,因此book_product_properties和movie_product_properties。因此,product和movie_product_properties或books_product_properties之间将是一对一的。

如何在Eloquent中为产品和许多不同属性表之间的关系建模?

我需要能够轻松地查询所有产品并获得那里的属性。

我尝试了EAV方法,将属性存储在键/值表中,但我一直在阅读EAV,大多数帖子都说要远离它,因为它的查询速度很慢,而且是维护的噩梦。

解决方案1:

表:

Products
id - integer
type - varchar
additional_data - json

迁移:

Schema::create('products', function (Blueprint $table) {
$table->id();
$table->string('type')
$table->json('additional_data')
});

模型:

class Product extends Model
{ 
$casts = [
'additional_data' => 'array'
];
}

解决方案2:

你可以使用One To Many (Polymorphic) https://laravel.com/docs/10.x/eloquent-relationships#one-to-many-polymorphic-relations

你的表看起来像:

Books
id - integer
title - string

Movies
id - integer
title - string

Products
id - integer
productable_id - integer
productable_type - string

迁移:

Schema::create('products', function (Blueprint $table) {
$table->id();
$table->morphs('productable') // this will create 2 fields: productable_id and productable_type;
//....
});

在你的模型中:

use IlluminateDatabaseEloquentModel;
use IlluminateDatabaseEloquentRelationsMorphTo;
class Product extends Model
{
/**
* Get the parent productable model (book or movie).
*/
public function productable(): MorphTo
{
return $this->morphTo();
}
}
use IlluminateDatabaseEloquentModel;
use IlluminateDatabaseEloquentRelationsMorphMany;

class Book extends Model
{
/**
* Get all of the book's products.
*/
public function products(): MorphMany
{
return $this->morphMany(Product::class, 'productable');
}
}

use IlluminateDatabaseEloquentModel;
use IlluminateDatabaseEloquentRelationsMorphMany;

class Movie extends Model
{
/**
* Get all of the movie's products.
*/
public function products(): MorphMany
{
return $this->morphMany(Product::class, 'productable');
}
}

相关内容

  • 没有找到相关文章

最新更新