Orm EntityManager未从数据库中提取?
我有实体:帖子、用户、具有双向关系的评论:Orm EntityManager未从数据库中提取?,orm,jpa,jsf-2,java-ee-6,jpa-2.0,Orm,Jpa,Jsf 2,Java Ee 6,Jpa 2.0,我有实体:帖子、用户、具有双向关系的评论: --------- 1 * --------- | Post | <--------> |Comment| --------- --------- --------- 1 * --------- | User | <--------> |Comment| --------- --------- viewpost如下所示: String usernam
--------- 1 * ---------
| Post | <--------> |Comment|
--------- ---------
--------- 1 * ---------
| User | <--------> |Comment|
--------- ---------
viewpost如下所示:
String username = getLoginName();
if(username != null)
{
User u = userBean.getUser(username);
post = postBean.getPost(post.getId());
comment.setPost(post);
comment.setUser(u);
commentBean.updateComment(comment);
post = postBean.getPost(post.getId());
}
return "viewpost?faces-redirect=true";
<ui:define name="content">
<h:outputText value="#{postController.post.title}"/>
<br/>
<h:outputText value="#{postController.post.body}"/>
<br/>
<h:dataTable value="#{postController.post.comments}" var="item">
<h:column>
<h:outputText value="#{item.body}"/>
<br/>
<h:outputText value="#{item.user.username}"/>
<br/>
</h:column>
</h:dataTable>
<h:form rendered="#{postController.loggedIn}">
<h:inputTextarea value="#{postController.comment.body}"/>
<h:commandButton value="Submit" action="#{postController.saveComment}"/>
</h:form>
</ui:define>
+-------+ 1 * +-------+ * 1 +-------+
| Post | <--------> |Comment| <--------> | User |
+-------+ +-------+ +-------+
但是,当我单击“提交”时,注释会保存到数据库中,但不会呈现。基本上是返回em.find(post.class,id)的post=postBean.getPost(post.getId())
是否应该重新加载post
,以便新的注释可用
在backingbean中也有viewPost操作,它执行相同的
post=postBean.getPost(post.getId())
,但似乎数据不是从数据库加载的。我从数据库中删除了评论,但它们仍然列在viewpost页面中。可以缓存帖子。你的帖子中的@ID是什么?若缓存中存在具有指定id的Post,则该Post将从缓存中获取,而不是从数据库中获取。尝试禁用缓存
我不确定,但我想
return "viewpost?faces-redirect=true";
不行。JSF导航处理程序接受这个字符串,并检查它是否在
faces config.xml
中配置。如果不存在,它会附加默认扩展名(可能是.xhtml),并尝试重定向到这样的页面。因此,它可能试图将您重定向到显然不存在的viewpost?faces redirect=true.xhtml
。您不必点击数据库(使用EntityManager#refresh()
,EntityManager.find()
如果post实例已经加载到持久性上下文中,则不会点击数据库)如果您适当地设置了双向关联
问题是,您没有这样做,并且在添加注释后对象图被破坏,因此需要从数据库重新加载帖子(这实际上是解决实际错误的一种方法)
基本上,您的模型是这样的:
String username = getLoginName();
if(username != null)
{
User u = userBean.getUser(username);
post = postBean.getPost(post.getId());
comment.setPost(post);
comment.setUser(u);
commentBean.updateComment(comment);
post = postBean.getPost(post.getId());
}
return "viewpost?faces-redirect=true";
<ui:define name="content">
<h:outputText value="#{postController.post.title}"/>
<br/>
<h:outputText value="#{postController.post.body}"/>
<br/>
<h:dataTable value="#{postController.post.comments}" var="item">
<h:column>
<h:outputText value="#{item.body}"/>
<br/>
<h:outputText value="#{item.user.username}"/>
<br/>
</h:column>
</h:dataTable>
<h:form rendered="#{postController.loggedIn}">
<h:inputTextarea value="#{postController.comment.body}"/>
<h:commandButton value="Submit" action="#{postController.saveComment}"/>
</h:form>
</ui:define>
+-------+ 1 * +-------+ * 1 +-------+
| Post | <--------> |Comment| <--------> | User |
+-------+ +-------+ +-------+
“设置双向关联链接的两侧”通常在实体上的帮助器方法中完成,例如在Post中:
@Entitysamples
public class Post {
...
public void addToComments(Comment comment) {
this.comments.add(comment);
comment.setPost(this);
}
}
这不太容易出错,更容易使用,更容易阅读
无论如何,关键是要设置关联的两边,不必强制从数据库重新加载来“修复”对象图。这是JSF 2.0的一部分。隐式导航。再也没有脸了。
?faces redirect=true
替换了旧式导航案例中的
。您使用的持久性提供程序是什么?例如,在eclipselink中,您必须添加到persistence.xml:或命名查询:setHint(QueryHints.CACHE\u USAGE,CacheUsage.DoNotCheckCache)。看这里: