Search code examples
javajsfprimefacesfacelets

JSF error message and program stuck. JSON parsing error and primefaces


I have the following form in facelets:

 <h:form styleClass="registrationForm">
            <h:panelGrid columns="3" cellpadding="5" style="width:600px">

                <h:outputLabel for="registerLogin" styleClass="registerLabel" value="Логин: " />
                <p:inputText id="registerLogin" styleClass="registerText" value="#{register.login}" 
                            required="true" requiredMessage="Введите Логин" />  
                <h:panelGrid width="200">
                    <p:message for="registerLogin" />   
                </h:panelGrid>

                <h:outputLabel for="registrationPassword" styleClass="registerLabel" value="Пароль: " />
                <p:password id="registrationPassword"  styleClass="registerText" feedback="true" promptLabel="Введите пароль" weakLabel="Слабый пароль"  
                            goodLabel="Нормальный пароль" strongLabel="Сложный пароль" value="#{register.password}" 
                            required="true" requiredMessage="Введите Пароль" /> 
                <h:panelGrid width="200">
                    <p:message for="registrationPassword" />    
                </h:panelGrid>              

                <h:outputLabel for="registrationMail" styleClass="registerLabel" value="Адрес эл. почты: " />
                <p:inputText id="registrationMail"  styleClass="registerText" value="#{register.email}" 
                        required="true" requiredMessage="Введите Адрес Почты" >
                    <f:validateRegex pattern="^[_A-Za-z0-9-\+]+(\.[_A-Za-z0-9-]+)*@[A-Za-z0-9-]+(\.[A-Za-z0-9]+)*(\.[A-Za-z]{2,})$" />
                </p:inputText>
                <h:panelGrid width="200">
                    <p:message for="registrationMail" />        
                </h:panelGrid>                               

                <h:outputLabel for="registrationSex" styleClass="registerLabel" value="Пол: " />
                <p:selectOneRadio id="registrationSex" value="#{register.sex}">
                    <f:selectItem itemLabel="М" itemValue="male" />
                    <f:selectItem itemLabel="Ж" itemValue="female" />           
                </p:selectOneRadio>             
                <h:outputText value="" />

                <h:outputLabel for="registrationName" styleClass="registerLabel" value="Отображаемое имя: " />
                <p:inputText id="registrationName"  styleClass="registerText" value="#{register.name}" 
                        required="true" requiredMessage="Ведите Имя" />
                <h:panelGrid width="200">
                    <p:message for="registrationName" />            
                </h:panelGrid>              

                <h:outputLabel for="registrationCalendar" styleClass="registerLabel" value="Дата рождения: " />
                <p:calendar id="registrationCalendar" size="24" navigator="true" yearRange="-68" 
                                locale="ru" effect="explode" value="#{register.birthdate}" 
                                required="true" requiredMessage="Введите Дату Рождения" />   
                <h:panelGrid width="200">
                    <p:message for="registrationCalendar" />            
                </h:panelGrid>                          

                <h:outputLabel for="registrationConfirm" styleClass="registerLabel" value="" />
                <p:commandButton id="registrationConfirm" value="Зарегистрироваться" styleClass="registerButton" 
                                actionListener="#{register.processRegistration}" update=":loginField :content :title" onclick="changeHeader()" />

            </h:panelGrid>  
        </h:form>

And the following backing bean:

@ManagedBean
@RequestScoped
public class Register {

    @PersistenceContext(unitName="EnglishOnline")
    private EntityManager em;
    @Resource
    UserTransaction utx;
    @ManagedProperty(value="#{login}")
    private Login loginbean;
    @ManagedProperty(value="#{navigationBean}")
    private NavigationBean nav;

    private String name;
    private Sex sex;
    private Date birthdate;
    private String email;
    private String login;
    private String password;

    ...getters and setters ...

    public void setLoginbean(Login log) {
        this.loginbean = log;
    }
    public void setNav(NavigationBean nav) {
        this.nav = nav;
    }

    public void processRegistration(ActionEvent event) throws Exception {   

        User user = new User();
        user.setLogin(login);
        user.setPassword(password);
        user.setEmail(email);
        user.setName(name);
        user.setBirthdate(birthdate);
        user.setSex(sex);
        user.setRegistrationdate(new Date());

        TypedQuery<User> query = em.createQuery("SELECT u FROM User u WHERE u.login = :uLogin OR u.email = :mail", User.class);
        query.setParameter("uLogin", user.getLogin());
        query.setParameter("mail", user.getEmail());
        List<User> users = query.getResultList();
        if (users.size() != 0) {
            FacesContext.getCurrentInstance().addMessage(null, new FacesMessage("Ошибка", "Пользователь с таким логином или почтовым адресом уже существует!"));    
        } else {
            utx.begin();
            em.persist(user);
            utx.commit();
            loginbean.setUser(user);        
            nav.setHeader("Главная");
            nav.setAddress("templates/start.xhtml");            
        }       

    }   

}

When I click once the registration button, and the error messages appear for some fields, then i cannot register anymore. I mean, if I manage to register at once without validation errors, then everything is ok...But if any validation messages appear, then the program stops responding - even if I change the field values, the register button cannot be clicked and error messages do not disappear anymore. What has gone wrong?

When I do the same actions: when form submitted for the first time, with the empty field, the validation proceeds and the "validation" word appears in the console. But upon the subsequent requests even the Validator does not start - it just does not print anything anymore. Any ideas? As for JavascriptMistakes:

Problem: SyntaxError: JSON.parse: unexpected non-whitespace character after JSON data
: http://localhost:8080/EnglishOnline/javax.faces.resource/jquery/jquery.js.jsf?ln=primefaces

Nothing suspicious else.

PPS. The following response is returned from the server:

<?xml version='1.0' encoding='UTF-8'?>
<partial-response><changes><update id="loginField"><![CDATA[<div id="loginField">
<form id="j_idt12" name="j_idt12" method="post" action="/EnglishOnline/index.jsf" class="login_form" enctype="application/x-www-form-urlencoded">
<input type="hidden" name="j_idt12" value="j_idt12" />
<span id="j_idt12:j_idt13"></span><script id="j_idt12:j_idt13_s" type="text/javascript">$(function(){PrimeFaces.cw('Growl','widget_j_idt12_j_idt13',{id:'j_idt12:j_idt13',sticky:false,life:1500,escape:true,msgs:[]});});</script><label for="j_idt12:login">
Логин: </label><input id="j_idt12:login" name="j_idt12:login" type="text" value="" class="ui-inputfield ui-inputtext ui-widget ui-state-default ui-corner-all login_field" /><script id="j_idt12:login_s" type="text/javascript">PrimeFaces.cw('InputText','widget_j_idt12_login',{id:'j_idt12:login'});</script><label for="j_idt12:password">
Пароль: </label><input id="j_idt12:password" name="j_idt12:password" type="password" class="ui-inputfield ui-password ui-widget ui-state-default ui-corner-all login_field" /><script id="j_idt12:password_s" type="text/javascript">$(function(){PrimeFaces.cw('Password','widget_j_idt12_password',{id:'j_idt12:password'});});</script><button id="j_idt12:j_idt16" name="j_idt12:j_idt16" class="ui-button ui-widget ui-state-default ui-corner-all ui-button-text-only login_button" onclick="PrimeFaces.ab({source:'j_idt12:j_idt16',update:'loginField'});return false;" type="submit"><span class="ui-button-text">Войти</span></button><script id="j_idt12:j_idt16_s" type="text/javascript">PrimeFaces.cw('CommandButton','widget_j_idt12_j_idt16',{id:'j_idt12:j_idt16'});</script>
</form><a id="j_idt20" href="#" class="ui-commandlink register_link" onclick="changeHeader();PrimeFaces.ab({source:'j_idt20',update:'content title'});return false;">Регистрация</a></div>]]></update><update id="title"><![CDATA[<span id="title">Регистрация</span>]]></update><update id="content"><![CDATA[<span id="content"><div class="registrationPanel">
<form id="registrationForm" name="registrationForm" method="post" action="/EnglishOnline/index.jsf" class="registrationForm" enctype="application/x-www-form-urlencoded">
<input type="hidden" name="registrationForm" value="registrationForm" />
<table cellpadding="5">
<tbody>
<tr>
<td><label for="registrationForm:registrationLogin" class="registerLabel">
Логин: </label></td>
<td><input id="registrationForm:registrationLogin" name="registrationForm:registrationLogin" type="text" value="" class="ui-inputfield ui-inputtext ui-widget ui-state-default ui-corner-all ui-state-error registerText" /><script id="registrationForm:registrationLogin_s" type="text/javascript">PrimeFaces.cw('InputText','widget_registrationForm_registrationLogin',{id:'registrationForm:registrationLogin'});</script></td>
</tr>
<tr>
<td><label for="registrationForm:registrationPassword" class="registerLabel">
Пароль: </label></td>
<td><input id="registrationForm:registrationPassword" name="registrationForm:registrationPassword" type="password" class="ui-inputfield ui-password ui-widget ui-state-default ui-corner-all registerText" /><script id="registrationForm:registrationPassword_s" type="text/javascript">$(function(){PrimeFaces.cw('Password','widget_registrationForm_registrationPassword',{id:'registrationForm:registrationPassword',feedback:true,inline:false,promptLabel:'Введите пароль',weakLabel:'Слабый пароль',goodLabel:'Нормальный пароль',strongLabel:'Сложный пароль'});});</script></td>
</tr>
<tr>
<td><label for="registrationForm:registrationMail" class="registerLabel">
Адрес эл. почты: </label></td>
<td><input id="registrationForm:registrationMail" name="registrationForm:registrationMail" type="text" value="" class="ui-inputfield ui-inputtext ui-widget ui-state-default ui-corner-all registerText" /><script id="registrationForm:registrationMail_s" type="text/javascript">PrimeFaces.cw('InputText','widget_registrationForm_registrationMail',{id:'registrationForm:registrationMail'});</script></td>
</tr>
<tr>
<td><label for="registrationForm:registrationSex" class="registerLabel">
Пол: </label></td>
<td><table id="registrationForm:registrationSex" class="ui-selectoneradio ui-widget"><td><div class="ui-radiobutton ui-widget"><div class="ui-helper-hidden-accessible"><input id="registrationForm:registrationSex:0" name="registrationForm:registrationSex" type="radio" value="male" /></div><div class="ui-radiobutton-box ui-widget ui-corner-all ui-radiobutton-relative ui-state-default"><span class="ui-radiobutton-icon"></span></div></div></td><td><label for="registrationForm:registrationSex:0">М</label></td><td><div class="ui-radiobutton ui-widget"><div class="ui-helper-hidden-accessible"><input id="registrationForm:registrationSex:1" name="registrationForm:registrationSex" type="radio" value="female" checked="checked" /></div><div class="ui-radiobutton-box ui-widget ui-corner-all ui-radiobutton-relative ui-state-default ui-state-active"><span class="ui-radiobutton-icon ui-icon ui-icon-bullet"></span></div></div></td><td><label for="registrationForm:registrationSex:1">Ж</label></td></table><script id="registrationForm:registrationSex_s" type="text/javascript">$(function(){PrimeFaces.cw('SelectOneRadio','widget_registrationForm_registrationSex',{id:'registrationForm:registrationSex'});});</script></td>
</tr>
<tr>
<td><label for="registrationForm:registrationName" class="registerLabel">
Отображаемое имя: </label></td>
<td><input id="registrationForm:registrationName" name="registrationForm:registrationName" type="text" value="" class="ui-inputfield ui-inputtext ui-widget ui-state-default ui-corner-all registerText" /><script id="registrationForm:registrationName_s" type="text/javascript">PrimeFaces.cw('InputText','widget_registrationForm_registrationName',{id:'registrationForm:registrationName'});</script></td>
</tr>
<tr>
<td><label for="registrationForm:registrationCalendar" class="registerLabel">
Дата рождения: </label></td>
<td><span id="registrationForm:registrationCalendar"><input id="registrationForm:registrationCalendar_input" name="registrationForm:registrationCalendar_input" type="text" class="ui-inputfield ui-widget ui-state-default ui-corner-all" size="24" /></span><script id="registrationForm:registrationCalendar_s" type="text/javascript">$(function(){PrimeFaces.cw('Calendar','widget_registrationForm_registrationCalendar',{id:'registrationForm:registrationCalendar',popup:true,locale:'ru',dateFormat:'dd.mm.y',yearRange:'-68',changeMonth:true,changeYear:true,showAnim:'explode',duration:'normal'});});</script></td>
</tr>
<tr>
<td><label for="registrationForm:registrationConfirm" class="registerLabel">
</label></td>
<td><button id="registrationForm:registrationConfirm" name="registrationForm:registrationConfirm" class="ui-button ui-widget ui-state-default ui-corner-all ui-button-text-only registerButton" onclick="PrimeFaces.ab({source:'registrationForm:registrationConfirm',process:'registrationForm',update:'loginField content title registrationForm'});return false;" type="submit"><span class="ui-button-text">Зарегистрироваться</span></button><script id="registrationForm:registrationConfirm_s" type="text/javascript">PrimeFaces.cw('CommandButton','widget_registrationForm_registrationConfirm',{id:'registrationForm:registrationConfirm'});</script></td>
</tr>
</tbody>
</table>
<div id="registrationForm:j_idt46" class="ui-message-error ui-widget ui-corner-all"><span class="ui-message-error-icon"></span><span class="ui-message-error-detail">registrationForm:registrationLogin: Validation Error: Value is required.</span></div>
</form></div></span>]]></update><update id="javax.faces.ViewState"><![CDATA[-7975648054570174914:1199185624285089158]]></update><extension ln="primefaces" type="args">{"validationFailed":true}</extension><extension ln="primefaces" type="args">{"validationFailed":true}</extension></changes></partial-response>

P{3,}S. If we take a look at this line:

<extension ln="primefaces" type="args">{"validationFailed":true}</extension>
<extension ln="primefaces" type="args">{"validationFailed":true}</extension>

Should it be called 2 times? Can it be caused by the fact that somewhere in my deployment, the primefaces library is referenced 2 times?


Solution

  • Finally solved! The problem was in the deployment of the primefaces .jar file. My web application is running on Glassfish v3 and I develop it in Eclipse. When I downloaded the primefaces jar-file, I put it inside glassfish/lib folder. After that I put the copy of this jar inside WEB-INF and deployed it like that. This was a problem. I didnt get why, but internally the script received 2 responses from both jars and stops working because of the parsing error.

    To conclude: never put copies of primefaces.jar in both glassfish/lib and WEB-INF/lib of the application. Hope it helps someone with the same problem.