Saturday, December 17, 2011

Thursday, December 8, 2011

PrimeFaces: ViewExpiredException Server error

You have to add the  com.sun.faces.enableRestoreView11Compatibility param-name and the javax.faces.application.ViewExpiredException exception-type to the web.xml:

<web-app version="3.0" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd">

...
....
<context-param>
        <param-name>com.sun.faces.enableRestoreView11Compatibility</param-name>
        <param-value>true</param-value>

</context-param>
...
...
...
...
<error-page>
        <exception-type>javax.faces.application.ViewExpiredException</exception-type>
        <location>/faces/Login/Login.xhtml</location>
    </error-page>
...
...
</web-app>


Reference:
http://mariosgaee.blogspot.com/2009/12/glassfish-and-adf-faces.html

PrimeFaces: The button/link/text component needs to have a Form in its ancestry. Please add

I got this warning while using a page:

The button/link/text component needs to have a Form in its ancestry. Please add <h:form>

By googling for a while I found it is a bug of Mojarra 2.1.1, so there are two posible solutions

1. Use Mojarra 2.0.4 which is the lastest stable mojarra release.
2. Change the param-value  "Production" of the to the param-name: javax.faces.PROJECT_STAGE:

<context-param>
        <param-name>javax.faces.PROJECT_STAGE</param-name>
        <param-value>Production</param-value> 
</context-param>

Resources:
http://www.geektilidie.com/?p=40
http://www.guj.com.br/java/240027-the-buttonlinktext-component-needs-to-have-a-form-in-its-ancestry-please-add-resolvido
http://code.google.com/p/primefaces/issues/detail?id=1586

Wednesday, December 7, 2011

PrimeFaces: Dealing with ViewExpiredException on Ajax Request Response

After pressing a p:commandButton :
<p:commandButton id="refresh" value="Send" action="#{connectionDBController.createDataTable}" update="result,messages"/>

I was getting this as a response in the browser:
<partial-response>
  <error>
    <error-name>class javax.faces.application.ViewExpiredException</error-name>
    <error-message><![CDATA[viewId:/index.xhtml - View /index.xhtml could not be restored.]]>
    </error-message>
  </error>
  <changes>
    <extension primefacesCallbackParam="validationFailed">{"validationFailed":false}</extension>
  </changes>
</partial-response>


BUT in the server log, there where NO LOG ERROR.The error was ONLY being sent through the http response, so the error-page tag in the web.xml couldn't work:

http://jhonjairoroa87.blogspot.com/2011/12/primefaces-viewexpiredexception-server.html

After googling for a couple of days , I couldn't find anything so  I decided to handle that error in my way, I know it could be better, but It works.

I added the oncomplete attrib to the p:commandButton:
<p:commandButton id="refresh" oncomplete="handleAjaxRequest2(xhr, status, args);" value="Send" action="#{connectionDBController.createDataTable}" update="result,messages"/>

The handleAjaxRequest method  has:


function handleAjaxRequest2(xhr, status, args){                       
            myValidationObject1 = new validationObject({'property':'data' , 'value':'class javax.faces.application.ViewExpiredException'}, null)
            myValidationObject2 = new validationObject({'property':'localName' , 'value':'error-name'}, myValidationObject1)
            myValidationObject3 = new validationObject({'property':'localName' , 'value':'error'}, myValidationObject2)
            myValidationObject4 = new validationObject({'property':'localName' , 'value':'partial-response'}, myValidationObject3)                                   
            myBoolResult = validateInternalPropery(xhr.responseXML , myValidationObject4);           
            if (myBoolResult == true){
                //alert("myBoolResult" + myBoolResult);
                alert("Session expired, please login again")
                window.location = '/myProject/faces/Login/Login.xhtml';
            }                      
        }

The validateInternalPropery method has

function validateInternalPropery(myObj , myValidationObject){
            returnValue = false;
            console.log("myObj");
            console.log(myObj);
            console.log("myValidationObject");
            console.log(myValidationObject);           
            //myObj = xhr.responseXML;
            if(myObj.hasChildNodes() == true){ //validate has chid nodes
                for(childNode in myObj.childNodes){ // iter child nodes in object
                    if (typeof myObj.childNodes[childNode] == 'object'){ // validate if the current childnode is an object
                        if(myObj.childNodes[childNode].hasOwnProperty(myValidationObject.iniValidation.property) == true){ // validate if the childnode has the given a Property
                            if(myObj.childNodes[childNode][myValidationObject.iniValidation.property] == myValidationObject.iniValidation.value){ // evaluatee the value of given property
                                if (myValidationObject.endValidation == null){
                                    returnValue = true;
                                    break;
                                }else{
                                    validateInternalPropery(myObj.childNodes[childNode] , myValidationObject.endValidation)
                                }                               
                            }
                        }
                    }
                }
            }
            return returnValue;
        }


The validationObject class method has

function validationObject(myIniValidation, myEndValidation){
            this.iniValidation = myIniValidation;
            this.endValidation = myEndValidation;
        }

I that way I can locate the error that I want , in this case, class javax.faces.application.ViewExpiredException, and do the window.location to redirect to the login page

References:
http://forum.primefaces.org/viewtopic.php?f=3&t=5909
http://yigitdarcin.wordpress.com/2011/10/06/dealing-with-viewexpiredexception-on-regular-and-ajax-requests/ 

http://weblogs.java.net/blog/driscoll/archive/2009/05/jsf_2_ajax_even.html 
http://stackoverflow.com/questions/6946078/primefaces-pajaxstatus-onerror-not-called