如何使用 Eloquent 保存 OneToMany 关系

Posted

技术标签:

【中文标题】如何使用 Eloquent 保存 OneToMany 关系【英文标题】:How to Save OneToMany relationship with Eloquent 【发布时间】:2019-05-12 06:29:49 【问题描述】:

我是 Laravel 堆栈的新手,目前正在使用 Lumen 和 Eloquent 开发一个 API。我需要将Order 模型与其OrderLines 一起保存。但是,它没有通过。你能告诉我怎么做吗?

以下是我的模型和控制器设置:

class Order extends Model 
    public function orderLines() 
       return $this->hasMany('App\OrderLine')
    


class OrderLine extends Model 
    .....


//inside OrdersController method I'm trying to save Order with Order lines received from JSON body

public function create(Request $request)

    $orderData = $this->validate($request, [
        'store' => 'required',
         ......
        'order_status' => 'bail|required|max:20',
        'delivery_date' => 'nullable|date',
        'customer_id' => 'nullable|numeric',
        'order_lines.*.product_id' => 'bail|required|numeric',
        'order_lines.*.description' => 'bail|required|max:80',
        'order_lines.*.unit_price' => 'bail|required|numeric',
        'order_lines.*.discount' => 'bail|required|numeric',
        'order_lines.*']);


    $order = new Order($orderData);

    $order->push(); // This does not save and gives me an error
    $order->refresh();
    return response()->json($order);

 

//This is the json body provided in the request

    "store" : "Some Store",
    ...
    "order_lines" : [
                "product_id": 1,
                "description": "TU001: Polka dots",
                "unit_price": 1000,
                "discount": 100,
                "units": 2
    ,
    
                "product_id": 2,
                "description": "TU002: Polka dots",
                "unit_price": 500,
                "discount": 0,
                "units": 1
    ]

当我尝试使用save 方法单独保存订单而不使用订单行时,它可以工作。但是OrderLines 失败了。

有人可以告诉我如何做到这一点。我曾经在 Cakephp 中这样做,但不确定在 Eloquent 中是如何完成的。

//编辑更多信息 在生成的插入 sql 查询中,我看到 orderLines 作为 Order 表中的一列。因为它给出了一个数组到字符串的转换错误。但实际上orderLines 的插入应该在单独的sql 查询中。

【问题讨论】:

'$order = Order::find(1); $order->orderLine()->create($data);' - 你尝试过类似的方法吗?我不确定单行是否可以满足您的要求。 @user3402600 是的,它没有用。 【参考方案1】:
public function create(Request $request)

    $this->validate($request, [
        'store' => 'required',
         ......
        'order_status' => 'bail|required|max:20',
        'delivery_date' => 'nullable|date',
        'customer_id' => 'nullable|numeric',
        'order_lines.*.product_id' => 'bail|required|numeric',
        'order_lines.*.description' => 'bail|required|max:80',
        'order_lines.*.unit_price' => 'bail|required|numeric',
        'order_lines.*.discount' => 'bail|required|numeric',
        'order_lines.*'
    ]);

    $order = new Order($request->except('order_lines'));
    $order->save();

    $order->orderLines()->createMany($request->input('order_lines'));

    $order->load('order_lines'); //not sure that you need this line

    return $order;

【讨论】:

"Lumen 不支持表单请求。如果你想使用表单请求,你应该使用完整的 Laravel 框架。"link 没问题,可以使用验证方法代替请求类。 是的,与 CakePHP 或 JPA 不同,Eloquent 无法一次性持久化相关模型。我必须在事务中调用多个 save 方法才能获得所需的结果。

以上是关于如何使用 Eloquent 保存 OneToMany 关系的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 Laravel Eloquent 在数据库中保存 JSON 响应,我收到错误“数组到字符串转换”

如何在没有 Laravel 尝试将其保存到数据库的情况下在 Eloquent 模型中使用受保护的属性

如何在 laravel eloquent 中保存布尔值

如何在 eloquent 中执行依赖于表的最后一行的更新和保存操作?

带有 Eloquent 的 Laravel 不会在数据库中保存模型属性

Payum - Laravel 4 的包。如何使用 Eloquent 而不是 FilesystemStorage 创建模型数据?