菜鸟笔记
提升您的技术认知

如何写一个技术方案-ag真人游戏

文章目录

  • 写技术方案的意义
    • 1、提高沟通效率
    • 2、提高开发效率和质量
  • 怎么样才是好的技术方案
  • 如何写一个技术方案
    • 1、需求说明
    • 2、概要设计
      • (1)总体设计
      • (2)模块设计
    • 3、详细设计
      • (1)开发约定
      • (2)功能实现
      • (3)可靠性设计
        • 容量预估
        • 灰度方案
        • 降级方案
        • 异常处理
        • 监控告警
    • 4、测试方案
      • (1)影响点
      • (2)自测用例
      • (3)测试注意点
    • 5、上线部署
      • (1)环境准备
      • (2)系统准备
      • (3)发布顺序
      • (4)线上验证

1、提高沟通效率

一份好的文档可以在未来替你向别人回答类似下面这些问题:

  1. 项目里的这些概念是什么意思?
  2. 系统整体的结构和请求链路是什么样的?
  3. 当时为什么是这么决策的?为什么选择这个方案而不是其他方案?

对于整个团队,通过技术方案文档和评审对齐,可以提高沟通效率:

  • 产品经理可以审查技术方案是否与产品设计有偏差,是否满足当前产品需求和后续产品设计规划;
  • 开发leader可以把控方案是否满足技术要求,包括技术规范,性能要求,实现复杂度,可拓展性等;
  • 测试同学可以掌握需求技术实现原理,改动点,影响点,再做针对性测试用例设计;
  • 后续接手项目的同学可以通过技术方案文档快速熟悉系统。

很多祖传项目都是没有文档或者文档只是画了几张架构图和寥寥几句话的,既没有给出每个需求的背景,也没有讲解业务逻辑和架构设计思路,代码注释也非常少。接手者只能强行阅读代码,推测每个变量的含义,一点点梳理业务逻辑,跟抱着一本厚书硬啃一样。

2、提高开发效率和质量

对于开发同学,通过写技术方案,可以提高开发效率和质量:

  • 提前把需求和实现梳理一遍,编码时思维更加清晰,提高编码效率和质量,避免等到编码阶段才发现前期考虑不全导致返工的情况。相信很多开发者都有遇到在写代码时突然发现某一个逻辑是之前没考虑到的,导致需要对之前写好的代码架构进行调整甚至是推倒重来,这无疑是在降低开发效率。(去年给线索通传page_id的需求我就前后改了三版方案,写了三个代码分支,最后的方案因为太复杂了做不下去。)
  • 后期功能出现bug需要修复时,可能对之前写的代码逻辑有些忘记了,需要再花时间把逻辑捋一遍,费时费力,而如果有详尽的技术方案,就可以迅速上手,修复bug。

在说如何编写一个好的技术方案之前,先说说一个错误的方案是什么样的。

错误方案 正确方案
没有思考清楚模块的职责、关系、边界(约束和指导原则)
a. 模块职责混乱(比如本该负责鉴权和数据交换的cgi层写了复杂的计算和io任务代码)
b. 模块关系混乱(比如用户服务中调用了订单服务用来显示用户买了什么订单,而订单服务又调用了用户服务显示订单中的收获地址,最好将双向依赖改为单向依赖,参考软件系统解耦:理解依赖关系)
c.边界混乱(用户服务中写了订单服务的代码,订单服务中写了用户服务的代码)
明确模块的职责关系边界
技术方案和技术选型没有纵向对比和横向对比
a.没有对以往的业务逻辑进行review,修改的代码导致以往的业务无法兼容,出现不可预知的bug
b.没有对技术选型进行业内调研和对比,用到的基础技术在某个环节无法支撑你的变更,只能重新选型。比如不建议在核心项目中使用不确定性高的新技术,否则容易踩坑。
技术方案和技术选型要进行纵向对比和横向对比
没有存储设计,或者给出的存储结构描述不够详细。
a.没有详细对齐每个字段的类型及其内部结构(比如一个string类型的uid列表,配置端认为[“111”,“222”],播放端认为是[111,222],导致播放端解析错误)
给出存储设计,给出详细的存储结构,对齐所有存储(es、mysql、redis、文件系统、cdn等等)
没有容量预估和流量预估
a.服务请求量增大,挤垮服务器的cpu和内存
b.ugc数据太多了,数据库很快就被打满了,没有分库分表方案
给出流量预估和容量预估,预估存储占用大小(内存、持久化)、接口高峰期流量、mq高峰期流量等
没有灰度方案。
在某种场景qa没有覆盖到,线上用户操作突然触发了,导致大量数据错误
给出灰度方案,灰度能够控制异常影响范围最低,出现异常时修复数据也最少
没有降级方案。
服务降级是服务自我保护的一种方式,一个服务的硬件资源是有限的,在流量激增的情况下,如果不能通过降级方案来拒绝多余的请求,会导致服务因为处理不过来而崩溃。
给出降级方案(自动降级、人工降级),要考虑降级是否对主流程产生影响,对数据是否产生影响,区分有损降级和无损降级,有损降级需要考虑后续数据修复的方案。(参考为什么需要服务降级以及常见的几种降级方式)
没有异常处理方案
即使经过了qa测试,实际生产情况也总会出现异常情况,比如
a. 网络抖动数据写入失败,业务请求的数据丢失,要赔偿用户的损失
b. 用户违法输入,产生了sql注入
c. 中间件或存储崩溃,业务中断
d. 依赖服务挂掉,业务中断
考虑所有可能出现的异常情况,给出异常处理方案。
a.对于抖动、依赖服务短时间崩溃要考虑重试机制。
b.读流程是否可降级为不展示,写流程是否可有备选通道支持(比如mq和接口双通道)
c.对核心链路的异常要有告警机制。

