@ManagedBean和@XxxScope可以放在基类中吗?

时间:2015-06-13 15:37:25

标签: jsf jsf-2 subclass managed-bean

我有两个@ManagedBean(javax.faces.bean.ManagedBean),父和子。父托管bean不是抽象的,因为我们必须让开发人员自由地使用父代,或者将其继承给具有特定功能的子代。

我在父bean中使用了注入bean和@PostConstruct带注释的方法时遇到了问题。

以下代码是我发现它有效的唯一方法。

@ManagedBean(name = "myBean")
@SessionScoped
public class BaseBean implements Serializable {
    @ManagedProperty(value = "#{serviceManagerController}")
    protected ServiceManagerController serviceManagerController;

     @PostConstruct
     public void init() {
       //do things
     }
}

和孩子豆

public class ChildBean extends BaseBean {
    @PostConstruct
    public void init() {
       super.init();
    }
}

要覆盖“myBean”bean并强制应用程序在需要时使用子bean,我必须在faces-config.xml

中声明子bean
<managed-bean>
    <managed-bean-name>myBean</managed-bean-name>
    <managed-bean-class>package.ChildBean</managed-bean-class>
    <managed-bean-scope>session</managed-bean-scope>
    <managed-property>
        <property-name>serviceManagerController</property-name>
        <property-class>package.ServiceManagerController</property-class>
        <value>#{serviceManagerController}</value>
    </managed-property>
</managed-bean>

这是所有工作的唯一方式,我不理解某些事情。

  1. 如果我没有在faces-config.xml中声明子bean,那么bean容器总是使用父bean实现,但继承了@ManagedBean
  2. 除非我在serviceManagerController子bean声明中声明<managed-property>,否则不会执行父bean中的注入,如faces-config.xml
  3. {1}}方法不会在父子项中执行,只会在@PostConstruct子项中执行。因此,我必须在子bean中的空@PostConstruct方法中调用super.init()
  4. 为什么我必须在父作品中进行三个步骤才能进行注射和postConstruct?

    当然,如果在我的应用程序中我不想继承BaseBean并希望在facelets中使用这个bean,所有工作都没有问题。

    此致

1 个答案:

答案 0 :(得分:3)

BaseBean设计错误。 Bean管理注释继承。从技术上讲,在同一个托管bean名称/标识符上注册不同子类的多个实例是没有任何意义的。 BaseBean类必须是abstract并且没有任何bean管理注释(因此,你和JSF都不能&#34;意外地&#34;实例化它)。将这些bean管理放在ChildBean上。您的faces-config.xml&#34;修复&#34;基本上就是这样。

public abstract class BaseBean implements Serializable {

    @ManagedProperty("#{serviceManagerController}")
    protected ServiceManagerController serviceManagerController;

    @PostConstruct
    public void init() {
        // ...
    }

    // ...
}
@ManagedBean("myBean")
@SessionScoped
public class ChildBean extends BaseBean {
    // ...
}

但是,如果您没有在子类中覆盖它们,则继承托管属性和后构造/预破坏注释。所以你不需要重新定义它们。

另见: