Laravel Store:结账时存储物品选项的最佳方式

时间:2014-10-17 23:59:18

标签: php laravel-4 eloquent

我正在努力建立一家商店,一切都很顺利。但是我遇到了一个问题,即我无法绕过头来找到最佳选择。

我有一个项目模型:

class Item extends \Eloquent implements \Cviebrock\EloquentSluggable\SluggableInterface
{
    protected $table = 'store_items';

    public function options()
    {
        return $this->belongsToMany('\Dcn\Store\Option', 'store_items_options', 'items_id', 'options_id');
    }
}

选项模型:

class Option extends \Eloquent implements \Cviebrock\EloquentSluggable\SluggableInterface
{
    protected $table = 'store_options';

    public function values()
    {
        return $this->belongsToMany('\Dcn\Store\OptionValues', 'store_option_values', 'options_id', 'op-values_id');
    }
}

OptionValues模型:

class OptionValues extends \Eloquent
{
    protected $table = 'store_op-values';

    public function options()
    {
        return $this->belongsToMany('\Dcn\Store\Option', 'store_option_values', 'op-values_id', 'options_id');
    }
}

最后是发票模型:

class Invoice extends \Eloquent
{
    protected $table = 'store_invoices';

    public function items()
    {
        return $this->belongsToMany('\Dcn\Store\Item', 'store_invoices_items', 'invoice_id', 'item_id');
    }
}

当用户结账时,我目前创建发票并附上商品,但我需要能够存储发票中每件商品的选项(颜色,尺寸等)。

我只是不确定在发票中存储项目选项的值的最佳方法是什么,因为用户可能有多个只是不同颜色的项目。任何意见都将不胜感激。

1 个答案:

答案 0 :(得分:1)

一种可能的解决方案涉及以下模型/表格/关系:

发票

与InvoiceItems的一对多关系。

Invoice->hasMany('InvoiceItem')


InvoiceItem

此模型包含每张发票的订单项,其中invoice_id(外键)将InvoiceItem与Invoice相关联,item_id将InvoiceItem与您的广告资源中的商品相关联。 (其他订单详细信息也将存储在此处,例如商品数量等)

InvoiceItem->belongsTo('Invoice')

InvoiceItem->belongsTo('Item')

然后,为了存储为每个InvoiceItem选择的选项及其值,与InvoiceItemOption存在一对多的关系。

InvoiceItem->hasMany('InvoiceItemOption')


InvoiceItemOption

对于每个InvoiceItem(由invoice_item_id链接),此模型存储0,1或更多选项(通过option_id从选项模型链接)和该选项的值(从值模型链接到value_id)。

InvoiceItemOption->belongsTo('InvoiceItem')

InvoiceItemOption->belongsTo('Option')

InvoiceItemOption->belongsTo('Value')


物品

这包含您的商品清单,即您的库存。它与InvoiceItem具有一对多关系(即每个Item可以出现在许多InvoiceItem上,每个InvoiceItem都有一个Item)。每个项目还有0,1或更多可用选项,因此它通过与选项的多对多关系链接。

Item->hasMany('InvoiceItem')

Item->belongsToMany('Option')


item_option

这是一个数据透视表,将每个项目与其可用选项相关联(item_idoption_id


方法

所有项目的所有可用选项。每个选项都有一个或多个可能的值,并通过与值

的多对多关系链接

Option->belongsToMany('Item')

Option->belongsToMany('Value')


请将option_value

这是一个数据透视表,将每个选项与其可用值相关联(option_idvalue_id)。


所有选项的所有可用值。

Value->belongsToMany('Option')


对于每个关系,我也定义了反向关系,这将为您提供最大的灵活性。但是,根据您的需要,其中一些反向关系可能是不必要的。


还有另外两种选择,我认为这两种选择都不错:

您可以通过多对多关系链接发票和商品(如您所做),并将发票订单项信息存储在中间invoice_item数据透视表中。但是,要执行此操作,您需要创建自定义数据透视表模型(而不是简单的数据透视表),因为该模型需要具有hasMany('InvoiceItemOption')关系来存储选定的选项和值。这会在一定程度上限制您与InvoiceItem模型交互的灵活性,并且这种方法无法获得任何好处。

(但是,如果您对如何设置此类自定义透视模型的一个很好的示例感兴趣,请参阅https://github.com/laravel/framework/issues/2093#issuecomment-39154456。)

第三个甚至是不太理想的选项是通过多对多关系链接发票和项目,并将序列化形式的选项和值存储在中间invoice_item数据透视表中,以及任何其他顺序细节如数量。为此,您需要在定义发票关系时指定额外字段:

$this->belongsToMany('Items')->withPivot('quantity', 'options_serialized')->withTimestamps();

这种方法非常不灵活,但是例如,对包含超大绿色衬衫的订单运行查询会很麻烦。