¿Cómo puedo mostrar ValidatorException y required = "true" del mismo campo de entrada en diferentes elementos de mensajes

Tomé el siguienteEjemplo de lanzamiento de BalusC y lo modifiqué un poco agregando un botón de envío y mensajes h: adicionales y eliminando elf:ajax desde elh:inputSecret's (retiró elf:ajax Causa por alguna razón cuando salgo de la primera.h:inputSecret inmediatamente muestra el error "el valor es requerido" para el segundoh:inputSecret - pero el usuario no ha tenido la oportunidad de escribirlo ... ??? <- otra pregunta futura? :))

OK, para hacer larga la historia corta:

Estoy tratando de averiguar cómo se pueden mostrar los errores de validación con respecto a los dos campos de contraseña (que las contraseñas no son iguales) en los mensajes h: globales y no en el mensaje h: individual de los campos de contraseña. = "true" se mostrará en el<h:message de cada campo ...

Pero en este momento, el mensaje de validación (emitido por mi excepción) y el requerido = "verdadero" se muestran en el mismo lugar

Aquí está el código:

<code><h:outputLabel for="password" value="Password:" />
<h:inputSecret id="password" value="#{bean.password}" required="true">
    <f:validator validatorId="confirmPasswordValidator" />
    <f:attribute name="confirm" value="#{confirmPassword.submittedValue}" />
</h:inputSecret>
<h:message id="m_password" for="password" />

<h:outputLabel for="confirm" value="Password (again):" />
<h:inputSecret id="confirm" binding="#{confirmPassword}" required="true">
</h:inputSecret>
<h:message id="m_confirm" for="confirm" />
</code>

Y adicionalh:commandButton conh:messages debajo de ese código:

<code><h:commandButton value="doSomething" action="#{myBean.myAction}">
    <f:ajax execute="password confirm" render="m_password m_confirm"></f:ajax>
</h:commandButton>
<h:messages globalOnly="true" styleClass="validation_value_required"/>
</code>
<code>@FacesValidator("confirmPasswordValidator")
public class ConfirmPasswordValidator implements Validator {

    @Override
    public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException {
        String password = (String) value;
        String confirm = (String) component.getAttributes().get("confirm");

        if (password == null || confirm == null) {
            return; // Just ignore and let required="true" do its job.
        }

        if (!password.equals(confirm)) {
            throw new ValidatorException(new FacesMessage("Passwords are not equal."));
        }
    }

}
</code>

también

Gracias por delante

Solución (Gracias a BalusC)

cambiado

<code><f:attribute name="confirm" value="#{confirmPassword.submittedValue}" />
</code>

a

<code><f:attribute name="confirm" value="#{confirmPassword}" />
</code>

y

<code>String confirm = (String) component.getAttributes().get("confirm");
</code>

dentro

<code>UIInput confirmPasswordComponent = (UIInput) component.getAttributes().get("confirm");
String confirm = (String) confirmPasswordComponent.getSubmittedValue();
</code>

y

<code>throw new ValidatorException(new FacesMessage("Passwords are not equal."));
</code>

dentro

<code>context.addMessage(null, new FacesMessage("Passwords are not equal."));
context.validationFailed();
((UIInput) component).setValid(false);
confirmPasswordComponent.setValid(false);
return;
</code>

Respuestas a la pregunta(1)

Su respuesta a la pregunta