我目前正在评估的Java EE 6 / JSF 2.1 RichFaces的。
该声明为一个bean
@ManagedBean
@ViewScoped
- 获取的ID集(以制备例如删除操作)。
- 通过JSF将显示确认弹出。
- 如果用户确认,删除方法被调用并删除该ID存储在第1步中的行。
由于CDI豆没有ViewScope我试图豆声明如下:
@Named
@ConversationScoped
现在的处理在步骤3中失败,因为这是在步骤1中(检查到)设置的值是不再可用。
我一定要使用Conversation.begin()
和Conversation.end()
方法?
如果是这样,这里将是很好的地方调用它们?
如果你可以升级到2.2 JSF,马上行动吧。 它提供了一个原生@ViewScoped
的CDI标注。
import javax.faces.view.ViewScoped;
import javax.inject.Named;
@Named
@ViewScoped
public class Bean implements Serializable {
// ...
}
另外,安装OmniFaces这带来了自己的CDI兼容@ViewScoped
,包括工作@PreDestroy
(这是JSF破@ViewScoped
)。
import javax.inject.Named;
import org.omnifaces.cdi.ViewScoped;
@Named
@ViewScoped
public class Bean implements Serializable {
// ...
}
另一种方法是安装MyFaces的CODI其中透明桥接JSF 2.0 / 2.1 @ViewScoped
到CDI。 这不仅增加了自动生成的请求参数的URL(如@ConversationScoped
会做)。
import javax.faces.bean.ViewScoped;
import javax.inject.Named;
@Named
@ViewScoped
public class Bean implements Serializable {
// ...
}
如果你确实需要使用@ConversationScoped
,那么你的确需要maunally开始和结束。 您需要@Inject
一个Conversation
并调用begin()
在@PostConstruct
和end()
在交谈中,通常会被重定向到一个新的视图操作方法的最新举措。
import javax.enterprise.context.Conversation;
import javax.enterprise.context.ConversationScoped;
import javax.inject.Named;
@Named
@ConversationScoped
public class Bean implements Serializable {
@Inject
private Conversation conversation;
// ...
@PostConstruct
public void init() {
conversation.begin();
}
public String submit() {
// ...
conversation.end();
return "some.xhtml?faces-redirect=true";
}
}
也可以看看:
我想你可以从CDI扩展受益于创建自己的范围,从而可以实现的背景下,并使用@NormalScope
。
- CDI触发一个事件
AfterBeanDiscovery
每个bean调用后 - 您可以使用CDI扩展到
@Observes
这一事件,并添加上下文实现 - 在你的范围内实现,您可以:
- 使用
Contextual
它的名字就可以获得你的bean FacesContext
ViewRoot
Map
和每个Ajax调用返回后回 - 使用
CreationalContext
如果从第一步bean的名字没有找到在创建它FacesContext
ViewRoot
Map
为了更深入的解释,我建议这个链接: http://www.verborgh.be/articles/2010/01/06/porting-the-viewscoped-jsf-annotation-to-cdi/
注入谈话到你的bean,并在@PostConstructor
方法展开对话,如果对话是短暂的。
和删除记录后,结束您的谈话,您引导到目的地页面。 当开始对话。 下面是一个例子
public class BaseWebBean implements Serializable {
private final static Logger logger = LoggerFactory.getLogger(BaseWebBean.class);
@Inject
protected Conversation conversation;
@PostConstruct
protected void initBean(){
}
public void continueOrInitConversation() {
if (conversation.isTransient()) {
conversation.begin();
logger.trace("conversation with id {} has started by {}.", conversation.getId(), getClass().getName());
}
}
public void endConversationIfContinuing() {
if (!conversation.isTransient()) {
logger.trace("conversation with id {} has ended by {}.", conversation.getId(), getClass().getName());
conversation.end();
}
}
}
@ConversationScoped
@Named
public class yourBean extends BaseWebBean implements Serializable {
@PostConstruct
public void initBean() {
super.initBean();
continueOrInitConversation();
}
public String deleteRow(Row row)
{
/*delete your row here*/
endConversationIfContinuing();
return "yourDestinationPageAfter removal";
}
}
有持有的一些推广到Java EE栈功能项目: DeltaSpike 。 这是缝3,阿帕奇CODI的整合。 在其他之上,它包括@ViewScoped到CDI。 这是一个古老的文章,现在已经达到1.3.0版本
您可以使用:
import javax.annotation.PostConstruct;
import javax.faces.view.ViewScoped;
import javax.inject.Named;
@Named
@ViewScoped
public class PageController implements Serializable {
private String value;
public void setValue(String value) {
this.value = value;
}
public String getValue() {
return value;
}
public void execute() {
setValue("value");
}
@PostConstruct
public void init() {
System.out.println("postcontructor");
}
}