Wednesday, December 21, 2011

How to use multi language translation in JSP in CQ / WEM

Use Case: You want to display certain text in page based on page language

Prerequisite: http://sling.apache.org/site/internationalization-support-i18n.html

Solution: You can use i18n bundle approach for this

Suppose you want to display certain text for a component in different language based on page language or URL. Take an example of /apps/geometrixx/components/homepage component.

1) Create a i18n node under /apps/geometrixx/components/homepage of type sling:Folder
2) create a node of type sling:Folder under i18n of mixin type mix:language
3) Add a property called jcr:language and assign value of lang code or lang_COUNTRY

Structure would be like

/apps/myApp
+-- English (nt:folder, mix:language)
| +-- jcr:language = en
| +-- mx (sling:messageEntry)
| +-- sling:key = "msgXXX"
| +-- slign:message = "An Application Text"
+-- Deutsch (nt:folder, mix:language)
+-- jcr:language = de
+-- mx (sling:messageEntry)
+-- sling:key = "msgXXX"
+-- slign:message = "Ein Anwendungstext"



4) Then on jsp page use following code

<cq:setContentBundle/>
<%
Locale pageLocale = currentPage.getLanguage(false);
//If above bool is set to true. CQ looks in to page path rather than jcr:language property.
ResourceBundle resourceBundle = slingRequest.getResourceBundle(pageLocale);
I18n i18n = new I18n(resourceBundle);
%>
I am printing using I18n <%=i18n.get("updateLocations") %>
I am printing using fmt:message now <fmt:message key="updateLocations"/>
I found page locale is <%=pageLocale.toString() %>

You can also test language using grid under http://localhost:4502/libs/cq/i18n/translator.html
More Info: http://labs.sixdimensions.com/blog/dklco/2012-05-25/adobe-cq5-translator

To change what languages are shown in the translator's grid, create a multi-value string property /etc/languages/languages (node structure must be created), containing the iso language codes (e.g. ["de", "fr", …]). The default is hard coded in the translator and maps the ootb CQ languages: ['de', 'fr', 'it', 'es', 'ja', 'zh-cn']


Some More Good blog Post on this:

http://blogs.adobe.com/dekesmith/2012/10/21/internationalization-within-sling-and-cq



10 comments:

  1. Hi Yogesh,

    thanks for this article. Could you please be more specific what needs to be done so I can see a different language in the cq translator? I tried to do the structure, but with no result, still have the hardcoded list.
    Thanks

    Jan

    ReplyDelete
    Replies
    1. @Jan,

      Done. http://www.wemblog.com/2012/06/how-to-add-new-supported-language-in-cq.html

      Yogesh

      Delete
  2. Thanks - this was really useful

    Another point to note is that you may want to have separate bundles for different applications.

    To do this, place a property "sling:basename" under myApps/i18n/en of a value (e.g. "TEST")

    Then reference either by


    or

    slingRequest.getResourceBundle("TEST", pageLocale);

    depending on the message you are using to access the bundle

    I'll write a blog post about this shortly

    ReplyDelete
    Replies
    1. Tim,

      Thanks for your feedback. For some reason I don't see [sling:Language] as registered mixin node type in CQ5.5 or in CQ5.6

      [sling:Language]
      mixin
      - sling:basename (string)
      - sling:basename (string) multiple

      Have you used this feature in CQ ?

      Yogesh

      Delete
  3. Hi Yogesh,

    Thanks for the info you have provided. I have a question on using the below line of code.

    <%=i18n.get("updateLocations") %>

    It works if I use pass String literal to i18n.get() method but doesn't work when I pass object reference. Do you have any idea why?

    String gtBodyText = "Name";
    <%=i18n.get(gtBodyText) %>

    Thanks,
    Stephen

    ReplyDelete
    Replies
    1. Stephen,

      That could be bug. Can you please work with daycare on this ?

      Yogesh

      Delete
  4. I have a component and try to print this fmt:message key="firstname"

    It works well for en,fr,de but not for en_UK and en_US.

    Is it needed to select the language for the parent path in page properties

    Ex: content/geometrixx/en/test.html - works fine
    content/geometrixx/en_UK/test.html - the key is returned as value and it is printed.

    ReplyDelete
    Replies
    1. I'm having the dame issue. How did you fix ir?

      Delete
    2. Have you tried Locale pageLocale = currentPage.getLanguage(false) ?

      Delete
  5. It is genuinely very useful for me.

    ReplyDelete