总共七个点,后面四个点都是在考虑各种异常情况下的各种补救措施,所以一个好的技术方案设计需要考虑到尽可能多的异常情况。

墨菲定理:凡事只要有可能出错,那就一定会出错。

1、需求说明

开发工程师需要对自己所接手的需求有清晰的认识,这包括:

  1. 这个需求的背景、目标和价值意义是什么;
  2. 负责这个需求的其它相关人员分别是谁,产品、前端、后端(引擎、中台、adq等)、测试等。

格式如下:

一、需求说明
  1、需求背景:因为xxxx,所以我们要xxxx,从而达到xxxxxxx的效果
  tapd链接:https...
  2、相关人员:
  产品:xxx
  形态组前端:xxx
  形态组后端:xxx
  效能组前端:xxx
  效能组后端:xxx
  引擎组:xxx
  天秤系统:xxx
  测试:xxx

把这些内容写在技术方案的开头,有利于其他看技术方案的人快速理解需求,后面如果遇到问题也可以立马精准地找到相应的人。

2、概要设计

思路不清晰的技术方案有一个常见的问题:在交代完需求背景之后,就直接开始介绍每个子需求的具体实现。这种技术方案各个部分比较分散细碎,没有统一成整体,阅读起来并不好把握,这些设计背后的思路是什么,为什么要这样设计。所以需要高屋建瓴,先概要地介绍系统的整体构成,以及每个部分的职责,后面章节再细节介绍每个部分的具体实现。

概要设计主要包括总体设计和模块设计两个部分。

(1)总体设计

说明系统总体上的架构设计,画系统架构图是介绍清楚系统架构的有效手段,架构图常见的归类有:

  • 按层级介绍,把具有相同属性或特征的信息块归为同一个层级,例如系统mvc分层架构。
  • 按照系统模块和处理流程介绍,介绍各个模块处理的步骤,模块间的交互。

注意画之前要想清楚这张图要表达什么内容,再针对性来画,不同的类型的图不要合在一起。例如想说明系统的部署结构,用部署图,说明业务的主要流程,用流程图等。

(2)模块设计

简要说明每个模块的职责,或者说每个模块在本次需求中需要作出的修改。

3、详细设计

详细设计可分成开发约定,功能实现,可靠性设计三个部分。

(1)开发约定

开发约定部分常见介绍的内容如下:

  • 方案新引入的名词,概念的解释,方便后面的内容引用。
  • 前期上下游对接达成一致的约定/协议。

(2)功能实现

软件系统工作的核心功能是对数据的处理。因此具体功能实现部分重点关注的是数据链路,数据链路包括:

  • 数据源:触发业务的流量来源是什么,例如对外提供的接口,定时任务,mq消费等;
  • 计算转换:数据如何做转换运算,加工处理的流程;
  • 数据存储设计。

具体来说,常见的功能实现需要讲解这些内容:

  • 接口设计:提供接口设计文档,包括入参出参字段定义,接口参数校验逻辑,异常情况的处理和返回的错误码。
  • 系统间交互流程:结合系统间流程图说明一个业务请求涉及哪些系统组成部分,业务的发起来源,系统间交互调用了具体哪个接口,请求处理基本步骤和数据落地存储逻辑。
  • 系统内处理流程:结合业务处理流程图说明请求如何加工计算数据,处理的具体步骤,最终处理完成之后结果如何保存,或者传输到什么地方。
  • 存储设计,包括存储结构(包括mysql、es、redis、memcache、tablekv等)设计,包括表和字段的概念定义,索引的设计,各个表之间的关联,业务系统如何使用这些库表等。

(3)可靠性设计

我们不仅要考虑如何高效地实现系统功能,而且要尽量保证系统的稳定可靠。可靠性设计包括容量预估、灰度方案、降级方案、异常处理和监控告警。

容量预估

容量评估需要根据请求量,评估要预留给程序多少相应的运行资源。包括内存,磁盘,cpu,存储服务等。

流量预估

流量来源一般包括对外接口和消息队列两种,用表格的形式给出

  • 接口平均qps、峰值qps、接口请求、报文大小
  • 消息队列的平均消息数、峰值消息数、报文大小。

这一部分如果是改动的业务,可以参考以前的监控,如果是新业务则需要拉运营、产品确定业务量。若预估峰值会很高,则需要进行压测。表格例子:

模块 接口/mq topic 报文大小 上线一周 上线一个月 上线半年 上线一年

