首页 > 数据库 >MyBatis if 和多数据库支持

MyBatis if 和多数据库支持

时间:2023-02-14 22:56:05浏览次数:55  
标签:username 数据库 支持 score User SQL MyBatis

1. 前言

动态 SQL 是 MyBatis 最标志性的特性之一。在其它框架中,你可能需要根据不同的条件来拼接 SQL,辗转在符号与条件的判断上,处理起来麻烦而且易错,而 MyBatis 的动态 SQL 可以让我们摆脱这种痛苦,简单而又高效的书写 SQL。

MyBatis 动态 SQL 由 OGNL 表达式和条件标签两部 分组成,我们将会分为多个小节进行介绍。

OGNL 表达式是动态 SQL 的基础,如果你还不了解,请务必点击学习一下。条件标签部分我们将会在四个小节中分别介绍,它们分别是MyBatis if 和多数据库支持(本小节),MyBatis choose和bind小节MyBatis where、set、trim小节MyBatis foreach小节

本小节,我们先来学习最基础的条件标签 if,以及如何使用 if 来让 MyBatis 来支持多数据库。

2. 定义

解释:if 常用于 where 语句中,通过判断参数来决定在 select 语句中是否使用某个查询条件,或者在 update 语句中判断是否更新一个字段,还可以在 insert 语句中决定是否插入一个满足条件的值。

3. 实例

我们以一个实际的例子来看一下 if 是如何工作的。

<select id="selectUserByAgeAndScore" parameterType="com.5axxw.mybatis.model.User" resultMap="userMap">
  SELECT * FROM 5axxw_user
  WHERE age = #{age}
  <if test="score != null">
    AND score = #{score}
  </if>
</select>

在 if 标签中,test 属性是 OGNL 的判断表达式。

selectUserByAgeAndScore 的作用是通过用户年龄和积分来查询用户,当 score 值为 null 时,if 判断不成立,此时生成的 SQL 语句为:

SELECT * FROM 5axxw_user WHERE age = ?

而当 if 成立时,生成的 SQL 语句为:

SELECT * FROM 5axxw_user WHERE age = ? AND score = ?

通过这样条件判断方式,MyBatis 能根据实际情况来动态生成 SQL 语句。

4. 实践

4.1 例1、动态查询用户

请使用 MyBatis 完成对 5axxw_user 表动态查询用户的功能, username为必须的查询条件,年龄和积分若为 null 则不使用该字段进行过滤。

分析:

按照 MyBatis 的开发模式,先在 UserMapper.xml 文件中添加动态查询用户的 select 标签,然后在 UserMapper.java 中增加上对应的方法。

步骤:

首先,在 UserMapper.xml 中添加 select 标签,并在标签中写入 SQL,使用 if 来判断属性值是否为 null,若为 null,则不使用该字段进行查询。如下:

<select id="selectUserByNameCondition" parameterType="com.5axxw.mybatis.model.User"
        resultType="com.5axxw.mybatis.model.User">
  SELECT * FROM 5axxw_user
  WHERE username = #{username}
  <if test="age != null">
    AND age = #{age}
  </if>
  <if test="score != null">
    AND score = #{score}
  </if>
</select>

通过 if 对属性的判断,SQL 的过滤条件就会发生相应的变化。

然后在 UserMapper.java 中添加上对应的接口方法,方法接受 User对象作为参数。

package com.5axxw.mybatis.mapper;

import org.apache.ibatis.annotations.Mapper;
import com.5axxw.mybatis.model.User;

@Mapper
public interface UserMapper {
   User selectUserByNameCondition(User user);
}

结果:

通过如下代码,我们运行 selectUserByNameCondition 这个方法。

UserMapper userMapper = session.getMapper(UserMapper.class);
User condition = new User();
condition.setUsername("pedro");
condition.setScore(200);
User pedro = userMapper.selectUserByNameCondition(condition);
System.out.println(pedro);

condition 对象 username 和 score 属性均不为空,而 age 属性为空,因此最后所执行的 SQL 为:

SELECT * FROM 5axxw_user WHERE username = ? AND score = ? 

成功后,结果为:

User{id=2, username='pedro', age=24, score=200}

5. 多数据库支持

MyBatis 可以根据不同的数据库厂商执行不同的语句,这种多厂商的支持是基于配置文件中的 databaseId。

5.1 配置

首先在 MyBatis 的全局配置文件中添加如下配置:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
  PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
  "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
  <databaseIdProvider type="DB_VENDOR" />
</configuration>

