找到一个好的应用架构对于Android来说并非易事,Goodle似乎并不那么关心这方面,因为他们并没有推荐一个合适的应用架构。但是对于应用来说一个良好的架构是非常重要的。不管你是否同意,每个应用都应该有一个架构。因此,你最好为你的应用设计一个架构,而不是任由它发展。
现在比较流行的架构是Bob大叔在2012年发表的、针对于Web应用的清晰的软件架构。
但是我发现这个清晰的软件架构对于Android应用来说太过重量级了。
通常来说,移动应用都比web应用要简单。移动技术变化得很快,以至于今天发布的应用可能在一年之后就过时了。
移动应用通常比较简单,比较多的使用场景只是对数据的处理。从API获取数据、向用户展示数据。更多的是阅读,很少有写内容的需求。
这也使得移动应用的业务逻辑不会太过于复杂,至少不会比后端的应用复杂。当然,你也需要处理一些移动平台的问题:内存,存储,暂停,重新运行,网络,地理位置等等。但是这些并不是你的业务逻辑。
因此,对于大多数应用来说并不会从复杂的分层架构或者具有优先级的任务队列中获得太多益处。
它们可能只是需要简单的方式来组织代码,使得各部分组件之间高效的一起工作,并且容易查找bug。
Flux应用架构被facebook用于架构客户端Web应用,与Clean Architecture类似它也不是针对于移动应用的,它更简洁性能够让我们很方面的适用于Android应用。
有两个关键特性能够帮助我们理解Flux :
数据流总是单向的
一个 单向数据流是Flux 应用架构的核心,这也使得它很容易学习。当你需要测试应用时它也提供了很便利的条件。
应用分为三部分 :
这三部分通过Action交互,Action是通过type标识的简单对象,它包含了一些与action相关的数据。
在Android开发中使用Flux原则的主要目标就是创建一个简单、可伸缩、易于测试的应用架构。
第一步需要做的就是在Android组件之间建立Flux元素的关系映射。
这两类元素非常容易实现 :
Action也不复杂,它们通常是一些含有如下两个主要属性的简单的对象:
例如,一个显示一些用户详细的action大致如下所示 :
1
2
3
4
|
Bundle
data
=
new
Bundle
(
)
;
data
.
put
(
"USER_ID"
,
id
)
;
Action
action
=
new
ViewAction
(
"SHOW_USER"
,
data
)
;
|
Stores应该是Flux概念里最难理解的了。
如果你以前使用过Clean Architecture,你会感觉它也不是那么容易理解,因为Stores会假设职责已经被分割到不同的层。
Stores包含了应用的状态以及业务逻辑,它们很像功能完备的数据模型,但它们能够管理各种对象的状态,而不仅仅是其中一个。
Stores对Dispatcher发出的Action做出响应,执行业务逻辑,处理完成之后发出一个change事件。
Stores只会输出一个change事件,任何对一个Store的内部状态感兴趣的组件都需要监听该事件,并且使用它来获取数据。
系统中的其他部分并不需要了解应用的状态。
最终,Store必须暴露一个接口来获取应用状态.这样一来,View元素就能够查询Store的状态以及更新UI。
例如,在一个酒吧查找App中,SearchStore被用于追踪搜索到的酒吧、搜索结果和经过的酒吧历史数据。另一个ReviewedStore包含查看过的酒吧列表以及必须的逻辑,例如排序。
然后,有有一个重要的概念你必须要记住 : Store不是Repositories。它们的职责不是从外部资源(API或者数据库)中获取数据,只是追中action提供的数据。
那么Flux如何获取数据呢 ?
在前面的Flux图表中我特意省略了一部分: 网络调用。下一个图表将会完善这部分细节。
异步网络调用会从Actions Creator触发,一个网络适配器会触发一个异步的网络调用并且将结果返回到Actions Creator中。
最终Actions Creator将含有相应type与数据的Action分发出去。
所有的网络请求和异步操作从Store中隔离出来有两个优点 :
Store中的操作都是是完全同步的 : 这使得Store中的业务逻辑非常简单,bug也易于发现。并且,自从”所有的状态变化都必须是同步的”的运用到实际中,测试Store变得非常容易,只需要加载action,然后对最终的状态做一个断言判断;
所有Action都是从Action Creator被触发 : 从一个统一的点创建和启动所有用户的action使得查找错误变得很简单。省去了在各种Class之间查找该action的发出点,所有的action都出自Action Creator。因为异步调用在action发出之前已经调用,因此其他ActionCreator的函数都是同步的,这很大程度上提升了代码的可追踪性和可测试性。
这个例子是按照Flux架构实现的To-Do Android应用。
我尝试着尽量简单的演示如何使用Flux架构来构建一个组织良好的应用。
关于这个实现的一些解释 :
Action中的数据也只是使用key为String、value为Object类型的HashMap来存储。因此这需要你在Store中进行强制类型转换,一般得到具体的Action数据。当然,这并不是类型安全的,还是那句话 : 为了保持简单性。
没有什么最好的Android应用架构,只有最适合你应用的架构。这个架构能够使你你和你的队友很方便地一起协作,在规定的时间内高质量的完成你的应用。
我相信Flux架构在这些方面还是比较靠谱的,不信就自己动手试试吧!
代码在这里