在架构的过程中,一个系统的质量属性主要考虑的是六个方面:可用性、可修改性、性能、安全性、可测试性以及易用性。实现这些质量属性依赖于基本的设计决策——战术,而战术就是影响质量属性响应控制的设计决策。其中包含六中战术分别对应系统质量属性考虑的六个方面,这六种战术的结合被称为“架构设计策略”,我个人认为更像是架构设计时的智慧。
接下来我分别针对六种质量属性的战术来谈一谈我的看法和见解,也会提供一些相应的实例来供大家思考。
可用性战术目标:可用性战术将会阻止错误发展成故障,或者至少能够把错误的影响限制在一定范围内,从而使系统恢复成为可能。
维持可用性的战术主要有三种:错误检测、自动恢复以及错误预防。错误检测是用来检测故障的某种类型的健康监视,可以通过信号/响应、心跳、抛出异常等方式来实现。自动恢复可以检测到故障时某种类型的恢复,可以通过监测和修复或者是重新引入等方式来实现。错误预防则是为了防止错误演变成故障,可以通过从服务中删除事务或设立进程监视器等方式来实现。
一切的目的都是为了持续的维持系统的可使用状态,不因为用户的误操作或者是系统本身的问题而导致错误的扩大,尽量保证系统的鲁棒性。
实例:最常见的提高系统可用性的方式就是在编码过程中多写try/catch,如果一个不够那就多写几个,一个好的程序员往往也都会有自己的库,其中就包含一个异常库,系统如果没有按照既定的方向运行就会throw出一个Exception,这些都会写入系统的运行日志当中,根据抛出不同的异常系统会做出相应的错误处理反应,避免出现因为错误而影响全局的情况。
除非你看到问题的发生,否则你不会知道现在的系统当中存在着什么问题。通过提高系统的可用性可以保持系统可以在可接受范围内处理错误,避免错误发展成为故障从而产生更大的影响。
可修改性战术目标:控制实现、测试和部署变更的时间和成本。
维持可修改性的战术主要有三种:局部化修改、防止连锁反应以及延迟绑定时间。局部化修改的目标是减少由某个变更直接影响的模块的数量,可以通过维持语义一致性、泛化模块、限制选择等方式来实现。防止连锁反应的目标是限制对局部化的模块的修改,以防止对某个模块的修改间接地影响到其他模块,可以通过隐藏信息、维持现有的接口、使用仲裁者等方式来实现。延迟绑定时间的目标是控制部署时间并允许非开发人员进行修改,可以通过运行时注册、配置文件、多态等方式来实现。
提高系统的可修改性的目的是为了增强系统的弹性,使系统向高内聚低耦合靠拢,让其具备更高的便携性,可以根据后期的反馈进行更新而不需要进行整体的大变动。从开发角度降低了修改的时间成本和金钱成本。
实例:软件设计模式当中的抽象工厂模式为例,每一个组件只负责单一简单的工作,通过组合来完成一个大的项目,使用抽象模块来建立各个工厂类之间的联系,在对一个具体的类进行修改或增加内容时也无需对其他部分进行改动。
一个好的系统不会是一成不变的,而是在面对用户的反馈进行一步一步的更新,提高系统的可修改性就可以减少在更新迭代中所付出的无用的返工成本。
性能战术目标:对一定的时间限制内到达系统的时间生成一个响应,这些时间可以是消息到达、定时器到时以及系统状态的变化。
维持性能的战术主要有三类:资源需求、资源管理以及资源仲裁。资源需求是分析影响性能的资源因素,可以通过提高计算效率、减少计算开销、管理时间率等方式来实现。资源管理是提高资源的应用效率,可以通过引入并发、维持多个副本、增加可用资源等方式来实现。资源仲裁是解决资源的争用,可以通过调整调度策略来实现。
提高系统的性能是为了加快系统的响应速度,缩短系统反应的时间。谁都不想使用一个反应迟钝的系统,如果用户在数秒之内没有获得系统应该给出的反应,那必然会影响使用体验,假若这个时间再长一些,用户怕是会立马关掉并且不会想再打开第二次了,那么这对于一个系统的架构来说就是失败的。
实例:老生常谈的12306春运高并发购票的问题,春运期间庞大的并发量直接将网站击垮,对此12306互联网购票系统的改造给了我们一个很好的答案。其建立了一个可伸缩扩展的云应用平台,在网络阻塞时可以动态增加带宽,当服务器CPU到达高位时,可以快速从资源池获取虚拟机资源来分摊负荷。这就是一个成功的案例,网站初次建立是由于硬件的技术和用户的需求,谁也没有想到会如此快速的增长到这么高的并发,但是随着时代的发展,系统的性能就显得尤为重要。