1

A quite simple and straight-forward question.

I have a session scoped managed bean as follows (demonstrating a PrimeFaces range slider).

@ManagedBean
@SessionScoped
public final class RangeSliderBean implements Serializable
{
    private static final long serialVersionUID = 1L;
    private static final byte scale=2;

    private BigDecimal maxPrice;
    private BigDecimal minPrice;

    public RangeSliderBean()
    {
        maxPrice=new BigDecimal(100).setScale(scale, RoundingMode.HALF_UP);
        minPrice=new BigDecimal(5).setScale(scale, RoundingMode.HALF_UP);
    }

    @PostConstruct
    private void init()
    {

    }

    //Mutators and accessors
}

The given two fields in the above session scoped managed bean are bound to an XHTML page.

<h:form id="rangeForm" prependId="true">
    <p:panel header="Shop by Price">
        <h:panelGrid id="rangeSliderPanelGrid" columns="1" style="margin-bottom:10px">
            <h:outputText id="displayRange" value="Min : #{rangeSliderBean.minPrice.toPlainString()} Max : #{rangeSliderBean.maxPrice.toPlainString()}"/>

            <p:slider for="txtMinPrice, txtMaxPrice" 
                      minValue="#{rangeSliderBean.minPrice}" 
                      maxValue="#{rangeSliderBean.maxPrice}" 
                      display="displayRange" 
                      style="width:170px" 
                      range="true" displayTemplate="Min : {min} Max : {max}"/>
        </h:panelGrid>

        <h:inputHidden id="txtMinPrice" value="#{rangeSliderBean.minPrice}" converter="#{bigDecimalConverter}"/>
        <h:inputHidden id="txtMaxPrice" value="#{rangeSliderBean.maxPrice}" converter="#{bigDecimalConverter}"/>
        <p:commandButton value="Submit"/> <!--Update/process is temporarily omitted.-->
    </p:panel>
</h:form>

If these fields are initialized in the method annotated by @PostConstruct i.e init(), in this case (instead of initializing them in the constructor as shown in the snippet), their specified values are not set unless and until a user logs in (unless a session is created).

How can they be initialized in the constructor then, just a little confusion? (I know that the constructor is called before the method annotated by @PostConstruct is invoked).

Tiny
  • 27,221
  • 105
  • 339
  • 599
  • *If these fields are initialized in the method annotated by `@PostConstruct` i.e `init()` (...) their specified values are not set unless and until a user logs in* note that method annotated by `@PostConstruct` will be called after creating the managed bean and after the injection of other components e.g. EJBs. Could you, otherwise, provide an example of this odd behavior? – Luiggi Mendoza Dec 06 '13 at 21:21
  • "*method annotated by `@PostConstruct` will be called after creating the managed bean*". This is the same as saying, method annotated by `@PostConstruct` will be called after the constructor has been called. "*...and after the injection of other components e.g. EJBs*". This also happens after the managed bean is constructed (i.e. after the constructor has finished its job). I can't visualize another example :). – Tiny Dec 06 '13 at 21:36
  • I mean: post a valid JSF/Facelets code using your `@SessionScoped` managed bean that demonstrates these fields are empty if they are initialized in the `@PostConstruct` method instead of being initialized in the class constructor. – Luiggi Mendoza Dec 06 '13 at 21:38

1 Answers1

2

How can they be initialized in the constructor then, just a little confusion? (I know that the constructor is called before the method annotated by @PostConstruct is invoked).

Use the @PostConstruct's init method only to initialize fields which are being injected (i.e Ejbs). If you don't have any injections and dependencies, init method becomes pretty useless. The bean's constructor is used to initialize bean's own properties. In your example, you don't have any injection, so you can safely remove that @PostConstruct's init method.

If these fields are initialized in the method annotated by @PostConstruct i.e init(), in this case (instead of initializing them in the constructor as shown in the snippet), their specified values are not set unless and until a user logs in (unless a session is created).

It's the normal behavior, there is no reason to emphasize on the not, because a @SessionScoped bean is created and initialized only when a new session is created.

For more info check the link, the question has already been answered : Why use @PostConstruct?

Community
  • 1
  • 1
  • Note that only one `@SessionScoped` bean can be created per session **only if you create it manually or reference it from the view**. **Actually it's not automatically created when session begins**. Your statement `is created and initialized only when a new session is created` could be understood as wrong. – Aritz Dec 07 '13 at 12:48
  • After certain changes were made long after this post, the problem as demonstrated in the question body cannot be reproduced. Therefore, I'm not certain about the exact root cause of the problem. Maybe some certain AJAX requests were culprits. Thanks. – Tiny May 16 '14 at 14:57