Backend Development 15 min read

Introduction and Usage Guide for MyBatis-Mate: Enterprise Features for MyBatis-Plus

This article introduces MyBatis-Mate, an official MyBatis‑Plus extension offering enterprise‑level capabilities such as dictionary binding, field encryption, data masking, dynamic DDL maintenance, sharding, multi‑datasource switching, performance logging, and data permission control, with detailed Spring Boot integration examples.

Selected Java Interview Questions
Selected Java Interview Questions
Selected Java Interview Questions
Introduction and Usage Guide for MyBatis-Mate: Enterprise Features for MyBatis-Plus

Today we introduce MyBatis‑Mate, an official MyBatis‑Plus tool that provides enterprise‑grade modules including sharding, data auditing, AC‑algorithm sensitive word filtering, field encryption, dictionary binding, data permission, and automatic DDL generation, aiming to handle data more agilely and elegantly.

Key Features

Dictionary binding

Field encryption

Data masking

Dynamic table structure maintenance

Data audit records

Data scope (data permission)

Database sharding, dynamic datasource, read‑write separation, health‑check auto‑switch

2. Usage

2.1 Dependency Import

Spring Boot automatic dependency annotation package

<dependency>
  <groupId>com.baomidou</groupId>
  <artifactId>mybatis-mate-starter</artifactId>
  <version>1.0.8</version>
</dependency>

Annotation (entity sub‑package usage)

<dependency>
  <groupId>com.baomidou</groupId>
  <artifactId>mybatis-mate-annotation</artifactId>
  <version>1.0.8</version>
</dependency>

2.2 Field Data Binding (Dictionary Write‑Back)

Example: map user_sex dictionary to sexText property.

@FieldDict(type = "user_sex", target = "sexText")
private Integer sex;

private String sexText;

Implement IDataDict to provide dictionary data source.

@Component
public class DataDict implements IDataDict {
    /** Retrieve from DB or cache */
    private Map
SEX_MAP = new ConcurrentHashMap
() {{
        put("0", "女");
        put("1", "男");
    }};

    @Override
    public String getNameByCode(FieldDict fieldDict, String code) {
        System.err.println("字段类型:" + fieldDict.type() + ",编码:" + code);
        return SEX_MAP.get(code);
    }
}

2.3 Field Encryption

Use @FieldEncrypt to encrypt storage and automatically decrypt on query; supports global and annotation‑level algorithms via IEncryptor injection.

@FieldEncrypt(algorithm = Algorithm.PBEWithMD5AndDES)
private String password;

2.4 Field Masking

Apply @FieldSensitive to mask data according to predefined SensitiveType strategies (9 built‑in types) or custom strategies.

@FieldSensitive(type = "testStrategy")
private String username;

@FieldSensitive(type = SensitiveType.mobile)
private String mobile;

Custom strategy registration example:

@Configuration
public class SensitiveStrategyConfig {
    /** Inject custom strategy */
    @Bean
    public ISensitiveStrategy sensitiveStrategy() {
        // custom testStrategy handling
        return new SensitiveStrategy().addStrategy("testStrategy", t -> t + "***test***");
    }
}

2.5 DDL Automatic Maintenance

Handles table structure upgrades for MySQL and PostgreSQL.

@Component
public class PostgresDdl implements IDdl {
    @Override
    public List
getSqlFiles() {
        return Arrays.asList("db/tag-schema.sql", "D:\\db\\tag-data.sql");
    }
}

Dynamic execution example:

ddlScript.run(new StringReader("DELETE FROM user;\nINSERT INTO user (id, username, password, sex, email) VALUES (20, 'Duo', '123456', 0, '[email protected]');"));

2.6 Dynamic Multi‑Datasource Switching

Use @Sharding to freely switch data sources at mapper level.

@Mapper
@Sharding("mysql")
public interface UserMapper extends BaseMapper
{
    @Sharding("postgres")
    Long selectByUsername(String username);
}

Custom sharding strategy example:

@Component
public class MyShardingStrategy extends RandomShardingStrategy {
    @Override
    public void determineDatasourceKey(String group, Invocation invocation, SqlCommandType sqlCommandType) {
        // custom key selection logic
        this.changeDatabaseKey(group, sqlCommandType, keys -> chooseKey(keys, invocation));
    }
}

2.7 Distributed Transaction Logging

Performance interceptor configuration for SQL timing, formatting, and optional log writing.

@Slf4j
@Component
@Intercepts({@Signature(type = StatementHandler.class, method = "query", args = {Statement.class, ResultHandler.class}),
             @Signature(type = StatementHandler.class, method = "update", args = {Statement.class}),
             @Signature(type = StatementHandler.class, method = "batch", args = {Statement.class})})
public class PerformanceInterceptor implements Interceptor {
    private long maxTime = 0;
    private boolean format = false;
    private boolean writeInLog = false;
    // ... interceptor implementation omitted for brevity ...
}

2.8 Data Permission

Add @DataScope on mapper methods to enforce row‑level permissions.

// Test data permission for "test" type with mixed pagination
@DataScope(type = "test", value = {
    @DataColumn(alias = "u", name = "department_id"),
    @DataColumn(alias = "u", name = "mobile")
})
@Select("select u.* from user u")
List
selectTestList(IPage
page, Long id, @Param("name") String username);

Custom data‑scope provider example (adds department IN clause and mobile LIKE condition).

@Bean
public IDataScopeProvider dataScopeProvider() {
    return new AbstractDataScopeProvider() {
        @Override
        protected void setWhere(PlainSelect plainSelect, Object[] args, DataScopeProperty dataScopeProperty) {
            if ("test".equals(dataScopeProperty.getType())) {
                for (DataColumnProperty dataColumn : dataScopeProperty.getColumns()) {
                    if ("department_id".equals(dataColumn.getName())) {
                        Set
deptIds = new HashSet<>(Arrays.asList("1", "2", "3", "5"));
                        ItemsList itemsList = new ExpressionList(deptIds.stream().map(StringValue::new).collect(Collectors.toList()));
                        InExpression inExpr = new InExpression(new Column(dataColumn.getAliasDotName()), itemsList);
                        plainSelect.setWhere(plainSelect.getWhere() == null ? new Parenthesis(inExpr) : new AndExpression(plainSelect.getWhere(), inExpr));
                    } else if ("mobile".equals(dataColumn.getName())) {
                        LikeExpression likeExpr = new LikeExpression();
                        likeExpr.setLeftExpression(new Column(dataColumn.getAliasDotName()));
                        likeExpr.setRightExpression(new StringValue("%1533%"));
                        plainSelect.setWhere(new AndExpression(plainSelect.getWhere(), likeExpr));
                    }
                }
            }
        }
    };
}

Final SQL example produced by the above configuration:

SELECT u.* FROM user u
WHERE (u.department_id IN ('1', '2', '3', '5'))
AND u.mobile LIKE '%1533%'
LIMIT 1, 10

For more MyBatis‑Mate usage examples, visit the official repository:

https://gitee.com/baomidou/mybatis-mate-examples

BackendJavaShardingSpring BootMyBatisdata encryptiondata masking
Selected Java Interview Questions
Written by

Selected Java Interview Questions

A professional Java tech channel sharing common knowledge to help developers fill gaps. Follow us!

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.