java编码规范

1,命名规范
必须见文知意,变量必须使用驼峰命名。
常量必须用纯大写字母,每个常量包含注释说明,多个单词用下划线分割,必须用final修饰
2,硬编码
方法之间或调用DAO的时候,因为上下文不是特别固定或者仅仅就一处使用,专门为此定义一个Pojo会导致大量臃肿的类定义,且维护成本较高,因此难免会出现使用Map作为参数的情况。为了保持良好的可维护性,所有的Map键必须引用常量定义,且字段常量最好是标准字段。如

Map<String,Object> param = new HashMap<String,Object>();
	  param.put(FUND_CODE,fundCode);

3,接口命名
 PK查询:get
 条件查询:query
 插入:insert
 多记录插入:insertBatch,为保证性能优化,使用批量增删改
 从其他表插入:insertFrom
 更新:update
 多记录更新:updateBatch,为保证性能优化,使用批量增删改
 多表更新:updateFrom
 插入或更新:merge
 删除:delete
 多记录删除:deleteBatch
 清空表:truncate
 重建索引:rebuildIndex
 备份表:backup
4,分页
查询列表和总行数两个独立的接口,并发发送2个请求以提供最佳用户体验,参数LightDB-EMQuery中的onlyCount字段(BaseQuery不支持)为true(推荐)仅查询总行数,false(默认,兼容现有代码)为同时查询。点击下一页/上一页的时候,不应请求查询总行数(此时通常不会变化,如果一定需要,那重新点击查询即可更新)
5,不分页
如果查询不需要分页,则将pageSize设置为-1。排序不受影响。
6,数据导出
可以提供ta-starter中提供的TaExcelUtils工具,其支持导出大数据量和模板化的Excel.
7,无论是单记录还是批量增删改查,均使用LightDB-EMParameter作为入参,其中T中包括业务参数,可以是List或Request。因为入参很有可能直接对应的是Pojo,因此命名上不限定为必须Request结尾,但是不允许使用Map类型。
8,安全编码与权限控制
默认情况下所有不在白名单的接口均无权限操作,要加入Shiro注解。
9,向后兼容性
 系统参数。在@Value注入时设置合适的默认值,如ip可以设置127.0.0.1、端口可以设置默认值(如zookeeper为2181);
 接口新增方法。使用jdk 8的新特性接口默认实现
 对象参数。设置对象参数的默认值,如是否仅查询行数,在BaseQuery上增加了属性private boolean onlyCount,默认为false,即可兼容(注:要求微服务接口必须使用对象参数)。
10,缓存
 缓存一致性遵循谁缓存、谁清理的原则,服务间依赖时,避免缓存对方领域的结果,性能不满足时提需求即可;
11,日志记录
a,为了能够随时切换到性能最优的日志实现,业务代码中务必使用SLF4J作为日志门面,而不使用具体的日志实现如log4j、jcl或其它。
正例:private static final Logger logger= LoggerFactory.getLogger(Abc . class );
12,正确使用日志级别
DEBUG 级别曰志记录对调试程序有帮助的信息。
• INFO 级别日志用来记录程序运行现场,虽然此处并未发生错误,但是对排查其他错误具有指导意义。
• WARN 级别日志也可以用来记录程序运行现场,但是更偏向于表明此处有出现潜在错误的可能。
• ERROR 级别日志表明当前程序运行发生了错误,需要被关注。但是当前发生的错误,没有影响系统的继续运行。
• FATAL 级别曰志表明当前程序运行出现了严重的错误事件,并且将会导致应用程序中断。
禁止不分重要程度,全部使用INFO或DEBUG进行记录。
正例:
if (logger.isDebugEnabled()) {
logger.debug(“翻译字典列表:{}”, JsonUtils.toJson(recordDictMaps));
}
try {

} catch (TaException e) {
logger.error(“获取翻译字典列表失败”,e);
}
反例:
if (logger.isInfoEnabled()) {
logger.debug(“翻译字典列表:{}”, JsonUtils.toJson(recordDictMaps));
}
try {

} catch (TaException e) {
logger.info(“获取翻译字典列表失败”,e);
}
13,线程池的创建与维护
阿里巴巴java编码规范中有一条,禁止使用Executors创建线程池,原因是为了让写的同学明确线程池的规则,避免资源耗尽。这一条其实说的并不准确,应该禁止的是Executors.newCachedThreadPool(),而非其他线程池如Executors.newFixedThreadPool(n,threadFactory),其目的一是为了防止前者爆掉,其次是在排查日志的时候,一眼就知道线程池的目的。
大多数高级开发人员都善用多线程提高性能,但是很多时候线程的运行都发生了失控,为了避免创建的线程过多或失控,所有线程池必须在com.hundsun.ta.base.ThreadPoolHolder进行注册(BusinessService以及BusinessController已经继承了它),禁止随意的new Thread,或Executors.newCachedThreadPool()等。包括三种中间件客户端自己如Kakfa、Zookeeper等创建的线程池也需要注册。
14,fork and join模式
本节我们所述的fork and join模式并非仅仅指的是ForkJoinPool、ForkJoinTask及相关接口,而是更加广义的异步模式。其之所以广受高级开发人员欢迎,主要得益于其能够成倍的降低响应时间。普通模式的调用和Future模式的工作差异如下:

