仓库模式是Eric Evans在其“ 领域驱动的设计”书中首次引入的。 实际上,存储库是应用程序访问域层的入口点。
简而言之,存储库允许您的所有代码使用对象,而不必知道对象的持久性。 该存储库包含所有持久性知识,包括从表到对象的映射。 这提供了持久层的更面向对象的视图,并使映射代码更加封装。
使您的存储库在Laravel中工作的唯一方法(作为真正的存储库-Eric Evans域驱动设计书)是将默认ORM从活动记录更改为数据映射器。 最好的替代品是主义 。
原则ORM
Doctrine是一种ORM(对象关系映射),它实现了数据映射器模式,并允许您将应用程序的业务规则与数据库的持久层完全分开。 教义使用DQL,而不是SQL。 DQL为您带来了对象查询语言,这意味着您将拥有对象术语的查询,而不是传统的关系查询术语。
它允许您以面向对象的方式编写数据库查询,并在需要以默认存储库方法无法实现的方式查询数据库时提供帮助。 我认为,DQL是与数据库保持联系的最强大方法。
教义与口才
原则实体只是普通的PHP简单类,不会给任何ORM继承增加开销。 Doctrine无需继承数据库即可管理具有相同继承的多个查询请求,这意味着整个请求都存在实体对象。
Doctrine的另一个不错的功能是,无需迁移文件来创建数据库模式,而是自动创建数据库以在实体注释中反映元数据。 另一方面,Eloquent不太复杂,并且非常易于使用。
要对这两者进行完整的比较,就需要另外写一篇文章。 如您所见,“教义”对象更轻,更抽象。 但是,Doctrine仅适合特定项目,因此有时可能会给您带来开销。 我相信这取决于程序员为应用程序选择最佳的ORM。
博客应用
现在是时候使用Laravel创建博客应用了。 首先,我们需要建立学说。 有一个桥可以与Laravel 5的现有配置匹配。 要在Laravel项目中安装Doctrine 2,我们运行以下命令:
composer require laravel-doctrine/orm
与往常一样,应将包作为服务提供者添加到app/config.php
:
LaravelDoctrine\ORM\DoctrineServiceProvider::class,
别名也应配置:
'EntityManager' => LaravelDoctrine\ORM\Facades\EntityManager::class
最后,我们发布带有以下内容的软件包配置:
php artisan vendor:publish --tag="config"
现在我们在这里完成了。
实体是应用程序App\Entities\Post.php
重要组成部分:
namespace App\Entity;
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity
* @ORM\Table(name="posts")
* @ORM\HasLifecycleCallbacks()
*/
class Post
{
/**
* @var integer $id
* @ORM\Column(name="id", type="integer", unique=true, nullable=false)
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*
*/
private $id;
/**
* @ORM\Column(type="string")
*/
private $title;
/**
* @ORM\Column(type="text")
*/
private $body;
public function __construct($input)
{
$this->setTitle($input['title']);
$this->setBody($input['body']);
}
public function setId($id)
{
return $this->id=$id;
}
public function getId()
{
return $this->id;
}
public function getTitle()
{
return $this->title;
}
public function setTitle($title)
{
$this->title = $title;
}
public function getBody()
{
return $this->body;
}
public function setBody($body)
{
$this->body = $body;
}
}
现在是时候创建存储库了 ,前面已经介绍过。 App/Repositories/PostRepo.php
:
namespace App\Repository;
use App\Entity\Post;
use Doctrine\ORM\EntityManager;
class PostRepo
{
/**
* @var string
*/
private $class = 'App\Entity\Post';
/**
* @var EntityManager
*/
private $em;
public function __construct(EntityManager $em)
{
$this->em = $em;
}
public function create(Post $post)
{
$this->em->persist($post);
$this->em->flush();
}
public function update(Post $post, $data)
{
$post->setTitle($data['title']);
$post->setBody($data['body']);
$this->em->persist($post);
$this->em->flush();
}
public function PostOfId($id)
{
return $this->em->getRepository($this->class)->findOneBy([
'id' => $id
]);
}
public function delete(Post $post)
{
$this->em->remove($post);
$this->em->flush();
}
/**
* create Post
* @return Post
*/
private function perpareData($data)
{
return new Post($data);
}
}
控制器: App/Http/Controllers/PostController.php
:
namespace App\Http\Controllers;
use App\Repository\PostRepo as repo;
use App\Validation\PostValidator;
class PostController extends Controller
{
private $repo;
public function __construct(repo $repo)
{
$this->repo = $repo;
}
public function edit($id=NULL)
{
return View('admin.edit')->with(['data' => $this->repo->postOfId($id)]);
}
public function editPost()
{
$all = Input::all();
$validate = PostValidator::validate($all);
if (!$validate->passes()) {
return redirect()->back()->withInput()->withErrors($validate);
}
$Id = $this->repo->postOfId($all['id']);
if (!is_null($Id)) {
$this->repo->update($Id, $all);
Session::flash('msg', 'edit success');
} else {
$this->repo->create($this->repo->perpare_data($all));
Session::flash('msg', 'add success');
}
return redirect()->back();
}
public function retrieve()
{
return View('admin.index')->with(['Data' => $this->repo->retrieve()]);
}
public function delete()
{
$id = Input::get('id');
$data = $this->repo->postOfId($id);
if (!is_null($data)) {
$this->repo->delete($data);
Session::flash('msg', 'operation Success');
return redirect()->back();
} else {
return redirect()->back()->withErrors('operationFails');
}
}
}
如您所见,我已经使用Flash帮助程序来管理消息(可以使用Laravel的消息)。 关于验证器,我应该补充说,您可以根据自己的喜好创建自己的(或我这样做)或使用Laravel默认值。
查看文件与平常相同。 在此示例视图中,该文件看起来像resources/views/admin/edit.blade.php
:
@if (Session::has('flash_notification.message'))
{!! Session::get('flash_notification.message') !!}
@endif
@if($errors->has())
@foreach ($errors->all() as $error)
- {!! $error !!}
@endforeach
@endif
</div>
</div>
路由和其他操作将照常进行。
结论
现在,您将了解如何在Laravel 5.0中轻松创建基于Doctrine的存储库,这将带来许多好处。
对于那些刚刚开始使用Laravel或希望通过扩展来扩展您的知识,网站或应用程序的人,我们可以在Envato Market中进行很多研究。
翻译自: https://code.tutsplus.com/tutorials/the-repository-pattern-in-laravel-5--cms-25464