在 Laravel / Lumen 中使用 With 联合

Union using With in Laravel / Lumen

我正在尝试建立一个联盟,例如:

$first = Content::selectRaw("id, title, channel_id, description")
->with('trailer')
->where('description', 'asdadadadaid');

$second = OtherTypeOfContent::selectRaw("id, title, channel_id, description")
->with('trailer')
->where('description', 'asdadadadaid');

$data = $first->union($second)->get();

对于内容,预告片关联到 table contents_trailers。对于 OtherTypeOfContent,预告片关联到 table othertypeofcontent_trailers.

当我尝试在这两个查询之间建立并集时,对于 with->('trailer'),我总是得到 contents_trailers 的值,对于第二个查询的结果也是如此。似乎只从第一个查询中获取关系。

我该如何解决这个问题?谢谢!

我认为问题是 Eloquent 没有 运行 核心查询的任何附加 with() 指令,而是选择所需的行,然后 运行 查询每个 with() 指令以获取您需要的任何其他数据。这解释了为什么使用 with() 指令在查询构建器上调用 toSQL() return 没有连接 - 它不会 运行 它们在该查询中。

因此,虽然我担心使用 with() 对您的联合不起作用,但您可以手动将联接构建到您的查询中。这就是我过去对工会所做的,这就是为什么我一开始认为 toSql() 会 return 连接。

这是一个联合示例,我已经在我的一个平台中使用了一段时间并且运行良好:

<?php

namespace App\Models;

use DB;
use Illuminate\Database\Eloquent\Model;

class Example extends Model
{
    /**
     * Unions the query contained within with the query returned from
     * buildGloballyScopedCampaignsQuery
     */
    public static function findScopedToChannelId($channel_id)
    {
        $first = static::buildGloballyScopedCampaignsQuery();

        return static::select('ac.*')
            ->from('ad_campaigns AS ac')
            ->join('ad_campaign_scopes AS acs', function ($join) use ($channel_id) {
                $join->on('ac.id', '=', 'acs.campaign_id')
                    ->where('acs.channel_id', '=', $channel_id);
            })
            ->where(function ($query) {
                $query->whereNull('ac.start_date')
                    ->orWhere('ac.start_date', '<', DB::raw('NOW()'));
            })
            ->where(function ($query) {
                $query->whereNull('ac.end_date')
                    ->orWhere('ac.end_date', '>', DB::raw('NOW()'));
            })
            ->union($first)
            ->orderBy('rank', 'DESC')
            ->get();
    }

    public static function buildGloballyScopedCampaignsQuery()
    {
        return static::select('ac.*')
            ->from('ad_campaigns AS ac')
            ->leftJoin('ad_campaign_scopes AS acs', 'ac.id', '=', 'acs.campaign_id')
            ->whereNull('acs.id')
            ->where(function ($query) {
                $query->whereNull('ac.start_date')
                    ->orWhere('ac.start_date', '<', DB::raw('NOW()'));
            })
            ->where(function ($query) {
                $query->whereNull('ac.end_date')
                    ->orWhere('ac.end_date', '>', DB::raw('NOW()'));
            });
    }
}