Wednesday, 28 August 2013

and localization in JSF

and localization in JSF

I have a <f:viewParam> tag on JSF pages that sets GET parameters into the
corresponding managed bean after conversion and validation.
If either conversion or validation errors occur, then an appropriate error
message is displayed in <p:messages> (may also be <p:growl> or
<h:messages>).
The application is multilingual. So, when a different language is
selected, a message should be displayed in that language but it always
displays in English.
Test.xhtml
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<ui:composition template="template/Template.xhtml"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:p="http://primefaces.org/ui"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:c="http://java.sun.com/jsp/jstl/core">
<ui:define name="title">Test</ui:define>
<ui:define name="content">
<h:form id="form" prependId="true">
<f:metadata>
---------------><f:viewParam name="id" id="paramId" rendered="#{not empty
param.id}" converter="#{testRowSelectionConverter}"
value="#{testManagedBean.entity}" maxlength="20"/>
</f:metadata>
<p:messages id="messages" for="paramId" globalOnly="false"
redisplay="false" showDetail="true" showSummary="false"
autoUpdate="false" closable="true"/>
</h:form>
</ui:define>
</ui:composition>
The managed bean:
@ManagedBean
@ViewScoped
public final class TestManagedBean implements Serializable
{
private Test entity;
public TestManagedBean(){}
public Test getEntity() {
return entity;
}
public void setEntity(Test entity) {
this.entity = entity;
}
}
The converter:
@ManagedBean
@RequestScoped
public final class TestRowSelectionConverter implements Converter
{
@EJB(mappedName="ejb/JNDI")
private TestService testService;
@Override
public Object getAsObject(FacesContext context, UIComponent component,
String value)
{
try
{
Integer parsedValue = Integer.parseInt(value);
if(parsedValue<=0)
{
throw new ConverterException(new
FacesMessage(FacesMessage.SEVERITY_ERROR, "",
Utility.getMessage("id.negativeOrZero")));
}
Test entity = testService.findById(parsedValue);
if(entity==null)
{
throw new ConverterException(new
FacesMessage(FacesMessage.SEVERITY_WARN, "",
Utility.getMessage("id.notFound")));
}
return entity;
}
catch (NumberFormatException e)
{
throw new ConverterException(new
FacesMessage(FacesMessage.SEVERITY_ERROR, "",
Utility.getMessage("id.conversion.error")), e);
}
}
@Override
public String getAsString(FacesContext context, UIComponent component,
Object value)
{
return value instanceof Test?((Test)value).getId().toString():"";
}
}
Except for the messages from <f:viewParam>, there is no problem. All other
kind of messages are displayed in the language selected by the user.



id.negativeOrZero, id.notFound and id.conversion.error in converter are
keys of respective messages in a resource bundle as it can be visualized.
There are different property files with different locale for each
language.
Is there any special thing with <f:viewParam>?



The following is the Template.xhtml file where the locale is set dynamically.
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html lang="#{localeBean.language}"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:p="http://primefaces.org/ui"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core">
----><f:view locale="#{localeBean.locale}" encoding="UTF-8"
contentType="text/html">
<f:loadBundle basename="messages.ResourceBundle" var="messages"/>
<h:head><title><ui:insert name="title">Default
Title</ui:insert></title></h:head>
<h:body>
<p:layout fullPage="true">
<p:layoutUnit position="north" size="135" collapsed="false"
resizable="false" closable="false" collapsible="false"
gutter="6">
<h:form>
<h:selectOneMenu id="languages"
value="#{localeBean.language}" onchange="submit();"
style="position: absolute; right: 0; top: 50px;">
<f:selectItem itemValue="en" itemLabel="English" />
<f:selectItem itemValue="hi" itemLabel="Hindi" />
</h:selectOneMenu>
</h:form>
</p:layoutUnit>
<p:layoutUnit position="west" id="leftPanel" size="225"
header="Menu Item" resizable="false" closable="false"
collapsible="true" gutter="6">
</p:layoutUnit>
<p:layoutUnit position="center" size="2500" maxSize="2500">
<ui:insert name="content">Put default content here, if
any.</ui:insert>
</p:layoutUnit>
</p:layout>
</h:body>
</f:view>
</html>
Again except for <f:viewParam>, everything is fine.



EDIT:
The getMessage() method:
import java.text.MessageFormat;
import java.util.Random;
import java.util.ResourceBundle;
import javax.faces.context.FacesContext;
public static String getMessage(String key, Object...params)
{
final String defaultMessage="Message not found.";
FacesContext context = FacesContext.getCurrentInstance();
ResourceBundle resourceBundle =
context.getApplication().evaluateExpressionGet(context, "#{messages}",
ResourceBundle.class);
return
key==null?defaultMessage:resourceBundle.containsKey(key)?MessageFormat.format(resourceBundle.getString(key),
params):defaultMessage;
}

No comments:

Post a Comment