Tabla de contenido
3. Comparación de funciones marco.
5.2 Configuración de la fuente de datos
5.3 Crear clases de entidad y tablas.
5.6 Crear prueba de interfaz del controlador
1. Introducción
Hay muchos marcos de mejora de Mybatis convencionales y, por supuesto, MybatisPlus es el más utilizado en proyectos. Pero los amigos que han usado MybatisPlus también saben que para operaciones de una sola tabla, el método de codificación encadenado y el soporte Lambda proporcionado pueden simplificar mucho código, pero para operaciones de múltiples tablas, parece ser más que suficiente. Por lo tanto, en la mayoría de los proyectos, todavía se elige XML para operaciones de múltiples tablas. Entonces, aquí presentamos un marco de mejora de Mybatis, que pretende integrar las ventajas de múltiples marcos como MybatisPlus. Ese es Mybatis-Flex.
2. ¿Qué es MyBatis-Flex?
Dirección del sitio web oficial: MyBatis-Flex - Sitio web oficial de MyBatis-Flex
Al igual que Mybatis Plus, Mybatis Flex también es un marco ORM mejorado basado en Mybatis. Pero es más ligero, más flexible y tiene mayor rendimiento que antes.
Lo siguiente es un extracto del sitio web oficial:
MyBatis-Flex es un elegante marco de mejora de MyBatis que es muy liviano y tiene un rendimiento y flexibilidad extremadamente altos. Podemos usar Mybaits-Flex fácilmente para conectarnos a cualquier base de datos, y su QueryWrapper incorporado nos ayuda a reducir en gran medida el trabajo de escritura SQL y reducir la posibilidad de errores.
Con todo, MyBatis-Flex puede mejorar en gran medida nuestra eficiencia y experiencia de desarrollo, permitiéndonos tener más tiempo para concentrarnos en nuestras propias cosas.
3. Comparación de funciones marco.
función o característica |
MyBatis-Flex |
MyBatis-Plus |
Fluent-MyBatis |
Adición, eliminación, modificación y consulta básica de entidades. |
✅ |
✅ |
✅ |
consulta de paginación |
✅ |
✅ |
✅ |
Caché total de consulta de paginación |
✅ |
✅ |
❌ |
Consulta de paginación sin diseño de análisis SQL (más liviana y de mayor rendimiento) |
✅ |
❌ |
✅ |
Consulta de varias tablas: desde varias tablas |
✅ |
❌ |
❌ |
Consulta de varias tablas: unión izquierda, unión interna, etc. |
✅ |
❌ |
✅ |
Consulta de varias tablas: unión, unión todo |
✅ |
❌ |
✅ |
Configuración de clave primaria única |
✅ |
✅ |
✅ |
Múltiples estrategias de generación de ID |
✅ |
✅ |
✅ |
Admite múltiples claves primarias y claves primarias compuestas |
✅ |
❌ |
❌ |
Configuración del controlador de tipo de campo |
✅ |
✅ |
✅ |
Excepto MyBatis, no hay otras dependencias de terceros (más livianas) |
✅ |
❌ |
❌ |
¿QueryWrapper admite la transmisión RPC en proyectos de microservicios? |
✅ |
❌ |
desconocido |
Lápida sepulcral |
✅ |
✅ |
✅ |
bloqueo optimista |
✅ |
✅ |
✅ |
auditoría SQL |
✅ |
❌ |
❌ |
llenado de datos |
✅ |
✅ |
✅ |
Desensibilización de datos |
✅ |
✔️(cargado) |
❌ |
Permisos de campo |
✅ |
✔️(cargado) |
❌ |
Cifrado de campo |
✅ |
✔️(cargado) |
❌ |
reescritura del diccionario |
✅ |
✔️(cargado) |
❌ |
Db + Fila |
✅ |
❌ |
❌ |
Monitoreo de entidades |
✅ |
❌ |
❌ |
Soporte para múltiples fuentes de datos |
✅ |
Con la ayuda de otros marcos o cargos. |
❌ |
Si varias fuentes de datos admiten la gestión de transacciones de Spring, como @Transactional y TransactionTemplate, etc. |
✅ |
❌ |
❌ |
¿Múltiples fuentes de datos admiten proyectos "que no son de Spring"? |
✅ |
❌ |
❌ |
multiinquilino |
✅ |
✅ |
❌ |
Nombre de tabla dinámica |
✅ |
✅ |
❌ |
Esquema dinámico |
✅ |
❌ |
❌ |
4. Comparación de rendimiento
Puede echar un vistazo a la comparación de rendimiento específica (no la he probado específicamente aquí), aquí está la conclusión del sitio web oficial:
5. Rápido de usar
5.1 Maven agrega dependencias
<dependencies>
<!-- 这里为mybatis-flex依赖 -->
<dependency>
<groupId>com.mybatis-flex</groupId>
<artifactId>mybatis-flex-spring-boot-starter</artifactId>
<version>1.6.4</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>1.2.8</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>dynamic-datasource-spring-boot-starter</artifactId>
<version>3.5.0</version>
</dependency>
<dependency>
<groupId>com.mysql</groupId>
<artifactId>mysql-connector-j</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.24</version>
</dependency>
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.8.21</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
</dependencies>
5.2 Configuración de la fuente de datos
La fuente de datos múltiples aquí utiliza la fuente de datos múltiples de SpringBoot, y Mybatis-Flex también admite la configuración de fuente de datos múltiples.
server:
port: 8080
spring:
application:
name: springboot-mybatis-flex
profiles:
active: dev
jackson:
# 不要全局限制,避免字段格式不一致
date-format: "yyyy-MM-dd HH:mm:ss"
locale: zh_CN
time-zone: GMT+8
# druid config
datasource:
dynamic:
primary: primary
datasource:
primary:
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/my-game?useUnicode=true&characterEncoding=utf8&useSSL=false
username: root
password: root
type: com.alibaba.druid.pool.DruidDataSource
druid:
validation-query: SELECT 1
initial-size: 10
min-idle: 10
max-active: 20
min-evictable-idle-time-millis: 180000
test-on-borrow: false
test-while-idle: true
remove-abandoned: true
remove-abandoned-timeout-millis: 1800
log-abandoned: true
pool-prepared-statements: true
max-open-prepared-statements: 100
filter:
slf4j:
enabled: false
web-stat-filter:
enabled: false
autoconfigure:
exclude: com.alibaba.druid.spring.boot.autoconfigure.DruidDataSourceAutoConfigure
5.3 Crear clases de entidad y tablas.
Usuario de clase de entidad:
package org.shamee.demo.entity;
import com.mybatisflex.annotation.Column;
import com.mybatisflex.annotation.Id;
import com.mybatisflex.annotation.KeyType;
import com.mybatisflex.annotation.Table;
import com.mybatisflex.core.keygen.KeyGenerators;
import lombok.*;
import java.io.Serializable;
import java.util.Date;
/**
* @Table 注解自动映射实体类和表字段
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
@Table("t_user")
public class User implements Serializable {
/**
* 声明主键ID,并指定生成器为雪花ID
*/
@Id(keyType = KeyType.Generator, value = KeyGenerators.snowFlakeId)
private String id;
/**
* Column声明字段名称,onInsertValue 自动填充时间
*/
@Column(value = "createdTime", onInsertValue = "now()")
private Date createdTime;
@Column(value = "updatedTime", onInsertValue = "now()", onUpdateValue = "now()")
private Date updatedTime;
/**
* Column声明字段名称,isLogicDelete 逻辑删除
*/
@Column(value = "isDeleted", isLogicDelete = true)
private Boolean isDeleted = false;
@Column(value = "userId")
private String userId;
@Column(value = "userName")
private String userName;
@Column(value = "isUse")
private Boolean isUse;
@Column(value = "battleNum")
private Integer battleNum;
@Column(value = "atk")
private Integer atk;
private String extension;
}
Tabla t_user:
CREATE TABLE `t_user` (
`id` varchar(100) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
`userId` varchar(300) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
`userName` varchar(300) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
`isUse` tinyint(4) NULL DEFAULT NULL,
`battleNum` int(11) NULL DEFAULT NULL,
`atk` int(11) NULL DEFAULT NULL,
`extension` text CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL,
`createdTime` datetime(0) NULL DEFAULT NULL,
`updatedTime` datetime(0) NULL DEFAULT NULL,
`isDeleted` tinyint(4) NULL DEFAULT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = DYNAMIC;
5.4 Crear Dao
package org.shamee.demo.dao;
import com.mybatisflex.core.BaseMapper;
import org.shamee.demo.entity.User;
public interface UserDao extends BaseMapper<User> {
}
5.5 Crear servicio
package org.shamee.demo.service;
import com.mybatisflex.core.query.QueryWrapper;
import com.mybatisflex.core.update.UpdateChain;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import org.shamee.demo.dao.UserDao;
import org.shamee.demo.entity.User;
import org.shamee.demo.entity.table.UserTableDef;
import org.springframework.stereotype.Service;
import java.util.List;
@Service
public class UserService extends ServiceImpl<UserDao, User> {
/**
* 查询全部
* @return
*/
public List<User> selectAll(){
return this.getMapper().selectAll();
}
/**
* 根据userId获取User数据
* @param userId
* @return
*/
public User listById(String userId){
QueryWrapper wrapper = QueryWrapper.create()
// 这里可以指定查询字段
.select(UserTableDef.USER.USER_ID, UserTableDef.USER.USER_NAME, UserTableDef.USER.ATK)
// sql from表名
.from(User.class)
// 查询条件,这里的UserTableDef.USER代码自动编译生成,类似lombok
.where(UserTableDef.USER.USER_ID.eq(userId));
return this.getMapper().selectOneByQuery(wrapper);
}
/**
* 新增
* @param user
*/
public void insert(User user){
this.getMapper().insert(user);
}
/**
* 更新User
* @param user
*/
public void updateEntity(User user){
this.getMapper().update(user);
}
/**
* 局部更新
* @param userId
* @param userName
*/
public void updateRow(String userId, String userName){
UpdateChain.of(User.class)
.set(User::getUserName, userName)
.where(User::getUserId).eq(userId).update();
}
/**
* 删除
* @param userName
*/
public void deleteByWrapper(String userName){
QueryWrapper queryWrapper = QueryWrapper.create().where(UserTableDef.USER.USER_NAME.eq(userName));
this.getMapper().deleteByQuery(queryWrapper);
}
}
5.6 Crear prueba de interfaz del controlador
package org.shamee.demo.controller;
import org.shamee.demo.entity.User;
import org.shamee.demo.service.UserService;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.annotation.Resource;
import java.util.List;
@RestController
@RequestMapping("/api/demo/user")
public class UserController {
@Resource
private UserService userService;
/**
* 查询全部
* @return
*/
@GetMapping("listall")
public List<User> listall(){
return userService.selectAll();
}
/**
* 按userId查询
* @return
*/
@GetMapping("listById")
public User listById(){
return userService.listById("zhangsan");
}
/**
* 新增
* @return
*/
@GetMapping("insert")
public Boolean insert(){
User user = User.builder().userId("zhangsan").userName("张三").atk(100).battleNum(200).build();
userService.insert(user);
return Boolean.TRUE;
}
/**
* 更新
* @return
*/
@GetMapping("update")
public Boolean update(){
userService.updateRow("zhangsan", "张三三");
return Boolean.TRUE;
}
/**
* 删除
* @return
*/
@GetMapping("delete")
public Boolean delete(){
userService.deleteByWrapper("张三三");
return Boolean.TRUE;
}
}
5.7 Resultados de la prueba
Después de ejecutar primero la interfaz de inserción para insertar datos, llame a listall para ver la lista de datos.
6. Resumen
Después de acostumbrarse a Mybatis Plus, comenzar con Mybatis Flex sigue siendo muy similar, pero habrá algunas diferencias de sintaxis. Como declarar anotaciones de clave principal, anotaciones de mapeo de campos, diferencias de uso de QueryWrapper, etc. En general, es una versión mejorada de Mybatis. El oficial también proporciona muchas configuraciones de uso avanzadas. Si está interesado, puede explorarlo.