流量评估主要是看机器的cpu和内存能否扛得住业务请求量,

  • 预估一个请求处理过程所需要的计算开销,防止服务cpu打满。
  • 预估一个请求过程产生的对象大小,防止服务内存打满。

如果新增的业务逻辑所需的计算量和内存占用比较大,则需要进行功能实现的优化或者申请更多的机器资源。

数据量预估

用表格形式给出用到的所有存储在一段时间的数据量增长:

模块 表/索引 上线一周 上线一个月 上线半年 上线一年

评估数据量增长后,存储系统是否能承受住压力,会不会存储空间被打满或者查询速度变慢,以及如何进行存储设计的优化。

灰度方案

灰度可以控制在出现bug的情况下的损失,一边灰度一边观察监控,有问题则及时回退。

  • 对于一些改动比较小的需求,通过发布系统的机器维度逐台灰度即可。
  • 对于一些改动量比较大或者改动核心模块的需求,需要设置多个灰度周期,拉长灰度的时间来暴露潜在的问题。

用表格给出灰度范围、配置灰度开关的参数、灰度周期。例子:

模块 灰度维度 配置变更 灰度周期(1) 灰度周期(2) 灰度周期(3)
请求流量 第一周:20%流量,比如某些二三线城市 第二周:50%流量,比如一些一线城市 二线城市 第三周:100%流量,比如全国

降级方案

即使通过灰度跑了很长时间,直到最后全量也没有出现问题,也不能100%保证这次代码改动是没有问题的。通常一个业务刚上线很稳定,但是随着时间的推移问题逐渐暴露,原因可能有很多:

  • 前期容量评估不准确,导致数据量变大了,存储空间不足或查询速度变慢,或者流量变大了,现有计算力不够(有的问题是横向扩容所不能解决的)
  • 用户操作花样百出,防不胜防
  • 依赖的服务不稳定,出现问题(包括网络、基础设施等)

所以降级方案是必须要有的,防止出现问题之后没有退路。所以说灰度是一个短期的及时止损方案,降级方案是一个长期的及时止损方案。

降级方案用表格给出业务模块或接口、降级方式(自动、手动)、降级是否对主要业务流程有损失、若有损失则要有对应的修复方案。在设计降级方案时,需要与产品、测试、业务人员进行充分沟通,说明降级方案,一起讨论可行性。

模块 主流程 是否可降级 降级流程 是否有损(对主流程) 备注

异常处理

没有人能考虑到所有异常,但是只要考虑到尽量多的异常情况并且给出对应的异常处理方案,总会让业务更可靠一点。

每种异常情况需要列出这些内容:

  • 异常场景
  • 异常处理流程(降级方案)
  • 如果降级方案是有损方案,则需要给出损失和数据恢复方法
模块 异常情景 处理流程 降级方案 损失与数据恢复

监控告警

监控告警可以帮助我们及时地发现问题,给出核心的业务指标和非业务指标(qps、响应耗时、消息积压数等),关键指标出现异常(低于或高于某个阈值)要进行报警。表格形式说明信息:模块,监控指标,监控阈值,报警方式等。例子:

模块 idkey 指标 阈值 报警形式

4、测试方案

良好的测试方案能有效提高开发质量,技术方案中不仅需要考虑开发自测,为了进一步提高研发质量,还需要考虑如何提高测试同学的测试质量和效率。测试方案需要考虑的点包括:影响点,自测用例,测试注意点。

(1)影响点

影响点可以用清单的形式列出本次开发影响了哪块功能,哪些接口,接口url,改动的内容是什么。这样测试同学在设计测试用例时可以做对照参考,减少功能遗漏测试的情况。

(2)自测用例

自测用例是介绍说明需求自测的用例设计,一般包括涉及场景,测试步骤,测试输入,期望输出等信息。

(3)测试注意点

有些隐藏的异常情况处理,边界条件,特殊处理逻辑,如果没有特别说明,测试同学测试的时候很容易遗漏这块,而线上bug往往出现在这一块。

5、上线部署

事先规划好上线部署的详细步骤,等到正式上线时就可以对着步骤来一步地执行和检查,减少上线事项遗漏或者处理出错的情况。

上线部署部分包括环境准备,系统准备,发布顺序,线上验证

(1)环境准备

系统依赖环境的准备包括mysql、redis、mq、es和nginx等服务搭建和初始化,机器资源等。

(2)系统准备

系统准备常见主要如下:

  • 依赖的服务配置,数据更新,例如数据库表创建,sql初始化脚本,mq的topic创建,监控配置,白名单申请,定时任务创建等。
  • 代码检查,分支merge。

(3)发布顺序

如果不同的服务之间有依赖关系,在技术方案中应当标明。发布上线的服务依赖其他服务的情况下,需要先发布被依赖的服务。

(4)线上验证

线上验证的部分,需要说明服务发布上线之后,怎么验证服务是否正常,需要做哪些检查验证项。例如

  • 检查服务器的cpu、内存、接口耗时曲线;
  • 检查监控和日志是否有报错;
  • 通过线上执行一次业务请求看是否正常。
网站地图