内核更新

This commit is contained in:
2017-03-16 12:03:34 +08:00
parent b355535009
commit a4d58f9f09
28 changed files with 438 additions and 217 deletions

View File

@@ -11,18 +11,23 @@
namespace think\model\relation;
use think\Collection;
use think\db\Query;
use think\Exception;
use think\Loader;
use think\Model;
use think\model\Pivot;
use think\model\Relation;
use think\Paginator;
class BelongsToMany extends Relation
{
// 中间表模型
// 中间表表名
protected $middle;
// 中间表模型
protected $pivot;
/**
* 构造函数
* @access public
@@ -42,6 +47,64 @@ class BelongsToMany extends Relation
$this->query = (new $model)->db();
}
/**
* 设置中间表模型
* @param $pivot
* @return $this
*/
public function pivot($pivot)
{
$this->pivot = $pivot;
return $this;
}
/**
* 实例化中间表模型
* @param $data
* @return mixed
*/
protected function newPivot($data)
{
$pivot = $this->pivot ?: '\\think\\model\\Pivot';
return new $pivot($this->parent, $data, $this->middle);
}
/**
* 合成中间表模型
* @param array|Collection|Paginator $models
*/
protected function hydratePivot($models)
{
foreach ($models as $model) {
$pivot = [];
foreach ($model->getData() as $key => $val) {
if (strpos($key, '__')) {
list($name, $attr) = explode('__', $key, 2);
if ('pivot' == $name) {
$pivot[$attr] = $val;
unset($model->$key);
}
}
}
$model->pivot = $this->newPivot($pivot);
}
}
/**
* 创建关联查询Query对象
* @return Query
*/
protected function buildQuery()
{
$foreignKey = $this->foreignKey;
$localKey = $this->localKey;
$middle = $this->middle;
// 关联查询
$pk = $this->parent->getPk();
$condition['pivot.' . $localKey] = $this->parent->$pk;
return $this->belongsToManyQuery($middle, $foreignKey, $localKey, $condition);
}
/**
* 延迟获取关联数据
* @param string $subRelation 子关联名
@@ -50,32 +113,74 @@ class BelongsToMany extends Relation
*/
public function getRelation($subRelation = '', $closure = null)
{
$foreignKey = $this->foreignKey;
$localKey = $this->localKey;
$middle = $this->middle;
if ($closure) {
call_user_func_array($closure, [ & $this->query]);
}
// 关联查询
$pk = $this->parent->getPk();
$condition['pivot.' . $localKey] = $this->parent->$pk;
$result = $this->belongsToManyQuery($middle, $foreignKey, $localKey, $condition)->relation($subRelation)->select();
foreach ($result as $set) {
$pivot = [];
foreach ($set->getData() as $key => $val) {
if (strpos($key, '__')) {
list($name, $attr) = explode('__', $key, 2);
if ('pivot' == $name) {
$pivot[$attr] = $val;
unset($set->$key);
}
}
}
$set->pivot = new Pivot($pivot, $this->middle);
call_user_func_array($closure, [& $this->query]);
}
$result = $this->buildQuery()->relation($subRelation)->select();
$this->hydratePivot($result);
return $result;
}
/**
* 重载select方法
* @param null $data
* @return false|\PDOStatement|string|Collection
*/
public function select($data = null)
{
$result = $this->buildQuery()->select($data);
$this->hydratePivot($result);
return $result;
}
/**
* 重载paginate方法
* @param null $listRows
* @param bool $simple
* @param array $config
* @return Paginator
*/
public function paginate($listRows = null, $simple = false, $config = [])
{
$result = $this->buildQuery()->paginate($listRows, $simple, $config);
$this->hydratePivot($result);
return $result;
}
/**
* 重载find方法
* @param null $data
* @return array|false|\PDOStatement|string|Model
*/
public function find($data = null)
{
$result = $this->buildQuery()->find($data);
$this->hydratePivot([$result]);
return $result;
}
/**
* 查找多条记录 如果不存在则抛出异常
* @access public
* @param array|string|Query|\Closure $data
* @return array|\PDOStatement|string|Model
*/
public function selectOrFail($data = null)
{
return $this->failException(true)->select($data);
}
/**
* 查找单条记录 如果不存在则抛出异常
* @access public
* @param array|string|Query|\Closure $data
* @return array|\PDOStatement|string|Model
*/
public function findOrFail($data = null)
{
return $this->failException(true)->find($data);
}
/**
* 根据关联条件查询当前模型
* @access public
@@ -95,12 +200,27 @@ class BelongsToMany extends Relation
* @access public
* @param mixed $where 查询条件(数组或者闭包)
* @return Query
* @throws Exception
*/
public function hasWhere($where = [])
{
throw new Exception('relation not support: hasWhere');
}
/**
* 设置中间表的查询条件
* @param $field
* @param null $op
* @param null $condition
* @return $this
*/
public function wherePivot($field, $op = null, $condition = null)
{
$field = 'pivot.' . $field;
$this->query->where($field, $op, $condition);
return $this;
}
/**
* 预载入关联查询(数据集)
* @access public
@@ -230,7 +350,7 @@ class BelongsToMany extends Relation
}
}
}
$set->pivot = new Pivot($pivot, $this->middle);
$set->pivot = $this->newPivot($pivot);
$data[$pivot[$this->localKey]][] = $set;
}
return $data;
@@ -250,10 +370,14 @@ class BelongsToMany extends Relation
// 关联查询封装
$tableName = $this->query->getTable();
$relationFk = $this->query->getPk();
return $this->query->field($tableName . '.*')
->field(true, false, $table, 'pivot', 'pivot__')
->join($table . ' pivot', 'pivot.' . $foreignKey . '=' . $tableName . '.' . $relationFk)
->where($condition);
$query = $this->query->field($tableName . '.*')
->field(true, false, $table, 'pivot', 'pivot__');
if (empty($this->baseQuery)) {
$query->join($table . ' pivot', 'pivot.' . $foreignKey . '=' . $tableName . '.' . $relationFk)
->where($condition);
}
return $query;
}
/**
@@ -327,7 +451,7 @@ class BelongsToMany extends Relation
foreach ($ids as $id) {
$pivot[$this->foreignKey] = $id;
$this->query->table($this->middle)->insert($pivot, true);
$result[] = new Pivot($pivot, $this->middle);
$result[] = $this->newPivot($pivot);
}
if (count($result) == 1) {
// 返回中间表模型对象