Message bundles in JSF - jsf

I am using JSF and I want to use message bundles so I added the XML configuration below. Now I wonder if someone could write some experiences they had when using them. Is it best practice to have one big properties file that contain all translation on the page, if so how do you name your keys. If not, then I guess you have multiple resource files, how do you structure them - what part of the page do they provide messages for? - and any naming practices?
I know this may be subjective but it could be valuable insights for me anyway.
<application>
<resource-bundle>
<base-name>com.myapp.blah</base-name>
<var>msgs</var>
</resource-bundle>
</application>

I suggest you begin with the single File approach, one per language. If it grows in a level that you simply can't manage anymore, thousands of lines, than you might split it.
Then you can internationalize your pages using a template that will have:
<f:view locale="#{userBean.userLocale}">
and you can enable a select component to hold the available languages for the users to switch:
FacesContext.getCurrentInstance().getViewRoot().setLocale(locale);
and in faces-config.xml:
<application>
<locale-config>
<default-locale>pt-br</default-locale>
<supported-locale>en</supported-locale>
</locale-config>
<resource-bundle>
<base-name>com.myapp.blah.ApplicationResources</base-name>
<var>msg</var>
</resource-bundle>
...
then you shall have one file per language:
ApplicationResources.properties
ApplicationResources_en.properties
ApplicationResources_pt_BR.properties

Related

Overriding PrimeFaces renderer not working when provided via module library

