2012-05-05 18 views
5

I Deseo implementar la validación de entrada archivada. Este es el código del bean administrado:Alcance en JSF Validator

<?xml version='1.0' encoding='UTF-8' ?> 
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> 
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"  
     xmlns:h="http://java.sun.com/jsf/html" 
     xmlns:f="http://java.sun.com/jsf/core" 
     xmlns:ui="http://java.sun.com/jsf/facelets"> 
    <h:head> 
     <ui:insert name="header">   
      <ui:include src="header.xhtml"/>   
     </ui:insert> 
    </h:head> 
    <h:body> 

     <h1><img src="resources/css/images/icon.png" alt="NVIDIA.com" /> History Center</h1> 
     <!-- layer for black background of the buttons --> 
     <div id="toolbar" style="margin: 0 auto; width:1180px; height:30px; position:relative; background-color:black"> 
      <!-- Include page Navigation --> 
      <ui:insert name="Navigation">   
       <ui:include src="Navigation.xhtml"/>   
      </ui:insert> 

     </div> 

     <div id="logodiv" style="position:relative; top:35px; left:0px;"> 
      <h:graphicImage alt="Demo Insert Form" style="position:relative; top:-20px; left:9px;" value="resources/images/logo_databasez.png" /> 
     </div> 
     <div id="main" style="margin: 0 auto; width:1190px; height:700px; position:absolute; background-color:transparent; top:105px"> 

      <div id="mainpage" style="margin: 0 auto; width:1190px; height:500px; position:absolute; background-color:transparent; top:80px"> 

       <div id="settingsHashMap" style="width:350px; height:400px; position:absolute; background-color:r; top:20px; left:1px"> 
        <h:form> 
         <div id="settingsdiv" style="width:750px; height:400px; position:absolute; background-color:r; top:20px; left:1px"> 

          <h:panelGrid columns="2"> 
           <h:panelGroup>Session ID</h:panelGroup> 
           <h:panelGroup> 
            <h:inputText id="sessionid" value="#{DatabaseController.formMap['sessionid']}" > 
             <f:validateLength minimum="0" maximum="15"/> 
             <f:validator binding="#{ValidatorController.validateMessage}" > 
              <f:attribute name="type" value="sessionid" /> 
             </f:validator> 
             <f:ajax event="blur" render="sessionidvalidate" />           
            </h:inputText> 
            <h:message id="sessionidMessage" for="sessionid" /> 
           </h:panelGroup> 

           <h:panelGroup>User ID</h:panelGroup> 
           <h:panelGroup> 
            <h:inputText id="userid" value="#{DatabaseController.formMap['userid']}" > 
             <f:validateLength minimum="0" maximum="15"/> 
            </h:inputText> 
           </h:panelGroup> 

           <h:panelGroup>Login Time</h:panelGroup> 
           <h:panelGroup> 
            <h:inputText id="logintime" value="#{DatabaseController.formMap['logintime']}" > 
             <f:validateLength minimum="0" maximum="35"/> 
            </h:inputText> 
           </h:panelGroup> 

           <h:panelGroup>Last Refresh Time</h:panelGroup> 
           <h:panelGroup> 
            <h:inputText id="lastrefreshtime" value="#{DatabaseController.formMap['lastrefreshtime']}" > 
             <f:validateLength minimum="0" maximum="35"/> 
            </h:inputText> 
           </h:panelGroup> 

           <h:panelGroup>User IP</h:panelGroup> 
           <h:panelGroup> 
            <h:inputText id="userip" value="#{DatabaseController.formMap['userip']}" > 
             <f:validateLength minimum="0" maximum="15"/> 
            </h:inputText> 
           </h:panelGroup> 

          </h:panelGrid>   

         </div> 

         <div id="settingstwodiv" style="width:150px; height:60px; position:absolute; background-color:transparent; top:380px; left:800px"> 

          <h:commandButton value="Create User" action="#{DatabaseController.saveData}"/> 

         </div> 
        </h:form> 

       </div> 

      </div> 
     </div> 

    </h:body> 
</html> 

Este es el código que he añadido en faces-config.xml

