CQRS

2015-06-04 15:33 by 敏捷的水, 177 阅读, 0 评论, 收藏编辑

CQRS是Command Query Responsibility Seperation(命令查询职责分离)的缩写。 世上很多事情都比较复杂,但是我们只要进行一些简单的分类后,那么事情就简单了很多,比如我们把人分为男人和女人,也可以把人分为大人和小孩,还比如,我们说国内和国外,城市和农村。经过一些类似这样的划分,我们的对不同的类就有不同的关注。 这样我们就会有妇女儿童医院专门让女人生孩子,而不会建一个医院让男女都生孩子。

CRUD

CRUD (Create, Read, Update, Delete) 增查改删,我们很多系统都是对数据的增查改删。过去我们很多系统比较简单,基本上增加的数据就是你要查询的数据,所以很多时候其实一个简单的Excel就能搞定。 而且增删改查也足够的简单,所以我们很多系统分层后在数据层Repository里仍是对单表的增删改查,这样对不少的系统都符合。

但是,系统规模稍微大一点,我们都知道我们的数据库里的数据模型很难和我们业务层需要的模型一致。 于是我们引入了Domain Model, Repository里就会做Domain Model的来回转换

同时我们在UI层要的数据,往往又和具体的Domain不同,这个时候我们又要定义一个ViewModel. 而这些ViewModel又是组合不同的DomainModel得来。

传统的代码里的问题:

  • 领域里有很多分页和排序,尤其是Repository里
  • 查询的方法里暴露了很多不应该有的领域模型的属性,因为需要组装DTO
  • 如果使用ORM,预加载了很多数据以提高性能,但是占用大量内存,而且需要维护这些数据。
  • 加载组合庞大的数据,比如页面是需要一个名字,我们也会把整个User数据取出来。

重要的原来把数据混在一起,复杂的查询相当难以优化。 尤其是数据库出现大量的Join 系统性能极速下降。

最重要的是我们把读写都放在了一起,显得责任不够清晰,代码也更复杂了一些,比如读数据是不太关心事物的,读数据是不需要验证的,只有写的时候才需要做数据校验,这也比较符合SRP(单一职责),但是用CRUD的思维是我们全都混在了一起。

CQRS

我们仔细看CRUD, 其实可以更简单的分为读(R)和写(CUD), 我们想想大部分情况都是,一个方法要么是执行一个Command完成一个动作,要么就是查询返回数据。 比如我们回答问题的人不应该去修改问题。

当我们读写分离后,我们对应的代码也会分离。

数据存储

写的一端需要保证事物,所以一般数据存储为第三范式,
读的一端一般都是反范式可以避免Join操作,这样我们只需要把数据存储为第一范式

扩展

大部分的系统里写数据要远远少于读数据,并且一般都是每次修改很少的一部分数据,所以在写这端扩展都不是特别紧迫,读数据基本都远大于写数据的次数, 所以扩展就更重要。 我们很难建立同一个Model 既能给写数据和读数据公用而且能够保证性能都比较好的。

查询端

查询端由于只是读数据,那么所有的方法应该都是返回数据,而且返回的数据就是界面直接需要的DTO, 这样可以减少传统的方法中把DomainModel映射为ViewModel或者DTO. 同时可以减少传统的领域里的一些混乱。

写端

由于把读分离出去,所以我们就只关注写,那么我们写这一段需要保证事物,数据输入的验证,另外一般写这一端都不需要及时的看到结果,所以大部分都需要一个void方法就可以,那么让我们系统异步就更加方便。这样使系统的扩展性大大增强。

代码更容易集中处理

当我在一些系统中使用CQRS后,很多地方代码大大简化,比如我所有的写操作都是一个Command, 那么我定义一个UICommand, 让所有的Command集成这个,那么我可以在这个UICommand里做一些通用的处理,比如Validation

同时我只需要定义一个CommandBus, 然后把对应的CommandBus分发到对应的Handler里(我前面几篇有实例代码),那么代码的耦合度大大降低。

代码分工协作更容易

由于读这一端直接读数据,而且对数据库没有任何操作,那么我们可以根据UI定义对应的DTO, 那么开发的时候我们可以用Mock数据,至于数据怎么存的,那么我们随后只要添加一层Thin Data Layer即可,实际上当我们使用CQRS后,很多时候我们把数据保存的时候都直接保存为Denormalize的,那么从数据里直接查询单表的数据就可以拿到页面需要的数据,大大提升读取数据的性能,同时代码也会极其的简化,开发读这一段代码的开发人员甚至都不需要对业务有太多了解。

实现

简单的实现

使用的Event后

使用了Event Source 和Service bus后

作者: 王德水
出处:http://www.cnblogs.com/cnblogsfans
版权:本文版权归作者和博客园共有,转载需经作者同意。

