0

I have a question about jsf lifecycle and back beans in JSP:

I have a button which I want to control if it was clicked once or twice. I have a flag for it in the back bean:

protected Boolean flagButtonClicked = false;

I am controlling its actions with:

public void selectAllButton_action(){    

    if(flagButtonClicked == false){
        System.out.println("flagButtonClicked == false");
        selectCB.setSelected(true);    
        setDisplayRerun(true);
        flagButtonClicked = true;
    }
    else {    
        System.out.println("flagButtonClicked == true");
        selectCB.setSelected(false);    
        setDisplayRerun(false);
        flagButtonClicked = false;
    }

}

when I click on the button I see

flagButtonClicked == false

when I click it again I again see

flagButtonClicked == false

so it never goes in the else state. Does it happen because I declare the protected Boolean flagButtonClicked = false in the back bean and whenever it is pushed it is declaring flagButtonClicked again? Or is there any other explanation?

Edit: here is the facelet:

<webuijsf:button actionExpression="#{user$reports.selectAllButton_action}" text="#{msg.report_select_all}"/>

Getter/Setter:

public Boolean getFlagButtonClicked() { 
  System.out.println("getFlagButtonClicked is called"); 
  return flagButtonClicked; 
} 

public void setFlagButtonClicked(Boolean flagButtonClicked) { 
  this.flagButtonClicked = flagButtonClicked; 
  System.out.println("setFlagButtonClicked is clicked"); 
}

EDIT 2: The last version of the code is:

