JSP / Servlet中的多语言支持

时间:2022-03-22 15:21:00

How to provide multi language support through JSP/Servlet? How to include static data of different languages at run time on basis of language selected?

如何通过JSP / Servlet提供多语言支持?如何根据所选语言在运行时包含不同语言的静态数据?

3 个解决方案

#1


10  

In a "plain vanilla" JSP/Servlet application, the best solution is the JSTL fmt taglib. (just drop jstl-1.2.jar in /WEB-INF/lib) How to use it is covered in Oracle Java EE 5 tutorial part II chapter 7 and in this answer: How to internationalize a Java web application?.

在“普通的vanilla”JSP / Servlet应用程序中,最好的解决方案是JSTL fmt taglib。 (只需删除/ WEB-INF / lib中的jstl-1.2.jar)Oracle Java EE 5教程第二部分第7章和本答案中介绍了如何使用它:如何使Java Web应用程序国际化?

If you're using a MVC framework such as Oracle JSF or Apache Struts, then you need to consult its specific documentation using keywords "internationalization" (i18n) or "localization" (l10n). In most cases they also provides specific tags for that, such as <f:loadBundle> in case of JSF, which in turn is covered in Oracle Java EE 5 tutorial part II chapter 15.

如果您正在使用诸如Oracle JSF或Apache Struts之类的MVC框架,那么您需要使用关键字“国际化”(i18n)或“本地化”(l10n)来查阅其特定文档。在大多数情况下,它们还为此提供了特定的标记,例如JSF中的 ,后者又在Oracle Java EE 5教程第二部分第15章中介绍。

Those i18n tags already checks the default language/locale by ServletRequest#getLocale() (you don't need to do it "low-level" by checking the header as one suggested before --which would involve more work parsing the header as per the HTTP spec). You can let the user choose the language itself (dropdown?) and store it in the session scope and instruct those taglibs to use it. Here's an example with JSTL fmt taglib:

那些i18n标签已经通过ServletRequest#getLocale()检查默认语言/语言环境(你不需要通过检查标题之前的“低级别”来执行它 - 这将涉及更多工作解析标头按照HTTP规范)。您可以让用户选择语言本身(下拉列表?)并将其存储在会话范围中,并指示这些标记库使用它。以下是JSTL fmt taglib的示例:

<fmt:setLocale value="${someSessionBean.locale}" />

