Class ResourceBundleMessageSource

  • All Implemented Interfaces:
    Aware, ClassLoaderAware, HierarchicalMessageSource, MessageSource

    public class ResourceBundleMessageSource
    extends AbstractMessageSource
    implements ClassLoaderAware

    (This class is a member of the Spring Framework.)

    MessageSource implementation that accesses resource bundles using specified basenames. This class relies on the underlying JDK's ResourceBundle implementation, in combination with the JDK's standard message parsing provided by MessageFormat.

    This MessageSource caches both the accessed ResourceBundle instances and the generated MessageFormats for each message. It also implements rendering of no-arg messages without MessageFormat, as supported by the AbstractMessageSource base class. The caching provided by this MessageSource is significantly faster than the built-in caching of the java.util.ResourceBundle class.

    Unfortunately, java.util.ResourceBundle caches loaded bundles forever: Reloading a bundle during VM execution is not possible. As this MessageSource relies on ResourceBundle, it faces the same limitation.

    Created: 2016. 2. 8.

    • Method Summary

      All Methods Instance Methods Concrete Methods 
      Modifier and Type Method Description
      protected java.util.ResourceBundle doGetBundle​(java.lang.String basename, java.util.Locale locale)
      Obtain the resource bundle for the given basename and Locale.
      java.lang.ClassLoader getClassLoader()  
      protected java.text.MessageFormat getMessageFormat​(java.util.ResourceBundle bundle, java.lang.String code, java.util.Locale locale)
      Return a MessageFormat for the given bundle and code, fetching already generated MessageFormats from the cache.
      protected java.util.ResourceBundle getResourceBundle​(java.lang.String basename, java.util.Locale locale)
      Return a ResourceBundle for the given basename and code, fetching already generated MessageFormats from the cache.
      protected java.lang.String getStringOrNull​(java.util.ResourceBundle bundle, java.lang.String key)
      Efficiently retrieve the String value for the specified key, or return null if not found.
      protected java.util.ResourceBundle loadBundle​(java.io.InputStream inputStream)
      Load a property-based resource bundle from the given input stream, picking up the default properties encoding on JDK 9+.
      protected java.util.ResourceBundle loadBundle​(java.io.Reader reader)
      Load a property-based resource bundle from the given reader.
      protected java.text.MessageFormat resolveCode​(java.lang.String code, java.util.Locale locale)
      Resolves the given message code as key in the registered resource bundles, using a cached MessageFormat instance per message code.
      protected java.lang.String resolveCodeWithoutArguments​(java.lang.String code, java.util.Locale locale)
      Resolves the given message code as key in the registered resource bundles, returning the value found in the bundle as-is (without MessageFormat parsing).
      void setBasename​(java.lang.String basename)
      Set a single basename, following ResourceBundle conventions: essentially, a fully-qualified classpath location.
      void setBasenames​(java.lang.String... basenames)
      Set an array of basenames, each following ResourceBundle conventions: essentially, a fully-qualified classpath location.
      void setCacheSeconds​(int cacheSeconds)
      Set the number of seconds to cache loaded resource bundle files.
      void setClassLoader​(java.lang.ClassLoader classLoader)
      Specify the ClassLoader to provide.
      void setDefaultEncoding​(java.lang.String defaultEncoding)
      Set the default charset to use for parsing resource bundle files.
      void setFallbackToSystemLocale​(boolean fallbackToSystemLocale)
      Set whether to fall back to the system Locale if no files for a specific Locale have been found.
      java.lang.String toString()  
      • Methods inherited from class java.lang.Object

        clone, equals, finalize, getClass, hashCode, notify, notifyAll, wait, wait, wait
    • Constructor Detail

      • ResourceBundleMessageSource

        public ResourceBundleMessageSource()
    • Method Detail

      • setDefaultEncoding

        public void setDefaultEncoding​(java.lang.String defaultEncoding)
        Set the default charset to use for parsing resource bundle files.

        Default is the java.util.ResourceBundle default encoding: ISO-8859-1.

        Parameters:
        defaultEncoding - the default encoding
      • setFallbackToSystemLocale

        public void setFallbackToSystemLocale​(boolean fallbackToSystemLocale)
        Set whether to fall back to the system Locale if no files for a specific Locale have been found. Default is "true"; if this is turned off, the only fallback will be the default file (e.g. "messages.properties" for basename "messages").

        Falling back to the system Locale is the default behavior of java.util.ResourceBundle. However, this is often not desirable in an application server environment, where the system Locale is not relevant to the application at all: Set this flag to "false" in such a scenario.

        Parameters:
        fallbackToSystemLocale - whether fallback to system locale
      • setCacheSeconds

        public void setCacheSeconds​(int cacheSeconds)
        Set the number of seconds to cache loaded resource bundle files.
        • Default is "-1", indicating to cache forever.
        • A positive number will expire resource bundles after the given number of seconds. This is essentially the interval between refresh checks. Note that a refresh attempt will first check the last-modified timestamp of the file before actually reloading it; so if files don't change, this interval can be set rather low, as refresh attempts will not actually reload.
        • A value of "0" will check the last-modified timestamp of the file on every message access. Do not use this in a production environment!
        • Note that depending on your ClassLoader, expiration might not work reliably since the ClassLoader may hold on to a cached version of the bundle file.
        Parameters:
        cacheSeconds - the cache seconds
      • getClassLoader

        public java.lang.ClassLoader getClassLoader()
      • setClassLoader

        public void setClassLoader​(java.lang.ClassLoader classLoader)
        Description copied from interface: ClassLoaderAware
        Specify the ClassLoader to provide. The ClassLoader can be set when the object is created, and allows the creator to provide the appropriate class loader to be used by the object when when loading classes and resources.
        Specified by:
        setClassLoader in interface ClassLoaderAware
        Parameters:
        classLoader - the ClassLoader to provide
      • setBasename

        public void setBasename​(java.lang.String basename)
        Set a single basename, following ResourceBundle conventions: essentially, a fully-qualified classpath location. If it doesn't contain a package qualifier (such as org.mypackage), it will be resolved from the classpath root.

        Messages will normally be held in the "/lib" or "/classes" directory of a web application's WAR structure. They can also be held in jar files on the class path.

        Note that ResourceBundle names are effectively classpath locations: As a consequence, the JDK's standard ResourceBundle treats dots as package separators. This means that "test.theme" is effectively equivalent to "test/theme", just like it is for programmatic java.util.ResourceBundle usage.

        Parameters:
        basename - the basename
        See Also:
        #setBasenames, java.util.ResourceBundle#getBundle(String)
      • setBasenames

        public void setBasenames​(java.lang.String... basenames)
        Set an array of basenames, each following ResourceBundle conventions: essentially, a fully-qualified classpath location. If it doesn't contain a package qualifier (such as org.mypackage), it will be resolved from the classpath root.

        The associated resource bundles will be checked sequentially when resolving a message code. Note that message definitions in a previous resource bundle will override ones in a later bundle, due to the sequential lookup.

        Note that ResourceBundle names are effectively classpath locations: As a consequence, the JDK's standard ResourceBundle treats dots as package separators. This means that "test.theme" is effectively equivalent to "test/theme", just like it is for programmatic java.util.ResourceBundle usage.

        Parameters:
        basenames - the basenames
        See Also:
        #setBasename, java.util.ResourceBundle#getBundle(String)
      • resolveCodeWithoutArguments

        protected java.lang.String resolveCodeWithoutArguments​(java.lang.String code,
                                                               java.util.Locale locale)
        Resolves the given message code as key in the registered resource bundles, returning the value found in the bundle as-is (without MessageFormat parsing).
        Overrides:
        resolveCodeWithoutArguments in class AbstractMessageSource
        Parameters:
        code - the code of the message to resolve
        locale - the Locale to resolve the code for (subclasses are encouraged to support internationalization)
        Returns:
        the message String, or null if not found
        See Also:
        #resolveCode, MessageFormat
      • resolveCode

        protected java.text.MessageFormat resolveCode​(java.lang.String code,
                                                      java.util.Locale locale)
        Resolves the given message code as key in the registered resource bundles, using a cached MessageFormat instance per message code.
        Specified by:
        resolveCode in class AbstractMessageSource
        Parameters:
        code - the code of the message to resolve
        locale - the Locale to resolve the code for (subclasses are encouraged to support internationalization)
        Returns:
        the MessageFormat for the message, or null if not found
        See Also:
        #resolveCodeWithoutArguments(String, java.util.Locale)
      • getResourceBundle

        protected java.util.ResourceBundle getResourceBundle​(java.lang.String basename,
                                                             java.util.Locale locale)
        Return a ResourceBundle for the given basename and code, fetching already generated MessageFormats from the cache.
        Parameters:
        basename - the basename of the ResourceBundle
        locale - the Locale to find the ResourceBundle for
        Returns:
        the resulting ResourceBundle, or null if none found for the given basename and Locale
      • doGetBundle

        protected java.util.ResourceBundle doGetBundle​(java.lang.String basename,
                                                       java.util.Locale locale)
                                                throws java.util.MissingResourceException
        Obtain the resource bundle for the given basename and Locale.
        Parameters:
        basename - the basename to look for
        locale - the Locale to look for
        Returns:
        the corresponding ResourceBundle
        Throws:
        java.util.MissingResourceException - if no matching bundle could be found
        See Also:
        java.util.ResourceBundle#getBundle(String, Locale, ClassLoader)
      • loadBundle

        protected java.util.ResourceBundle loadBundle​(java.io.Reader reader)
                                               throws java.io.IOException
        Load a property-based resource bundle from the given reader.

        The default implementation returns a PropertyResourceBundle.

        Parameters:
        reader - the reader for the target resource
        Returns:
        the fully loaded bundle
        Throws:
        java.io.IOException - in case of I/O failure
        See Also:
        PropertyResourceBundle#PropertyResourceBundle(Reader)
      • loadBundle

        protected java.util.ResourceBundle loadBundle​(java.io.InputStream inputStream)
                                               throws java.io.IOException
        Load a property-based resource bundle from the given input stream, picking up the default properties encoding on JDK 9+.

        This will only be called with "defaultEncoding" set to null, explicitly enforcing the platform default encoding (which is UTF-8 with a ISO-8859-1 fallback on JDK 9+ but configurable through the "java.util.PropertyResourceBundle.encoding" system property). Note that this method can only be called with a ResourceBundle.Control: When running on the JDK 9+ module path where such control handles are not supported, any overrides in custom subclasses will effectively get ignored.

        The default implementation returns a PropertyResourceBundle.

        Parameters:
        inputStream - the input stream for the target resource
        Returns:
        the fully loaded bundle
        Throws:
        java.io.IOException - in case of I/O failure
        See Also:
        loadBundle(Reader), PropertyResourceBundle(InputStream)
      • getMessageFormat

        protected java.text.MessageFormat getMessageFormat​(java.util.ResourceBundle bundle,
                                                           java.lang.String code,
                                                           java.util.Locale locale)
                                                    throws java.util.MissingResourceException
        Return a MessageFormat for the given bundle and code, fetching already generated MessageFormats from the cache.
        Parameters:
        bundle - the ResourceBundle to work on
        code - the message code to retrieve
        locale - the Locale to use to build the MessageFormat
        Returns:
        the resulting MessageFormat, or null if no message defined for the given code
        Throws:
        java.util.MissingResourceException - if thrown by the ResourceBundle
      • getStringOrNull

        protected java.lang.String getStringOrNull​(java.util.ResourceBundle bundle,
                                                   java.lang.String key)
        Efficiently retrieve the String value for the specified key, or return null if not found.
        Parameters:
        bundle - the ResourceBundle to perform the lookup in
        key - the key to look up
        Returns:
        the associated value, or null if none
        See Also:
        ResourceBundle#getString(String), ResourceBundle#containsKey(String)
      • toString

        public java.lang.String toString()
        Overrides:
        toString in class java.lang.Object