贴一份我以前整理的 JAVA开发规范:前端
JAVA开发规范java
luo@leader.cn程序员
代码总体风格 web
你们使用统一的规范,方便交流,减小维护成本 redis
服务分层、命名规范 sql
服务名\服务名-api\src\main\java\com\wisdom\服务名\ 数据库
service 全部的服务接口,统一前缀为I,后缀为 Service 编程
子模块名x 后端
IXxxService 设计模式
子模块名y
IXxxService
IMainXxx1Service 不要出现 XxxParam、 XxxSearch
IMainXxx2Service
IMainXxx3Service
bank other service
dto 全部的先后端交互对象,统一后缀为 DTO
exception 全部的自定义异常,应该继承于运行时异常,统一后缀为Exception
服务名\服务名-provider\src\main\java\com\wisdom\服务名\
common 全部全局的共享东西:全部的常量、枚举、静态类,包括各类工具类,redis、mq访问工具类
Constants 当前服务共用的常量类
XxxUtil 当前服务共用的工具类
XxxBaseService 当前服务共用的服务类
XxxRedisUtil 当前服务共用的redis工具类
XxxRabbitMqUtil 当前服务共用的mq工具类
XxxConfig 示例:com.wisdom.jasmine.mvc.CheckLoginInterceptor
XxxHandler 示例:com.wisdom.jasmine.mvc.GlobalExceptionHandler
XxxException 特有的异常类
service 处理业务逻辑,全部的服务接口实现类,统一后缀为 ServiceImpl,若有必要,下面还能够建立一层package,代表子模块名,可是package不宜太深
子模块名x
XxxServiceImpl
子模块名y
YyyServiceImpl
MainXxx1ServiceImpl
MainXxx2ServiceImpl
MainXxx3ServiceImpl
mapper 全部的数据库访问类,统一后缀为Mapper
XxxMapper
YyyMapper 只有复杂的 查询sql, 不该该有修改、新增、删除sql
model 全部的数据库实体映射类,统一后缀为Model
XxxModel
YyyModel
message 后端和mq 交互的pojo,尽可能少使用,应该使用DTO
Web层就是controller层,直接前端对接项目,服务名必定要有一个 web 后缀
服务名\服务名-web\src\main\java\com\wisdom\服务名\
controller 处理视图,全部的Controller类,统一后缀为 Controller
XxxController
api 服务的dto,provider服务的model 应该不相同,不然考虑是否服务没定义 / 划分好。
每一个表对应一个model,一个mapper。但不须要每个model 一个service,好比一些关联表的查询/新增/修改/删除操做,直接在主表对于的service完成。
每一个service应该有对应的一个主表。但有时候也可能有多个。
通常状况下,service和mapper和model和数据库表 同名。
XxxParam、 XxxSearch、XxxMessage 不能忘文知义,增长沟通成本,并且转换起来很麻烦。
为何Service层不能调用其它Service?
比较清晰的单向关联:
N向关联(可能存在循环依赖):
通常命名规范
Controller层 |
Service层 |
DAO层 |
|
query/page |
getOne |
selectOne |
获取单个实体,参数就是实体自己 |
getByYyy |
selectById |
按照ID获取单个实体 |
|
list Page
|
selectByXxx |
按照某条件获取单个实体,参数就是实体某个字段 |
|
|
按照某条件,获取实体的list集合 |
||
listAll |
selectAll |
返回全部行 |
|
add |
add |
insert |
新增单个实体。不存在 insertByXxx 方法 |
modify |
modify |
update |
更新单个实体 |
updateByXxx |
这个状况少见, 通常是经过id 进行更新 |
||
save |
save |
|
新增或修改, 不须要saveOrUpdate 方法名 |
业务方法 |
相同 业务方法 |
相同或不须要 |
|
Service 层:
list获取实体的list集合
page 分页查询,统一返回, PageInfo<实体Model>
数据流转:
数据库层命名规范
字段使用要统一, state、status、 统一 status
表: 表的业务含义应该清晰明确, 不宜使用过多字段。< 30 ..
princ inter
不要这样引发误会的缩写,
要么就不使用缩写,而是全写,要么使用通用的缩写,
pom 规范
pom 提取公共配置 commons
使用最少的dependency,尽可能从parent中继承
依赖应该尽可能简化
须要仔细考虑每个dependency 是不是必须的
注释规范
每一个类写明 用途、注释、做者、关联
每次修改 写明缘由、做者、时间
/**
* 这个类是为了作什么,主要用途是abc
*
* @author LK(lk@qq.com)
* @Time 2018-12-29
*/
javadoc 注释标签语法
@author 对类的说明 标明开发该类模块的做者
@version 对类的说明 标明该类模块的版本
@see 对类、属性、方法的说明 参考转向,也就是相关主题
@param 对方法的说明 对方法中某参数的说明
@return 对方法的说明 对方法返回值的说明
@exception 对方法的说明 对方法可能抛出的异常进行说明
日志规范
理解和使用 debug、info、warn、error 各个级别,通常日志使用info基本,捕捉到错误若是要记录异常,必须使用 error 级别。
异常处理规范
尽可能不要try catch(Exception e) 这个由统一的MVC的ExceptionHandler 来作
不合理的示例
mapper.AttachmentMapper#deleteAttachmentByObject 方法是否是能够简化为 delete ?
mapper.AttachmentMapper#queryByObject queryByObject -> query
provider.RepayOverdueProvider#insertOrUpdateCommit 奇怪的命名
provider.CreditorAdvanceProvider provider 是什么? service 仍是Dao?
lock.LockKeys lock 一个package 只有一个类, 是否是放到 constants 更好?
invite.enums.QueryDateTypeEnum enums 是否是放到 constants 更好?
invite.utils.ActivityInviteUtil 不须要单独创建util 包
product.utils.UploadUtils UploadUtils 并非 product 才有的一个工具类
product.service.impl.ProductServiceImpl provider 服务 使用service 仍是 service.impl ? 至少应该是统一
domain.custom.CollectionCalendarView
search.CreditorAdvanceSearch
com.wisdom.daffodil.model.bank.BindCardReq 不要搞特殊化,统一使用DTO就好
阿里巴巴规范
【强制】POJO 类中布尔类型的变量,都不要加 is ,不然部分框架解析会引发序列化错误。
【强制】不要使用一个常量类维护全部常量,应该按常量功能进行归类,分开维护
【强制】全部的覆写方法,必须加@ Override 注解。
【强制】全部的相同类型的包装类对象之间值的比较,所有使用 equals 方法比较。
【强制】关于基本数据类型与包装数据类型的使用标准以下:
1 ) 全部的 POJO 类属性必须使用包装数据类型。
2 ) RPC 方法的返回值和参数必须使用包装数据类型。
3 ) 全部的局部变量【推荐】使用基本数据类型。
【强制】定义 DO / DTO / VO 等 POJO 类时,不要设定任何属性默认值。
【强制】 POJO 类必须写 toString 方法。使用 IDE 的中工具: source > generate ,toString时,若是继承了另外一个 POJO 类,注意在前面加一下 super.toString 。
【强制】关于 hashCode 和 equals 的处理,遵循以下规则:
1) 只要重写 equals ,就必须重写 hashCode 。
2) 由于 Set 存储的是不重复的对象,依据 hashCode 和 equals 进行判断,因此 Set 存储的对象必须重写这两个方法。
3) 若是自定义对象作为 Map 的键,那么必须重写 hashCode 和 equals 。
【强制】 ArrayList 的 subList 结果不可强转成 ArrayList , 不然会抛出 ClassCastException异常: java . util . RandomAccessSubList cannot be cast to java . util . ArrayList ;
【强制】 在 subList 场景中,高度注意对原集合元素个数的修改,会致使子列表的遍历、增长、删除均产生 ConcurrentModificationException 异常。
【强制】使用工具类 Arrays . asList() 把数组转换成集合时,不能使用其修改集合相关的方法,它的 add / remove / clear 方法会抛出UnsupportedOperationException 异常。
【强制】线程资源必须经过线程池提供,不容许在应用中自行显式建立线程。
【强制】线程池不容许使用 Executors 去建立,而是经过 ThreadPoolExecutor 的方式,这样的处理方式让写的同窗更加明确线程池的运行规则,规避资源耗尽的风险。
【强制】 SimpleDateFormat 是线程不安全的类,通常不要定义为 static 变量,若是定义为
static ,必须加锁,或者使用 DateUtils 工具类。
【强制】对多个资源、数据库表、对象同时加锁时,须要保持一致的加锁顺序,不然可能会形成死锁。
【强制】多线程并行处理定时任务时, Timer 运行多个 TimeTask 时,只要其中之一没有捕获抛出的异常,其它任务便会自动终止运行,使用 ScheduledExecutorService 则没有这个问题。
【强制】在一个 switch 块内,每一个 case 要么经过 break / return 等来终止,要么注释说明程序将继续执行到哪个 case 为止 ; 在一个 switch 块内,都必须包含一个 default 语句而且放在最后,即便它什么代码也没有。
【强制】不要捕获 Java 类库中定义的继承自 RuntimeException 的运行时异常类,如:
IndexOutOfBoundsException / NullPointerException,这类异常由程序员预检查
来规避,保证程序健壮性。
【强制】异常不要用来作流程控制,条件控制,由于异常的处理效率比条件分支低。
【强制】对大段代码进行try-catch,这是不负责任的表现。catch时请分清稳定代码和非稳定代码,稳定代码指的是不管如何不会出错的代码。对于非稳定代码的catch尽量进行区分异常类型,再作对应的异常处理。
【强制】捕获异常是为了处理它,不要捕获了却什么都不处理而抛弃之,若是不想处理它,请将该异常抛给它的调用者。最外层的业务使用者,必须处理异常,将其转化为用户能够理解的内容。
【参考】在代码中使用“抛异常”仍是“返回错误码”,对于公司外的http/api开放接口必须使用“错误码”;而应用内部推荐异常抛出;跨应用间RPC调用优先考虑使用Result方式,封装isSuccess()方法、“错误码”、“错误简短信息”。
文件是:
https://files.cnblogs.com/files/FlyAway2013/2018-JAVA%E5%BC%80%E5%8F%91%E8%A7%84%E8%8C%83.rar