Eloquent ORM 实例教程 —— 模型创建、更新及批量赋值

guide-to-eloquent-orm

1、创建模型

1.1 使用save方法创建模型

调用Eloquent模型类的save方法即可创建模型并插入数据到数据库:

$post = new Post;
$post->title = 'test 4';
$post->content = 'test content';
$post->user_id = 1;
$post->cat_id = 1;
if($post->save()){
    echo '添加文章成功!';
}else{
    echo '添加文章失败!';
}

在浏览器中访问http://laravel.app:8000/test,如果输出内容为:

添加文章成功!

则表明插入成功,我们去数据库查看数据,确实新增了一条记录:

使用save创建模型

1.2 使用create方法插入数据

除此之外还可以使用create方法插入数据,由于该方法中用到了批量赋值(Mass Assignment),所以我们需要在模型类中设置$fillable属性或者$guarded属性,以表明哪些属性可以通过该方法设置,哪些不可以。

开始之前,我们先解释下什么是批量赋值,以及为什么要使用批量赋值

批量赋值的英文名称是Mass Assignment,所谓的批量赋值是指当我们将一个数组发送到模型类用于创建新的模型实例的时候(通常是表单请求数据),我们可以简单通过如下方式实现:

$post = Post::create(Input::all());

而不是像使用save方法那样一个一个的设置属性值,如果模型属性很多的话,使用save简直是噩梦有木有。

但事物总是相对的,使用批量赋值是很方便,但同时也带来了安全隐患,很多时候模型类的某些属性值不是我们所期望通过批量赋值修改的,比如用户模型有个user_type属性,如果用户通过请求数据将其类型修改为管理员类型,这显然是不允许的,正是基于这一考虑,Eloquent模型类为我们提供了$fillable属性和$guarded属性,我们可以将其分别看作“白名单”和“黑名单”,定义在$fillable中的属性可以通过批量赋值进行赋值,而定义在$guarded中的属性在批量赋值时会被过滤掉。

那么如果我们确实想要修改定义在$guarded中的属性怎么办?答案是使用save方法。

此外需要注意的是$fillable$guarded方法同时只能定义一个,原因嘛很简单,非黑即白,定义了一个另外一个也就确定了。

可见批量赋值不仅为我们创建模型提供了便利,还避免了安全隐患,提高了系统的安全性。

下面我们来演示一下批量赋值的使用。首先在Post模型中定义$guarded属性如下:

protected $guarded = ['views','user_id','updated_at','created_at'];

然后在控制器中实现创建模型实例的逻辑:

$input = [
    'title'=>'test 5',
    'content'=>'test content',
    'cat_id'=>1,
    'views'=>100,
    'user_id'=>2
];
$post = Post::create($input);
dd($post);

在浏览器中输入http://laravel.app:8000/test,则页面输出:

使用批量赋值创建模型

可见user_idviews字段都没有插入进去,这正是$guarded发挥了作用,如果要设置这两个值也很简单:

$input = [
    'title'=>'test 5',
    'content'=>'test content',
    'cat_id'=>1,
    'views'=>100,
    'user_id'=>2
];
$post = Post::create($input);
$post->user_id = 2;
$post->views = 100;
$post->save();
dd($post);

对应输出如下:

使用save方法保存$guarded数据

1.3 其他插入数据的方法

Eloquent模型类还支持其它插入数据的方法——firstOrCreatefirstOrNew,两者都是先通过通过传入属性值在数据库中查找匹配记录,如果没有找到则创建一个新的模型实例,不同之处在于后者不会将数据持久化到数据库,需要调用save方法才行。

2、更新模型

2.1 使用save方法更新模型

save方法还可以用于更新模型,要更新模型数据,先要获取该模型实例,然后修改模型属性,再调用save方法保存即可:

$post = Post::find(1);
$post->title = 'test 1 title';
if($post->save()){
    echo '更新文章成功!';
}else{
    echo '更新文章失败!';
}

在浏览器中访问http://laravel.app:8000/test,如果显示:

更新文章成功!

则表明数据库对应表记录更新成功:

使用update方法更新模型

2.2 使用update方法更新数据

create相对应的,Eloquent模型类还支持使用update方法更新数据,同样要用到批量赋值:

$input = [
    'title'=>'test 6 title',
    'content'=>'test content 6',
    'cat_id'=>1,
    'views'=>200,
    'user_id'=>1
];
$post = Post::find(6);
if($post->update($input)){
    echo '更新文章成功!';
    dd($post);
}else{
    echo '更新文章失败!';
}

对应输出为:

使用update更新模型

可见user_idviews并没有更新。

学院君

学院君 has written 548 articles

资深PHP工程师,Laravel学院院长