【问题标题】:Eager loading returning ID instead of model渴望加载返回 ID 而不是模型
【发布时间】:2016-02-13 01:59:57
【问题描述】:

我在使用以下代码时遇到了急切加载问题。

问题在于状态模型

$ticket = Ticket::where('id', $id)->with(['customer', 'status', 'notes' => function($query) {
    $query->orderBy('updated_at', 'desc');
}])->first();

如果我这样做,

return response()->json($ticket);

我得到了预期的响应,一切正常

{"id":1,"customer_id":10001,"ztk_ticket_no":"ZTK0000001","status":{"id":1,"value":"Open","deleted_at":null,"created_at":"2016-02-13 01:36:20","updated_at":"2016-02-13 01:36:20"},"deleted_at":null,"created_at":"2016-02-13 01:36:20","updated_at":"2016-02-13 01:36:20","customer":{"id":1,"customer_id":10001,"title":"Test Company","deleted_at":null,"created_at":"2016-02-13 01:36:20","updated_at":"2016-02-13 01:36:20"},"notes":[{"id":1,"ticket_id":1,"note":"Lorem ipsum dolor sit amet, ","status":1,"deleted_at":null,"created_at":"2016-02-13 01:36:20","updated_at":"2016-02-13 01:36:20"}]}

如果我这样做了

return response()->json($ticket->status);

我得到的是状态的 id,而不是模型

1

状态模型:

class Status extends Model
{
    protected $table = 'statuses';
}

票种:

class Ticket extends Model
{
    public function status() {
        return $this->hasOne('App\Status', 'id', 'status');
    }
}

【问题讨论】:

  • 试试:$ticket->status()->get();
  • 哦,这行得通,谢谢。知道为什么我必须这样做吗?

标签: php laravel eloquent eager-loading eager


【解决方案1】:

根据您的关系定义,您的Ticket 模型似乎有一个名为status 的字段。如果您的模型上有一个与您的关系方法之一同名的字段名称,当您执行$ticket->status 时,您将获得字段的值,而不是相关对象。

因此,根据我所见,您的 tickets.status 字段似乎是 statuses 表的外键。如果是这种情况,那么就会有一些问题。

首先,您的status 字段应重命名为status_id。这将有助于消除字段名称和相关对象之间的歧义。

其次,由于您的 Ticket 模型包含外键,它位于关系的 belongsTo 一侧。听起来可能有点奇怪,但一个Status 可以有多个Tickets,但一个Ticket 属于一个Status。因此,您需要将您的status() 关系从hasOne 更改为belongsTo

如果将status 字段重命名为status_id,则可以将方法更改为:

public function status() {
    return $this->belongsTo('App\Status');
}

这样,您可以使用$ticket->status_id 访问id 字段,并使用$ticket->status 访问相关的Status 对象。

如果您无法更改 status 字段,那么最好重命名您的 status() 关系方法,因此您的方法应如下所示:

// relationship method renamed
public function relatedStatus() {
    // second parameter required since foreign key does not conform to Laravel conventions
    return $this->belongsTo('App\Status', 'status');
}

这样,您可以使用$ticket->status 访问id 字段,使用$ticket->relatedStatus 访问相关的状态对象。

【讨论】:

    【解决方案2】:

    将您的代码更改为

    $ticket->status()->get();
    

    这将返回对象。

     $ticket->status;
    

    这个只会返回原始ID。

    【讨论】:

    • 这是因为我的列名与模型相同吗?状态?
    • 不,默认情况下您调用的只是模型ID。为了将模型对象作为一个集合获取,您可以在关系上调用 get 函数。
    • 如果我调用 $ticket->customer 怎么会工作,然后我得到模型?
    • @JilsonThomas $ticket->status 只会在 Ticket 模型除了一个名为 status() 的关系之外还有一个名为 status 的字段时返回原始 ID。
    猜你喜欢
    • 2021-09-08
    • 2012-06-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-05-06
    • 1970-01-01
    相关资源
    最近更新 更多