如何自動填充SQL語句中的公共字段 1. 前言 2. 通用方式 2.1 開發Mybatis審計插件 2.2 Mybatis Plus 自動填充 基於 Mybatis Plus 3.3.0 3. 總結

寫在前面:2020年面試必備的Java後端進階面試題總結了一份複習指南在Github上,內容詳細,圖文並茂,有需要學習的朋友可以Star一下!
GitHub地址:https://github.com/abel-max/Java-Study-Note/tree/master

1. 前言

我們在設計數據庫的時候一定會帶上新增、更新的時間、操作者等審計信息。 之所以帶這些信息是因爲假如有一天公司的數據庫被人爲刪了,儘管可能有數據庫備份可以恢復數據。但是我們仍然需要追蹤到這個事是誰幹的,在什麼時間乾的,具體幹了哪些事等等,方便定責和修補。但是我們變更每條數據都要去顯式變更這些信息就十分繁瑣,我們希望無感知的來處理這些信息。

2. 通用方式

那麼有什麼好的解決思路呢?在 Spring Data 框架中提供 @CreatedBy 和 @LastModifiedBy 來捕捉誰創建或修改的實體以及 @CreatedDate 和 @LastModifiedDate 來捕捉合適創建或修改了實體。如果你使用相關的框架就可以使用這些特性。那麼其實我們知道國內 Spring Data JDBCSpring Data JPA 並不是主流,主流的是 Mybatis 。那麼我們有哪些選擇?

2.1 開發Mybatis審計插件

如果你使用了原生的 Mybatis 可以編寫一個審計插件來實現這些功能。我在之前講解過 Mybatis 插件的教程,並不是非常難的事。如果你想拿來就用,其實 GitHub 上提供了很多可供選擇的 Mybatis 審計組件,本來我打算手寫一個,但是確實人家寫的好。你可以通過關鍵詞 Mybatis Audit 來搜索到它們選擇一款最適合你的。

2.2 Mybatis Plus 自動填充

如果你使用了 Mybatis Plus ,可以藉助於其自動填充功能來實現。

基於 Mybatis Plus 3.3.0

只需要實現 MetaObjectHandler 接口:

@Component
public class MybatisAuditHandler implements MetaObjectHandler {
    @Override
    public void insertFill(MetaObject metaObject) {
        // 聲明自動填充字段的邏輯。
        String userId = AuthHolder.getCurrentUserId();
        this.strictInsertFill(metaObject,"creator",String.class, userId);
        this.strictInsertFill(metaObject,"createTime", LocalDateTime.class,LocalDateTime.now());
    }
    @Override
    public void updateFill(MetaObject metaObject) {
        // 聲明自動填充字段的邏輯。
        String userId = AuthHolder.getCurrentUserId();
        this.strictUpdateFill(metaObject,"updater",String.class,userId);
        this.strictUpdateFill(metaObject,"updateTime", LocalDateTime.class,LocalDateTime.now());
    }
}

然後我們擴展一下 Mybatis Plus 的 Model<T> 把公共審計字段放進去並聲明對應的填充策略:

public abstract class BaseEntity<T extends Model<?>> extends Model<T> {
    @TableField(fill = FieldFill.INSERT)
    private String creator;
    @TableField(fill = FieldFill.INSERT)
    private LocalDateTime addTime;
    @TableField(fill = FieldFill.UPDATE)
    private String updater;
    @TableField(fill = FieldFill.UPDATE)
    private LocalDateTime updateTime;
}

最後我們的實體類不再直接繼承 Model<T> 改爲上面的 BaseEntity<T> :

@Data
@EqualsAndHashCode(callSuper = false)
public class UserInfo extends BaseEntity<UserInfo> {
    @TableId(value = "user_id", type = IdType.ASSIGN_ID)
    private String userId;
    private String username;
    @Override
    protected Serializable pkVal() {
        return this.userId;
    }}

這樣我們就不用再關心這幾個公共字段了,當然你可以根據需要添加更多你需要填充的字段。

3. 總結

今天我們SQL審計中的一些公共字段的自動填充的常用方案進行了一些介紹,特別對 Mybatis Plus 提供的功能進行了介紹相信能夠幫助你簡化一些樣板代碼的編寫。但是SQL審計並不僅僅這麼簡單,根據你的業務的不同會有不同的設計。如果設計的更加精細化的話,會通過鏡像或探針的方式採集所有數據庫的訪問流量,並基於SQL語法、語義的解析技術,記錄下數據庫的所有訪問和操作行爲。

來源:https://www.tuicool.com/articles/im6nmuq

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章