最近要开始搞网页端钱包,本着干一行爱一行的原则,撸起了前端框架。前端
项目基于蚂蚁金服的dva框架,其实是对几个流行的开源框架的整合,技术栈包括:react
在开始介绍以前,先说一说MV*。你们必定都据说过MVC,在这以后又衍生出了MVP和MVVM,这些均可以统称为MV*。可是,随着前端代码复杂度的增长,人们发现愈来愈难以管理程序的状态,模块之间耦合严重,代码难以调试,所以不少人认为“前端MVC已死”。编程
2014年,facebook提出了一个新的概念:Flux,旨在解决这些问题,其核心思想是“组件化 + 单向数据流”。这个框架很快流行了起来,而且逐渐成为目前的主流前端框架之一。为了更深入地理解这一变化,咱们来逐一比较一下它们之间的异同:redux
用户首先经过View发起交互,View调用Controller执行业务逻辑,Controller修改Model,而后View经过观察者模式检测到Model的变化(具体表现形式能够是Pub/Sub或者是触发Events),刷新界面显示。前端框架
从这里能够看出,主要业务逻辑都在Controller中,Controller会变得很重。MVC比较明显的缺点:服务器
为了克服MVC的上述缺点,MVP应运而生。在MVP中,View和Model是没有直接联系的,全部操做都必须经过Presenter进行中转。View向Presenter发起调用请求,Presenter修改Model,Model修改完成后通知Presenter,Presenter再调用View的相关接口刷新界面。这样,View就不须要监听具体Model的变化了,只须要提供接口给Presenter调用就能够了。MVP具备如下优势:antd
为了进一步解放生产力,把Presenter中调用View的接口同步数据变化的重复工做抽象出来,作成一个binder模块,这就变成了MVVM。开发者只须要指明绑定关系,binder模块会自动完成数据同步,这就是所谓的“双向数据流”,无论哪一端的数据发生变化,都会当即同步到另外一端。实际上,Vue.js、Angular这些流行的前端框架都使用了双向数据流设计。react-router
双向数据流极大地简化了开发者的工做,可是诟病也随之而来。因为绑定的随意性,某个View对Model进行的修改有可能会对其余的View形成“连锁反应”,再加上各类异步回调,给代码调试形成了很大的困难,每每难以定位数据究竟是被谁修改掉的。用专业一点的术语来说,代码的“可预测性”很是差。所以,为了提升可预测性,不少人主张回归到“单向数据流”模式,其中的典型表明就是facebook的Flux框架。框架
其实Flux并非什么新鲜事物,其背后仍是经典的MVC思想,可是实现方式上有所不一样。Flux的核心是“组件化+单向数据流“,下面逐一进行介绍。异步
在传统的MVC设计中,Model中不只要存储应用程序数据,还须要存储UI状态。另外一方面,Controller中不只要处理业务逻辑,还须要实现各类事件处理逻辑。若是把这部份内容抽出来,和View组合在一块儿,就变成了“组件”。这样一来,各个模块均可以各司其职,专一于本身的领域,代码的可读性和复用性均可以获得提升。
在实际编程中,通常把纯界面展现的View实现成一个“无状态组件”,在其上层再包装一个Controller-View(也能够称为Container),专门监听事件并更新数据,而后把数据做为props传递给View。这种编程模式能够最大程度地提升组件的可复用性。
为了提升代码的可预测性,Flux采用单向数据流设计。这里引入了3个新概念:
当Store数据发生变化时,会发送一个事件,View或者Controller-View能够监听这个事件,而后完成界面刷新。整个过程是“单向”的,若是View想要继续修改Store,必须从新发起一个Action。
固然,除了View之外,服务器或者Web API也能够直接发送Action给Dispatcher,这就是为何图中Dispatcher有两个输入的缘由。
更为详细的Flux流程参见下图:
经过以上分析能够发现,所谓单向数据流并非什么新鲜概念,实际上最最经典的MVC设计中,数据流就是单向的。虽然Flux官方宣称它们不是MVC,但我我的认为其实它实际想说的是MVVM,由于MVVM才是双向数据流。
固然,Flux也不是完美的,在多Store协同管理上存在必定的设计缺陷,这也是后来Redux出现的缘由,且听下回分解。
最后,以一张思惟导图结束本篇文章: