偷偷摘套内射激情视频,久久精品99国产国产精,中文字幕无线乱码人妻,中文在线中文a,性爽19p

記錄業(yè)務(wù)系統(tǒng)操作日志方案實(shí)踐

開(kāi)發(fā) 前端
通過(guò)以上實(shí)踐,我們可以實(shí)現(xiàn)對(duì)業(yè)務(wù)系統(tǒng)中數(shù)據(jù)變更的追蹤和記錄,通過(guò)通用的接口規(guī)則,可以動(dòng)態(tài)地展示不同業(yè)務(wù)數(shù)據(jù)模型變更過(guò)程。這種方案的核心是將數(shù)據(jù)變更的追蹤和記錄與業(yè)務(wù)邏輯分離,使其成為一個(gè)通用的、可復(fù)用的服務(wù)。通過(guò)注解和 AOP技術(shù),我們可以輕松地在業(yè)務(wù)系統(tǒng)中引入這種服務(wù),而無(wú)需修改原有的業(yè)務(wù)代碼。不僅可以提高代碼的可維護(hù)性,而且記錄用戶的操作日志也更加優(yōu)雅。

1. 背景

在日常業(yè)務(wù)需求開(kāi)發(fā)中,經(jīng)常有對(duì)關(guān)鍵業(yè)務(wù)功能做操作日志記錄,即某用戶在某一時(shí)間操作某功能,操作前后的數(shù)據(jù)記錄。尤其是在按業(yè)務(wù)功能模塊拆分成多個(gè)project時(shí),就會(huì)面臨記錄操作日志與業(yè)務(wù)邏輯之間解耦、記錄操作日志更加簡(jiǎn)單、操作前后業(yè)務(wù)數(shù)據(jù)(字段)對(duì)比等問(wèn)題。

接下來(lái)我們將介紹一種易于理解、簡(jiǎn)單接入操作日志的方法,同時(shí)提供一個(gè)通用的接口,方便前端開(kāi)發(fā)者進(jìn)行頁(yè)面展示。

2. 預(yù)期目標(biāo)

設(shè)計(jì)并實(shí)現(xiàn)一種通用的數(shù)據(jù)變更追蹤和動(dòng)態(tài)展示(對(duì)象描述)實(shí)踐方案,該解決方案允許開(kāi)發(fā)人員通過(guò)簡(jiǎn)單的注解來(lái)標(biāo)記需要追蹤的業(yè)務(wù)數(shù)據(jù)。該系統(tǒng)能夠自動(dòng)捕獲所有標(biāo)記數(shù)據(jù)的添加、修改等操作,并詳細(xì)記錄數(shù)據(jù)變更的每一步。同時(shí),提供的動(dòng)態(tài)展示接口,可以清晰、直觀地展示數(shù)據(jù)的變更明細(xì),讓數(shù)據(jù)的前后差異一目了然。具體包括:

  • 提供通用數(shù)據(jù)結(jié)構(gòu)的接口,無(wú)需給前端額外定義接口字段描述。
  • 低成本、快速記錄數(shù)據(jù)Model的每一個(gè)字段變更前后的值。

3. 技術(shù)選型與對(duì)比

3.1業(yè)務(wù)代碼嵌套

在應(yīng)用層面,可以在業(yè)務(wù)代碼中添加日志,記錄下關(guān)鍵操作和數(shù)據(jù)的變更以及字段描述。例如,可以在每個(gè)數(shù)據(jù)庫(kù)操作前后添加日志,記錄下操作名稱、時(shí)間、影響的數(shù)據(jù)等信息。這種方案需要改變業(yè)務(wù)代碼(散彈式),增加編碼的復(fù)雜性,麻煩且不夠通用。

3.2Canal

Canal 是阿里巴巴開(kāi)源的一款基于 MySQL 二進(jìn)制日志(binlog)的增量數(shù)據(jù)訂閱和消費(fèi)組件。其主要功能是提供對(duì) MySQL 數(shù)據(jù)庫(kù)變更的實(shí)時(shí)監(jiān)聽(tīng),包括表結(jié)構(gòu)或數(shù)據(jù)變動(dòng)等。Canal 記錄數(shù)據(jù)變更時(shí),它捕獲的是數(shù)據(jù)庫(kù)層面上的原始變更事件,即 insert、update 和 delete 操作。這些事件是基于單個(gè)數(shù)據(jù)庫(kù)事務(wù)的,Canal 本身并不處理關(guān)聯(lián)數(shù)據(jù)的變更。當(dāng)一個(gè)業(yè)務(wù)模型關(guān)聯(lián)了多個(gè)表的數(shù)據(jù)時(shí),訂閱 binlog,需要根據(jù)業(yè)務(wù)的實(shí)際情況對(duì)獲取的 binlog 數(shù)據(jù)進(jìn)行正確組裝和解析,包括正確的將多個(gè)表的變更合并到一個(gè)業(yè)務(wù)對(duì)象中。

這種方案的優(yōu)點(diǎn)是和業(yè)務(wù)邏輯完全解耦。缺點(diǎn)也很明顯,缺點(diǎn)是只能對(duì)數(shù)據(jù)庫(kù)的更改做記錄。

3.3觸發(fā)器

觸發(fā)器會(huì)增加數(shù)據(jù)庫(kù)的復(fù)雜性和維護(hù)成本,如果處理不當(dāng),觸發(fā)器可能導(dǎo)致性能問(wèn)題,不考慮。

3.4AOP

面向切面編程(Aspect-Oriented Programming,AOP)是一種編程范式,主要用于將那些與業(yè)務(wù)邏輯無(wú)關(guān),但在多個(gè)地方都需要使用的公共操作(如日志記錄、安全檢查、事務(wù)處理等)分離出來(lái),降低系統(tǒng)的耦合度。AOP的運(yùn)行需要?jiǎng)討B(tài)生成代理類和織入切面,本實(shí)現(xiàn)方案一部分基于AOP實(shí)現(xiàn)。

4. 系統(tǒng)設(shè)計(jì)與實(shí)現(xiàn)

本實(shí)現(xiàn)方案基于Annotation+AOP+SpringEL+Swagger實(shí)現(xiàn),AOP用于攔截配置自定義注解的Controller方法執(zhí)行前后記錄操作前后的數(shù)據(jù)。鑒于多數(shù)業(yè)務(wù)系統(tǒng)中,每一個(gè)業(yè)務(wù)模塊都有根據(jù)ID查詢明細(xì)數(shù)據(jù),由此在記錄數(shù)據(jù)時(shí)回調(diào)此業(yè)務(wù)的getById方法獲取明細(xì)數(shù)據(jù)。SpringEL默認(rèn)為調(diào)用業(yè)務(wù)模塊的Service的getById方法,如果是uuid等其他條件獲取數(shù)據(jù)時(shí)可以自定義配置。Swagger用于獲取模型定義,在引入此類庫(kù)的項(xiàng)目啟動(dòng)時(shí),會(huì)掃描帶有@ApiModel注解的模型并緩存,當(dāng)模型發(fā)生變更時(shí),找到相對(duì)應(yīng)的模型定義一同存儲(chǔ)。為這種不確定的實(shí)體字段存儲(chǔ),本方案采用MongoDB作為數(shù)據(jù)庫(kù)。

圖片圖片

4.1定義Filter(TrackingAccessFilter)

圖片圖片

說(shuō)明:初始化請(qǐng)求Context,并解析request相關(guān)信息。

4.2定義注解(@TrackingPoint)

定義操作類型與注解,操作類型為便于搜索,注解用于標(biāo)記需要追蹤變更的 Controller 方法。

圖片圖片

圖片圖片

說(shuō)明:

  • TrackingType 操作類型。
  • moduleAlias 接口對(duì)應(yīng)的模塊名稱,moduleClass接口對(duì)應(yīng)的模塊名稱枚舉類,如配置modelClass時(shí),moduleAlias必為枚舉類中的字段。主要為了方便模塊名稱的管理。
  • title,標(biāo)題,此次操作類型的簡(jiǎn)單描述,通常為接口功能描述。
  • login,接口是否是登錄后訪問(wèn),如登錄后訪問(wèn),會(huì)回調(diào)AccessUserService獲取當(dāng)前用戶信息。
  • id,業(yè)務(wù)模型ID,也可以是UUID獲其他。
  • tracker:業(yè)務(wù)模塊的對(duì)應(yīng)Service的Bean,結(jié)合id最終拼接成SpringEL表達(dá)式,如Expression描述。
  • preEvent:即在controller執(zhí)行前執(zhí)行的表達(dá)式,如為空時(shí)則默認(rèn)使用Expression定義。當(dāng)默認(rèn)表達(dá)式不滿足需求時(shí)可自定義。
  • postEvent:與preEvent相同,只是在controller執(zhí)行后執(zhí)行。

4.3定義Tracker,業(yè)務(wù)模型回調(diào)接口