<validator> 
    <validator-id>ValidatorController</validator-id> 
    <validator-class>com.DX_57.HM_57.FormValidator</validator-class> 
</validator> 

Este es el código del Validador que he tratado de prueba:

import javax.enterprise.context.SessionScoped; 
import javax.faces.application.FacesMessage; 
import javax.faces.component.UIComponent; 
import javax.faces.context.FacesContext; 
import javax.faces.validator.Validator; 
import javax.faces.validator.ValidatorException; 
import javax.inject.Named; 

@Named("ValidatorController") 
@SessionScoped 
public class FormValidator implements Validator { 

    public FormValidator() { 
    } 

    @Override 
    public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException { 
     throw new UnsupportedOperationException("Not supported yet."); 
    } 

    public void validateMessage(FacesContext context, UIComponent component, Object value) throws ValidatorException { 

     if (value.equals("test")) { 
      throw new ValidatorException(new FacesMessage(FacesMessage.SEVERITY_ERROR, 
        "Session ID is already in use, please choose another.", null)); 
     } 
    } 
} 

el problema es este error que consigo cuando intento ejecutar el ejemplo:

[#|2012-05-05T22:39:00.096+0300|INFO|glassfish3.1.2|org.glassfish.osgiweb|_ThreadID=58;_ThreadName=Thread-2;|Removed bundle 710 against context path /test |#] 

[#|2012-05-05T22:39:00.097+0300|WARNING|glassfish3.1.2|org.glassfish.osgijavaeebase|_ThreadID=58;_ThreadName=Thread-2;|Failed to deploy bundle com.DX_57.History-Module-57 [710] 
org.glassfish.osgijavaeebase.DeploymentException: Deployment of com.DX_57.History-Module-57 [710] failed because of following reason: Failed while deploying bundle com.DX_57.History-Module-57 [710] : java.lang.RuntimeException: Failed to deploy bundle [ com.DX_57.History-Module-57 [710] ], root cause: Exception while loading the app 
    at org.glassfish.osgijavaeebase.AbstractOSGiDeployer.deploy(AbstractOSGiDeployer.java:125) 
    at org.glassfish.osgijavaeebase.OSGiContainer.deploy(OSGiContainer.java:154) 
    at org.glassfish.osgijavaeebase.JavaEEExtender.deploy(JavaEEExtender.java:107) 
    at org.glassfish.osgijavaeebase.JavaEEExtender.access$200(JavaEEExtender.java:61) 
    at org.glassfish.osgijavaeebase.JavaEEExtender$HybridBundleTrackerCustomizer$1.call(JavaEEExtender.java:151) 
    at org.glassfish.osgijavaeebase.JavaEEExtender$HybridBundleTrackerCustomizer$1.call(JavaEEExtender.java:148) 
    at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:334) 
    at java.util.concurrent.FutureTask.run(FutureTask.java:166) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1110) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:603) 
    at java.lang.Thread.run(Thread.java:722) 
Caused by: java.lang.RuntimeException: Failed to deploy bundle [ com.DX_57.History-Module-57 [710] ], root cause: Exception while loading the app 
    at org.glassfish.osgijavaeebase.OSGiDeploymentRequest.deploy(OSGiDeploymentRequest.java:196) 
    at org.glassfish.osgijavaeebase.OSGiDeploymentRequest.execute(OSGiDeploymentRequest.java:118) 
    at org.glassfish.osgijavaeebase.AbstractOSGiDeployer.deploy(AbstractOSGiDeployer.java:121) 
    ... 10 more 
Caused by: org.glassfish.deployment.common.DeploymentException: WELD-000072 Managed bean declaring a passivating scope must be passivation capable. Bean: Managed Bean [class com.DX_57.HM_57.FormValidator] with qualifiers [@Any @Default @Named] 
    at org.glassfish.weld.WeldDeployer.event(WeldDeployer.java:181) 
    at org.glassfish.kernel.event.EventsImpl.send(EventsImpl.java:128) 
    at org.glassfish.internal.data.ApplicationInfo.load(ApplicationInfo.java:277) 
    at com.sun.enterprise.v3.server.ApplicationLifecycle.deploy(ApplicationLifecycle.java:460) 
    at com.sun.enterprise.v3.server.ApplicationLifecycle.deploy(ApplicationLifecycle.java:240) 
    at org.glassfish.osgijavaeebase.OSGiDeploymentRequest.deploy(OSGiDeploymentRequest.java:183) 
    ... 12 more 
