为什么用 Contracts

最后更新于:2022-04-01 15:05:03

你可能有很多关于 contracts 的问题。如为什么要使用接口?使用接口会不会变的更复杂? 让我们用下面的标题来解释为什么要使用接口:低耦合和简单性。 低耦合 首先,看一些强耦合的缓存实现代码。如下: ~~~ <?php namespace App\Orders; class Repository { /** * The cache. */ protected $cache; /** * Create a new repository instance. * * @param \SomePackage\Cache\Memcached $cache * @return void */ public function __construct(\SomePackage\Cache\Memcached $cache) { $this->cache = $cache; } /** * Retrieve an Order by ID. * * @param int $id * @return Order */ public function find($id) { if ($this->cache->has($id)) { // } } } ~~~ 在上面的类里,代码跟缓存实现之间是强耦合。理由是它会依赖于扩展包库( package vendor )的特定缓存类。一旦这个扩展包的 API 更改了,我们的代码也要跟着改变。 同样的,如果想要将底层的缓存技术(比如 Memcached )抽换成另一种(像 Redis ),又一次的我们必须修改这个 repository 类。我们的 repository 不应该知道这么多关于谁提供了数据,或是如何提供等等细节。 比起上面的做法,我们可以改用一个简单、和扩展包无关的接口来改进代码: ~~~ <?php namespace App\Orders; use Illuminate\Contracts\Cache\Repository as Cache; class Repository { /** * Create a new repository instance. * * @param Cache $cache * @return void */ public function __construct(Cache $cache) { $this->cache = $cache; } } ~~~ 现在上面的代码没有跟任何扩展包耦合,甚至是 Laravel。既然 contracts 扩展包没有包含实现和任何依赖,你可以很简单的对任何 contract 进行实现,你可以很简单的写一个替换的实现,甚至是替换 contracts,让你可以替换缓存实现而不用修改任何用到缓存的代码。 简单性 当所有的 Laravel 服务都简洁的使用简单的接口定义,就能够很简单的决定一个服务需要提供的功能。** 可以将 contracts 视为说明框架特色的简洁文档。 除此之外,当你依赖简洁的接口,你的代码能够很简单的被了解和维护。比起搜索一个大型复杂的类里有哪些可用的方法,你有一个简单,干净的接口可以参考。
';