开发手册
2018-08-29 本文已影响15人
汤圆叔
规范标准可以帮你规避不必要的风险、极大地提升工作效率、潜移默化地使你的工作方式日趋完美。每次开发新需求前,请反复、认真地把我读几遍。
开发流程
系统设计(数据来源确认、关键流程设计、工时评估浮动25%、延期风险提前报备)
- 别有啥心里负担,只要你不糊弄,认认真真地把该做的都做了就好。
- 逐条分析需求,确认各需求点的数据来源是否满足。优先做好关键业务流程部分的系统设计,设计不完善的部分要在接口设计及开发阶段尽早报备出来,避免延期风险。
- 工时评估尽量按照每天8小时的时间标准,为需求的不确定性部分留出加班时间,工时申请量必须在正常工时量基础上增加至少25%(实际开发每天10小时),避免延期风险。
- 项目进展中由于外部环节不畅导致的延期风险要及时、尽快地报备给项目经理和技术负责人,避免最终延期造成的后期责任扯皮。
接口设计(尽快提供接口文档)
- 优先针对前端PRD做好接口设计,提供好接口文档。
系统开发(及时上线优先、业务架构设计、关键TODO点、分解TODO点、重构在所难免)
- 基于业务模型,并结合接口设计,做好业务架构设计,各功能点实现可以先标记主要TODO点实现内容、方案,整体业务架构搭好后和架构师或技术负责人确认一下业务架构是否合理及是否存在不足,有问题及时调整。
- 调整完业务架构后,将主要TODO点分解为细粒度的具体实现内容TODO点,逐个击破。
- 实现过程中,可以先不必过于在意系统的性能,优先实现功能。
- 优化重构是在所难免的,保证系统上线是第一要务,后续还可以提技改优化需求,一天把一年的活干完不现实,循序渐进的可持续推进才是一个良性循环。
需求分析模型
- 需求中的字段的值在不同的业务场景下始终都是一致的吗?如果不是每种情况都该怎么处理?
- 需求中的字段的值是否有严格的时效要求?如果有何处可以获取最新的数据?如果无法获取到最新的数据如何处理?
- 需求对应的业务是否有逆向流程?如果有,具体如何处理?
- 需求中哪些数据需要用户提供?响应用户时应响应哪些数据,是否要做转换处理?
- 需求中出现异常的场景如何处理?
设计规则
- 查询数据时优先使用缓存,尽量避免数据库操作,无法避免的情况请通过异步化等限流策略控制对数据库的访问压力。
- 前后端系统同步数据应尽可能通过发送MQ消息的形式实现。尽量避免使用网关接口形式,否则在安全、可靠、耦合等方面需要做大量的处理工作。注意:Java系统间,查询、非异步操作可以通过RPC服务形式实现
- 本地数据库事务操作内的外部调用(RPC等)尽量添加超时降级,避免外部调用时间过长导致的数据库事务无法提交,以致最终数据库连接资源耗尽。
- 事务的粒度、锁的粒度要尽可能的小,避免长事务、长连接造成的资源耗尽情况。
- 在设计异常处理时,接口对外提供可控的异常返回码,内部设计时对于使用者不需要了解的异常信息建议采用统一的异常码返回,内部异常处理本着对于关键业务异常需要报警,非关键业务异常仅打印异常信息的原则设计。
- 针对数据库查询(where、order by)要建立合适的索引,尽量避免实时count等统计操作,对于分页查询频率较高的场景可以通过Canal异步将数据库数据同步到ES。
命名规范
- function、param、variable统一驼峰命名。eq:getHttpMessage
- 常量统一大写、下划线分隔单词,命名清晰,别嫌长。eq:MAX_STOCK_COUNT
- 实体类属性别用is开头的属性名,可能会导致RPC反序列化异常。eq:success
- 包名使用1个单词、小写的方式命名,当你纠结词组如何命名时,尝试换一个,放心总会有一个词可以的,哪怕不能完全表达意思。eq:明星闲置:star
- 使用了设计模式,类名要体现出来。eq:public class LoginProxy
- 枚举类统一Enum后缀、成员名称大写、下划线分隔单词。eq:枚举名字:DealStatusEnum,成员名称:SUCCESS / UNKOWN_REASON
躲坑小技巧
- if的{}必须写。避免误读
- 包装类型相等比较必须使用equals。IntegerCache是个大坑
- Long类型赋值常量,后缀用大写L。防止误读为1
- 实体类中除了id,其他属性尽量避免使用基本类型。因为默认值可能会影响业务,Null与0、false并不代表一种业务含义
- 实体类属性不要设置默认值。可能会造成误更新,关于展示的处理可以重新自定义访问器
- 实体类访问器中尽量不要有业务逻辑。否则会增加排查问题的难度
- 尽可能的实现toString,便于打印日志时查问题
- 异常点、关键业务点必须打印日志。便于排查问题。日志要素:业务场景描述、关键业务数据。
参数校验
- 通用参数校验,尽量通过 Hibernate Validator 完成,详情参见:https://blog.csdn.net/dh554112075/article/details/80790464
- 空指针必须校验
- 参数校验是抛异常还是返回错误结果。
- Preconditions.checkNotNull(neme, "neme为null");
- Preconditions.checkArgument(age>0, "age 必须大于0");
单元测试
- 网关接口自动化测试可以通过postman完成,详情参见:https://blog.csdn.net/cai_iac/article/details/81030619
- 单元测试:Mock
IDEA技巧
- Ctrl+Shift+V:打开剪贴板
- Ctrl+Shift+E:打开最近编辑的文件
- 注释折叠代码块
// region 注释内容
。。。
// endregion 注释内容