从原始查询

时间:2016-08-22 10:50:19

标签: php mysql laravel-5 eloquent query-builder

我正在使用Laravel 5,我有一个用户表,两个表'客户'和'雇员',其中包含用户之间的关系。

我想获得登录用户的所有客户和员工。

我有一个原始查询,可以正常工作:

select users.* from clients, users
where clients.id_marchand = 8 and users.id = clients.id_client 
union 
select users.* from employes, users 
where employes.id_marchand = 8 and users.id = employes.id_employe 
order by `seen` asc, `created_at` desc limit 25 offset 0

原始查询返回一个数组,但我需要得到一个Eloquent Collection,如:

return $this->model
->where(...)
->oldest('seen')
->latest()
->paginate($n);

我尝试了很多不同的可能性,但没有一个可以工作......

用子查询或其他方法没有办法做到这一点吗?

4 个答案:

答案 0 :(得分:0)

我试过这个:

return DB::select(DB::raw('select users.* from clients, users where clients.id_marchand = 8 and users.id = clients.id_client union select users.* from employes, users where employes.id_marchand = 8 and users.id = employes.id_employe order by `seen` asc, `created_at` desc limit 25 offset 0'), [1]);

但在UserController.php中,我有:

public function indexSort($role)
{
    $counts = $this->user_gestion->counts();
    $users = $this->user_gestion->index(25, $role);
    $links = $users->render();
    $roles = $this->role_gestion->all();

    return view('back.users.index', compact('users', 'links', 'counts', 'roles'));      
}

Laravel告诉我,我无法申请'渲染'数组的方法......

所以我认为我需要获得一个Eloquent Collection ...

我也试过这样的事情:

$liste_clients = $this->model
->with('clients')
->where('clients.id_marchand', '=', auth()->user()->id)
->where('users.id', '=', 'clients.id_client');

$liste_employes = $this->model
->with('employes')
->where('employes.id_marchand', '=', auth()->user()->id)
->where('users.id', '=', 'employes.id_employe')
->union($liste_clients);

return $liste_employes
->oldest('seen')
->latest()
->paginate($n);

但我最大的问题是我无法从带有查询构建器的多个表中进行选择。

即使加入:

$liste_clients = $this->model
->join('clients', function ($join) {
    $join->on('users.id', '=', 'clients.id_client')
    ->where('clients.id_marchand', '=', auth()->user()->id);
});

$liste_employes = $this->model
->join('employes', function ($join) {
    $join->on('users.id', '=', 'employes.id_employe')
    ->where('employes.id_marchand', '=', auth()->user()->id);
})
->union($liste_clients);

return $liste_employes
->oldest('seen')
->latest()
->paginate($n);

我收到错误消息:

  

SQLSTATE [21000]:基数违规:1222使用的SELECT语句具有不同的列数(SQL :(选择计数(*)作为users内部联接employes上的聚合{{1 } {。{1}} = usersidemployesid_employe = 8)union(select * from employes inner join {{1 } id_marchandusers = clientsusersidclients = 8)按id_client asc排序, clients desc)

在另一个论坛上,一个人告诉我只需在存储库中执行此操作:

id_marchand

然后在视图中与一些foreach一起玩,例如:

seen

但我无法得到任何结果,我也不知道为什么......

答案 1 :(得分:0)

您可以运行查询,然后使用hydrate将其填充到模型中: 例如:

$userData = DB::select('SELECT * FROM users ...');
$userModels = User::hydrate($userData);

答案 2 :(得分:0)

您可以仅使用collect()

将查询结果转换为集合
$users = \DB::select( "SELECT users.*
FROM clients,
       users
  WHERE clients.id_marchand = 8
    AND users.id = clients.id_client
  UNION
  SELECT users.*
  FROM employes,
       users
  WHERE employes.id_marchand = 8
    AND users.id = employes.id_employe
  ORDER BY `seen` ASC,
           `created_at` DESC LIMIT 25
  OFFSET 0" );

return collect( $users );

如果结果不只是模型集合,则应使用hydrate()https://laravel.com/api/5.3/Illuminate/Database/Eloquent/Model.html#method_hydrate) 对于您提供的示例,代码应如下:

$users = \DB::select( "SELECT users.*
  FROM clients,
       users
  WHERE clients.id_marchand = 8
    AND users.id = clients.id_client
  UNION
  SELECT users.*
  FROM employes,
       users
  WHERE employes.id_marchand = 8
    AND users.id = employes.id_employe
  ORDER BY `seen` ASC,
           `created_at` DESC LIMIT 25
  OFFSET 0" );

return User::hydrate($users);
  

请注意,此方法比较慢,并且对于大量数据,   如果结果太大而无法分配,则此方法可能会崩溃   公羊

答案 3 :(得分:-1)

你可以直接使用这样的原始查询:

 return DB::select(DB::raw("
    select * from table_name where column_name = :columnName
 "),['columnName'=>$columnName]);