@ViewScoped
@ManagedBean(name="user$reports", eager=true)
public class reports extends AbstractPageBean {

protected Boolean flagButtonClicked = false;

public Boolean getFlagButtonClicked() {
    System.out.println("getFlagButtonClicked is called");
    return flagButtonClicked;
}

public void setFlagButtonClicked(Boolean flagButtonClicked) {
    this.flagButtonClicked = flagButtonClicked;
    System.out.println("setFlagButtonClicked is clicked" + flagButtonClicked );
}

public void selectAllButton_action(){
if(flagButtonClicked== Boolean.FALSE){
        System.out.println("flagButtonClicked == false");
        selectCB.setSelected(true);System.out.println("selectCB.setSelected(true); ");
        setDisplayRerun(true);System.out.println("setDisplayRerun(true);");
        setFlagButtonClicked(true);System.out.println(" setFlagButtonClicked(true);");
    }
    else {
        System.out.println("flagButtonClicked == true");       
        selectCB.setSelected(false);System.out.println("selectCB.setSelected(false);");
        setDisplayRerun(false);System.out.println("selectCB.setSelected(false);");
        setFlagButtonClicked(false);System.out.println("setFlagButonClicked(false)");
    }
}

Output is:

[#|2011-10-26T21:45:14.645+0300|INFO|glassfishv3.0|null|_ThreadID=29;_ThreadName=Thread-1;|flagButtonClicked == false|#]

[#|2011-10-26T21:45:14.646+0300|INFO|glassfishv3.0|null|_ThreadID=29;_ThreadName=Thread-1;|selectCB.setSelected(true); |#]

[#|2011-10-26T21:45:14.646+0300|INFO|glassfishv3.0|null|_ThreadID=29;_ThreadName=Thread-1;|setDisplayRerun(true);|#]

[#|2011-10-26T21:45:14.646+0300|INFO|glassfishv3.0|null|_ThreadID=29;_ThreadName=Thread-1;|setFlagButtonClicked is clicked true|#]

[#|2011-10-26T21:45:14.646+0300|INFO|glassfishv3.0|null|_ThreadID=29;_ThreadName=Thread-1;| setFlagButtonClicked(true);|#]
[#|2011-10-26T21:46:03.892+0300|INFO|glassfishv3.0|null|_ThreadID=31;_ThreadName=Thread-1;|flagButtonClicked == false|#]

[#|2011-10-26T21:46:03.892+0300|INFO|glassfishv3.0|null|_ThreadID=31;_ThreadName=Thread-1;|selectCB.setSelected(true); |#]

[#|2011-10-26T21:46:03.892+0300|INFO|glassfishv3.0|null|_ThreadID=31;_ThreadName=Thread-1;|setDisplayRerun(true);|#]

[#|2011-10-26T21:46:03.892+0300|INFO|glassfishv3.0|null|_ThreadID=31;_ThreadName=Thread-1;|setFlagButtonClicked is clicked true|#]

[#|2011-10-26T21:46:03.892+0300|INFO|glassfishv3.0|null|_ThreadID=31;_ThreadName=Thread-1;| setFlagButtonClicked(true);|#]

I tried to check bean instance:

public void init() {

        super.init();

        try {
            _init();
        } catch (Exception e) {
            log("recentreports Initialization Failure", e);
            throw e instanceof FacesException ? (FacesException) e: new FacesException(e);
        }


FacesContext facesContex = FacesContext.getCurrentInstance();
        System.out.println("facesContex.getCurrentInstance();" + facesContex.getCurrentInstance().toString() );
        System.out.println("facesContex.getExternalContext().toString() " + facesContex.getExternalContext().toString());

    }

and the output is:

[#|2011-10-28T11:58:03.130+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|facesContex.getCurrentInstance();com.sun.faces.context.FacesContextImpl@19ea246|#]

[#|2011-10-28T11:58:03.130+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|facesContex.getExternalContext().toString() com.sun.faces.context.ExternalContextImpl@1afa48b|#]

[#|2011-10-28T11:58:03.206+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|flagButtonClicked == false|#]

[#|2011-10-28T11:58:03.206+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|selectCB.setSelected(true); |#]

[#|2011-10-28T11:58:03.206+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|setDisplayRerun(true);|#]

[#|2011-10-28T11:58:03.207+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|setFlagButtonClicked is clicked true|#]

[#|2011-10-28T11:58:03.207+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;| setFlagButtonClicked(true);|#]

[#|2011-10-28T11:58:10.513+0300|WARNING|glassfishv3.0|org.apache.catalina.connector.Request|_ThreadID=32;_ThreadName=Thread-1;|PWC4011: Unable to set request character encoding to UTF-8 from context /lrms, because request parameters have already been read, or ServletRequest.getReader() has already been called|#]

[#|2011-10-28T11:58:10.533+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|facesContex.getCurrentInstance();com.sun.faces.context.FacesContextImpl@a1b3e9|#]

[#|2011-10-28T11:58:10.533+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|facesContex.getExternalContext().toString() com.sun.faces.context.ExternalContextImpl@2a92a1|#]

[#|2011-10-28T11:58:10.578+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|flagButtonClicked == false|#]

[#|2011-10-28T11:58:10.579+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|selectCB.setSelected(true); |#]

[#|2011-10-28T11:58:10.579+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|setDisplayRerun(true);|#]

[#|2011-10-28T11:58:10.579+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;|setFlagButtonClicked is clicked true|#]

[#|2011-10-28T11:58:10.579+0300|INFO|glassfishv3.0|null|_ThreadID=32;_ThreadName=Thread-1;| setFlagButtonClicked(true);|#]

I am afraid this post is going to be the longest post in Stackoverflow :)

lamostreta
  • 2,359
  • 7
  • 44
  • 61
  • Could you add the part of your facelet where the action method is called? – Matt Handy Oct 27 '11 at 11:32
  • Is your `setFlagButtonClicked(..)` method called at all? Did you verify it with the debugger? – Matt Handy Oct 27 '11 at 12:05
  • no, it is not called :( but getter/settter methods exist inside the bean declaration as: public Boolean getFlagButtonClicked() { System.out.println("getFlagButtonClicked is called"); return flagButtonClicked; } public void setFlagButtonClicked(Boolean flagButtonClicked) { this.flagButtonClicked = flagButtonClicked; System.out.println("setFlagButtonClicked is clicked"); } I don't know why it is not called.. – lamostreta Oct 27 '11 at 13:06
  • The setter method is not called because you and your application never call it (as far as I can see from the source code you added). They are not called if you modify the field directly (e.g. `flagButtonClicked=true`) – Matt Handy Oct 27 '11 at 13:35
  • I tried the same as your code, and the result is nothing wrong? The only difference is that my bean is **ViewScoped** – BachT Oct 27 '11 at 15:50
  • I also tried viewscoped, but it is not working neither:( I added the latest version of the code. – lamostreta Oct 28 '11 at 06:04
  • Hm... You should check if it is really the same instance of the bean by checking the object id in debugger. – Matt Handy Oct 28 '11 at 06:18
  • I am getting a little bit confused about the scopes of beans.. I tried to google it, but couldn't find how to check if it is the same instance of the bean. Could you tell me how to do it? – lamostreta Oct 28 '11 at 07:44
  • iffacesContex.getCurrentInstance() is the right method, I tried it and it turned out to be there are different bean instances. Why this is happening and What should I do now? – lamostreta Oct 28 '11 at 09:22
  • I don't know if it is sufficient to check the FacesContext. You could use the method hashCode() (e.g. with `this.hashCode()` in your bean and print the result (it is an integer that must be equal if the instance is the same) – Matt Handy Oct 28 '11 at 11:10
  • you were right! Everytime I click on the select all button, another instance of button is created (different hash codes for the button object). Why this is happening? What should I do now? – lamostreta Oct 31 '11 at 07:08

1 Answers1

0

i am not sure but i think the problem is with the scope of your bean. check to see if on the second click a new bean is initialized , because if it does then every time you click, a new bean is initialized with a new variable flagButtonClicked which you are initializing to false on creation.

Khizar
  • 2,288
  • 5
  • 32
  • 53
  • Hi Khizar, first thanks for answering. My bean was request scoped. I tried the sessionscope and also application scope, neither of them worked. – lamostreta Oct 27 '11 at 10:30