..where ${someSessionBean.locale} can return en, en_US, en_UK, etc. Those are in turn used by the java.util.ResourceBundle API to load the localized text (you don't need to create/load the ResourceBundle itself, the taglibs already do that, just read the linked javadoc to learn a bit more about how it works).

..where $ {someSessionBean.locale}可以返回en,en_US,en_UK等。这些由java.util.ResourceBundle API反过来用于加载本地化文本(您不需要创建/加载ResourceBundle本身,taglibs已经这样做了,只需阅读链接的javadoc以了解它的工作原理。

If you want the language available as first pathinfo part of URL (such as http://example.com/en/, which is best for SEO), then you can best use a Filter for this which listens on /*, checks the pathinfo, splits the language part from it, stores/compares it as/with session value and forwards the request without language part in pathinfo further to the desired front controller.

如果您希望语言可用作URL的第一个pathinfo部分(例如http://example.com/en/,最适合SEO),那么您最好使用一个过滤器来监听/ *,检查pathinfo,从中分离语言部分,将其作为/存储/与会话值进行比较,并将请求中没有语言部分的请求转发到所需的前端控制器。

#2


-1  

There are several important aspects to this issue. The first part is determining each request's locale. You can use something like this:

这个问题有几个重要方面。第一部分是确定每个请求的语言环境。你可以使用这样的东西:

HttpServletRequest req ...;
String browserLocale = req.getHeader("Accept-Language"); // typically something like 'en'

Next, you need to decide how to manage the site's localized content. The most Java-like (not necessarily the best) approach is to externalize all messages using a ResourceBundle. You can learn about the core Java facilities for I18N, G13N in their Isolating Locale Specific Data tutorial.

接下来,您需要决定如何管理网站的本地化内容。最类似Java(不一定是最好的)方法是使用ResourceBundle外部化所有消息。您可以在他们的Isolating Locale Specific Data教程中了解I18N,G13N的核心Java工具。

Using only this approach is quite poor in my opinion. Different languages' content size differently, match better with different layouts, etc. So you can completely eliminate resource bundles (if you don't have a lot of multi-locale data) or augment the approach by using XSLT or other templating that is locale specific.

在我看来,仅使用这种方法是非常差的。不同语言的内容大小不同,可以更好地匹配不同的布局等。因此,您可以完全消除资源包(如果您没有大量的多语言环境数据)或通过使用XSLT或其他模板语言来扩充方法具体。

One very performant but high-development overhead approach is to use a servlet filter to redirect traffic to language- (or locale-) specific subsites. In this case, anyone hitting http://my.domain.fake/xyz would get redirected to http://my.domain.fake/en/xyz

一种非常高性能但高开发的开销方法是使用servlet过滤器将流量重定向到语言(或语言环境)特定子站点。在这种情况下,任何点击http://my.domain.fake/xyz的人都会被重定向到http://my.domain.fake/en/xyz

Finally, it is worth noting that most of the serious web frameworks have their own I18N support. Their approaches differ based on the framework philosophy.

最后,值得注意的是,大多数严肃的Web框架都有自己的I18N支持。他们的方法因框架哲学而异。

#3


-1  

We can to create messages.properties, messages_????.properties and to place this files into /scr/java directory. (where ???? - en_US, ru_RU and other)

我们可以创建messages.properties,messages _ ????。属性并将这些文件放入/ scr / java目录。 (其中???? - en_US,ru_RU等)

Example lines into messages.properties:

示例行到messages.properties:

About = About
Buy = Buy
Company = Company
ContactUs = Contact Us 

Then to paste into jsp file for example lines:

然后粘贴到jsp文件中,例如行:

   Locale locale = Locale.getDefault(); 
   String lng = locale.getCountry(); 

   session.setAttribute( "language", lng);

   if (lng.equals( "UA"))
       locale = new Locale( "uk", "UA");
   else if (lng.equals( "RU"))
       locale = new Locale( "ru", "RU");
   else
       locale = Locale.US;

   ResourceBundle boundle = ResourceBundle.getBundle( "messages", locale);

   for (Enumeration e = boundle.getKeys(); e.hasMoreElements(); ) {
       String key = (String) e.nextElement();
       String s = boundle.getString(key);
       session.setAttribute( key, s);
   }

Now you can paste ${name} into next jsp code (${About}, ${Buy}, ...).

现在,您可以将$ {name}粘贴到下一个jsp代码中($ {About},$ {Buy},...)。

#1


10  

In a "plain vanilla" JSP/Servlet application, the best solution is the JSTL fmt taglib. (just drop jstl-1.2.jar in /WEB-INF/lib) How to use it is covered in Oracle Java EE 5 tutorial part II chapter 7 and in this answer: How to internationalize a Java web application?.

在“普通的vanilla”JSP / Servlet应用程序中,最好的解决方案是JSTL fmt taglib。 (只需删除/ WEB-INF / lib中的jstl-1.2.jar)Oracle Java EE 5教程第二部分第7章和本答案中介绍了如何使用它:如何使Java Web应用程序国际化?

If you're using a MVC framework such as Oracle JSF or Apache Struts, then you need to consult its specific documentation using keywords "internationalization" (i18n) or "localization" (l10n). In most cases they also provides specific tags for that, such as <f:loadBundle> in case of JSF, which in turn is covered in Oracle Java EE 5 tutorial part II chapter 15.

如果您正在使用诸如Oracle JSF或Apache Struts之类的MVC框架,那么您需要使用关键字“国际化”(i18n)或“本地化”(l10n)来查阅其特定文档。在大多数情况下,它们还为此提供了特定的标记,例如JSF中的 ,后者又在Oracle Java EE 5教程第二部分第15章中介绍。

Those i18n tags already checks the default language/locale by ServletRequest#getLocale() (you don't need to do it "low-level" by checking the header as one suggested before --which would involve more work parsing the header as per the HTTP spec). You can let the user choose the language itself (dropdown?) and store it in the session scope and instruct those taglibs to use it. Here's an example with JSTL fmt taglib:

那些i18n标签已经通过ServletRequest#getLocale()检查默认语言/语言环境(你不需要通过检查标题之前的“低级别”来执行它 - 这将涉及更多工作解析标头按照HTTP规范)。您可以让用户选择语言本身(下拉列表?)并将其存储在会话范围中,并指示这些标记库使用它。以下是JSTL fmt taglib的示例:

<fmt:setLocale value="${someSessionBean.locale}" />

..where ${someSessionBean.locale} can return en, en_US, en_UK, etc. Those are in turn used by the java.util.ResourceBundle API to load the localized text (you don't need to create/load the ResourceBundle itself, the taglibs already do that, just read the linked javadoc to learn a bit more about how it works).

..where $ {someSessionBean.locale}可以返回en,en_US,en_UK等。这些由java.util.ResourceBundle API反过来用于加载本地化文本(您不需要创建/加载ResourceBundle本身,taglibs已经这样做了,只需阅读链接的javadoc以了解它的工作原理。

If you want the language available as first pathinfo part of URL (such as http://example.com/en/, which is best for SEO), then you can best use a Filter for this which listens on /*, checks the pathinfo, splits the language part from it, stores/compares it as/with session value and forwards the request without language part in pathinfo further to the desired front controller.

如果您希望语言可用作URL的第一个pathinfo部分(例如http://example.com/en/,最适合SEO),那么您最好使用一个过滤器来监听/ *,检查pathinfo,从中分离语言部分,将其作为/存储/与会话值进行比较,并将请求中没有语言部分的请求转发到所需的前端控制器。

#2


-1  

There are several important aspects to this issue. The first part is determining each request's locale. You can use something like this:

这个问题有几个重要方面。第一部分是确定每个请求的语言环境。你可以使用这样的东西:

HttpServletRequest req ...;
String browserLocale = req.getHeader("Accept-Language"); // typically something like 'en'

Next, you need to decide how to manage the site's localized content. The most Java-like (not necessarily the best) approach is to externalize all messages using a ResourceBundle. You can learn about the core Java facilities for I18N, G13N in their Isolating Locale Specific Data tutorial.

接下来,您需要决定如何管理网站的本地化内容。最类似Java(不一定是最好的)方法是使用ResourceBundle外部化所有消息。您可以在他们的Isolating Locale Specific Data教程中了解I18N,G13N的核心Java工具。

Using only this approach is quite poor in my opinion. Different languages' content size differently, match better with different layouts, etc. So you can completely eliminate resource bundles (if you don't have a lot of multi-locale data) or augment the approach by using XSLT or other templating that is locale specific.

在我看来,仅使用这种方法是非常差的。不同语言的内容大小不同,可以更好地匹配不同的布局等。因此,您可以完全消除资源包(如果您没有大量的多语言环境数据)或通过使用XSLT或其他模板语言来扩充方法具体。

One very performant but high-development overhead approach is to use a servlet filter to redirect traffic to language- (or locale-) specific subsites. In this case, anyone hitting http://my.domain.fake/xyz would get redirected to http://my.domain.fake/en/xyz

一种非常高性能但高开发的开销方法是使用servlet过滤器将流量重定向到语言(或语言环境)特定子站点。在这种情况下,任何点击http://my.domain.fake/xyz的人都会被重定向到http://my.domain.fake/en/xyz

Finally, it is worth noting that most of the serious web frameworks have their own I18N support. Their approaches differ based on the framework philosophy.

最后,值得注意的是,大多数严肃的Web框架都有自己的I18N支持。他们的方法因框架哲学而异。

#3


-1  

We can to create messages.properties, messages_????.properties and to place this files into /scr/java directory. (where ???? - en_US, ru_RU and other)

我们可以创建messages.properties,messages _ ????。属性并将这些文件放入/ scr / java目录。 (其中???? - en_US,ru_RU等)

Example lines into messages.properties:

示例行到messages.properties:

About = About
Buy = Buy
Company = Company
ContactUs = Contact Us 

Then to paste into jsp file for example lines:

然后粘贴到jsp文件中,例如行:

   Locale locale = Locale.getDefault(); 
   String lng = locale.getCountry(); 

   session.setAttribute( "language", lng);

   if (lng.equals( "UA"))
       locale = new Locale( "uk", "UA");
   else if (lng.equals( "RU"))
       locale = new Locale( "ru", "RU");
   else
       locale = Locale.US;

   ResourceBundle boundle = ResourceBundle.getBundle( "messages", locale);

   for (Enumeration e = boundle.getKeys(); e.hasMoreElements(); ) {
       String key = (String) e.nextElement();
       String s = boundle.getString(key);
       session.setAttribute( key, s);
   }

Now you can paste ${name} into next jsp code (${About}, ${Buy}, ...).

现在,您可以将$ {name}粘贴到下一个jsp代码中($ {About},$ {Buy},...)。