1. 程式人生 > >關聯模型(1:n)

關聯模型(1:n)

time mes 解決 可能 spa 關聯 tle 模式 this

關聯模型 (1對n)

ThinkPHP5.0 的關聯采用了對象化的操作模式,你無需繼承不同的模型類
只是把關聯定義成一個方法,並且直接通過當前模型對象的屬性名獲取定義的關聯數據。

關聯定義:一個user有多本書book

DROP TABLE IF EXISTS `think_user`;
CREATE TABLE IF NOT EXISTS `think_user` (
`id` int(6) UNSIGNED NOT NULL AUTO_INCREMENT,
`nickname` varchar(25) NOT NULL,
`name` varchar(25) NOT NULL,
`password` varchar(50) NOT NULL,
`create_time` int(11) UNSIGNED NOT NULL,
`update_time` int(11) UNSIGNED NOT NULL,
`status` tinyint(1) DEFAULT 0,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;



DROP TABLE IF EXISTS `think_book`;
CREATE TABLE IF NOT EXISTS `think_book` (
`id` int(8) UNSIGNED NOT NULL AUTO_INCREMENT,
`title` varchar(255) NOT NULL,
`publish_time` int(11) UNSIGNED DEFAULT NULL,
`create_time` int(11) UNSIGNED NOT NULL,
`update_time` int(11) UNSIGNED NOT NULL,
`status` tinyint(1) NOT NULL,
`user_id` int(6) UNSIGNED NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;

在User 模型類添加Book 關聯如下:

  • hasMany

hasMany 的參數如下:
hasMany(‘關聯模型名‘,‘關聯外鍵‘,‘關聯模型主鍵‘,‘別名定義‘)

步驟一、定義Uer模型和關聯方法book

<?php 
namespace app\index\model;
use think\Model;
class User extends Model
{
// 開啟自動寫入時間戳
protected $autoWriteTimestamp = true;
// 定義自動完成的屬性
protected $insert = [‘status‘ => 1];

    // 定義關聯hasMany
    public function books()
    {
    return $this->hasMany(‘Book‘);
    }
}

步驟二、定義book模型

<?php 
namespace app\index\model;
use think\Model;
class Book extends Model
{
protected $type = [
‘publish_time‘ => ‘timestamp:Y-m-d‘,
];
    // 開啟自動寫入時間戳
    protected $autoWriteTimestamp = true;
    // 定義自動完成的屬性
    protected $insert = [‘status‘ => 1];
}

 ?>

1. 關聯新增

添加addBook 方法用於新增關聯數據:

public function addBook()
{
$user = UserModel::get(1);
$book = new Book;
$book->title = ‘ThinkPHP5快速入門‘;
$book->publish_time = ‘2016-05-06‘;
$user->books()->save($book);
return ‘添加Book成功‘;
}

對於一對多關聯,也可以批量增加數據:

public function addBook()
{
$user = UserModel::get(1);
$books = [
[‘title‘ => ‘ThinkPHP5快速入門‘, ‘publish_time‘ => ‘2016-05-06‘],
[‘title‘ => ‘ThinkPHP5開發手冊‘, ‘publish_time‘ => ‘2016-03-06‘],
];
$user->books()->saveAll($books);
return ‘添加Book成功‘;
}

2.關聯查詢

可以直接調用模型的屬性獲取全部關聯數據,例如:

public function read()
{
$user = UserModel::get(1);
$books = $user->books;
dump($books);

一對多查詢同樣可以使用預載入查詢,例如:

public function read()
{
$user = UserModel::get(1,‘books‘);
$books = $user->books;
dump($books);
}

一對多預載入查詢會在原先延遲查詢的基礎上增加一次查詢,可以解決典型的N+1 次查詢問題。
如果要過濾查詢,可以調用關聯方法:

public function read()
{
$user = UserModel::get(1);
// 獲取狀態為1的關聯數據
$books = $user->books()->where(‘status‘,1)->select();
dump($books);
// 獲取作者寫的某本書
$book = $user->books()->getByTitle(‘ThinkPHP5快速入門‘);
dump($book);
}

還可以根據關聯數據來查詢當前模型數據,例如:

public function read()
{
// 查詢有寫過書的作者列表
$user = UserModel::has(‘books‘)->select();
// 查詢寫過三本書以上的作者
$user = UserModel::has(‘books‘, ‘>=‘, 3)->select();
// 查詢寫過ThinkPHP5快速入門的作者
$user = UserModel::hasWhere(‘books‘, [‘title‘ => ‘ThinkPHP5快速入門‘])->select();
}

3.關聯更新

public function update($id)
{
$user = UserModel::get($id);
$book = $user->books()->getByTitle(‘ThinkPHP5開發手冊‘);
$book->title = ‘ThinkPHP5快速入門‘;
$book->save();

或者使用查詢構建器的update 方法進行更新(但可能無法觸發關聯模型的事件

public function update($id)
{
$user = UserModel::get($id);
$user->books()->where(‘title‘, ‘ThinkPHP5快速入門‘)->update([‘title‘ => ‘ThinkPHP5開
發手冊‘]);
}

4. 關聯刪除

刪除部分關聯數據:

    public function delete($id){
    $user = UserModel::get($id);
    // 刪除部分關聯數據
    $book = $user->books()->getByTitle(‘ThinkPHP5開發手冊‘);
    $book->delete();
    }

刪除所有的關聯數據:

public function delete($id){
    $user = UserModel::get($id);
    if($user->delete()){
    // 刪除所有的關聯數據
    $user->books()->delete();
    }
}

關聯模型(1:n)