在 configuration 中加入 databaseIdProvider 后,还需要在 databaseIdProvider 标签中添加上需要使用到的数据库名称,如:SQL Server。每一个 property 属性都代表了一个数据库,name 表示数据库厂商名称,value 用来设置别名。

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
  PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
  "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
  <databaseIdProvider type="DB_VENDOR">
    <property name="SQL Server" value="sqlserver"/>
    <property name="MySQL" value="mysql"/>
    <property name="PostgreSQL" value="postgre"/>
  </databaseIdProvider>
</configuration>

5.2 使用

配置完毕后,我们就可以在 mapper xml 文件中,通过 if 来判断当前的数据库厂商,从而动态生成不同数据库的 SQL。

例如,PostgreSQL 支持使用 ||来拼接字符串,而 MySQL 需要使用 concat函数来拼接字符串。

因此,如果在模糊查询的时候,不同的数据库厂商需要不同的 SQL 语句,通过 if 来判断数据库厂商来生成对于的 SQL 语句。

如下:

<select id="selectUserByLikeName" resultType="com.5axxw.mybatis.model.User">
  SELECT * FROM 5axxw_user
  WHERE username LIKE
  <if test="_databaseId == 'mysql'">
    CONCAT('%',#{username},'%')
  </if>
  <if test="_databaseId == 'postgre'">
    '%' || #{username} || '%'
  </if>
</select>

注意,这里 _databaseId 参数是由 MyBatis 提供的内置参数,对应于 databaseIdProvider 中配置的数据库名称。

通过 databaseIdProvider 配置,即时数据库厂商之间存在差异,但仍然可以通过动态 SQL 的形式来支持多数据库。

6. 小结

  • if 简单且好用,是动态 SQL 中的最基础的标签,一看便会。
  • 多数据库支持的应用场景其实较少,但如果真的需要,也可通过 MyBatis 来方便的实现。

标签:username,数据库,支持,score,User,SQL,MyBatis
From: https://www.cnblogs.com/10zhan/p/17121152.html

相关文章

  • 数据库的相关概念
    1.数据库(dataBase)存储数据的仓库,本质是一个文件系统;2.DBMS数据库管理系统DatabseManageMnetSystem 操作和管理数据可的大型软件,用于简历和维护数据库,对数据库......
  • Python 使用mysql.connector、pymysql和 MYSQLdb(MysqlClient)操作MySQL数据库
    MySQL是一个关系型数据库管理系统,由瑞典MySQLAB公司开发,属于Oracle旗下产品。MySQL是最流行的关系型数据库管理系统之一。本文主要介绍安装mysql.connector,、pymysql......
  • Spring+MyBatis声明事务
    一、原则在之前的开发中,事务代码都是分布在业务代码中,难以重用,调整麻烦。所以,Spring提供了声明事务,将事务代码和业务代码分离,再使用AOP实现,事务代码全部在配置文件中完成。......
  • 数据库基础操作 - 5(索引及数据库设计规范)
    7、索引MySQL管饭对索引的定义为:索引(Index)是帮助MySQL高效获取数据的数据结构。提取句子主干,就可以得到索引的本质:索引是数据结构。7.1、索引的分类在一个表中,主键......
  • 数据库基础操作 - 4
    6、事物6.1、什么是事物要么都成功,要么都失败一一一一一1、SQL执行A给B转账A1000-->200B2002、SQL执行B收到A的钱A800B400一一一一一将一组SQL放......
  • Mybatis17 - 逆向工程
    概念正向工程:先创建Java实体类,由框架负责根据实体类生成数据库表。Hibernate是支持正向工程的。逆向工程:先创建数据库表,由框架负责根据数据库表,反向生成如下资源:Java......
  • Mybatis18 - 分页插件
    分页插件JavaWeb服务器实现分页需要在SQL中使用limit,需要获取index,pageSize,pageNum等数据pageSize:每页显示的条数pageNum:当前页的页码index:当前页的起始索引,i......
  • 如何关闭gorm 1.20.0中的数据库实例
    因为我没有在带有*gorm实例的Close()函数中找到dbURI:=fmt.Sprintf("user=%spassword=%sdbname=%sport=%ssslmode=%sTimeZone=%s","username","password","......
  • Mybatis13 - 缓存介绍
    介绍理解缓存的工作机制和缓存的用途。1、缓存机制介绍2、一级缓存和二级缓存①使用顺序查询的顺序是:先查询二级缓存,因为二级缓存中可能会有其他程序已经查出来的......
  • Mybatis12 - 动态SQL
    动态SQLMybatis框架的动态SQL技术是一种根据特定条件动态拼装SQL语句的功能,它存在的意义是为了解决拼接SQL语句字符串时的痛点问题。Oneofthemostpowerfulfeatures......