JSF管理bean EJB注入 [英] JSF managed-bean EJB injection

查看:206
本文介绍了JSF管理bean EJB注入的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在企业应用程序模块中有一个EJB(PersonManager),它注入另一个EJB(Person):

  @Stateful 
public class PersonManager实现PersonManagerLocal {
@EJB
private PersonLocal person;

@Override
public void setPersonName(String name){
person.setName(name);
}

@Override
public String getPersonName(){
return person.getName();
}
}

我想在JSF网页中使用PersonManager EJB应用程序。我在faces-config.xml中定义它:

 < managed-bean> 
< managed-bean-name> personManager< / managed-bean-name>
< managed-bean-class> ejb.PersonManager< / managed-bean-class>
< managed-bean-scope> session< / managed-bean-scope>
< / managed-bean>

问题是,注入PersonLocal EJB不会发生。 person属性始终为NULL。我怎么了?



但是,如果我将一个JSF管理的bean中的PersonManager注入到这个文件中:

  @ManagedBean 
@RequestScoped
public class Index {
@EJB
private PersonManagerLocal personManager;
....

IT WORKS。我需要第一种情况,请帮助我:-D

解决方案

您正在混合EJB和JSF托管bean的职责。 faces-config.xml 仅注册JSF工件,例如受管Bean而不是EJB。您在 faces-config.xml中的注册

 < managed-bean> ; 
< managed-bean-name> personManager< / managed-bean-name>
< managed-bean-class> ejb.PersonManager< / managed-bean-class>
< managed-bean-scope> session< / managed-bean-scope>
< / managed-bean>

基本上与

  @ManagedBean 
@SessionScoped
public class PersonManager {
// ...
}
换句话说,您正在将该类注册为JSF托管的bean,该bean可以通过#{personManager} 。这不代表与EJB容器管理的实例相同的实例。您可以并且应该使用 faces-config.xml 注册EJB。您可以使用 javax.ejb 包中的注释,例如 @Stateless @Stateful 。这就是注册一个EJB所需要的。



实际上,在 faces-config.xml 中注册JSF托管bean是JSF 2.x中的旧JSF 1.x方式已被新的 @ManagedBean 注释所取代。






更新 p>

 < h:form> 
< h:inputText value =#{personManager.person.name}/>
...
< h:commandButton value =保存action =#{personManager.save}/>
< h:messages />
< / h:form>

控制器(JSF托管bean):

  @ManagedBean 
@ViewScoped
public class PersonManager implements Serializable {

private Person person;

@EJB
私人PersonService personService;

@PostConstruct
public void init(){
person = new Person();
}

public void save(){
personService.create(person);
FacesContext.getCurrentInstance()。addMessage(null,
new FacesMessage(Person successfully created,new ID is+ person.getId()));
}

// ...
}

Model(JPA实体):

  @Entity 
public class Person implements Serializable {

@Id
private Long id;

private String name;

// ...
}

服务无状态EJB):

  @Stateless 
public class PersonService {

@PersistenceContext
private EntityManager em;

public void create(Person person){
em.persist(person);
}

// ...
}


I have an EJB (PersonManager) in the Enterprise Application modul, which injects another EJB (Person):

@Stateful
public class PersonManager implements PersonManagerLocal {
    @EJB
    private PersonLocal person;

    @Override
    public void setPersonName(String name) {
        person.setName(name);
    }

    @Override
    public String getPersonName() {
        return person.getName();
    }
}

I want to use the PersonManager EJB in a JSF web app. I define it in the faces-config.xml:

<managed-bean>
    <managed-bean-name>personManager</managed-bean-name>
    <managed-bean-class>ejb.PersonManager</managed-bean-class>
    <managed-bean-scope>session</managed-bean-scope>
</managed-bean>

The problem is that, the injection of the PersonLocal EJB doesn't happen. The person property is always NULL. What did I wrong?

But if I inject the PersonManager in a JSF managed bean like this:

@ManagedBean
@RequestScoped
public class Index {
    @EJB
    private PersonManagerLocal personManager;
    ....

IT WORKS. I need the first scenario, please help me :-D

解决方案

You are mixing the responsibilities of EJBs and JSF managed beans. The faces-config.xml registers only JSF artifacts, such as managed beans and not EJBs. Your registration in faces-config.xml

<managed-bean>
    <managed-bean-name>personManager</managed-bean-name>
    <managed-bean-class>ejb.PersonManager</managed-bean-class>
    <managed-bean-scope>session</managed-bean-scope>
</managed-bean>

does basically exactly the same as

@ManagedBean
@SessionScoped
public class PersonManager {
    // ...
}

In other words, you're registering the class as a JSF managed bean which is available in views by #{personManager}. This does not represent the same instance as is managed by the EJB container. You can and should not use faces-config.xml to register EJBs. There you use the annotations from the javax.ejb package for, such as @Stateless and @Stateful. That's all you need to register an EJB.

Actually, registering JSF managed beans in faces-config.xml is an old JSF 1.x way which has in JSF 2.x been replaced by the new @ManagedBean annotation.


Update the proper approach would be:

View (the Facelets file):

<h:form>
    <h:inputText value="#{personManager.person.name}" />
    ...
    <h:commandButton value="Save" action="#{personManager.save}" />
    <h:messages />
</h:form>

Controller (the JSF managed bean):

@ManagedBean
@ViewScoped
public class PersonManager implements Serializable {

    private Person person;

    @EJB
    private PersonService personService;

    @PostConstruct
    public void init() {
        person = new Person();
    }

    public void save() {
        personService.create(person);
        FacesContext.getCurrentInstance().addMessage(null,
            new FacesMessage("Person successfully created, new ID is " + person.getId()));
    }

    // ...
}

Model (the JPA entity):

@Entity
public class Person implements Serializable {

    @Id
    private Long id;

    private String name;

    // ...
}

Service (the stateless EJB):

@Stateless
public class PersonService {

    @PersistenceContext
    private EntityManager em;

    public void create(Person person) {
        em.persist(person);
    }

    // ...
}

这篇关于JSF管理bean EJB注入的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