用户您好!请先登录!

软件项目架构设计研发管理过程的评估和优化

软件项目架构设计研发管理过程的评估和优化

简单来说,架构设计包括了功能性架构和技术架构设计两个部分的内容,功能性架构解决业务流程和功能问题,而技术架构解决非功能性需求等问题。

两种架构都包括了动态和静态两个方面的内容,对于功能性架构中动态部分为业务流程驱动全局用例,用例驱动的用例实现等;对于技术架构中动态部分为架构运行机制,而静态部分为框架,分层等方面的内容。

一个智慧家庭项目背景

对于该项目是一个智慧家庭大项目中的智慧小区项目,即实现智慧小区的信息化和服务化运营,对于智慧小区来说实际上包括了两个方面的内容。

一个就是小区本身日常管理工作的信息化,这里面包括了类似基础设施管理,公告信息管理,物业管理,停车场管理,门禁管理,视频监控等。另外一个就是智慧小区提供的服务化内容,包括了社区商圈和内容电商,售后等便民服务等。

从上面信息可以看到其包括了后台管理功能和APP前端功能,同时对于后台管理功能本身还涉及到和各种门禁,视频等物联网应用平台的接口集成。

一个典型的智慧社区架构图可以参考如下:

对一个软件项目架构设计研发管理过程的评估和优化

本项目典型特征仍然是体现了平台+应用构建模式,既有后台管理端,也有面向C端用户的服务和运营应用。如果按照当前中台架构思路话,可以从上图分为:

基础层+技术中台层+业务中台层+服务层+前端应用

这也是我们经常说到的中台分层构建模式,同时在中台层构建的时候通过微服务思想进行大拆小处理形成独立自治的微服务模块。

项目采用的技术开发框架

整个项目整体采用Spring Cloud框架体系进行构建,这也是当前主流的微服务开发框架,同时进行了微服务模块的划分,按前后台分离的方式进行应用构建。

技术架构咨询该如何做?

对一个软件项目架构设计研发管理过程的评估和优化

一个技术架构咨询既要考虑功能性架构,又要考虑非功能性架构,同时还要考虑整体研发过程管理,技术标准规范体系建设。

搞清具体的业务目标和技术目标

在进行具体的架构设计和架构诊断的时候,首先还是需要搞清楚具体的业务目标,业务需求和技术目标。这个是架构设计的基础。同时也再次重申,没有最先进的架构,只有最适合的架构。我们看到太多一开始将简单的架构复杂化的问题,反而极大的增加了后期开发,集成,测试和运维的工作量。

功能性架构的设计

基于当前中台和微服务的思想,我们需要去评估当前的微服务组件划分是否合理,每个微服务暴露的接口是否合理,是否满足粗粒度和可复用等基本特征。是否考虑了按SOA的思路进行组件分层设计,共性技术能力和业务能力是否平台化和中台化。

最终我们需要给出完整的分层应用架构设计图,技术架构图,组件间的集成关系图。同时将关键的业务功能实现分配到具体的微服务组件模块里面。

非功能性架构的设计

首先最重要的仍然是高可用性设计,当前的整个架构是否满足高可用设计要求。其中包括了高可靠,高性能和高扩展性设计。对于高可靠性本身又分为了IT基础设施的高冗余,HA和集群化设计;同时又包括了软件架构本身的高可靠性设计,类似消息,缓存,事务处理机制设计等。

对于性能和扩展性,我在前面很多文章都有专门的描述,在IT基础设施架构层面你会看到两者存在强关联。比如我们常说的通过IT架构的集群化扩展来提升性能。但是对于性能提升仍然还有软件代码层面优化,技术组件的选择等多个方面的内容。比如就拿最简单的API网关来说,我们可能就会更加推荐采用Kong网关而不是Zuul网关以获取更好的性能。

其次,我们还需要考虑安全,日志异常处理,消息,文件缓存等诸多技术组件和共性技术能力实现。还需要考虑软件开发编码规范,API接口设计标准等。这些都需要统一纳入到非功能性架构设计。

研发过程管理优化

另外一个重点内容就是研发过程管理。仍然是需要基于IT项目管理PMBOK,CMMI和敏捷研发方法论等多方面的知识,基于企业实际情况来制定相应的研发过程管理规范体系。

IT基础设施,部署架构和中间件选择

简单来说,在进行这块内容Review的时候,核心就是整体部署架构应该满足高可靠和高扩展性要求,在具备集群等可扩展性能力的时候,往往也同时具备了高性能能力。

数据库架构搭建

当前数据库采用的是Mysql数据库,但是是单点架构模式,建议更好为Mysql DualMaster架构模式。对于DualMaster架构简单来说就是两个节点都双活状态,但是某一个时点只有一个节点提供服务能力,同时AB两个节点通过Binlog来实现快速的日志复制。

DualMaster架构模式满足了基本的高可靠性,但是如何提升进一步的扩展能力,在这里我们提出两个点需要进行优化改进。

其一是读写分离扩展配置

即可以在当前DualMaster架构下扩展Master-Slave进行读写分离,对于Slave节点的数据仍然是通过Binlog进行实时日志服务以保持数据一致性。

其二是考虑数据库本身的横向拆分和纵向拆分

当前数据库是一个大库,但是已经分了不同的database,这个是好的方面,即后续可以按Database进一步进行拆库处理。当前要注意的就是不要去做跨database库的join连接操作,这样的话多个database库之间本身又变成了一个紧耦合的状态。

其次,数据库要具备横向拆分的能力,比如我们常说的一个智慧社区运营平台,如果推广了100个小区,数据量和并发量都增大,那么我们的物业管理数据库能否进一步按区域进行水平拆分,形成不同的切片库,而这个可以通过DaaS访问中间件来是实现。如果具备这个能力,那么Database层基本满足要求。

通过DaaS统一数据服务层来提供数据访问

对一个软件项目架构设计研发管理过程的评估和优化

这个可以作为预留扩展,即在Mysql库上面构建DaaS数据访问层,提供统一的数据访问集群和路由能力。

数据库接口代理:实现统一的数据访问接口代理,业务组件或模块通过接口代理来访问底层的数据库服务。在接口代理的实现过程中需要考虑数据库连接池的管理,数据库负载均衡等相关内容。

SQL解析:负责解析客户请求的SQL语法,需解析出语句的读、写特性,并根据语句特性进一步解析其中的schema、表、字段、条件等信息。如:新增语句需解析出所插入字段的字段名和值;查询、修改、删除语句需解析出Where条件中包含了哪些条件表达式。

数据路由:负责根据语法解析的结果,在规则池中查找与之相关的规则。找到后将解析结果代入规则中进行运算,得到语句需要转发的具体物理数据库节点。而对于规则池则主要包括语句的读写规则,水平拆分的分片规则,数据对象的访问规则等。

多租户管理:可以实现在数据库实例和数据库Schema两个级别的多租户共享和管理功能。数据库层共享以数据库为基本的划分单元,即为每一个租户创建/分配一个数据库实例,共享存储和服务器。Schema层共享以User/Schema为基本的划分单元,即数据库实例已经创建,在此基础上为每一个租户创建一个Schema,多租户之间共享存储、服务器、操作系统服务和数据库实例。

管控代理:为实现对整个数据库资源池的集中管控和性能监控,需要对每一个数据库物理节点放置数据库管控代理。管控代理一方面实现对物理数据库节点的统一操作入口,一方面实现对资源的实时监控和性能数据采集。

管控功能:提供对服务集群中的不同数据库服务节点进行节点的添加、删除、启动、停止等功能。完成服务集群的伸缩;完成节点信息的采集,以及针对节点进行的手动操作的日志记录; 完成和节点代理服务进行交互的工作;完成和监控系统进行交互;共同完成服务的管理和监控功能。

现在市场上有成熟的DaaS数据库中间件,根据业务与技术需要评估使用即可。

数据库的基础设施选择

再回来看下为何选择Mysql DualMaster架构,在这种架构下我们是不需要使用任何集中化存储设备的,直接使用本次磁盘存储即可。

其次对于数据库服务器的安装,仍然是建议采用X86服务器物理机进行,以获取更好的IO性能。对于磁盘IO实际上是影响数据库性能的一个关键点,如果数据库安装在虚拟机环境里面,本身将降低数据库的IO性能,而影响到整个数据库的性能。

应用中间件的选择

对一个软件项目架构设计研发管理过程的评估和优化

在本项目里面,原来采用了Undertow轻量web服务器。

Undertow 是红帽公司开发的一款基于 NIO 的高性能 Web 嵌入式服务器。它是一个 Web 服务器,但不像传统的 Web 服务器有容器概念,核心特点就是轻量和高性能,它由两个核心 Jar 包组成,加载一个 Web 应用可以小于 10MB 内存。由于Undertow采用Java语言开发,可以直接嵌入到Java项目中使用。同时, Undertow完全支持Servlet和Web Socket,在高并发情况下表现非常出色。