前面的同步逻辑正常编写,到了可异步的点随时异步,这样响应时间就仅取决于最慢的那个,甚至可以发三个不同的请求,哪个先完成就哪个,例如同时读取Redis缓存或MySQL,以哪个快就返回哪个。互联网公司之所以能够做到限制所有的SQL语句不超过3表关联,且保证响应时间不超过SLA规定的值,其中之一也是得益于此。所以一个业务服务执行时,需要调用很多无相互依赖关系的服务,应采用本模式。如根据客户ID查询客户的基本信息、资产、最近交易明细等,就非常适合采用本模式实现。因此适应异步API的开发非常有用,异步API提供了巨大的性能优势,简化了错误恢复工作。java异步回调机制及使用模式可以参见:https://www.cnblogs.com/zhjh256/p/11876104.html

15,分布式锁
要求统一使用Redis分布式锁。可以通过调用com.hundsun.ta.utils.RedisUtil#tryGetDistributedLock得到分布式锁,com.hundsun.ta.utils.RedisUtil#releaseDistributedLock释放分布式锁。
16,定时任务
禁止使用JDK/Spring自带的定时任务。定时任务是配置在数据库中,通过框架到时候会自动运行。
17,
b) List/Map中查找数据是否存在
由于Map的values是集合,而判断一个集合中是否存在一个对象,JDK是进行遍历判断的,因此复杂度为O(N),如果集合较大的化,性能会非常低下。因此在Map中不要使用containsValue(),在List中不要使用contains(),如果有此需求,则新建一个Map,将key设计为value.toString()(务必重写hashCode()),实际值存储对象,这样可以保证复杂度降低为O(2)。
18,弱业务逻辑相关工具
非业务类型的工具类统一使用 ta-jrescloud-starter中com.hundsun.ta.utils包中的工具类,工具类名以Util结尾、不要以Utils结尾。
19,日期
SimpleDateFormat 是线程不安全的类,定义为static对象,会有数据同步风险,在高并发的情况下,发生的概率很高。所以推荐的方式是推荐的方式之一就是使用Threa dLocal,让每个线程单独拥有这个对象。相比于每次创建一个新的SimpleDateFormat,它的效率会高很多。
正例:
public static ThreadLocal SDF_SHORT_DATE_NUM = new ThreadLocal() {

@Override
protected SimpleDateFormat initialValue() {
return new SimpleDateFormat(SHORT_DATE_FORMAT_NUM);
}
};
20,excel库导入导出文件
对于导出操作,统一使用TaExcelUtils类库进行导出。如果数据量比较大,推荐优先使用csv格式最小化内存需求和防止发生OOM,TaExcelUtils提供对应的输出格式选择(功能上完全相同)。
21,禁止使用Spring Template
Spring虽然为各种中间件封装了易于使用的Template模板,并设置了相关的各种默认值,尤其是MQ的ACK机制。在大容量和特殊场景下,其不够稳定,且故障排查不方便。因此除了RedisTemplate外禁止使用Spring相关Template库,包括但不限于如下:
 RabbitTemplate及Listener
 RestTemplate
 KafkaTemplate及Listener
 MongoTemplate
22,文件和系统命令相关
对于文件上传、下载、创建、删除,操作系统命令执行等功能,一定不要直接调用三方库,这些三方库很可能是不再满足安全要求的,例如apache common-io模块,甚至find-sec-bugs推荐的解决方法在新的安全要求下仍然是不安全的,因为安全漏洞在一直更新,所以无论如何,请直接访问com.hundsun.ta.file模块操作文件,com.hundsun.utils执行命令(包括sftp、shell、telnet等),最小化维护成本。
23,过期的三方包
无论是JDK自带的类库还是三方apache、spring类库,对于标记了@Deprecated注解的类或方法,避免使用,它们一般在注释上说明了推荐的新方法或类,例如JDK自带的Base64相关类。
24,sql规范
 所有表必须包含单字段主键(分区键除外),它可以有意义、也可以无意义,也可以数字(最好为数字,推荐可以使用snowflake id)或非数字(但是必须跨数据库兼容且取值完全相同,不能mysql int类型,oracle varchar类型),且多张表不能共用一个序列或计数器;
 所有表必须包含创建时间、最后更新时间字段,且每次DML操作维护最后更新时间;
 所有核心表(也就是数据量超过10w的表)必须包含分页定位串(建议数字类型或者固定长度,字段名为pos_id),确保无论是否分库分表架构,分页查询排序性能均佳;

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值