圖片圖片

說(shuō)明:業(yè)務(wù)模塊Service實(shí)現(xiàn)此接口,這樣就能獲取到業(yè)務(wù)實(shí)體Model。通過(guò)Spring EL表達(dá)式調(diào)用業(yè)務(wù)基礎(chǔ) Service 的 getById或listByIds等方法,分別獲取方法執(zhí)行前后的數(shù)據(jù)快照。將兩次數(shù)據(jù)快照進(jìn)行對(duì)比,然后獲取相對(duì)應(yīng)的Model描述,并生成詳細(xì)的變更記錄存儲(chǔ)到MongoDB中。為不污染原業(yè)務(wù)Service代碼,建議適配Tracker接口并注入原Service來(lái)實(shí)現(xiàn)getById、listByIds方法。雖增加了實(shí)現(xiàn)類,但對(duì)于 項(xiàng)目中一個(gè)模塊的業(yè)務(wù)確是一勞永逸。

4.4定義AccessUserService用戶信息回調(diào)接口

圖片圖片

說(shuō)明:當(dāng)注解中l(wèi)ogin為true時(shí),回調(diào)此接口,獲取當(dāng)前登錄用戶信息,如為false時(shí),回調(diào)getAnonymousUser()方法。

4.5定義TrackingPointAspect攔截請(qǐng)求

圖片圖片

圖片圖片

說(shuō)明:

  • 此切面用于在帶有自定義注解的 Controller 方法執(zhí)行前后進(jìn)行攔截。主要功能解析注解內(nèi)容生成SpringEL并執(zhí)行,獲取數(shù)據(jù)模型。
  • before同步執(zhí)行。當(dāng)為修改操作時(shí),為避免出現(xiàn)數(shù)據(jù)不一致,所以同步查詢數(shù)據(jù)修改前的快照。
  • afterReturing方法中,當(dāng)業(yè)務(wù)執(zhí)行完成后,發(fā)送事件,異步執(zhí)行以提高效率。

4.6日志存儲(chǔ)

圖片圖片

圖片圖片

說(shuō)明:因預(yù)期目標(biāo)想做到通用,業(yè)務(wù)字段的變更不確定,故而采用NoSQL數(shù)據(jù)庫(kù)存儲(chǔ),本實(shí)現(xiàn)方案內(nèi)置以MongoDB為默認(rèn)存儲(chǔ)數(shù)據(jù)庫(kù),僅對(duì)埋點(diǎn)的接口追蹤日志存儲(chǔ),業(yè)務(wù)方可自定義日志處理器。如業(yè)務(wù)方自定義實(shí)現(xiàn)存儲(chǔ),實(shí)現(xiàn)AccessLogPersist接口并且配置為Bean即可,默認(rèn)存儲(chǔ)即失效。

4.7定義通用接口規(guī)則

為兼容不同業(yè)務(wù)Model不同的字段定義,接口返回變更前后的數(shù)據(jù)同時(shí),將字段描述同時(shí)返回,以用戶修改為例定義接口如下:

圖片圖片

圖片圖片

說(shuō)明:

  • oldObject:變更前數(shù)據(jù)節(jié)點(diǎn)。
  • newObject:變更后數(shù)據(jù)節(jié)點(diǎn)。
  • objectDescription:數(shù)據(jù)字段自釋義節(jié)點(diǎn),key為對(duì)象節(jié)點(diǎn)key,value值即是字段的含義。
  • user: 修改人的信息。
  • 如節(jié)點(diǎn)為object對(duì)象節(jié)點(diǎn),同級(jí)節(jié)點(diǎn)下會(huì)自動(dòng)添加 *Description后綴關(guān)鍵詞,說(shuō)明該對(duì)象描述,支持多級(jí)。
  • 通用數(shù)據(jù)展示某一條修改日志明細(xì)
  • 日志接口數(shù)據(jù)中含有數(shù)據(jù)節(jié)點(diǎn)的字段描述,以實(shí)現(xiàn)一個(gè)數(shù)據(jù)變更明細(xì)的動(dòng)態(tài)展示,后文加以示例。
  • module:模塊
  • title:標(biāo)題
  • type:操作類型

5. 實(shí)戰(zhàn)案例

5.1以修改用戶信息請(qǐng)求為例,執(zhí)行時(shí)序圖

圖片圖片

本節(jié)將以一個(gè)簡(jiǎn)單的用戶(User)和任務(wù)(Task)的修改操作為例,介紹如何使用本方案實(shí)現(xiàn)數(shù)據(jù)變更追蹤和動(dòng)態(tài)展示功能。

