You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

升级至Hibernate 5.4.3后出现空指针异常,求技术支持

Hibernate 5.4.3升级后findUniqueWithNamedQuery方法空指针异常问题

原Web应用的HibernateCrudServiceDAO类在Hibernate 5.1.0版本下运行稳定,升级到5.4.3版本后出现问题:

  • IntelliJ提示org.hibernate.Query类和org.hibernate.query.Query.setFlushMode()方法过时,已替换为org.hibernate.query.Query类和setHibernateFlushMode()方法
  • 替换后,findUniqueWithNamedQuery方法抛出空指针异常

相关代码

HibernateCrudServiceDAO方法

@SuppressWarnings("unchecked")
public <T> T findUniqueWithNamedQuery(String queryName, Map<String, Object> params){
    Set<Entry<String, Object>> rawParameters = params.entrySet();
    Query query = session.getNamedQuery(queryName); 

    for(Entry<String, Object> entry : rawParameters){
        query.setParameter(entry.getKey(), entry.getValue());
    } 

    return (T) query.setHibernateFlushMode(FlushMode.MANUAL).uniqueResult();
}

调用代码

User user = crudService.findUniqueWithNamedQuery(User.BY_CREDENTIALS, QueryParameters.with("userName", userName).and("password", digest).parameters());

命名查询

@NamedQuery(name = User.BY_CREDENTIALS, query = "Select u from User as u where u.userName = :userName and u.password = :password")

问题分析与解决方法

空指针的可能来源及对应处理:

  1. Session或Named Query为空

    • session.getNamedQuery(queryName)可能返回null(比如命名查询不存在、Session未正确初始化)
    • 解决:增加非空校验,快速定位问题
  2. Params参数为空

    • 如果传入的params为null,调用params.entrySet()会直接抛出空指针
    • 解决:先判断params是否为空,再遍历参数
  3. 链式调用隐藏空指针

    • 链式调用query.setHibernateFlushMode(...).uniqueResult()如果query为空,会直接抛空指针,且难以定位是哪一步出问题
    • 解决:拆分链式调用,分步执行

修改后的代码:

@SuppressWarnings("unchecked")
public <T> T findUniqueWithNamedQuery(String queryName, Map<String, Object> params){
    // 校验Session有效性
    if (session == null) {
        throw new IllegalStateException("Hibernate Session 未初始化");
    }
    // 获取Named Query并校验
    Query query = session.getNamedQuery(queryName);
    if (query == null) {
        throw new IllegalArgumentException("未找到指定命名查询: " + queryName);
    }
    // 处理参数(避免params为空时抛异常)
    if (params != null && !params.isEmpty()) {
        for (Map.Entry<String, Object> entry : params.entrySet()) {
            query.setParameter(entry.getKey(), entry.getValue());
        }
    }
    // 拆分链式调用,避免空指针定位模糊
    query.setHibernateFlushMode(FlushMode.MANUAL);
    return (T) query.uniqueResult();
}

额外注意:确保代码中导入的Query是org.hibernate.query.Query,不要残留旧的org.hibernate.Query导入,避免类混淆。

内容的提问来源于stack exchange,提问作者Christopher Dodunski

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.19 19:28:16