如何不保留 sqlSession.selectOne 返回值?

How to not persist sqlSession.selectOne returned value?

我的目标是不保留 SqlSession.selectOne returned 值。问题是,如果您执行 sqlSession.selectOne(使用 API 端点)然后直接编辑数据库,例如使用 MySQL workbench。在您编辑数据库并执行另一个 API 端点请求后,returned 值将不会更改。

这就是您重现问题的方式:

  1. 获取对端点的请求。 returned 值为 false。
  2. 更新数据库,这样如果您再次执行获取请求,returned 值应该为真。相反,它 returned false.

解决此问题的唯一方法是重新启动服务器,这是不可行的。

我就是这样 sqlSession.selectOne:

  1. 布尔值=sqlSession.selectOne(参数);
  2. sqlSession.commit();
  3. return值;
@Repository
public class Admin_LoginImpl {
  private SqlSession sqlSession;

  public Admin_LoginImpl() {
    Reader reader = null;
    try {
      reader = Resources.getResourceAsReader("mybatis-config.xml");
    } catch (IOException e) {
      e.printStackTrace();
    }
    SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
    sqlSession = sqlSessionFactory.openSession();
  }

  public void createTableIfNotExists() {
    sqlSession.update("Admin_Login.createTableIfNotExists");
    sqlSession.commit();
  }

  public boolean exist(String User_ID) {
    boolean isExist = sqlSession.selectOne("Admin_Login.exist", User_ID);
    sqlSession.commit();
    return isExist;
  }
}

mybatis-config.xml

<?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>
    <properties resource="application.properties"/>
    <environments default="development">
        <environment id="development">
            <transactionManager type="JDBC"/>
            <dataSource type="POOLED">
                <property name="driver" value="${spring.datasource.driver-class-name}"/>
                <property name="url" value="${spring.datasource.url}"/>
                <property name="username" value="${spring.datasource.username}"/>
                <property name="password" value="${spring.datasource.password}"/>
            </dataSource>
        </environment>
    </environments>
    <mappers>
        <mapper resource="builder/User_LoginMapper.xml"/>
        <mapper resource="builder/User_InfoMapper.xml"/>
        <mapper resource="builder/User_DetailMapper.xml"/>
        <mapper resource="builder/TransactionsMapper.xml"/>
        <mapper resource="builder/Transactions_ProgressMapper.xml"/>
        <mapper resource="builder/StatementsMapper.xml"/>

        <mapper resource="builder/admin/Admin_LoginMapper.xml"/>
        <mapper resource="builder/admin/Admin_TransactionsMapper.xml"/>
    </mappers>
</configuration>

build/admin/Admin_LogginMapper.xml

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="Admin_Login">
    <update id="createTableIfNotExists">
        CREATE TABLE IF NOT EXISTS `admin_login` (
        `ID` int NOT NULL AUTO_INCREMENT,
        `User_ID` char(12) NOT NULL,
        PRIMARY KEY (`ID`),
        UNIQUE KEY `User_ID_UNIQUE` (`User_ID`)
        ) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci
    </update>
    <select id="exist" parameterType="String" resultType="boolean">
        SELECT EXISTS(SELECT 1 FROM admin_login WHERE User_ID=#{User_ID})
    </select>
</mapper>

我做了什么:

  1. 尝试过 sqlSession.close(); // 这会导致错误。
  2. 试图做 sqlSession.clearCache(); // 没有帮助。

我负担不起:

  1. 删除@Repository 并为每个休息端点请求手动创建新对象Admin_LoginImpl。这将显着增加响应时间。

发生此问题是因为您在 Admin_LoginImpl 中创建了一个 SqlSession 并重复使用它。这不是推荐的使用 mybatis 的方式。默认情况下,mybatis 使用绑定到会话的缓存,因此如果您重复相同的查询,它将 return 缓存结果。

会话创建不是一项繁重的操作,应该针对每个请求执行一次。您遇到的性能问题不是由会话创建引起的,因为 SqlSessionFactory 创建需要时间。

要解决此问题,您可以在存储库的构造函数中保留 SqlSessionFactory 创建,但为每个事务创建 SqlSession

但更好的解决方案是使用 MyBatis-Spring 集成,它可以让您正确集成 spring 和免费的会话管理。