CQRS的更多相关文章

  1. DDD CQRS架构和传统架构的优缺点比较

    明天就是大年三十了,今天在家有空,想集中整理一下CQRS架构的特点以及相比传统架构的优缺点分析.先提前祝大家猴年新春快乐.万事如意.身体健康! 最近几年,在DDD的领域,我们经常会看到CQRS架构的概 ...

  2. 谈一下关于CQRS架构如何实现高性能

    CQRS架构简介 前不久,看到博客园一位园友写了一篇文章,其中的观点是,要想高性能,需要尽量:避开网络开销(IO),避开海量数据,避开资源争夺.对于这3点,我觉得很有道理.所以也想谈一下,CQRS架构 ...

  3. 分享一个CQRS/ES架构中基于写文件的EventStore的设计思路

    最近打算用C#实现一个基于文件的EventStore. 什么是EventStore 关于什么是EventStore,如果还不清楚的朋友可以去了解下CQRS/Event Sourcing这种架构,我博客 ...

  4. 一种简单的CQRS架构设计及其实现

    一.为什么要实践领域驱动? 近一年时间我一直在思考一个问题:"如何设计一个松耦合.高伸缩性.易于维护的架构?".之所以有这样的想法是因为我接触的不少项目都是以数据库脚本来实现业务逻 ...

  5. 浅谈命令查询职责分离(CQRS)模式

    在常用的三层架构中,通常都是通过数据访问层来修改或者查询数据,一般修改和查询使用的是相同的实体.在一些业务逻辑简单的系统中可能没有什么问题,但是随着系统逻辑变得复杂,用户增多,这种设计就会出现一些性能 ...

  6. 新项目的CQRS设计

    刚换了个工作,闲话不说了.前两天开始一个新项目,大概是一个任务管理系统,由使用者来选取任务,执行任务,反馈完成,我大概做了些设计,本来是打算看能不能在新公司铺垫一下DDD,不过后来这块功能没分到我这, ...

  7. 【DDD/CQRS/微服务架构案例】在Ubuntu 14.04.4 LTS中运行WeText项目的服务端

    在<WeText项目:一个基于.NET实现的DDD.CQRS与微服务架构的演示案例>文章中,我介绍了自己用Visual Studio 2015(C# 6.0 with .NET Frame ...

  8. WeText项目:一个基于.NET实现的DDD、CQRS与微服务架构的演示案例

    最近出于工作需要,了解了一下微服务架构(Microservice Architecture,MSA).我经过两周业余时间的努力,凭着自己对微服务架构的理解,从无到有,基于.NET打造了一个演示微服务架 ...

  9. CQRS框架:AxonFramework 之 Hello World

    Command Query Responsibility Segregation,CQRS 这个架构好象最近博客园里讨论得比较多,有几篇园友的文章很有深度,推荐阅读: CQRS架构简介 浅谈命令查询职 ...

  10. 通过一组RESTful API暴露CQRS系统功能

    命令和查询责任分离(CQRS)是由Greg Young提出的一种将系统的读(查询).写(命令)操作分离为两种独立子系统的架构模式.命令通常是异步执行的,并存储在一个事务型数据库中,而读操作则通常是最终 ...

随机推荐

  1. asp.net使用mysql数据库

    Asp.net连接mysql 不推荐使用ODBC,推荐是用mysql官网提供的组件MySQL.Data.Dll,放在bin下面,添加引用即可 下面是封装的几个常用操作 using System; us ...

  2. Please read “Security” section of the manual to find out how to run mysqld as root!错误解决(转)

    2016-03-12T15:40:45.717762Z 0 [Warning] TIMESTAMP with implicit DEFAULT value is deprecated. Please ...

  3. CoreGraphics QuartzCore CGContextTranslateCTM 说明

    CoreGraphics.h 一些经常使用旋转常量 #define M_E 2.71828182845904523536028747135266250 e 
#define M_LOG2E 1.442 ...

  4. SP2010 3D标签云Web部分--很酷的效果,强烈推荐!!

    SP2010 3D标签云Web部分--很酷的效果.强烈推荐! ! 项目描述叙事         基于简单Flash的3D标签云Web部件.SP Server 2010使用. 建立在内置标签云Web部件 ...

  5. Shell在大数据的魅力时代:从一点点思路百度大数据面试题

    供Linux开发中的同学们,Shell这可以说是一个基本功. 对于同学们的操作和维护.Shell也可以说是一种必要的技能,Shell.对于Release Team,软件配置管理的同学来说.Shell也 ...

  6. Linux中查看socket状态(转)

    Linux中查看socket状态:cat /proc/net/sockstat #(这个是ipv4的) sockets: used 137 TCP: inuse 49 orphan 0 tw 3272 ...

  7. 集合hashCode()方法和equals()办法

    1.哈希码:         Object中的HashCode方法会返回该对象的的内存真实地址的整数化表示,这个形象的不是真正抵制的整数值就是哈希码. 2.利用哈希码向集合中插入数据的顺序?     ...

  8. Chapter 1 Securing Your Server and Network(2):管理服务的SIDs

    原文出处:http://blog.csdn.net/dba_huangzj/article/details/37927319 ,专题文件夹:http://blog.csdn.net/dba_huang ...

  9. 解决linux看温度是报错No sensors found问题

    今日因为同事的linuxserver频繁死机,其型号和配置与我的一致,故此与其对照了一下server的内存使用率.CPU使用率.温度等信息. 在对照温度信息的时候发现无法使用sensors进行温度查看 ...

  10. Thanks

    今天,突然有一种爽的感觉.是做题做到爽的感觉,晚上就不是非常强烈了,脖子疼,要断了. 中午.妈妈给我打了电话,后来才知道爸爸的嗓子都哑了.说不出话来了都,哎,这都快一个月没有下雨了.地都干得要命了.好 ...