3

I have two scenario
I have two actions which have logic in bean like
My buttons

<h:commandButton  value="Submit" action="#{bean.test}" />
<h:commandButton  value="Submit" action="#{bean.testOne}" />

This are the two commnadButtons and there logic in bean

public void test() {
    log.info("I m in test");
}

public void testOne() {
    log.info("I m in testOne");
    try {
        FacesContext.getCurrentInstance()
            .addMessage("", new FacesMessage("Record Saved successfully."));
        FacesContext
                .getCurrentInstance()
                .getExternalContext()
                .redirect(
                        FacesContext.getCurrentInstance()
                            .getExternalContext().getRequestContextPath()
                                + "/cycle/page");

    } catch (IOException e) {
        log.error(e.getMessage());
    }
}

When I am going to click on 1st button (test action) that time jsf life cycle goes to every phase like
restore view
Apply request values
Process validation
update models
invoke application
render response
But when I click on testOne button that time jsf life cycle skip render response after invoke application like
restore view
Apply request values
Process validation
update models
invoke application
restore view
render response

In simple language When I am navigate the page through facesContext that time jsf skips that phase.
But why this happens? I am not getting the problem.

Aritz
  • 30,971
  • 16
  • 136
  • 217
user3800551
  • 27
  • 1
  • 3

1 Answers1

3

According to the JSF docs, that's what the INVOKE_APPLICATION phase does:

During this phase, the JavaServer Faces implementation handles any application-level events, such as submitting a form or linking to another page.

At this point, if the application needs to redirect to a different web application resource or generate a response that does not contain any JavaServer Faces components, it can call the FacesContext.responseComplete method.

If the view being processed was reconstructed from state information from a previous request and if a component has fired an event, these events are broadcast to interested listeners.

Finally, the JavaServer Faces implementation transfers control to the Render Response phase.

What you're doing is calling FacesContext#getCurrentInstance#getExternalContext#redirect in this phase, which performs your redirection. This method triggers FacesContext#getCurrentInstance#responseComplete, which ends the JSF lifecycle. The redirection is performed to a JSF view, so a new cycle starts after that.

Apart from that and unrelated to the concrete issue, do not perform redirections like that if you want to redirect to an internal JSF view. Just return the navigation case + ?faces-redirect=true in your action method (i.e. /cycle/page?faces-redirect=true). Use the external context only if you want to access external urls.

See also:

Community
  • 1
  • 1
Aritz
  • 30,971
  • 16
  • 136
  • 217
  • How can I achieve faces-redirect=true in my case? Please me some example. – user3800551 Jul 04 '14 at 10:21
  • Change your `testOne` method signature to return a String and return the String I mention in the last paragraph. – Aritz Jul 04 '14 at 10:23
  • @user3800551 if this worked for you, remember to mark the post as answered clicking on the check mark (✓) at the left of the answer. – Aritz Jul 07 '14 at 13:13