我看到很多例子将bean标记为实体bean (@Entity) &命名bean (CDI),以避免创建2个类(托管bean &实体bean),也利用bean验证,以便验证可以在客户端和amp;服务器。
所以我应该使用单一类或不,是否有任何问题,或者我应该让我的管理bean或服务层使用管理bean的数据创建实体bean ?
@Named或@ManagedBean注释通常用于让bean容器(CDI/JSF)在被JSF中的表达式语言引用时按需创建bean的实例。
对于@Entity bean,仅仅获取一个任意的新实例通常没有多大意义。@Entity与持久标识紧密相连。因此,这样的实体是从Entity Manager
请求的,而不是从bean容器请求的。
典型的模式是有一个(精简的)支持bean,它被命名为对服务的调用(在Java EE中通常是@Stateless)。然后服务返回实体。
在一些非常简单的系统中,人们有时确实会命名服务,从而直接对EL可用。然而,最终您通常希望让"后台代码"生成面孔消息或处理(表)选择,这些都不应该是纯业务服务所关注的事情。
另一个常见的快捷方式是让后台bean直接包含业务代码(例如,检索实体的实体管理器)。这使得业务代码难以重用,但如果应用程序是微不足道的,没有必要重用,你可能会侥幸逃脱。
但是让实体作为支持bean是很少见的,并且违背了常见的Java EE模式。
请注意,支持bean可以直接返回实体,因此仍然可以使用bean验证。很久以前出现的奇怪的"分散/聚集"模式是没有必要的(参见这个问题的第二个例子)。
。
@ViewScoped
@ManagedBean
public class BackingBean {
private SomeEntity myEntity; // + getter
@EJB
private Service service;
@PostConstruct
public void init() {
myEntity = service.getSomeEntity();
}
public void save() {
service.save(myEntity);
FacesContext.getCurrentInstance().addMessage(..., ...);
}
}
假设SomeEntity
在@Entity注释的bean中,bean验证现在可以在Facelet上使用,如:
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
>
<h:body>
<h:form>
<h:inputText value="#{backingBean.myEntity.name}" />
<h:commandButton value="Save" action="#{backingBean.save}" />
</h:form>
</h:body>
</html>
如果SomeEntity.name
有约束,则验证