文档章节

From Apprentice To Artisan 翻译 02

zgldh
 zgldh
发布于 2014/08/22 14:09
字数 1391
阅读 5501
收藏 2

上一篇

Taking It Further 更进一步

Let's consider another example to solidify our understanding. Perhaps we want to notify customers of charges to their account. We'll define two interfaces, or contracts. These contracts will gie us the flexibility to change out their implementations later.

让我们考虑另一个例子来巩固理解。 可能我们想要去提醒用户该交钱了。 我们会定义两个接口, 或者约定。这些约定使我们在更改实际实现时更加灵活。

<!-- lang: php -->
interface BillerInterface {
    public function bill(array $user, $amount);
}

interface BillingNotifierInterface {
    public function notify(array $user, $amount);
}

Next we'll build an implementation of our BillerInterface contract:

接下来我们要写一个BillerInterface的实现:

<!-- lang:php -->
class StripeBiller implements BillerInterface{
    public function __construct(BillingNotifierInterface $notifier)
    {
        $this->notifier = $notifier;
    }
    public function bill(array $user, $amount)
    {
        // Bill the user via Stripe...
        $this->notifier->notify($user, $amount);
    }

By separating the responsibilities of each class, we're now able to easily inject various notifier implementations into our billing class. For example, we could inject a SmsNotifier or an EmailNotifier. Our biller is no longer concerned with the implementation of notifyingg, but only the contract. As long as a class abides by its contract (interface), the biller will gladly accept it. Furthermore, not only do we get added flexibility, we can now test our biller in isolation from our notifiers by injecting a mock BillingNotifierInterface.

只要遵守了每个类的责任划分,我们很容易将不同的提示器(notifier)注入到账单类里面。 比如,我们可以注入一个SmsNotifier或者EmailNotifier。账单类只要遵守了约定,就不用再考虑如何实现提示功能。只要是遵守约定(接口)的类, 账单类都能用。这不仅仅是方便了我们的开发,而且我们还可以通过模拟BillingNotifierInterface来进行无痛测试。

Be The Interface 使用接口

While writing interfaces might seem to a lot of extra work, they can actually make your development more rapid. Use interfaces to mock and test the entire back-end of your application before writing a single line of implementation!

写接口可能看上去挺麻烦,但实际上能加速你的开发。你不用实现任何接口,就能使用模拟库来模拟你的接口,进而测试整个后台逻辑!

So, how do we do dependency injection? It's simple:

那我们如何依赖注入呢?很简单:

<!-- lang:php -->
$biller = new StripeBiller(new SmsNotifier);

That's dependency injection. Instead of the biller being concerned with notifying users, we simply pass it a notifier. A change this simple can do amazing things for your applications. Your code immediately becomes more maintainable since class responsibilities are clearly delineated. Also, testability will skyrocket as you can easily inject mock dependencies to isolate the code under test.

这就是依赖注入。 biller不需再考虑提醒用户的事儿,我们直接传给他一个提示器(notifier)。 这种微小的改动能使你的应用焕然一新。 你的代码马上就变得更容易维护, 因为明确指定了类的职责边界。 并且更容易测试, 你只需使用模拟依赖即可。

But what about IoC containers? Aren't they necessary to do dependency injection? Absolutely not! As we'll see in the following chapters, containers make dependency injection easier to manage, but they are not a requirement. By following the principles in this chapter, you can practice dependency injection in any of your projects, regardless of whether a container is avaliable to you.

那IoC容器呢? 难道依赖注入不需要IoC容器么?当然不需要!在接下来的章节里面你会了解到,容器使得依赖注入更易于管理,但是容器不是依赖注入所必须的。只要遵循本章提出的原则, 你可以在你任何的项目里面实施依赖注入,而不必管该项目是否使用了容器。

Too Much Java? 太像Java了?

A common criticism of use of interfaces in PHP is that it makes your code too much like "Java". What people mean is that it makes the code very verbose. You must define an interface and an implementation, which leads to a few extra key-strokes.

有人会说使用接口让PHP代码看上去太像Java了——即代码太罗嗦了——你必须定义接口然后实现它,要多按好多下键盘。

For small, simple applications, this criticism is probably valid. Interfaces are often unnecessary in these applications, and it is "OK" to just couple yourself to an implementation you know won't change. There is no need to use interfaces if you are certain your implementation will not change. Architecture astronauts will tell you that you can "never be certain". But, let's face it, sometimes you are.

对于小而简单的应用来说,以上说法也对。 接口通常是不必要的。将代码耦合到那些你认为不会改变的地方也是可以的。在你确信不会改变的地方就没有必要使用接口了。架构师说“不会改变的地方是不存在的”。不过话说回来,有时候的确不会改。

Interfaces are very helpful in large applications, and the extra key-strokes pale in comparison to the flexibility and testability you will gain. The ability to quickly swap implementations of a contract will "wow" your manager, and allow you to write code that easily adapts to change.

在大型应用中接口是很有帮助的。和提升的代码灵活性、可测试性比起来,多敲键盘费的功夫就微不足道了。当你迅速的切换了代码实现的时候,你的经理一定会被你的神速吓一跳的。你也可以写出更适应变化的代码。

So, in conclusion, keep in mind that this book presents a very "pure" architecture. If you need to scale it back for a small application, don't feel guilty. Remember, we're all trying to "code happy". If you're not enjoying what you're doing or you are programming out of guilt. step back and re-evaluate.

总而言之, 记住本书提倡“简单”架构。如果你在写小程序的时候无法遵守接口原则, 别觉得不好意思。 要记住做码农呢,最重要就是开心。如果你不喜欢写接口,那就先简单的写代码吧。日后再精进即可。

下一篇

© 著作权归作者所有

共有 人打赏支持
zgldh
粉丝 95
博文 35
码字总数 46344
作品 2
高级程序员
私信 提问
加载中

评论(1)

maskwang
maskwang
写的不错
From Apprentice To Artisan 翻译 20

上一篇 Dependency Inversion Principle 依赖反转原则 Introduction 介绍 We have reached our final destination in our overview of the five SOLID design principles! The final princip......

zgldh
2015/03/19
0
4
From Apprentice To Artisan 翻译 17

上一篇 Open Closed Principle 开放封闭原则 Introduction 介绍 Over the life time of an application, more time is spent adding to the existing codebase rather than constantly addi......

zgldh
2015/03/18
0
0
From Apprentice To Artisan 翻译 08

上一篇 As Organizer 作为管理工具 One of the keys to building a well architected Laravel application is learning to use service providers as an organizational tool. When you are ......

zgldh
2014/12/09
0
0
From Apprentice To Artisan 翻译 16

上一篇 Single Responsibility Principle 单一职责原则 Introduction 介绍 The "SOLID" design principles, articulated by Robert "Uncle Bob" Martin, are five principles that provide ......

zgldh
2015/03/17
0
0
From Apprentice To Artisan 翻译 10

上一篇 Application Structure 应用结构 Introduction 介绍 Where does this class belong? This question is extremely common when building applications on a framework. Many develope......

zgldh
2014/12/29
0
1

没有更多内容

加载失败,请刷新页面

加载更多

从源码入手,一文带你读懂Spring AOP面向切面编程

之前《零基础带你看Spring源码——IOC控制反转》详细讲了Spring容器的初始化和加载的原理,后面《你真的完全了解Java动态代理吗?看这篇就够了》介绍了下JDK的动态代理。 基于这两者的实现上...

公众号_Zack说码
12分钟前
1
0
maven 常用命令

mvn deploy -Dmaven.test.skip=true mvn source:jar deploy -Dmaven.test.skip=true mvn dependency:tree -Doutput=1.txt...

yzzzzzzzz
14分钟前
0
0
JavaScript之Promise对象

Promise 是异步编程的一种解决方案,比传统的解决方案——回调函数和事件——更合理和更强大。它由社区最早提出和实现,ES6 将其写进了语言标准,统一了用法,原生提供了 Promise 对象。 Pr...

前端攻城老湿
14分钟前
1
0
mysql事务,select for update,及数据的一致性处理

在MySQL的InnoDB中,预设的Tansaction isolation level 为REPEATABLE READ(可重读) 在select 的读取锁主要分为两种方式 select .... lock in share mode select ..... for update   这两...

细节探索者
16分钟前
0
0
python 将txt文件转换成excel

emmm,作为一个小白,不会的东西真的太多了,这两天好头大啊!加油坚持吧! #file_affilication = open('Affiliations.txt','r')import xlwtimport os import sysdef txt_xls(...

BellaYu
21分钟前
1
2

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部