在本项目里面我们仍然建议采用Tomcat作为应用服务器容器,网上有很多tomcat和undertow对比性能测试的文章可以看到,undertow在并发测试下的性能优势并没有那么夸张。

而这种情况下采用大家熟知,稳定可靠的tomcat作为Web容器才是最好的选择。

简单来说,就是你搭建的一个应用架构性能绝对不会说因为采用了Tomcat而无法满足性能要求,如果真正部分满足性能要求往往也是基础设施集群扩展,软件代码,数据库等方面原因导致。

应用中间件负载均衡

现在最常用的仍然是采用Ngnix来进行负载均衡,对于Tomcat多节点部署。

在实际项目里面我们看到,如何完全采用微服务和前后分层开发模式,那么后端应用朝前端提供的全部是Http Rest API接口,接口本身无状态,也不需要Session保持。

因此对于后端应用我们可以接入一个单点的Ngnix进行负载均衡,这个时候走四层负载即可以满足要求,同时获取最高性能。

而对于前端应用,由于需要会话保持,我们其余七层负载均衡模式。

其次,如果软件负载均衡无法满足性能要求,建议配置提升为硬件负载均衡设备。

对于Tomcat服务器节点的假死探测

对于集群配置中,一定要注意解决服务器节点的假设问题,比如对于Tomcat服务器,TCP连接的TIME_WAIT过多,新的请求服务器无法响应处于假死状态。但是Ngnix仍然可能继续分发请求到该服务器。这就是必须要解决的一个问题点。

即需要能够自动探测到假死情况,并停止请求分发,同时对节点进行重启处理。

技术开发框架和技术组件选择

微服务开发框架选择

对一个软件项目架构设计研发管理过程的评估和优化

对于究竟是选择Dubbo还是Spring Cloud,是我们进行微服务开发架构搭建的时候最常遇到的一个问题点。由于Dubbo本身支持RPC能够获取到更好的性能,因此很多架构往往会选择Dubbo开发框架,但是要注意的就是采用Dubbo后,后续对各种微服务治理能力的集成和定制开发往往工作量更大。

虽然走Http Rest接口交互会牺牲一定的性能,但是在应用架构搭建过程中,不会因为没有走RPC而导致明显的性能瓶颈。除非你是做类似天猫这种海量并发的运营服务平台。

因此对于这个项目选择Spring Cloud框架体系没有任何问题。

而Spring Cloud框架体系里面单个微服务开发核心还是Spring Boot,你还可以看到Spring Boot开发的微服务本身也可以脱离完整的Spring Cloud框架运行。

对于本项目而言,我们也可以看到

  • 后端组件间接口调用:走注册中心,配合Eureka,Feign和Ribbon三个组件使用
  • 前端到后端:使用微服务网关,通过Zuul网关进行调用

对于Hystrix限流熔断,服务链监控等,一开始可以不启用这些能力模块。后续项目扩展的时候既可以使用SpringCloud体系中能了,也可以使用类似SkyWalking等其它开源实现方案。

从Zuul微服务网关到API网关

保留扩展点,后续可以从Zuul网关升级到Kong API网关。主要是处于两个方面的考虑。

  • 其一:KongAPI网关本身在日志,安全,限流各方面能力强于Zuul,也方便扩展
  • 其二:KongAPI网关基于OpenResrty和Lua语言,性能好于Zuul网关

对于仅仅是微服务架构内部的接口API注册和发布,采用Zuul网关一般可以满足需求,但是如果还存在集成第三方服务商的API接口服务能力,那么采用Kong网关更加合适。

Redis缓存服务

对于缓存服务,项目里面采用Redis库是没有问题的。Redis的持久化、数据结构、吞吐量性能等诸多优异因素,使得Redis已经是WEB应用开发缓存操作的不二之选

发现问题主要还是当前部署架构是单节点部署,不支持冗余和高可靠性。

对一个软件项目架构设计研发管理过程的评估和优化

搭建redis集群,建议至少需要准备3台服务器,共搭建6个节点,3个master,3个slave,并且要求3个master节点不能全部跑到同一台服务器上,保证节点安全,3台服务器的配置相同。

数据访问层方案

本MyBatis作为数据持久层框架是没有问题的。

对一个软件项目架构设计研发管理过程的评估和优化

