Forma correcta descrita en esta respuesta: https://stackoverflow.com/a/52772444/2519714
La respuesta más popular en el momento actual no es totalmente correcta.
De esta manera, https://stackoverflow.com/a/24838367/2519714 no es correcto en algunos casos, como: la selección secundaria tiene enlaces donde, luego se une la tabla a la selección secundaria, luego se agregan otros sitios a todas las consultas. Por ejemplo consulta:
select * from (select * from t1 where col1 = ?) join t2 on col1 = col2 and col3 = ? where t2.col4 = ?
Para realizar esta consulta, escribirás un código como:
$subQuery = DB::query()->from('t1')->where('t1.col1', 'val1');
$query = DB::query()->from(DB::raw('('. $subQuery->toSql() . ') AS subquery'))
->mergeBindings($subQuery->getBindings());
$query->join('t2', function(JoinClause $join) {
$join->on('subquery.col1', 't2.col2');
$join->where('t2.col3', 'val3');
})->where('t2.col4', 'val4');
Durante la ejecución de esta consulta, su método $query->getBindings()
devolverá enlaces en orden incorrecto, como ['val3', 'val1', 'val4']
en este caso, correctos ['val1', 'val3', 'val4']
para el sql sin formato descrito anteriormente.
Una forma más correcta de hacer esto:
$subQuery = DB::query()->from('t1')->where('t1.col1', 'val1');
$query = DB::query()->fromSub($subQuery, 'subquery');
$query->join('t2', function(JoinClause $join) {
$join->on('subquery.col1', 't2.col2');
$join->where('t2.col3', 'val3');
})->where('t2.col4', 'val4');
Además, los enlaces se fusionarán automática y correctamente con la nueva consulta.
belongsToMany
subselección, debe agregargetQuery()
dos veces =>$sub->getQuery()->getQuery()