java - 如何处理@ViewScoped页面中的 'cached'实例?

标签 java jpa caching eclipselink

应用以 JSF 运行, Primefaces , eclipselink ,不是一个小应用程序,大约 100 页/bean 都运行良好

我在理解我的 @ViewScoped 时遇到了一些麻烦页面有效,我得到一个 select UI组件,填充了一个简单的List<People>和一个后端 selectedPeople在我的 bean 里


// all getters, setters, JPA annotations, all good
public class People {
    private String name;
    private List<Car> cars;
}

@ManagedBean
@ViewScoped
public class PeopleBean {
    @EJB
    private Service sPeople;
    private People selectedPeople;
    private List<People> listPpl;

    @PostConstruct
    public void init(){
        listPpl = sPeople.readAll();      // always good, same as DB values
    }

    public People getSelectedPeople(){
       return selectedPeople;
    }

    public People setSelectedPeople(People p){     // p is an old element
       selectedPeople = p;                         // BREAKPOINT
    }

    // getter for the list too
    public void method(){
        Logger.getAnoymousLogger().severe(selectedPeople.getCars()); // the one the old people, not the ne contained in the actual list
    }
}

<p:selectOneMenu id="selectP" value="#{peopleBean.selectedPeople}" converted="#{genericSecuerdConverter}" >
    <p:ajax event="change" partialSubmit="true" listener="#{peopleBean.method()}" />
    <f:selectItems value="#{peopleBean.listPpl}" var="people" itemLabel="#{people.name}" itemValue="#{people}" />
</p:selectOneMenu>

使用顺序和问题是(从调试中获取的信息):

  • 转到peoplePage.xhtml选择元素在哪里,IDs列表的元素是 #410, #411, #412 (3 人)
  • 转到modif.xhtml , 换第三个人(去掉一个 car , 存入DB(check in DB))
  • 回到peoplePage.xhtml ,列表没问题,IDs在调试中是 #650, #651, #652
  • 更改 selectUI 的值(来自 null )以选择一个人,并在断点处,p似乎是 #412元素,所以它的汽车列表上的变化是不可见的,它不是来自 listPpl (因为只包含有效元素,对应DB),是一种缓存

我试图禁用 ecpliselink 缓存状态 EclipleLink cache

  • 更改 eclipselink 属性
  • 更改JPA属性
  • 使用@Cacheable(false)

没有人有效果,也没有进入私有(private)导航,也没有清除浏览器缓存并返回页面,p元素仍然是第一次加载时的旧元素

我以为@ViewScoped允许每次都像第一次一样打开一个页面,但似乎不是,无法确定可以存储/缓存元素的位置


编辑 目前我使用了一种解决方法,但这显然是最佳解决方案

public People setSelectedPeople(People p){    
    if(p!=null)
        selectedPeople = sPeople.read(p.getId());                         
}

最佳答案

您正在寻找的是@RequestScoped。每次您执行合适的 HTTP 请求时,它都会创建所有内容。否则不能保证销毁 @ViewScoped bean。 Omnifaces 文档中的示例:ViewScoped .

例如,当用户使用浏览器的后退和前进按钮时,此功能可用于帮助重新创建页面。

@RequestScoped Bean lives as long as the HTTP request-response lives. It gets created upon a HTTP request and gets destroyed when the HTTP response associated with the HTTP request is finished.

@ViewScoped Bean lives as long as the user is interacting with the same JSF view in the browser window/tab. It gets created upon a HTTP request and gets destroyed once the user postbacks to a different view.

描述来源:https://www.tutorialspoint.com/jsf/jsf_managed_beans.htm

关于java - 如何处理@ViewScoped页面中的 'cached'实例?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51706289/

相关文章:

java - 使用 Jackson 进行 JSON 反序列化 : No suitable constructor found for type - providing default constructor or annotate constructor is imposible

java - 如何将单个SQLite数据显示到textview中?

oracle - 列出所有数据库表 - JPA

java - Hibernate 4 和 5 的 db2 中序列 SQL 的差异

caching - Redis 缓存 vs 直接使用内存

java - 找不到属性文件 ReloadableResourceBundleMessageSource 错误

java - 如何在 JTable 中呈现复选框?

sql - 使用 JPA/Hibernate 进行国际化的最优雅的解决方案?

laravel - Redis 连接拒绝 [tcp ://127. 0.0.1:6379]

ios - UITableViewCells 中的 UIImageViews 正在缓存的单元格中重新创建自己