Laravel中tosql()是如何返回sql
前言
1. laravel version 5.5
2. 关键字sql解析的代码,我就不上了。有兴趣的童鞋,可以去Illuminate\Database\Query\Grammars\Grammar观望,我也就简单说下,Laravel的主体思路。
源码
首先找到tosql()方法所在的位置,Illuminate\Database\Query\Builder:
/**
* Get the SQL representation of the query.
*
* @return string
*/
public function toSql()
{
return $this->grammar->compileSelect($this);
}
接着,去 Illuminate\Database\Query\Grammars\Grammar
/** * The components that make up a select clause. * 关键字数组,用于下面的根据对应关键字拼接对应方法 * @var array */ protected $selectComponents = [ 'aggregate', 'columns', 'from', 'joins', 'wheres', 'groups', 'havings', 'orders', 'limit', 'offset', 'unions', 'lock', ];
/**
* Compile a select query into SQL.
*
* @param \Illuminate\Database\Query\Builder $query
* @return string
*/
public function compileSelect(Builder $query)
{
// If the query does not have any columns set, we'll set the columns to the
// * character to just get all of the columns from the database. Then we
// can build the query and concatenate all the pieces together as one.
$original = $query->columns;
if (is_null($query->columns)) {
$query->columns = ['*'];
}
// To compile the query, we'll spin through each component of the query and
// see if that component exists. If it does we'll just call the compiler
// function for the component which is responsible for making the SQL.
// 然鹅,最主体的方法就在这里。
$sql = trim($this->concatenate(
$this->compileComponents($query))
);
$query->columns = $original;
return $sql;
}
/**
* Concatenate an array of segments, removing empties.
*
* @param array $segments
* @return string
*/
protected function concatenate($segments)
{
// 将空值过滤,并且转换为一个字符串,返回。(也就是最终返回的sql)
return implode(' ', array_filter($segments, function ($value) {
return (string) $value !== '';
}));
}
/**
* Compile the components necessary for a select clause.
*
* @param \Illuminate\Database\Query\Builder $query
* @return array
*/
protected function compileComponents(Builder $query)
{
$sql = [];
// laravel 会根据sql的关键字,for循环出一个sql数组
foreach ($this->selectComponents as $component) {
// To compile the query, we'll spin through each component of the query and
// see if that component exists. If it does we'll just call the compiler
// function for the component which is responsible for making the SQL.
if (! is_null($query->$component)) {
$method = 'compile'.ucfirst($component);
$sql[$component] = $this->$method($query, $query->$component);
}
}
return $sql;
}
总结
我个人也就是,简略的通过表象的源码分析下laravle的toSql()如何返回sql而已,尚未研究更为深透。
为什么开个博文来记录呢?因为,最近一直在看laravel的源码,觉得这种思想真的很新颖!!!
共勉~~~