I have a very tricky problem when overriding JSF-renderers.
This is a part of my faces-config.xml:
<?xml version="1.0" encoding="UTF-8"?>
<faces-config xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xi="http://www.w3.org/2001/XInclude" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_2_0.xsd"
version="2.0">
<render-kit>
<renderer>
<component-family>org.primefaces.component</component-family>
<renderer-type>org.primefaces.component.MenubarRenderer</renderer-type>
<renderer-class>de.mycompany.web.MenuRenderer</renderer-class>
</renderer>
</render-kit>
<factory>
<exception-handler-factory>de.mycompany.web.ValidationExceptionHandlerFactory</exception-handler-factory>
</factory>
</faces-config>
The structure of my web-project is following
webapp (building war), Dependencies to core and gui
core (building jar)
gui (building jar), Dependencies to core, containing xhtmls and #Named Beans, Dependency to com.sun.faces:jsf-impl Version 2.1.25
When I place the content of the faces-config.xml in
webapp/src/main/webapp/META-INF or
core/src/main/webapp/META-INF
both, the MenuRenderer and the ValidationExceptionHandlerFactory, are getting used. Yeah.
When I place the content of the faces-config in
gui/src/main/webapp/META-INF
the ValidationExceptionHandlerFactory is getting used, but not the MenuRenderer. WTF?
Also all other features (phase-listeners, system-event-listeners I use in my faces-config are working except ones in the render-kit-nodes.
What am I doing wrong?
You're trying to override a renderer supplied by another external library, not a standard renderer.
The loading order of faces-config.xml provided by external libraries is by default undefined. In your specific case, your library is apparently loaded before PrimeFaces library is loaded.
You can explicitly specify the loading order via <ordering> element in faces-config.xml. The name of the PrimeFaces library is primefaces. So, just add the below entry to your faces-config.xml. Make sure you supply your library a name too so that endusers can in turn reorder in their own faces-config.xml if necessary.
<name>yourlibrary</name>
<ordering>
<after>
<name>primefaces</name>
</after>
</ordering>
A real world example can be found in e.g. OptimusFaces which also extends PrimeFaces.

message always shown in the same language instead of configuring the browser not to

I am trying to show a welcoming message in a JSF page in different languages (English or Spanish) depending on the user's browser configuration.
These are the steps I follow:
1-In Netbeans I create a WAR project
2-In the folder Source Packages I create a package named locale, and inside that package, I create 2 files (messages.properties, messages_es.properties)
messages.properties
greeting = Welcome!
messages_es.properties
greeting = Bienvenido!
3-In the folder Web Pages I create the file index.html
<h:outputText value="#{msg['greeting']}" />
4-In faces-config.xml I write this code:
<locale-config>
<default-locale>en</default-locale>
<supported-locale>es</supported-locale>
</locale-config>
<resource-bundle>
<base-name>locale.messages</base-name>
<var>msg</var>
</resource-bundle>
When I run the application in my browser always is shown the welcoming message in Spanish (BIenvenido!), also when I change the preference order (Preferences-Content-Language) to show the web page in English.
What am I doing wrong?
I finally managed to find the error. I changed the messages.properties file name to messages_en.properties and it works well.

CSRF & XSS not working using HDIV

I am using HDIV in my project for securing from OWASP list but text boxs are accepting <script>alert(1);</script> as an input and saving to db.
I want to write test case for all OWASP issue.
Below are the project configuration
web.xml Configuration
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>
WEB-INF/spring/applicationContext-db.xml
WEB-INF/spring/spring-security.xml
WEB-INF/spring/hdiv-config.xml
</param-value>
</context-param>
webmvc-config.xml Configuration
<import resource="applicationContext-hdiv.xml" />
applicationContext-hdiv.xml Configuration
<beans>
<bean id="requestDataValueProcessor" class="org.springframework.security.web.servlet.support.csrf.CsrfRequestDataValueProcessor" />
<bean id="editableValidator" class="org.hdiv.web.validator.EditableParameterValidator"/>
<mvc:annotation-driven validator="editableValidator" />
</beans>
hdiv-config.xml Configuration
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:hdiv="http://www.hdiv.org/schema/hdiv" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.hdiv.org/schema/hdiv http://www.hdiv.org/schema/hdiv/hdiv.xsd">
<hdiv:config excludedExtensions="css,js,ttf" errorPage="/manage/security-error" maxPagesPerSession="10" confidentiality="true" strategy="memory" randomName="true">
<hdiv:sessionExpired loginPage="/main/common" homePage="/"/>
<hdiv:startPages method="get">/,/.*,/manage/.*,/login</hdiv:startPages>
</hdiv:config>
<hdiv:validation id="customValidation" componentType="text">
<hdiv:acceptedPattern><![CDATA[^[a-zA-Z0-9#.\-_]*$]]></hdiv:acceptedPattern>
<hdiv:rejectedPattern><![CDATA[(\s|\S)*(--)(\s|\S)*]]></hdiv:rejectedPattern>
</hdiv:validation>
<hdiv:editableValidations registerDefaults="true">
<hdiv:validationRule url=".*" enableDefaults="false">customValidation</hdiv:validationRule>
</hdiv:editableValidations>
</beans>
XSS is an output problem, not an input problem. Input validation is about making sure data is correct according to the domain. So for instance you want to check that a field expecting to take a year actually receives a number within the expected range. You may also want to make sure that only allowed characters are in use. And in many cases this will stop many attacks.
However for complex inputs, this is no longer viable. Consider a text field where you want to allow users to comment. The user should be allowed to to write a comment such as "An hence x < 4". Now we are allowing characters used to build html tags.
Now we have two options:
Use a tool to strip out dangerous HTML - likely to fail at some point
Use context aware escaping as described in the OWASP XSS prevention cheat sheet
Remove 'requestDataValueProcessor' and 'editableValidator' beans from 'applicationContext-hdiv.xml' file, they are automatically created by tag.
Have a look at this project configuration for a working example:
https://github.com/hdiv/hdiv-spring-mvc-showcase

Customize default taglib prefix

I don't know if this has a solution or is an IDE enhancement, but, when I'm using primefaces components in Netbeans, the autocomplete suggest the taglib p:..., no matter the id is http://primefaces.org/ui (should suggest pou), but if you're using primefaces extensions instead give pe as the showcase, gives poue.
So, now, I created a custom tag lib with id http://zeitek.net/ui, but as extensions is suggested znu, I know I can change it manually, but since is a collaborative project, I would like to use ztk as the predefined prefix to keep the standard in the code, is there anyway to achieve this with a JSF parameter or Netbeans configuration?
Well, if someone need this, i was missing this:
You need to create a tag-lib like normal and add this param:
<facelet-taglib
xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facelettaglibrary_2_0.xsd"
version="2.0"
id="zinf">
<namespace>http://zeitek.net/infraction/jsf/ui</namespace>
<composite-library-name>zinf</composite-library-name>
The last part is the important one: < composite-library-name>zinf< /composite-library-name>

Flow scope navigation to start page does not work

It is not so much a question, more of a note.
With Glassfish4, in a JEE7 application I tried to use the flow scope using programmatic flow definition (java class annotated with #Produces #FlowDefinition).
I navigated to the start page of the flow with a h:commandButton (just as it is done in the JEE7 tutorial example https://svn.java.net/svn/javaeetutorial~svn/trunk/examples/web/jsf/checkout-module.
When I pressed the button it stayed on the same page, where the button was, instead of going to the flow's start page.
After many hours of suffering, I realized that the problem is in the beans.xml, in my beans.xml I had this:
bean-discovery-mode="annotated"
which is the recommended setting according to the documentation (http://www.oracle.com/webfolder/technetwork/jsc/xml/ns/javaee/beans_1_1.xsd).
When I changed this to
bean-discovery-mode="all"
it started to work.
Somehow CDI does not recognize the flow definition as an annotated class. I tried to make it a #Named class, or a #ApplicationScoped class, but non of these helped.
I don't know if it is the intended behavior, or a bug.
Hope it saves a few ours to someone.
This is related to how CDI detects bean archives. When bean-discovery-mode="annotated", only classes annotated with bean defining annotations are picked up by CDI; note that #Named and #FlowScoped aren't on that list.
Because of this, as you've documented here, using Flow annotations requires bean-discovery-mode="all" to be set.
There's a spec issue open to discuss if this is a desired behavior.
Thank you!
Of course you can always fallback to using an XML declaration for your view. Such as creating a file example/example-flow.xml with contents such as
<?xml version='1.0' encoding='UTF-8'?>
<faces-config version="2.2"
xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/web-facesconfig_2_2.xsd">
<flow-definition id="example">
<flow-return id="actionId" >
<from-outcome>#{somebean.returnValue}</from-outcome>
</flow-return>
</flow-definition>
</faces-config>

Resources