Localizing Published Web Sites

Localizing a published web site with Brightspot is similar to that for other Java-based web applications. In Brightspot’s MVVM paradigm, you need to—

  • Define resource files that contain key-value lookups for the localized labels.
  • Place the lookup and output mechanisms in the ViewModel.
  • Insert label placeholders in the Styleguide files.

This steps in this section demonstrate localizing the following short form into French.

../../../_images/localized-signup-form-en.png

Step 1: Make a Localization Resource File

A localization resource file contains the key-value pairs for localized strings. As a best practice, place all your localization files in a single directory. The directory must be under /src/main/resources/.

  1. Under /src/main/resources/i18n/, create a default resource file site.properties and enter the following text:

    first.name = First name
    last.name = Last name
    
  2. In the same directory, create a resource file site_fr.properties and enter the following text:

    first.name = Prénom
    last.name = Nom de famille
    
  3. Depending on your development or run-time environment, you may need to escape non-ASCII characters in the properties files. For example, in the previous file, we needed to change Prénom to Pr\u00e9nom using Java’s native2ascii utility.

For information about creating a properties file for localization, see Backing a ResourceBundle with Properties Files. In particular, the two letters before .properties in the file name must be a language code that Java recognizes. For a list of two-letter language codes, see Codes for the Representation of Names of Languages.

Step 2: Add Localization Property to Site

Localization is almost always done at the site level; if one page in a site appears in French, all other pages appear in French. As explained in Step 6, the ViewModel determines in which locale to display content by reading a site’s locale field. Brightspot’s Site class does not include a locale field, so you need to add it using the Modification class.

  1. Under /src/main/java/content/article/, create a file SiteModification.java and enter the following text:
package content.article;

import com.psddev.cms.db.Site;
import com.psddev.dari.db.Modification;
import java.util.Locale;

public class SiteModification extends Modification<Site> {

    SiteModification () {};

    private Locale locale;

    public Locale getLocale() {
        return locale;
    }

    public void setLocale(Locale locale) {
        this.locale = locale;
    }

}

This Model adds the locale field to the Site Model, making it visible on the Edit Site widget.

../../../_images/modified-edit-site-widget.png

For additional information about extending classes such as Site, see Modifications.

Step 3: Create a Signup Model

Create a simple Model that displays fields for first name and last name in a signup form.

  1. Under /src/main/java/content/article/, create a file Signup.java and enter the following text:
package content.article;

import com.psddev.cms.db.Content;

public class Signup extends Content {

    private String firstName;

    private String lastName;

    /* Setters and getters */
}

Step 4: Create a Template File

Localization typically involves displaying a locale-specific string for each static label on the GUI. Continuing our example, create a Handlebars file that has a placeholder for each label on the form.

  1. Under /styleguide/content/article/, create a file Signup.hbs and enter the following text:
<table>
    <tr>
        <td>{{firstNameLabel}}</td>
        <td><input type="text"/></td>
    </tr>
    <tr>
        <td>{{lastNameLabel}}</td>
        <td><input type="text"/></td>
    </tr>
</table>

Step 5: Create a Data File

Create a data file that has a placeholder for each label in the form.

  1. Under /styleguide/content/article/, create a file Signup.json and enter the following text:
{
  "_template": "Signup.hbs",
  "firstNameLabel": "{{words(1)}}",
  "lastNameLabel": "{{words(1)}}"
}

Step 6: Create a Localized ViewModel

The ViewModel includes the logic for retrieving localized strings based on the requested site’s locale.

  1. Under /src/main/java/content/article/, create a file SignupViewModel.java and enter the following text:
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
package content.article;

import com.psddev.cms.db.Site;
import com.psddev.cms.view.ViewModel;
import com.psddev.cms.view.PageEntryView;
import com.psddev.cms.view.servlet.CurrentSite;
import styleguide.content.article.SignupView;
import java.util.Locale;
import java.util.ResourceBundle;

public class SignupViewModel extends ViewModel<Signup> implements SignupView, PageEntryView  {

    @CurrentSite
    private Site site;

    @Override
    public String getFirstNameLabel() {
        ResourceBundle labels = getLabels();
        String firstNameLabel = labels.getString("first.name");
        return firstNameLabel;
    }

    @Override
    public String getLastNameLabel() {
        ResourceBundle labels = getLabels();
        String lastNameLabel = labels.getString("last.name");
        return lastNameLabel;
    }

    private ResourceBundle getLabels() {
        Locale locale = site.as(SiteModification.class).getLocale();
        ResourceBundle resourceBundle = ResourceBundle.getBundle("i18n.site",locale);
        return resourceBundle;
    }

}

In the previous snippet—

  • Lines 13–14 retrieve the requested site into a Site variable. The annotation @CurrentSite returns null for Brightspot’s global site. Therefore, when creating localized sites, ensure editors publish to a site other than global.
    • For information about creating a site which you can use for localization, see Creating Sites.
    • For information about publishing content to a site other than global, see Multi-Site and URLs.
  • Lines 16–21 return the localized string for first.name.
  • Lines 23–28 return the localized string for last.name.
  • Lines 30–34 return the resource bundle that contains the localized strings.

Running the ViewModel displays the expected result.

../../../_images/localized-signup-form-fr.png

See also: