<?xml version="1.0" encoding="UTF-8"?>
<feed xmlns="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <title>Components redisplaying  model values when validation fails</title>
  <link rel="self" href="https://liferay.dev/c/message_boards/find_thread?p_l_id=119785294&amp;threadId=112239338" />
  <subtitle>Components redisplaying  model values when validation fails</subtitle>
  <id>https://liferay.dev/c/message_boards/find_thread?p_l_id=119785294&amp;threadId=112239338</id>
  <updated>2026-04-07T01:28:23Z</updated>
  <dc:date>2026-04-07T01:28:23Z</dc:date>
  <entry>
    <title>RE: Components redisplaying  model values when validation fails</title>
    <link rel="alternate" href="https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=112245612" />
    <author>
      <name>Kyle Joseph Stiemann</name>
    </author>
    <id>https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=112245612</id>
    <updated>2019-02-06T00:49:18Z</updated>
    <published>2019-02-06T00:49:18Z</published>
    <summary type="html">&lt;html&gt;&lt;head&gt;&lt;/head&gt;&lt;body&gt;Hi Abraham,&lt;br&gt;As you noted, this is a bug in the JSF spec that has been fixed in JSF 2.3. There's no easy fix without changing Mojarra, but it may be possible to work around this issue using JSF extension points. Perhaps you could add a custom &lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;ResponseWriterWrapper&lt;/span&gt; that renders the &lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;"value"&lt;/span&gt; property as an empty string when appropriate:&lt;br&gt;&lt;br&gt;&lt;pre&gt;&lt;code&gt;public final class CustomResponseWriter extends ResponseWriterWrapper{

    private final ResponseWriter wrappedResponseWriter;
    private final LinkedList&amp;lt;editablevalueholder&amp;gt; editableValueHolders;

    public CustomResponseWriter(ResponseWriter responseWriter) {

        this.wrappedResponseWriter = responseWriter;
        this.editableValueHolders = new LinkedList&amp;lt;editablevalueholder&amp;gt;();
    }

    @Override
    public void writeText(Object text, UIComponent uiComponent, String property) throws IOException {

        if (shouldRenderAsEmptyString(property)) {
            super.writeText("", uiComponent, property);
        }
        else {
            super.writeText(text, uiComponent, property);
        }
    }

    @Override
    public void writeText(Object text, String property) throws IOException {

        if (shouldRenderAsEmptyString(property)) {
            super.writeText("", property);
        }
        else {
            super.writeText(text, property);
        }
    }

    @Override
    public void writeURIAttribute(String name, Object value, String property) throws IOException {

        if (shouldRenderAsEmptyString(property)) {
            super.writeURIAttribute(name, "", property);
        }
        else {
            super.writeURIAttribute(name, value, property);
        }
    }

    @Override
    public void writeAttribute(String name, Object value, String property) throws IOException {

        if (shouldRenderAsEmptyString(property)) {
            super.writeAttribute(name, "", property);
        }
        else {
            super.writeAttribute(name, value, property);
        }
    }

    @Override
    public void startElement(String name, UIComponent uiComponent) throws IOException {

        if (uiComponent instanceof EditableValueHolder) {
            editableValueHolders.push((EditableValueHolder) uiComponent);
        }
        else {
            editableValueHolders.push(null);
        }

        super.startElement(name, uiComponent);
    }

    @Override
    public void endElement(String name) throws IOException {

        super.endElement(name);
        editableValueHolders.pop();
    }

    private boolean shouldRenderAsEmptyString(String property) {
        return "value".equalsIgnoreCase(property) &amp;amp;amp;&amp;amp;amp;
                editableValueHolders.peek() != null &amp;amp;amp;&amp;amp;amp;
                editableValueHolders.peek().getSubmittedValue() == null &amp;amp;amp;&amp;amp;amp;
                !editableValueHolders.peek().isValid();
    }

    @Override
    public ResponseWriter getWrapped() {
        return wrappedResponseWriter;
    }
}&amp;lt;/editablevalueholder&amp;gt;&amp;lt;/editablevalueholder&amp;gt;&lt;/code&gt;&lt;/pre&gt;&lt;br&gt;You'll need to add this &lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;ResponseWriter&lt;/span&gt; using a custom &lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;RenderKit&lt;/span&gt; (&lt;a href="https://github.com/liferay/liferay-faces-bridge-impl/blob/4.1.2/bridge-impl/src/main/java/com/liferay/faces/bridge/renderkit/html_basic/internal/RenderKitBridgeImplCompat.java#L48-L54"&gt;example custom &lt;span style="font-family: &amp;quot;Courier New&amp;quot;, Courier, monospace"&gt;RenderKit&lt;/span&gt; in Liferay Faces&lt;/a&gt;) which is registered in your &lt;strong&gt;&lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;faces-config.xml&lt;/span&gt;&lt;/strong&gt; file:&lt;br&gt;&lt;br&gt;&lt;pre&gt;&lt;code&gt;    &amp;lt;render-kit&amp;gt;
        &amp;lt;render-kit-id&amp;gt;HTML_BASIC&amp;lt;/render-kit-id&amp;gt;
        &amp;lt;render-kit-class&amp;gt;your.custom.renderkit.CustomRenderKit&amp;lt;/render-kit-class&amp;gt;
    &amp;lt;/render-kit&amp;gt;&lt;/code&gt;&lt;/pre&gt;&lt;br&gt;&lt;strong&gt;I haven't tested this code&lt;/strong&gt;, and there are potential problems with this solution: certain renderers may omit the &lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;"value"&lt;/span&gt; property so it may not be possible to tell when they are rendering their value, this &lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;ResponseWriter&lt;/span&gt; may interfere with other &lt;span style="font-family: &amp;quot;Courier New&amp;quot;"&gt;ResponseWriter&lt;/span&gt;s&amp;nbsp; (and vice-versa) etc. But this is the best workaround I could come up with. Let me know if it works for you.&lt;br&gt;&lt;br&gt;​​​​​​- Kyle&lt;/body&gt;&lt;/html&gt;</summary>
    <dc:creator>Kyle Joseph Stiemann</dc:creator>
    <dc:date>2019-02-06T00:49:18Z</dc:date>
  </entry>
  <entry>
    <title>Components redisplaying  model values when validation fails</title>
    <link rel="alternate" href="https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=112239337" />
    <author>
      <name>Abraham Duffidall</name>
    </author>
    <id>https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=112239337</id>
    <updated>2019-02-05T10:51:03Z</updated>
    <published>2019-02-05T10:51:03Z</published>
    <summary type="html">&lt;html&gt;&lt;head&gt;&lt;/head&gt;&lt;body&gt;Hi all,&lt;br&gt;&lt;br&gt;I am experiencing an issue that can be reproduced by deploying the demo&lt;br&gt;&lt;br&gt;&lt;a href="http://central.maven.org/maven2/com/liferay/faces/demo/com.liferay.faces.demo.jsf.cdi.applicant.portlet/4.1.0/com.liferay.faces.demo.jsf.cdi.applicant.portlet-4.1.0.war"&gt;JSF CDI Applicant Portlet&lt;/a&gt;&lt;br&gt;&lt;br&gt;to liferay-ce-portal-7.1.0-ga1.&lt;br&gt;&lt;br&gt;As I want to use bean validation in an upcoming project,&lt;br&gt;I added the context parameter to the web.xml and deployed it to LR for testing...&lt;br&gt;&lt;br&gt;&lt;pre&gt;&lt;code&gt;[code]&amp;lt;context-param&amp;gt;
    &amp;lt;param-name&amp;gt;javax.faces.INTERPRET_EMPTY_STRING_SUBMITTED_VALUES_AS_NULL&amp;lt;/param-name&amp;gt;
    &amp;lt;param-value&amp;gt;true&amp;lt;/param-value&amp;gt;
&amp;lt;/context-param&amp;gt;&lt;/code&gt;&lt;/pre&gt;&lt;br&gt;Now, if validation fails for a required input value, the (old) model value is redisplayed.&lt;br&gt;&lt;br&gt;Steps to reproduce:&lt;br&gt;1) Enter only "first name"&lt;br&gt;2) Submit&lt;br&gt;3) Remove value from "first name" again&lt;br&gt;4) Submit&lt;br&gt;&lt;br&gt;Now the old value (from model) is redisplayed.&lt;br&gt;I am pretty sure that this behavior is related to the following issue:&lt;br&gt;&lt;br&gt;https://github.com/javaee/javaserverfaces-spec/issues/671&lt;br&gt;https://stackoverflow.com/questions/3933786/jsf-2-bean-validation-validation-failed-empty-values-are-replaced-with-las&lt;br&gt;&lt;br&gt;But none of the workarounds worked for me.&lt;br&gt;Any ideas?&lt;br&gt;&lt;br&gt;Thanks&lt;br&gt;Abraham&lt;/body&gt;&lt;/html&gt;</summary>
    <dc:creator>Abraham Duffidall</dc:creator>
    <dc:date>2019-02-05T10:51:03Z</dc:date>
  </entry>
</feed>
