在 Laravel 应用中使用 Repository Design pattern 模式

🌟 入门

在本教程中,我们将向上一教程中构建的应用程序添加功能。克隆github存储库,运行composer install,npm install并连接到您的数据库。

$ mysql -uroot -p
mysql> create database laravelTaskApp;

如果您在这里有遇到问题,请查看我写过的其他文章 安装MySQL 和 initial Laravel setup. 访问 localhost:8000, 您可以看到一个异步添加和删除任务的应用程序。这意味着它将执行操作并显示最新数据,而无需刷新网页。

这是我们在上一教程中构建的任务应用程序。

🏁 仓库设计模式

在上一教程中,我们在控制器中编写了所有应用程序逻辑。另一种开发方法是将一些调用抽象到称为存储库的PHP类中。这个想法是我们可以将模型与控制器解耦,并为复杂的查询分配可读的名称。

我们将重构我们的应用程序以使用存储库模式。第一步是为app/Repositories/Repository.php.创建文件

<?php
 namespace App\Repositories;

use Illuminate\Database\Eloquent\Model;

class Repository implements RepositoryInterface
{
    // 类实例上的模型属性
    protected $model;

    // 将模型绑定到仓库的构造器
    public function __construct(Model $model)
    {
        $this->model = $model;
    }

    // 获取模型的所有实例
    public function all()
    {
        return $this->model->all();
    }

    // 在数据库中创建新记录
    public function create(array $data)
    {
        return $this->model->create($data);
    }

    // 更新数据库中的记录
    public function update(array $data, $id)
    {
        $record = $this->find($id);
        return $record->update($data);
    }

    // 从数据库中删除记录
    public functi delete($id)
    {
        return $this->model->destroy($id);
    }

    // 显示具有给定id的记录
    public function show($id)
    {
        return $this->model-findOrFail($id);
    }

    // 获取关联的模型
    public function getModel()
    {
        return $this->model;
    }

    // 设置关联的模型
    public function setModel($model)
    {
        $this->model = $model;
        return $this;
    }

    // 渴望负载数据库关系
    public function with($relations)
    {
        return $this->model->with($relations);
    }
}

该文件定义了我们的Repository类。此类的实例具有一个模型属性,我们将其绑定到一个Eloquent模型。一旦将其绑定到构造函数中,我们就可以从类方法中调用对应的方法,比如:findOrFailupdate 或者 all

implements RepositoryInterface部分不是严格必需的,但它为我们的代码增加了一层额外的结构。接口是定义类必须定义的方法的协定。在我们的例子中,界面如下所示:

<?php namespace App\Repositories;

interface RepositoryInterface
{
    public function all();

    public function create(**array** $data);

    public function update(**array** $data, $id);

    public function delete($id);

    public function show($id);
}

如果我们创建实现该接口的新仓库,我们将始终知道这些方法已经被定义。接口提供了结构,因此我们知道我们的代码需要做什么。

回到我们的 TaskController.php文件,我们实例化一个仓库并将Task模型传递给它。

<?php

namespace App\Http\Controllers;

use App\Task;
use App\Repositories\Repository;
use Illuminate\Http\Request;

class TaskController extends Controller
{
    // 我们可以从中使用存储库的空间
   protected $model;

   public function __construct(Task $task)
   {
       // 设置模型
       $this->model = new Repository($task);
   }

   public function index()
   {
       return $this->model->all();
   }

   public function store(Request $request)
   {
       $this->validate($request, [
           'body' => 'required|max:500'
       ]);

       // 创建记录并仅传递可写入的字段
       return $this->model->create($request->only($this->model->getModel()->fillable));
   }

   public function show($id)
   {
       return $this->model->show($id);
   }

   public function update(Request $request, $id)
   {
       // 更新模型并仅传递可写入字段
       $this->model->update($request->only($this->model->getModel()->fillable), $id);

       return $this->model->find($id);
   }

   public function destroy($id)
   {
       return $this->model->delete($id);
   }
}

Laravel 服务容器将自动解析我们的依赖项并将其注入到控制器实例中(docs).

至此,我们的应用程序的工作原理完全相同,但是我们的代码已重构为使用苍鹭,并且我们添加了两个API端点。

GitHub上可用源代码

本文中的所有译文仅用于学习和交流目的,转载请务必注明文章译者、出处、和本文链接
我们的翻译工作遵照 CC 协议,如果我们的工作有侵犯到您的权益,请及时联系我们。

原文地址:https://medium.com/employbl/use-the-repo...

译文地址:https://learnku.com/laravel/t/39599

本文为协同翻译文章,如您发现瑕疵请点击「改进」按钮提交优化建议
《L03 构架 API 服务器》
你将学到如 RESTFul 设计风格、PostMan 的使用、OAuth 流程,JWT 概念及使用 和 API 开发相关的进阶知识。
《G01 Go 实战入门》
从零开始带你一步步开发一个 Go 博客项目,让你在最短的时间内学会使用 Go 进行编码。项目结构很大程度上参考了 Laravel。
讨论数量: 6
MasterShu

注意啦! 审阅翻译的时候,发现代码中有加粗的标志,像下面这样的,然后,我就去追溯了下原文,发现并没有这些东西。

**use** ...
 **class** ...

烦请提交翻译和翻译的人员注意一下,我们的代码片段有自己的高亮方式,不要把这个不必要的格式加进入,影响观看。

4年前 评论
Summer

@MasterShu 提交翻译人员比较随意随意,文章格式错乱了。

也是我权限放太开了,自我检讨下。以后发布的每篇翻译我都会严格审阅。

4年前 评论
Summer

我们的作品,定义了我们!

很多时候,别人(你的老板、你的用户、你的同事)是从作品来判断你优秀与否。这里的作品不止是代码,有时候只是一篇文章一段文字。一个事物,只要是我们经手的,都应该金光闪闪。

希望与君共勉。

4年前 评论

这篇翻译文章是我提交的 这里先道个歉 我只是做了个简单的分块处理 确实没有关注排版问题(其实就是没用心) 感谢指出 @MasterShu @Summer

4年前 评论

@MasterShu @Remember @Summer 抱歉 默默检讨下。。。下次一定注意。。

4年前 评论
MasterShu

@Summer

社区大了,肯定不是一个人可以审阅的过来的,这个大佬不必自责。

@Thans @Remember

其实大家作为见习版主,有一部分也是为了积分,我也是这样,希望大家能一起维护好我们的社区。以前我也出现过类似的问题,不过正好是本人翻译的文章,所以及时纠正了。大家在每个人都在各自的环节都稍微用点儿心,社区肯定会越来越好的。

人人都参与进来,而不是机械的翻译,这个也是技术精进的过程。和大家共勉哈。不要把责任都压在管理员 Summer 身上。作为版主,这点儿责任还是要一起承担的。

4年前 评论
Thans 4年前

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!