Java項目實現【記錄系統操作日志】功能

? 哈嘍,屏幕前的每一位開發者朋友,你們好呀!??

當你點開這篇文章時,或許正對著 IDE 里閃爍的光標發呆,或許剛解決一個卡了三天的 bug,正端著咖啡松口氣 —— 不管此刻的你在經歷什么,都想先和你說聲:“辛苦了,同行者!” 👋?

作為一名摸爬滾打多年的開發工程師,我始終覺得,我們敲出的每一行代碼,不僅是業務邏輯的堆疊,更是無數個 “踩坑與爬坑” 的縮影。從第一次上線時的手忙腳亂,到如今能冷靜應對突發 bug;從對著文檔啃源碼的迷茫,到能給新人講清設計思路 —— 這些藏在鍵盤敲擊聲里的成長,太值得被好好梳理和分享了。 📝?

所以,這一系列文章里,不會有太多高深的架構理論,也不會羅列晦澀的技術文檔。我想聊的,是那些 “教科書里沒寫” 的實戰細節:?

比如上線前必做的 3 個自查動作(親測能減少 80% 的線上問題)🛡?;?

比如和產品經理 “友好溝通” 需求的 5 個小技巧(避免反復改需求到崩潰)🤝;?

比如如何用最少的時間,快速定位線上性能瓶頸(曾靠這招拯救過一次緊急故障)🚀;?

再比如那些看似 “浪費時間” 的重構,其實藏著怎樣的長期價值…… ???

當然,更想和大家聊聊 “技術之外” 的事:如何平衡加班與生活(畢竟身體是敲代碼的本錢)💪,如何在團隊中清晰表達自己的想法(別讓好方案被沉默埋沒)🗣?,甚至是 “35 歲焦慮” 來襲時,我是如何調整心態的…… 🌱?

如果你也和我一樣,相信 “經驗不是用來炫耀的資本,而是能幫同行少走彎路的路燈”,那不妨坐下來喝杯茶,一起在評論區聊聊:你最近遇到的最大挑戰是什么?有沒有哪個瞬間,讓你覺得 “啊,原來我真的成長了”? 💬?

畢竟,開發這條路從來不是孤軍奮戰。我們分享的每一個踩坑故事,都可能成為別人的指路牌;你留下的每一條評論,或許也會給我新的啟發。 🌟?

那么,準備好了嗎?讓我們開始這場 “代碼背后的成長對話” 吧!接下來的每一篇,都等你來拍磚、補充、共鳴 —— 因為最好的經驗,永遠在交流里生長。 🌱?

目錄

一.需求分析

二.實現邏輯(完全由后端實現)

1.自定義注解OperatorLog

2.在所有controller的方法上,添加該自定義注解

3.編寫切面類OperationLogAspect

三.效果展示

1.使用一下管理系統的某個功能

2.查看數據庫,肯定會多一條操作日志

四.特別聲明


一.需求分析

我要實現的效果是,我訪問管理系統的任何一個功能之后,都要往數據庫插入一條操作日志。

舉例:我在管理系統中,新增了一條合同記錄,此時就需要往數據庫插入一條操作日志,樣式如下

二.實現邏輯(完全由后端實現)

1.自定義注解OperatorLog

@Target(ElementType.METHOD)//表明這個注解只能加在方法上
@Retention(RetentionPolicy.RUNTIME)//表明這個注解在程序運行的時候還能被讀取到,而不是用完就丟)
public @interface OperationLog {String moduleName();//模塊名String operationType();//操作類型
}

2.在所有controller的方法上,添加該自定義注解

舉例:

3.編寫切面類OperationLogAspect

@Aspect
@Component
public class OperationLogAspect {//注入SysOperationLogMapper對象@Autowiredprivate SysOperationLogMapper sysOperationLogMapper;//攔截所有加了@OperationLog注解的方法,進行功能無侵入增強(環繞通知)@Around("@annotation(operationLog)")public Object around(ProceedingJoinPoint joinPoint, OperationLog operationLog) throws Throwable {//ProceedingJoinPoint joinPoint:攔截的方法本身(我們要攔截controller層的方法)//OperationLog operationLog:在所攔截的方法上,添加的注解內容//獲取當前的HTTP請求對象HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();//1.獲取請求的controller方法的模塊名稱、操作類型(從注解中獲取)String moduleName = operationLog.moduleName();String operationTypeStr = operationLog.operationType();//2.獲取本次請求的請求方式(如GET、POST、PUT、DELETE)String requestMethod = request.getMethod();//3.獲取請求發起人的用戶名稱(直接從請求對象中獲取即可(別的服務放進去的))//3.1先獲取controller方法的參數實體類Object[] args = joinPoint.getArgs();Object entity = args[0];//必須默認controller的實體類參數放在第一個//3.2通過反射,拿到實體類中的用戶名稱(curUserName)Method getCurUserName = entity.getClass().getMethod("getCurUserName");String operator = (String)getCurUserName.invoke(entity);//4.獲取請求發起人的主機ipString hostIp = ClientIpUtil.getClientIpAddress(request);//5.獲取操作時間(就是當前的時間)Date operationTime = new Date();//6.先默認操作狀態為成功Integer operationStatus = 1;//7.獲取請求方法的全類名,如:com.hxb.xltj.controller.SysLogControllerString methodFullName = joinPoint.getTarget().getClass().getName();//System.out.println(methodFullName);//8.被增強的controller方法的返回結果(字符串類型)String methodResult = null;//9.請求路徑String requestUrl = request.getRequestURI();//10.請求參數String requestParam = JSON.toJSONString(entity);try{//放行被增強的方法Object result = joinPoint.proceed();//查看被增強方法是否執行成功if(result instanceof ResultBody){ResultBody resultBody = (ResultBody) result;//如果返回的結果響應碼不是“000000”,則說明請求失敗了,直接令該日志的狀態為0(失敗)operationStatus = !resultBody.getReturnCode().equals("000000")? 0:1;//如果是“導出”操作,就將返回體ResultBody的data屬性設為空(不給前端展示,太長了)if(operationTypeStr.equals("導出")){methodResult = "";}else{//給返回結果賦值methodResult = result.toString();}}//將結果返回出去,不要讓切面吞被增強方法的原有邏輯return result;}catch(Exception e){throw e;//繼續拋出異常,不影響原有錯誤處理}finally{//看看都獲取到了哪些日志信息//System.out.println(moduleName);//測試模塊//System.out.println(operationType);//查詢//System.out.println(requestMethod);//POST//System.out.println(hostIp);//127.0.0.1//System.out.println(operationTime);//Thu Aug 21 10:48:07 CST 2025//System.out.println(operationStatus);//1(代表成功)//將操作類型轉為整型,再存入數據庫Integer operationType = operationTypeStr.equals("新增")?1:operationTypeStr.equals("刪除")?2:operationTypeStr.equals("修改")?3:operationTypeStr.equals("查詢")?4:operationTypeStr.equals("授權")?5:operationTypeStr.equals("導出")?6:operationTypeStr.equals("導入")?7:operationTypeStr.equals("強退")?8:operationTypeStr.equals("生成代碼")?9:operationTypeStr.equals("清空數據")?10:null;//封裝系統操作日志記錄對象SysOperationLog sysOperationLog = new SysOperationLog(null, moduleName, operationType, requestMethod, operator, hostIp, operationStatus, operationTime,methodFullName,methodResult,requestUrl, requestParam,0,null,null);//將系統操作日志,存入數據庫sysOperationLogMapper.insert(sysOperationLog);}}
}

上述代碼,核心邏輯就是:獲取到【系統日志表】需要的所有字段,然后寫入數據庫即可。

三.效果展示

1.使用一下管理系統的某個功能

2.查看數據庫,肯定會多一條操作日志

四.特別聲明

1.如果你想讓管理系統的所有行為,都記錄到操作日志表中,你需要把后端所有的controller方法,都加上自定義注解@OperatorLog(因為只有這樣,才會被AOP切面進行代碼無侵入增強)

2.由于AOP切面類OperationLogAspect里面,有一些反射操作(通過controller方法的形參獲取操作信息),因此需要團隊伙伴在寫controller方法時,要遵循一定的約束(比如:controller方法必須通過Body接收參數,且Body參數必須放在形參列表的第一位)。

諸如此類,具體需要團隊伙伴遵循哪些約束,需要具體看需求和代碼邏輯,我們主要有這個意識就行,其他都好說。

以上就是通過SpringAOP切面編程,實現【記錄系統操作日志】功能的詳細流程,喜歡的話可以留個免費的關注呦~~~

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/95142.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/95142.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/95142.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

響應式編程框架Reactor【4】

文章目錄七、調度與線程模型7.1 概述7.2 Scheduler: Reactor 的線程調度器7.3 兩大核心操作符:subscribeOn vs publishOn7.4 示例詳解7.4.1 subscribeOn()的全局影響7.4.2 publishOn() 的局部切換7.4.3 多個publishOn切換7.4.4 線程切換時序圖7.5 核心調度器7.5.1 B…

第21節:環境貼圖與PBR材質升級——構建電影級真實感渲染

第21節:環境貼圖與PBR材質升級——構建電影級真實感渲染 概述 基于物理的渲染(Physically Based Rendering, PBR)是當代計算機圖形學中最重要的技術進步之一,它徹底改變了實時渲染的質量標準。在本節中,我們將深入探索…

【ROS2】ROS2 基礎學習教程 、movelt學習

主要博主 參考資料: ROS系列: b站荔枝橙 b戰哈薩克斯坦x 《ROS 2機器人開發從入門到實踐》6.2.2 在RViz中顯示機器人_嗶哩嗶哩_bilibili 動手學ROS2–魚香肉絲 ??????? 古月居ros2教程 北京華清智能科技 ros教程 moveit系列: 愛喝青…

Java類加載與JVM詳解:從基礎到雙親委托機制

在Java開發中,理解JVM(Java虛擬機)和類加載機制是掌握高級特性的關鍵。本文將從JDK、JRE、JVM的關系入手,深入講解JVM的內存結構,并詳細剖析類加載的全過程,包括加載時機、流程以及核心機制——雙親委托模型…

準備機試--圖【y總版】[重要]【最短路】

常用代碼模板3——搜索與圖論 - AcWing 一般,稀疏圖(m約等于n):堆優化版本的dj;稠密圖(mn^2):樸素dj 最短路的難點在于建圖【抽象出點和邊】 樸素dj

Python API接口實戰指南:從入門到精通

🌟 Hello,我是蔣星熠Jaxonic! 🌈 在浩瀚無垠的技術宇宙中,我是一名執著的星際旅人,用代碼繪制探索的軌跡。 🚀 每一個算法都是我點燃的推進器,每一行代碼都是我航行的星圖。 &#x…

Spring和mybatis整合后事務攔截器TransactionInterceptor開啟提交事務流程

目錄一、說明二、TransactionInterceptor開啟事務(1)、攔截方法(2)、開啟事務綁定數據庫連接(3)、mybatis中sql執行數據庫連接獲取(4)、事務提交和當前線程ThreadLocal清理&#xff…

05.《ARP協議基礎知識探秘》

ARP協議基本介紹與實踐 文章目錄**ARP協議基本介紹與實踐**ARP概述ARP報文類型ARP工作過程解析ARP工作原理示意圖無故ARP/免費ARP實驗案例**實驗目標**實驗環境實驗步驟ARP概述 作用:ARP(Address Resolution Protocol,地址解析協議&#xff…

互聯網大廠面試:大模型應用開發崗位核心技術點解析

互聯網大廠面試:大模型應用開發崗位核心技術點解析 第一輪:大模型基礎與上下文工程 問題 1:你能簡單介紹 Transformer 架構的工作原理嗎? 小C:嗯,我理解是 Transformer 主要依賴自注意力機制(Se…

【深度學習新浪潮】有沒有什么方法可以將照片變成線描稿,比如日式漫畫的那種?

一、技術原理與研究進展 1. 線描生成的核心技術路徑 傳統方法:基于邊緣檢測(如Canny算子)和形態學操作,但難以處理復雜紋理和藝術風格。 深度學習方法: 端到端生成:使用U-Net架構(如ArtLine項目)直接學習照片到線描的映射,結合自注意力機制和感知損失提升細節保留能力…

NV032NV037美光固態閃存NV043NV045

NV032NV037美光固態閃存NV043NV045在數字化浪潮席卷全球的當下,存儲技術的每一次突破都深刻影響著從個人消費到企業級應用的各個領域。美光科技作為行業領軍者,其NV系列固態閃存產品始終以技術創新為核心驅動力。本文將聚焦NV032、NV037、NV043、NV045四…

天碩G40工業固態硬盤破解軌道存儲難題

在高鐵與軌道交通高速發展的今天,軌道檢測探傷是保障列車安全運行的核心環節。據統計,我國鐵路總里程已突破16萬公里,日均檢測數據量超10TB。加固平板一體機作為軌道探傷領域的“移動工作站”,需要在跨越大江南北的極端環境中實時…

基于Velero + 阿里云 OSS的Kubernetes 集群的備份與恢復

在 Kubernetes(K8s)中,備份和恢復是保障數據安全與業務連續性的關鍵環節,主要方式包括 ETCD 備份恢復 和 Velero 備份恢復,兩者在備份粒度、恢復影響范圍、存儲位置等方面存在以下差異: 1、ETCD 備份恢復&…

解構與重構:“真人不露相,露相非真人” 的存在論新解 —— 論 “真在” 的行為表達本質

解構與重構:“真人不露相,露相非真人” 的存在論新解 —— 論 “真在” 的行為表達本質緒論:傳統解釋的突圍 —— 從 “藏才” 到 “存真”“真人不露相,露相非真人” 這句諺語,自明代《西游記》以降,便長期…

數據結構:哈希表、排序和查找

一、哈希算法1.將數據通過哈希算法映射成一個健值,存取都在同一個位置,實現數據的高效存儲和查找,時間復雜度由O(n)->O(1)2.哈希碰撞:多個數據通過哈希算法得到的鍵值相同二、哈希表1.構建哈希表存放0-100之間的數據2.哈希算法…

【Java基礎】Java I/O模型解析:BIO、NIO、AIO的區別與聯系(Netty入門必備基礎)

Java I/O模型深度解析:BIO、NIO、AIO的區別與聯系 引言 在Java的網絡編程與文件操作中,I/O(輸入/輸出)模型是繞不開的核心話題。從早期的BIO(Blocking I/O)到Java 1.4引入的NIO(Non-blocking I/…

windows PowerToys之無界鼠標:一套鍵鼠控制多臺設備

💻簡介 在多設備協作的工作場景中,如何實現一套鍵鼠控制多臺設備了?微軟推出的 PowerToys 工具集中的 Mouse Without Borders(無界鼠標),通過軟件層實現跨設備的鍵鼠共享與數據同步功能,為多臺…

一道比較難的sql題,篩選出重復字段的行數

select * from 導入數據表; id city_column 1 北京,上海,廣州 2 上海,上海,深圳 3 北京,杭州,北京 4 上海,廣州,深圳select substring_index(khmc,,,1), * from 導入數據表 truncate table 導入數據表 select count(distinct khmc) from 導入數據表; …

【K8s】整體認識K8s之與集群外部訪問--service

這一篇文章主要是對service發現新的理解 為什么要使用service服務發現? 首先pod的IP,是動態的,當我們重啟一個pod的時候,它會給它分配一個新的IP,但是如果微服務a想要去調用微服務b,他是需要知道微服務b所有…

k8s(自寫)

kubernetes k8s是什么?Kubernetes是什么?架構是怎么樣的?6分鐘快速入門_嗶哩嗶哩_bilibili kubernetes是google開源神器,介于應用服務和服務器之間,能夠通過策略協調和管理多個應用服務,只需要一個yaml文…