Caused by: org.jboss.weld.exceptions.DefinitionException: WELD-000072 Managed bean declaring a passivating scope must be passivation capable. Bean: Managed Bean [class com.DX_57.HM_57.FormValidator] with qualifiers [@Any @Default @Named] 
    at org.jboss.weld.bean.ManagedBean.checkType(ManagedBean.java:405) 
    at org.jboss.weld.bean.AbstractBean.initializeAfterBeanDiscovery(AbstractBean.java:149) 
    at org.jboss.weld.bean.AbstractClassBean.initializeAfterBeanDiscovery(AbstractClassBean.java:308) 
    at org.jboss.weld.bean.ManagedBean.initializeAfterBeanDiscovery(ManagedBean.java:361) 
    at org.jboss.weld.bootstrap.BeanDeployment.doAfterBeanDiscovery(BeanDeployment.java:216) 
    at org.jboss.weld.bootstrap.BeanDeployment.afterBeanDiscovery(BeanDeployment.java:208) 
    at org.jboss.weld.bootstrap.WeldBootstrap.deployBeans(WeldBootstrap.java:352) 
    at org.glassfish.weld.WeldDeployer.event(WeldDeployer.java:179) 
    ... 17 more 
|#] 

Parece que la clase Validator no está en el alcance correcto. ¿Qué alcance tengo que usar?

mejores deseos

+3

Matt ha respondido a su ac actual Oblem, pero también tiene otros errores importantes en el validador. Repare su validador para que coincida exactamente con el ejemplo en mi respuesta a su pregunta anterior. Deberías hacer el trabajo en el método 'validate()' de la interfaz 'Validator', no en un método personalizado. No debería necesitar la antigua declaración JSF 1.x '' en 'faces-config.xml'. Debería hacer referencia a la instancia concreta de validación en 'binding', no solo a su método. – BalusC

+0

Ok, pero si elimino la declaración en faces-config.xml, ¿puedo usar CDI en el validador? Quiero implementar un validador personalizado porque si tengo 20 campos de entrada, tengo que implementar 20 validadores estándar en diferentes clases y archivos de Java. Quiero hacerlo en un archivo. –

+0

¿Es esto posible? –

Respuesta

1

Prueba este código:

<h:panelGroup>Session ID</h:panelGroup> 
<h:panelGroup> 
    <h:inputText id="sessionid" value="#{DatabaseController.formMap['sessionid']}" 
        validator="#{ValidatorController.validatebean}">           
     <f:ajax event="blur" render="sessionidMessage" />           
    </h:inputText> 
    <h:message id="sessionidMessage" for="sessionid" /> 
</h:panelGroup> 

Este es el frijol:

@Named("ValidatorController") 
@ViewScoped 
public class FormValidator implements Validator { 

    public FormValidator() { 
    } 

    @Override 
    public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException { 
     if (value.equals("test")) { 
      throw new ValidatorException(new FacesMessage(FacesMessage.SEVERITY_ERROR, 
        " Session ID is already in use, please choose another.", null)); 
     } 
    } 

    public void validatebean(FacesContext context, UIComponent component, Object value) throws ValidatorException { 
     if (value.equals("test")) { 
      throw new ValidatorException(new FacesMessage(FacesMessage.SEVERITY_ERROR, 
        " Session ID is already in use, please choose another.", null)); 
     } 
    } 

} 
+0

Wow, no sé por qué y cómo pero este código funciona. ¡Gracias a todos! –

10

De la documentación SOLDADURA:

granos administradas con alcance @SessionScoped o @ConversationScoped deben ser serializable, ya que el contenedor pasiva la sesión HTTP de vez en cuando.

Puede haber otras razones, pero la sesión de CDI con ámbito de frijol al menos debería implementar la interfaz Serializable:

@Named("ValidatorController") 
@SessionScoped 
public class FormValidator implements Validator, Serializable { 
... 
}