## La clase ResourceBundle

#### Cómo se relaciona un ResourceBundle con una Locale

Conceptualmente hablando, un ResourceBundle es un conjunto de subclases relacionadas que comparten el mismo nombre base. La siguiente lista muestra un conjunto de subclases relacionadas. El nombre base es ButtonLabel. Los caracteres que siguen al nombre base son el código del idioma, el códido del país y el código de la variante de un Locale. Por ejemplo, ButtonLabel_en_GB corresponde con la localidad específicada por el código del idioma Inglés, (en) y el código del país para Gran Bretaña (GB).

    ButtonLabel
    ButtonLabel_de
    ButtonLabel_en_GB
    ButtonLabel_fr_CA_UNIX

Para seleccionar el ResourceBundle apropiado, se llama al método getBundle. Los siguientes ejemplo seleccionan el ButtonLabel ResourceBundle para localidad que corresponden con el idioma Francés , el país Canada y la plataforma UNIX:

    Locale currentLocale = new Locale("fr", "FR", "UNIX");

    ResourceBundle introLabels =
       ResourceBundle.getBundle("ButtonLabel", currentLocale);

Si no existe una clase ResourceBundle para la localidad especificada. getBundle trata de encontrar la correspondencia más cercarna. Por ejemplo, si no existiera una clase para ButtonLabel_fr_CA_UNIX, getBundle buscará las clases en el siguiente orden:

    ButtonLabel_fr_CA_UNIX
    ButtonLabel_fr_CA
    ButtonLabel_fr
    ButtonLabel

Si getBundle no encuentra una correspondencia en la lista anterior, intentará una búsqueda similar utilizando la localidad por defecto. Si vuelve a fallar, getBundle lanzará una MissingResourceException.

Siempre se debe proporciona una clase base sin sufijos. En el ejemplo anterior, si existiera una clase llamada ButtonLabel, getBundle no lanzaría MissingResourceException.

#### Las subclases ListResourceBundle y PropertyResourceBundle

La clase abstracta ResourceBundle tiene dos subclases: ListResourceBundle y PropertyResourceBundle. La subclase elegida depende de cómo estén localizados los datos.

Un PropertyResourceBundle está constituido por uno o más ficheros de propiedades. Se deberían almacenar objetos String traducibles en ficheros de propiedades. Cómo los ficheros de propiedades son sólo ficheros de texto y no forman parte del código fuente Java, pueden ser creados y actualizados por los traductores. No se requiere experiencia en programación. Un traductor puede añadir soporte para una localidad adicional con sólo crear un nuevo fichero de propiedades. No se necesita un nuevo fichero de clase. Los ficheros de propiedades sólo pueden contener valores para objetos String. Si necesitamos otros tipos de objetos, se debe utilizar un ListResourceBundle. Construir un ResourceBundle con Ficheros de Propiedades te muestra como utilizar PropertyResourceBundle.

La clase ListResourceBundle maneja recursos con una lista. Cada ListResourceBundle está constituido por un fichero de clase. Se puede almacenar cualquier objeto específico de la localidad en un ListResourceBundle. Para añadir soporte para nuevas localidades, se debe crear otro fichero fuente, y compilarlo. Como los traductores normalmente no son programadores, no se deberían almacenar objetos String que requieran traducción en un ListResourceBundle. Utilizar un ListResourceBundle contiene código de ejemplo que de puede resultar útil.

La clase ResourceBundle es flexible. Si primero decidimos cargar nuestros objetos Strings específicos de la localidad en un ListResourceBundle, y luego decidimos utilizar un PropertyResourceBundle, el impacto en nuestro código será limitado. Por ejemplo, la siguiente llamada a getBundle recuperará un ResourceBundle para la localidad apropiada, tanto si ButtonLabel está constituido por una clase o por un fichero de propiedades:

    ResourceBundle introLabels =
       ResourceBundle.getBundle("ButtonLabel", currentLocale);

#### Parejas Clave-Valor

Los objetos ResourceBundle contienen un array de parejas clave-valor. La clave, que debe ser un String, es lo que se especificará cuando querramos recuperar el valor desde el ResourceBundle. El valor es el objeto específico de la localidad. En el siguiente ejemplo, las claves son los objetos String "OkKey" y "CancelKey":

    class ButtonLabel_en extends ListResourceBundle {
       // English version
       public Object[][] getContents() {
         return contents;
       }
       static final Object[][] contents = {
          {"OkKey", "OK"},
          {"CancelKey", "Cancel"},
       };
    }

Para recuperar el String "OK" desde el ResourceBundle, deberíamos especificar la clave apropiada cuando llamemos a getString:

    String okLabel = ButtonLabel.getString("OkKey");

El ejemplo precedente es muy simple, porque los valores String están codificados en el código fuente. Esto no es una buena práctica, porque tus traductores necesitan trabajar con ficheros de propiedades que están separados del código fuente.

Un fichero de propiedades contiene parejas de clave-valor. La clave está en el lado izquiedo del signo igual y el valor en el lado derecho. Cada pareja está en una línea independiente. Las claves sólo pueden estar representadas por objetos String. El siguiente ejemplo muestra el contenido de un fichero de propiedades llamado ButtonLabel.properties:

    OkKey = OK
    CancelKey = Cancel

Ozito