首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >JPA nativeQuery返回缓存的resultList

JPA nativeQuery返回缓存的resultList
EN

Stack Overflow用户
提问于 2015-12-27 19:49:43
回答 2查看 1.5K关注 0票数 0

我有以下课程:

Company.class:

代码语言:javascript
复制
public class Company {
    @JoinTable(name = "company_employee", joinColumns = @JoinColumn(name = "company_id") , inverseJoinColumns = @JoinColumn(name = "employee_id") )
    @ManyToMany(fetch = FetchType.LAZY)
    private Set<Employee> employees;

    @Column(name = "score")
    private BigDecimal score;
}

和Employee.class

代码语言:javascript
复制
public class Employee {
         @ManyToMany(fetch = FetchType.EAGER, mappedBy="employees")
         private Set<Company> companies;
}

Company的Score列在db中始终为null,从不通过dao更新,因为还有其他表包含每个唯一的对Company-Employee的得分。我只需要Score的值,只有当我用id获取Employee时,所以这个情况下,集合中的所有Company实例都应该包含得分,因此我将得到Employee得分对,其中employee是取Employee的。为了实现这一点,我有以下代码:

代码语言:javascript
复制
public Employee get(Long id) {
    Employee emp = (Employee) dao.find(id);
    List<Company> compList = compnanyService.getByEmpId(id);
    Set<Company> compSet = new HashSet<Company>(compList);
    emp.setCompanies(compSet);
    return emp;
}

而公司Dao包含的方法:

代码语言:javascript
复制
public List<Company> getByEmpId(Long id) {
        final Query query = this.entityManager.createNativeQuery("select company.comp_id, ...some other fields, score.score from company join score on company.company_id=score.company_id where score.employee_id=:employee_id",
                Company.class);
        query.setParameter("employee_id", id);
        List<Company> comps = query.getResultList();
        return comps;
}

问题是,getByEmpId(id)给出了一个ResultList,其中company.score为null,尽管在db中执行,但它不是null。

我怀疑存在一些缓存干预,所以我尝试从本机查询中删除一些列,并且它应该在映射时调用一个带有“没有找到列”(或类似的)消息的异常,但是这个方法仍然给List<Company>提供了它们位置上的所有字段,尽管Hibernate在控制台中打印出我的本机查询并进行了所有更改。我在这里做错了什么,如何实现我所需要的?谢谢。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-12-28 17:17:55

所以我就这么做了:

从查询中在db中创建视图:

  1. CREATE VIEW companyscore AS select company.comp_id, score.emp_id ...some other fields, score.score from company join score on company.comp_id=score.comp_id;
  2. 创建相应的实体CompanyScore,将主id组合为comp_id和emp_id,并创建视图作为表。
  3. 将雇员实体更改为: 公共级雇员{ @OneToMany(fetch = FetchType.EAGER) @JoinColumn(name = "emp_id")私营成套公司; }

这样,我不仅有得分字段始终一致,而且我可以选择一组字段显示,因为整个公司类是相当广泛的,我不需要所有的字段为这个特殊的情况。

票数 0
EN

Stack Overflow用户

发布于 2015-12-28 14:12:04

它可能与第一级缓存相关联,当使用本机SQL查询时,缓存可能不同步。来自这里

如果您绕过JPA并直接在数据库上执行DML,则可以通过原生SQL查询、JDBC或JPQL更新或删除查询执行DML,那么数据库可能与第一级缓存不同步。如果您在执行DML之前访问过对象,它们将保持旧状态,而不包括更改。根据您正在做的事情,这可能是可以的,否则您可能希望从数据库中刷新受影响的对象。

因此,您可以尝试使用来自refreshEntityManager方法。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34484203

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档