MyBatis因为具有封装少,映射多样化,支持存储过程,可以进行SQL优化等特点。使得它取代了Hibernate成为了java互联网中首选的持久框架。

无论MyBatis或Hibernate都可以称为ORM框架,Hibernate的设计理念是完全面向POJO的,而MyBatis不是。Hibernate基本不再需要编写SQL就可以通过映射关系来操作数据库,是一种全表映射的体现,而MyBatis需要我们提供SQL去运行。程序员不用精通SQL,只要懂得操作POJO就能够操作对应数据库的表。

虽然采用MyBatis导致跨数据库能力,移植性变弱,但是采用MyBatis可以获取更好的性能扩展。同时项目本身要基于MyBatis制定相应的规范体系,约束Sql语句的使用范围。

消息中间件的选择

对一个软件项目架构设计研发管理过程的评估和优化

对于消息中间件的选择,首先还是需要搞清楚业务使用场景。比如你是用于前端写入的削锋,还是异步解耦和可靠性,还是需要实现消息发布订阅。不同的场景实际我们都需要考虑采用不同的消息中间件。

比如我们常说的RabbitMQ,由于基于AMQP协议,性能比ActiveMQ消息中间好,但是本身并不支持事务处理,如果你的架构需求里面有基于BASE的事务最终一致性要求实现,那么就不能选择RabbitMQ。再比如你的消息中间件使用场景就是单纯的日志数据采集和处理,那么采用Kafka就是最好的解决方案,也是主流解决方案。

基于本项目,我们看到消息中间件使用场景是跟物联网应用相关的集成场景,更多是消息接收后的缓冲处理,因此我们建议采用RabbitMQ作为消息中间件。

非功能性架构关键点评估

安全性评估

本项目采用SpringSecurity+JWT的用户认证和安全机制。

对一个软件项目架构设计研发管理过程的评估和优化

SpringSecurity 是企业应用系统的权限管理框架,应用的安全性包括用户认证(Authentication)和用户授权(Authorization)两个部分。用户认证一般要求用户提供用户名和密码。系统通过校验用户名和密码来完成认证过程,用户授权指的是验证某个用户是否有权限执行某个操作。在一个系统中,不同用户所具有的权限是不同的。

Spring security的主要核心功能为认证和授权,所有的架构也是基于这两个核心功能去实现的。

JSON Web Token (JWT) 是 JSON 格式的被加密了的字符串。在传统的用户登录认证中,都是基于session的登录认证。用户登录成功,服务端会保存一个session,当然会给客户端一个 sessionId,客户端会把 sessionId 保存在cookie中,每次请求都会携带这个 sessionId。

cookie+session这种模式通常是保存在内存中,而且服务从单服务到多服务会面临的session共享问题,随着用户量的增多,开销就会越大。而 JWT 不是这样的,只需要服务端生成token,客户端保存这个token,每次请求携带这个token,服务端认证解析。

采用cookie+session传统模式还是SpringSecurity+JWT

由于JWT方案本身存在注销和续签两个关键问题,因此在这里我们参考网上的一个说法,即对于传统的应用系统的登录,用户身份认证,状态保持,仍然采用传统的cookie+session方案来实现。而仅仅对前端调用后端的Http Rest API接口采用SpringSecurity+JWT方案。

DMZ隔离区设置

对一个软件项目架构设计研发管理过程的评估和优化

如果整个数据中心是在企业内部私有云,同时后端开放的API接口服务又需要暴露给APP端进行访问,那么在这种情况下必须设置DMZ隔离区。

对于DMZ隔离区是一台独立的服务器,最简单的即是Ngnix服务器,实现最简单的Http请求转发即可。当然也可以在DMZ区部署一套API网关,增加对API接口的其它管控能力。

日志和异常管理

对于目前采用的logback日志框架推荐使用,但目前项目的配置较为简单,存在以下不足:

  1. 目前日志输出格式为默认格式,建议调整为包名+类名全路径方式
  2. 目前日志文件切割仅按天进行切割,建议先按天再按照大小进行切割
  3. 日志存储按照不同级别分类,即建议debug、info、warn、error通过配置自动生成四个文件夹,存放历史日志,而当日上述四类文件存储顶层目录
  4. 根据不同开源框架进行日志划分,以便关注重点框架,例如:com.rex与org.springframework.security.web和com.ibatis建议设置为debug,以便及时查看项目代码、安全代码、持久化代码的日志轨迹,而其他框架则设置为warn

