Search code examples
jsfmyfacesjsf-1.2

tr:commandLink action method does not navigate to next page.Instead loads same page again


In my JSF application ,after successful login, i am navigating to my home page of my application where i have a Logout link.

Here is the related html for logout link.

<div id="top_white">
        <div style="float: right"><tr:form><tr:commandLink id="logout" action="#{Controller.Logout}"><img alt="logout" src="../../images/logout.gif"/></tr:commandLink></tr:form></div>
    </div>

And here is my Controller which is sessionscoped

public class Controller {

    private static Logger LOGGER = Logger.getLogger(Controller.class);

    public Controller() {
        req = (HttpServletRequest)FacesContext.getCurrentInstance().getExternalContext().getRequest();
        session = req.getSession(false);
        String userid = session.getAttribute("userid").toString();
        if(List == null){
            List = new ArrayList<List>();
            List = new DAO().loadListByid(Long.valueOf(userid));
            LOGGER.debug("successfully loaded the list for the user");
        }
    }

    private long Username;
    private String Password=null;
    HttpServletRequest req;
    HttpSession session;


    private List<List> List=null;
    // getter and setters


    public String Logout(){
        session.invalidate();
        LOGGER.debug("In LogOut");
        return "loggedout";
    }
}

In the Constructor i check for userid in the session and load specific list to the user.

I also have a ServletFilter which checks for some id in each session.If it is not found it redirects to InvalidUser page.My filter is mapped to /faces/jsp/* so that for all jsp's in the jsp folder are checked for id in the session.

Here is the doFilter method of my filter

public void doFilter(ServletRequest req, ServletResponse res,
            FilterChain chain) throws IOException, ServletException {

            LOGGER.debug("In doFilter");
            HttpServletRequest request = (HttpServletRequest) req;
            HttpServletResponse response = (HttpServletResponse) res;
            HttpSession session = request.getSession(false);
            LOGGER.debug("request:" + request.getRequestURL().toString());
            try{
                if (session.getAttribute("id") != null) {
                    LOGGER.debug("id found:" + session.getAttribute("id"));
                    chain.doFilter(req, res); // id found, so just continue request.
                } 
            }catch(NullPointerException e){
                LOGGER.debug("No id found Exception: ", e);
                response.sendRedirect(properties.getProperty(INVALID_USER_REDIRECTURL, true)); // No id found, so redirect to Invalid user page.

            }

    }

I also added a PhaseListener to debug JSF life cycle which is taken from here.

When the page is first loaded i see the following server log with only first and last phases of JSF lifecycle

["http-bio-8090"-exec-114] DEBUG SessionFilter - In doFilter
["http-bio-8090"-exec-114] DEBUG SessionFilter - request:http://my homepageurl
["http-bio-8090"-exec-114] DEBUG SessionFilter - id found
["http-bio-8090"-exec-114] ERROR org.apache.myfaces.config.FacesConfigurator - Configuration objects do not support clean-up. Update aborted
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE RESTORE_VIEW(1)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE RESTORE_VIEW(1)
["http-bio-8090"-exec-114] DEBUG org.apache.myfaces.lifecycle.LifecycleImpl - exiting from lifecycle.execute in RESTORE_VIEW(1) because getRenderResponse is true from one of the after listeners
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE RENDER_RESPONSE(6)
["http-bio-8090"-exec-114] INFO  org.apache.myfaces.config.annotation.DefaultLifecycleProviderFactory - Using LifecycleProvider org.apache.myfaces.config.annotation.AllAnnotationLifecycleProvider
["http-bio-8090"-exec-114] DEBUG Controller - id found in controller
["http-bio-8090"-exec-114] DEBUG DAOProperties - dao.properties loaded successfully
["http-bio-8090"-exec-114] DEBUG SvrConnection - In JNDI
["http-bio-8090"-exec-114] DEBUG DAO - Successfully connected to database
["http-bio-8090"-exec-114] DEBUG DAO - connection closed
["http-bio-8090"-exec-114] DEBUG Controller - successfully loaded the list for the user
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE RENDER_RESPONSE(6)

The above log is as expected because there is no form submission type of stuff.So only first and last phases are listed.

But the real problem comes when i click the Logout commandLink which i mentioned in the top of this post.

After i click the Logout link, here is the server log.

["http-bio-8090"-exec-114] DEBUG SessionFilter - In doFilter
["http-bio-8090"-exec-114] DEBUG SessionFilter - request:http://my homepage url
["http-bio-8090"-exec-114] DEBUG SessionFilter - appid found
["http-bio-8090"-exec-114] ERROR org.apache.myfaces.config.FacesConfigurator - Configuration objects do not support clean-up. Update aborted
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE RESTORE_VIEW(1)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE RESTORE_VIEW(1)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE APPLY_REQUEST_VALUES(2)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE APPLY_REQUEST_VALUES(2)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE PROCESS_VALIDATIONS(3)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE PROCESS_VALIDATIONS(3)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE UPDATE_MODEL_VALUES(4)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE UPDATE_MODEL_VALUES(4)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE INVOKE_APPLICATION(5)
["http-bio-8090"-exec-114] DEBUG Controller - In LogOut
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE INVOKE_APPLICATION(5)
["http-bio-8090"-exec-114] DEBUG org.apache.myfaces.lifecycle.LifecycleImpl - exiting from lifecycle.execute in INVOKE_APPLICATION(5) because getRenderResponse is true from one of the after listeners
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - START PHASE RENDER_RESPONSE(6)
["http-bio-8090"-exec-114] DEBUG LifeCycleListener - END PHASE RENDER_RESPONSE(6)
["http-bio-8090"-exec-116] DEBUG SessionFilter - In doFilter
["http-bio-8090"-exec-116] DEBUG SessionFilter - request:http://my homepage url
["http-bio-8090"-exec-116] DEBUG SessionFilter - No id found Exception:
java.lang.NullPointerException

From the above log ,as expected my action method is invoked in the INVOKE_APPLICATION and my controller's Logout() method is called and session is invalidated and string loggedout is returned.

I have the following navigation rule in the faces-config.xml

<navigation-rule>
    <from-view-id>/jsp/Services.jsp</from-view-id>
    <navigation-case>
      <from-outcome>loggedout</from-outcome>
      <to-view-id>/others/Logout.jsp</to-view-id>
    </navigation-case>
  </navigation-rule>

But this navigation-rule does not execute. Instead in the RENDER_RESPONSE Phase, it tries to reload my same home page url.obviously it does not have the id in the session which is causing to throw a NullPointerException.

I have the jsp's in the respective folders as given above.I am using JSF 1.2 and myFaces 1.2.9.

1)Why navigation-case does not execute?

2)Why it is reloading my home page url again?

Please somebody help.


Solution

  • I found out that this is a logout problem in JSF.Not problem with tr:commandLink.

    I read some posts about JSF logout problem here on SO and implemented the same.

    It works as expected.