Difference between app # getResourceBundle () and ResourceBundle # getBundle () in JSF 2.0

To restore Strings from resource bundle, I am trying to compare the result with these two methods, below example for code:

First example:

baseName: the fully qualified name of the resource package ( <base-name>

in <resource-bundle>

).

FacesContext context = FacesContext.getCurrentInstance();
Application app = context.getApplication();
ResourceBundle bundle = app.getResourceBundle(context, baseName);

      

Second example:

varName: a string representing <var></var>

in<resource-bundle>

FacesContext context = FacesContext.getCurrentInstance();
Locale locale = context .getViewRoot().getLocale();
ClassLoader loader = Thread.currentThread().getContextClassLoader();
ResourceBundle bundle = ResourceBundle.getBundle(varName, locale, loader);

      

What is the difference between these towing examples? if it made no difference what would be the best practice to get the ResourceBundle (use Application # getMessageBundle () or ResourceBundle # getBundle ())?

+3


source to share


1 answer


First of all, you have mixed the varName / baseName name of the approaches. Actual approaches:

Application#getResourceBundle()

varName

: this is a string representing <resource-bundle><var>

infaces-config.xml

FacesContext context = FacesContext.getCurrentInstance();
Application application = context.getApplication();
ResourceBundle bundle = application.getResourceBundle(context, varName);

      

ResourceBundle#getBundle()

baseName

: this is the fully qualified name of the resource package, for example <resource-bundle><base-name>

FacesContext context = FacesContext.getCurrentInstance();
Locale locale = context.getViewRoot().getLocale();
ClassLoader loader = Thread.currentThread().getContextClassLoader();
ResourceBundle bundle = ResourceBundle.getBundle(baseName, locale, loader);

      

The former receives it via JSF Application

, which under the covers also uses UIViewRoot#getLocale()

(aside from Locale#getDefault()

), and the latter receives it directly.

As for the technical and final result, there is no difference. You will get exactly the same package in both cases (assuming the language is correct). However, when it comes to maintainability, it is definitely different. Resource bundles fall under "config" and must be externalized (c faces-config.xml

).

Hardcoding FQNs, as in baseName

, is bad practice. You cannot easily quickly change the FQN without recompiling and rebuilding the entire code. If it was in a third party JAR file, it would be even more annoying. Otherwise, you could just override it with another <resource-bundle>

one on the same <var>

inside your webapp. Also, JSF component libraries / utilities can provide their own wrapper Application

that can decorate the call getResourceBundle()

to do some awesomeness. This would not be possible if you received it directly through ResourceBundle#getBundle()

.


There's a third approach by the way: just type it in.



In a JSF managed bean, provided <var>text</var>

:

@ManagedProperty("#{text}")
private ResourceBundle text;

      

Or in a CDI managed bean:

@Inject
private PropertyResourceBundle text;

      

With this producer:

public class BundleProducer {

    @Produces
    public PropertyResourceBundle getBundle() {
        FacesContext context = FacesContext.getCurrentInstance();
        return context.getApplication().evaluateExpressionGet(context, "#{text}", PropertyResourceBundle.class);
    }

}

      

Note: The EL rating of the package is #{text}

used under the covers Application#getResourceBundle()

.

+8


source







All Articles