对于日志管理,在日志分类的基础上还需要进一步提升异常编码规范能力。即对于各类异常信息进行明确的异常编码,方便后续对异常信息进行跟踪和分析。

比如下面的异常编码和规范定义可参考:

对一个软件项目架构设计研发管理过程的评估和优化

易用性和交互设计

当前这块整体欠缺比较多,因此需要后续重点提升。

整体可以采用借鉴Scrum敏捷研发思路,但是前期需求仍然需要采用类似Axure先进行原型和交互设计,在评审通过后再详细分解用户故事和业务功能点。同时需要进一步制定易用性标准规范,UI标准规范体系。但是整体UI规范标准制定是一个长期的过程,需要逐步积累。

对一个软件项目架构设计研发管理过程的评估和优化

研发管理过程优化

对一个软件项目架构设计研发管理过程的评估和优化

要做好研发项目管理,过程管理并不是一件容易的事情,我有时候就在想,就连最基本的PMS任务日志下达,日志按时反馈都无法做到位情况下,很多其它研发管理规范流程要求就更加无法落地。

这一方面是研发管理中的执行力问题,一方面是团队成员形成的研发文化和过程意识问题。下面重点记录下研发管理要改进的一些重点内容。

对于后续系统的新增和变更功能优化更新,首先对已有的需求规范文档进行更新和版本升级,同时对增加的内容进行条目化处理,对于条目化需求不再准备Excel文档,而是直接录入到禅道。

录入禅道后,在禅道中进行版本规划,并开始安排版本研发,下达PMS任务。

  • 需求采集:用户需求文档保留,重点是需求采集和初步需求分析和条目化拆分
  • 原型开发:全新模块需要,变更可直接在需求提交附图
  • 需求提交:直接采用禅道需求管理,不要求项目必须先有完整软件需求说明书
  • 需求评审:变更类和全新模块类分开,需求评审记录直接附加在条目化需求后
  • 需求实现:需求点对应到项目和版本规划,项目关联到具体的产品

对于研发版本规划好后,基于研发版本进行PMS研发任务下达,研发人员填写PMS日志,研发负责人对开发进度进行PMS任务跟踪管控。对于研发版本,建议采用短周期迭代模式,即2到4周为一个版本,2周的开发时间,1周的测试环境发布和验证时间,1周的正式生产环境部署时间。

  • 产品管理:按部门内产品线划分设置产品经理,一个产品管理可负责多个项目
  • 项目管理:产品经理和研发经理都可兼项目经理,不再设专门的项目经理
  • 版本规划:短周期迭代模式,最短周期1周,最长周期8周,运维类项目单列
  • 任务管理:启用任务管理和日志反馈,研发人员必须每天反馈任务和填写日志

对于测试,仍然是和具体的研发版本对应,测试提交的功能Bug要对应到具体的研发版本。前期我们采用持续集成和自动化构建,而现在本身我们研发DevOps平台后,对于我们管控平台的研发也可以迁移到DevOps平台上来实现自动化的产品构建和打包。

  • 测试设计:测试用例设计,新增和变更类分开,变更直接对应到需求
  • 持续集成:前期采用Maven和Jekin实现,当前专业到我们自研的DevOps支撑平台
  • 缺陷管理:采用禅道项目管理工具进行,前期已经在云团队使用
  • 版本发布:测试评估报告,版本发布评审必选环节,进一步规范产品发布流程

开发修改问题或Bug,修改完成后将Bug状态转为待验证(在这里没有待部署状态)。测试人员在DevOps平台触发流水线自动部署,部署完成后测试人员对Bug进行验证。在Bug全部验证完毕后对当前版本进行基线和打标签,同时将当前版本进行环境迁移,从开发测试环境迁移到SIT或UAT测试环境,转前方进一步测试。通过这种方式更好的实现异地协同和多方联动。

版本测试完成并验证通过后,测试人员出测试评估报告,准备发版申请说明书进行版本发布。同时版本发布准备好具体的部署包,准备Sql部署脚本和数据初始化脚本,以方面出现问题继续回退。

研发过程增加关键评审内容,一个就是每一个版本的需求需要进行评审和Review,一个就是要增加开发完成后的CodeReview和代码走查工作,加强代码编写的规范性。同时对于配置管理也需要加强,特别是配置分支,基线,配置审计等工作,实际上在前期做的并不好。

行走的code
行走的code

要发表评论,您必须先登录