5.2引入pom

圖片圖片

5.3實(shí)現(xiàn)用戶信息回調(diào)接口

圖片圖片

說(shuō)明:項(xiàng)目中實(shí)現(xiàn)權(quán)限,當(dāng)為登錄接口時(shí),自動(dòng)回調(diào)此方法將LoginUser設(shè)置到AccessLog.user對(duì)象中。

5.4業(yè)務(wù)接口回調(diào)實(shí)現(xiàn)

圖片圖片

圖片圖片

圖片圖片

說(shuō)明:任務(wù)模塊Service同理

5.5業(yè)務(wù)接口埋點(diǎn)

圖片圖片

5.6修改請(qǐng)求

分別修改User和Task id為1的User和Task,分別提交修改數(shù)據(jù)如下:

{
  "age": 32,
  "id": 1,
  "username": "姜強(qiáng)"
}
{
  "contractName": "jturbo",
  "id": 1,
  "name": "任務(wù)名稱2"
}

說(shuō)明:returncode為0說(shuō)明業(yè)務(wù)接口返回成功。

5.7通用展示

由上面兩條日志,根據(jù)接口規(guī)則定義,前端查看變更明細(xì)時(shí)展示如下:

用戶模塊時(shí):

圖片圖片

任務(wù)模塊時(shí):

圖片圖片

前端可忽略業(yè)務(wù),根據(jù)接口規(guī)則動(dòng)態(tài)渲染,也可使用JSONDiff,高亮差異。

6. 總結(jié)與展望

通過(guò)以上實(shí)踐,我們可以實(shí)現(xiàn)對(duì)業(yè)務(wù)系統(tǒng)中數(shù)據(jù)變更的追蹤和記錄,通過(guò)通用的接口規(guī)則,可以動(dòng)態(tài)地展示不同業(yè)務(wù)數(shù)據(jù)模型變更過(guò)程。這種方案的核心是將數(shù)據(jù)變更的追蹤和記錄與業(yè)務(wù)邏輯分離,使其成為一個(gè)通用的、可復(fù)用的服務(wù)。通過(guò)注解和 AOP技術(shù),我們可以輕松地在業(yè)務(wù)系統(tǒng)中引入這種服務(wù),而無(wú)需修改原有的業(yè)務(wù)代碼。不僅可以提高代碼的可維護(hù)性,而且記錄用戶的操作日志也更加優(yōu)雅。

雖然當(dāng)前已經(jīng)能夠滿足大部分需求,但在未來(lái),還計(jì)劃增加功能:

在業(yè)務(wù)場(chǎng)景允許的情況下增加一鍵回退功能。

對(duì)于此方案大家有更好的建議,歡迎留言討論。

作者簡(jiǎn)介

姜強(qiáng)強(qiáng)姜強(qiáng)強(qiáng)


經(jīng)銷商技術(shù)部-商業(yè)資源團(tuán)隊(duì)

016年加入汽車之家,目前主要負(fù)責(zé)經(jīng)銷商事業(yè)部?jī)?nèi)創(chuàng)新商業(yè)項(xiàng)目的研發(fā)工作,熱衷于業(yè)內(nèi)新技術(shù)的探索與實(shí)踐。

責(zé)任編輯:武曉燕 來(lái)源: 之家技術(shù)
相關(guān)推薦

2024-04-25 08:24:51

C#系統(tǒng)操作日志

2024-11-29 10:00:00

Python日志記錄

2023-03-06 11:36:13

SpingBoot注解

2012-09-06 09:31:14

PHPmysqlpdo

2013-01-17 09:04:41

微軟云操作系統(tǒng)System Cent

2011-09-02 09:42:04

.NET平臺(tái)

2019-04-04 09:19:08

日志京東流式計(jì)算

2014-02-26 11:01:28

日志優(yōu)化系統(tǒng)日志

2010-04-07 09:09:49

Oracle查詢

2023-10-16 07:39:02

ELKpod日志

2016-06-01 11:27:24

2023-10-20 15:08:28

pod日志采集

2024-09-02 00:27:51

SpringAOP自定義

2024-10-17 08:26:53

ELKmongodb方案

2025-09-09 02:00:00

2010-04-09 14:20:59

Unix操作系統(tǒng)

2025-05-14 03:22:00

2017-05-02 09:34:49

QQ空間

2022-07-18 10:29:33

數(shù)據(jù)分布式系統(tǒng)
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)