Springboot中如何优雅的写好Service层代码

news2025/1/13 13:31:17

前言

Springboot中如何优雅的写好controller层代码》一不小心进入了全站综合热榜,收到了大家热情的支持,非常感谢大家,同时说明大家都有同样一个诉求,想好好写代码,不想给别人挖坑,争取可以早点下班。今天我再接再厉,再和家大家分享一下对如何写好service层代码一点粗略看法,欢迎大家点评指正。

如何优雅写好Service层代码

其实如果controller层规划好了,完成了入参数据的统一校验,返回结果统一封装,那么servcie层就相对简洁清爽多了,基本上就是纯纯的业务逻辑。具体的业务功能千变万化,但是大致的套路都差不多。

在当下的很多项目建设当中,微服务架构、分布式部署、前后端分离,基本上属于标配了,所以在service层的业务逻辑和传统的单体项目相比,除了会调用Dao层的数据库操作方法,也会调用一些远程的方法。以电商项目为例来说,调用订单服务接口进行下单操作时,要先确认是否有库存,就会在订单服务接口内调用远程的库存服务接口,确认是否有库存,如果确认还有库存,继续调用订单服务的dao接口进行下单的业务逻辑,并调用库存服务的减库存接口,进行扣减库存。

因此,如何优雅写好service层代码,基本就分成了两块:

  • 如何优雅调用本地dao接口

  • 如何优雅调用远程服务接口

优雅调用本地dao接口

本地的dao接口调用其实相对简单的多,根据实际业务需要去调用即可。唯一需要注意的地方就是关于异常的处理,不管是增加、删除、修改、查询,尽量不要在dao调用上去try catch。为什么呢?没有必要,因为SQL写正确了,大概率是不会有异常的;如果在执行前SQL写的不正确,启动的时候就会报异常了,再去try catch捕获异常,有些画蛇添足。同样的道理,如果数据库挂了,连接失败,即便是捕获了异常,依然什么也做不了。所以这样的try catch没有意义,没有意义的事的又何必去做呢。反而,如果try catch中捕获了异常,那么你就必须进行有意义的异常处理,仅仅打印个日志不算处理,有意义的处理是指通过个异常处理可以保证后续程序的正确执行,因为异常的正确处理和事务回滚也有关系。很多时候,如果你发现,由于业务发生异常时应该数据回滚但却没有回滚,十有八九和不当的异常处理有关。

如果在SQL执行过程中异常,且当前SQL执行异常不希望影响后续业务逻辑,那么可以捕获。另外处理异常的时候,如果实在处理不了就向上抛,或者进行一些业务处理,以保证异常不会影响后续业务程序的正常执行。

大批量数据的写

关于数据写操作的dao调用,要特别注意,比较优雅的做法是,在删除、修改、增加的数据时候,先预估一下大致的数据量,如果数据量不多,直接操作也不会有太大影响;如果数据量很大,建议划分分若干组,小批量的进行操作,这样做有以下两个原因:

  • 大批量的数据写操作,会造成大量数据锁定状态,引起其他业务操作的阻塞;

  • 大批量的数据写操作,会引起索引结构的调整,消耗的时间更长;

小批量操作的好处,就是不会造成大量数据长时间锁定而阻塞其他业务请求,另外也索引结构的调整时间也会小一些,但这不代表把全部数据写完所消耗的时间会更短,因为影响数据库读写的因素有很多,小批量数据写操作更多考虑的是对业务整体的影响要更小。

优雅调用远程服务接口

在《Springboot中如何优雅的写好controller层代码》中,有小伙伴留言SpringCloud架构的项目,也能按这样的模式进行吗?其实完全没有问题,因为SpringCloud架构的项目,本质上是若干个springboot项目组成、彼此之间可以相互远程调用,所以只要是springboot项目都可以采用这样的模式让controller层的代码清爽起来。

因此,如果是使用SpringCloud或Dubbo这样分布式架构的项目,在service层就会有一些远程调用,即调用另外一个项目的接口。这种情况,建议使用用try catch进行异常捕获处理,捕获后有两种选择:如果这个远程调用失败不影响当前业务的继续执行,可以仅仅打印日志就行;如果这个远程调用失败与当前业务是强耦合关系,那就不仅要记录异常日志,还要处理这个异常,处理的方式有很多,这举几个例子供作参考:

  • 抛出自定义的运行时异常,以便上层需要回滚就回回滚;

  • 在catch里手动回滚其他数据操作;

  • 记录一下发生异常时的数据信息,让程序继续向下执行,另外采用数据补偿机制来补救;

  • 在catch中实现重试机制(一般情况下,dubbo、springcloud中有重试机制,不需要自己单独实现,这里主要是针对那些需要自己实现重试机制的情况);

总之,异常处理的本质是为保证程序顺利执行,记录日志是为了发生异常时可以定位追踪问题原因。不要为了记录日志而去try catch,需要记录的话,在关键位置记录一下日志就可以了,满屏都是try catch,太影响阅读体验了。毕竟代码最终是给虚拟机执行的,但是首先是给人看的,阅读性好,后续其他人在维护这段代码的时候效率就高,那就可以少加班了,多爽。

同步方法与异步方法

一般情况下,程序里的方法调用都同步方法,即方法之间是顺序执行的。异步方法是指异步方法被调用的时候,不用等异步方法执行完或有返回结果就可以继续向下顺序执行其他方法。有的时候业务逻辑比较复杂,全部采用同步方法执行,所需要消耗的时间就是所有顺序执行方法之和。一个比较有效的代化思路,就是可以把复杂业务逻辑中,对主线业务逻辑没有影响的业务逻辑抽取成异步方法,这样整个调用时间=同步方法的调用时间之和+异步方法中执行最长时间;在性能上会有一定提高 。

控制方法长度

为什么要控制方法长度?最主要的原因是为了程序的可阅读性和可维护性。相对比较短的方法,读着就舒服,就让人心情好,维护的时候能快速找到重点,改的时候效率就高。

怎么才能控制好方法长度?

建议了解一下设计模式六大原则中的单一职责;

有没有什么好的标准呢?

给编程工具里安装一个阿里编码规约插件,如果我没有记错好像是80行,但是这个也不绝对,标准是死的,个别可以根据实际情况灵活变通,不要动不动就搞个几百行、上千行的就行,如果给你一篇几千字的文章,就一个段落,你会怎么想?

总之,大家不要相互挖坑,写好代码,早点下班,陪陪女朋友,陪陪家人、孩子,多香呀。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/156403.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【Spring源码】CommonAnnotationBeanPostProcessor.postProcessMergedBeanDefinition()详解

CommonAnnotationBeanPostProcessor的postProcessMergedBeanDefinition()中一共包含3个方法,上篇文章我们介绍了的第一个方法,它一个父类调用(如下图),其实就是处理PostConstruct和PreDestroy这两个注解的这篇我们继续…

一起聊聊数据治理

统一赵秦车轨,推行秦篆,统一七国文字,兵器统一标准,统一度量衡… 我们优秀的数据治理专家-秦始皇! 数据治理这个名字起得好,一般人听不懂,实际上并不是IT人员的专属,广义上来说我们日…

纳米软件分享:为什么要进行电池充放电测试?电池充放电系统测试步骤

在日常生活中电能一直是我们接触过的最为方便的能源,而我们也通过各种方法对电能进行储存从而让我们能随时随地的使用这种能源,比如手机中的锂电池、电动车中的充电电池等。 充电锂电池经过多年的技术革新,综合性能不断提升,已经应…

基于node.js和Vue的食堂窗口美食评价系统/美食网站

摘要本论文主要论述了如何使用Node.js语言开发一个食堂窗口美食评价系统,本系统将严格按照软件开发流程进行各个阶段的工作,采用B/S架构,面向对象编程思想进行项目开发。在引言中,作者将论述食堂窗口美食评价系统的当前背景以及系…

【高级人工智能】国科大《高级人工智能》联结主义 笔记 + 考试回忆

国科大《高级人工智能》吴老师部分——联结主义笔记 吴老师上课dddd,上课东西太多太杂,听不太懂比较煎熬,但是课后花点时间理解理解,还是挺有帮助的考试按照重点复习即可,虽然答疑时提到的传教士野人没考😅…

神经网络、激活函数

目录1.双层神经网络计算神经网络层数的时候不包括输入层。2.逻辑回归的神经网络如何实现隐藏单元如何计算?,3x1矩阵,3x1矩阵,上标[1]表示第一层向量化(单个训练样本):隐藏层:,,为4x3矩阵,x为3x1…

spring cloud gateway 整合sentinel使用过程使用遇到的问题

最近在进行spring cloud gateway 整合 sentinel 在此过程中遇到的问题进行汇总 1. spring gateway 整合sentinel gateway的路由会自动加一个前缀 效果如下 问题原因 代码在 org.springframework.cloud.gateway.discovery.DiscoveryClientRouteDefinitionLocator#DiscoveryClie…

【迅为iMX6Q】开发板 Linux 5.15.71 RTL8211E 以太网驱动适配

相关参考 【迅为iMX6Q】开发板 u-boot 2022.04 SD卡 启动 【迅为iMX6Q】开发板 u-boot 2020.04 RTL8211E 以太网驱动适配 【迅为iMX6Q】开发板 Linux 5.15.71 SD卡 启动 开发环境 win10 64位 VMware Workstation Pro 16 ubuntu 22.04 -【迅为imx6q】开发板,…

【学习笔记】【Pytorch】三、常用的Transforms

【学习笔记】【Pytorch】三、常用的Transforms学习地址主要内容一、Transforms模块介绍二、transforms.ToTensor类的使用1.使用说明2.代码实现三、transforms.Normalize类的使用1.使用说明2.代码实现四、transforms.Resize类的使用1.使用说明2.代码实现五、transforms.Compose类…

IIC协议初识及OLED写入指令、数据和显示的代码实现

目录 一、IIC协议概述 二、IIC协议起始和终止信号 三、应答信号 四、数据发送的时序 五、OLED写入指令和数据 六、OLED显示一个点的思路 七、OLED显示一个点的代码 八、OLED列地址 九、OLED显示图片 一、IIC协议概述 1、IIC概述 IIC(集成电路总线&#…

UI设计师与UE设计师有什么区别?

设计在我们的生活中扮演着重要的角色,但是面对越来越多的专业术语和相近的岗位职责,人们总是困惑:明明是差不多的岗位,为什么要整那么多的词?其实,在它们神似的外表下,潜藏着巨大的差异&#xf…

虹科分享 | 实时操作系统INtime RTOS第7版功能更新介绍

INtime简介 INtime是专为基于PC的嵌入式解决方案而设计的可扩展实时操作系统,功能包括动态控制多个主机上多个节点(核心)上的进程,以及系统所有节点之间的丰富进程间通信,可应用于多核x86兼容处理器的非对称多处理(AM…

【阶段三】Python机器学习17篇:机器学习项目实战:随机森林回归模型

本篇的思维导图: 项目实战(随机森林回归模型) 项目背景 作为国家的支柱产业,房地产的稳定发展关乎国际民生。近几年,房地产价格飞速上涨,连创新高。在这种情况下研究房价的影响因素,具有重要的理论和现实意义。弄清影响房价的主要经济因素,探究我国房地产投资是…

calc()方法的使用

calc实现css中动态计算 环境 根据元素高度的变化,动态控制padding值 <marquee:name"up index"behavior"scroll"scrolldelay"30"direction"up"v-else-if"item.scrollPocition 3 ? true : false":style"{--positi…

核心乐理---五线谱基础

音符 音符的长度 音符的长度都是相对的定义 一般来说讲全音符设为一拍&#xff0c;但如果将二分音符设为一拍的话&#xff0c;全音符就是两拍 附点音符 可以在音符后跟上一个小点来改变音符的长度&#xff0c;如果一个音符后面跟了n个原点&#xff0c;它的长度就会变为原来的…

【学习记录】阿里云服务器+宝塔

环境&#xff1a;阿里云服务器&#xff0c;linux Centos系统 一、安装宝塔 参考链接&#xff1a;阿里云 ECS 服务器入门使用宝塔安装使用 1、进入云服务器控制台&#xff0c;打开远程连接 2、初次使用&#xff0c;可重置登录密码和连接密码 这是远程连接时需要输入的密码 这…

测试开发基础 | 计算机网络篇(二):物理层与数据链路层

计算机网络知识是自动化测试等技术基础&#xff0c;也是测试面试必考题目。霍格沃兹测试学院特别策划了本系列文章&#xff0c;将带大家一步步夯实计算机网络的基础知识。一、物理层由于物理层知识在互联网软件研发工作中用到的并不多&#xff0c;所以可以仅做一个简单的了解。…

Prompt: No !!!

Prompt is Not Good. Prompt 这个方法实际上并不是很好 Prompt 可以是in-context learning的一种。prompt-based learning has taken NLP by storm!! prompt-based的方法在NLP中引起风暴。但&#xff0c;Prompt-based的方法实际上不太行&#xff1a; 1. Inefficiency: The pro…

基于python的企业编码生成系统 (完整的代码+项目说明)

《企业编码生成系统》程序使用说明 在PyCharm中运行《企业编码生成系统》即可进入如图1所示的系统主界面。在该界面中可以选择要使用功能对应的菜单进行不同的操作。在选择功能菜单时&#xff0c;只需要输入对应的数字即可。 图1 系统主界面 具体的操作步骤如下&#xff1a;…

匿名内部类的理解(java + Android)

是不是有同学跟我一样学了知识&#xff0c;不使用&#xff0c;一段时间就忘了&#xff1f; 今天说说java的匿名内部类这个东西&#xff0c;今天就因为这个东西被程序媛欺负了&#xff0c;我心里难受啊。 匿名内部类的官方说法特别不容易理解&#xff0c;是从"有没有名字…