struts2国际化

来源:互联网 发布:dnf几分钟就网络中断 编辑:程序博客网 时间:2024/05/17 09:41

1、应用基础
(国际化Internationalization-I18N,本地化Localization-L10N。)
Java程序国际化主要通过3个类完成:
 iava.util.ResourceBundle:用于加载一个资源包。
 java.util.Locale:对应一个特定的国家/区域、语言环境。
 java.util.ResourceBundle:用于将消息格式化。
2、配置资源文件

   在struts-default.xml

定义了 <interceptor name="i18n" class="com.opensymphony.xwork2.interceptor.I18nInterceptor"/>

国际化拦截器

 

 

Struts2加载全局资源文件
加载全局资源文件的方式是通过配置常量来实现的。(struts.custom.i18n.resources) ,如果需要在项目中提供国际化功能,则需要指定struts.custom.i18n.resources常量,可以在struts.properties、struts.xml和web.xml中定义

在struts.properties中定义basename

struts.custom.i18n.resources=globalMessages

 

在struts.xml中培植basename

<constant name="struts.custom.i18n.resorces" value="globalMessages"/>

 

在web.xml中定义

<init-param>

 <param-name>struts.custom.i18n.resources</param-name>

<param-value>globalMessages</param-value>

</init-param>

 
 
3、配置文件资源
为了实现国际化,必须先提供程序所需的资源文件(key-value对)。资源文件的命名可以有一下三种形式:
 baseName_language_country.properties
 baseName_language.properties
 baseName.properties
其中baseName是资源文件的基本名,用户可以自由定义。而language和country都不是可以随便定义的,必须是Java所支持的语言和国家。
若为非西欧字符集,则需要使用native2ascii转换工具转换为Unicode编码即可。


4、访问国际化资源
 JSP页面输出:<s:text name=”username” />  用name属性来加载资源文件的key值。
 Action中访问:可以使用ActionSupport类的getText方法。该方法可以接受一个name参数,既资源文件的key值。
 表单元素的Label里输出:直接用对应表单的key属性。

5、输出带占位符号的国际化信息
 JSP页面输出:在<s:text name=”username” />标签中使用多个<s:param …/>

在视图中输出支持占位符的国际化资源信息需要使用标签苦,可以在<s:text../>标签中定义多个<s:param../>子元素来分别对应<s:text../>引用的国际化资源中的占位符
 Action中访问:使用getText(String aTextName,List args)或者getText(String key,String[] args)。

带占位符的:

 username=Your Name
password1=Password
birthday=Birthday
regsuccessmsg={0},Welcome!
regfaltmsg={0},Sorry!
welcomemsg=Hello {0},Now is{1}
实例

package ;

import java.util.Date;

import com.opensymphony.xwork2.ActionSupport;

public class Reg_placeholder extends ActionSupport {
 // 定义用户名属性
 private String username;
 // 定义处理信息:注意同http中的msg不同名称
 private String mymsg;
 // 定义密码属性
 private String password1;
 // 定义确认密码
 private String password2;
 // 定义生日属性
 private Date birthday;

 public String execute() throws Exception {

  if (username != null && getPassword1().equals(getPassword2())
    && !getUsername().trim().equals("")) {
   // 获得当前日期时间
   Date now = new Date();
   // 填充占位符,并打印到控制台
   System.out.println(getText("regsuccessmsg",
     new String[] { username }));
   // 填充占位符,并打印到控制台
   System.out.println(getText("welcomemsg", new String[] { username,
     now.toString() }));
   // 获得无占位符的静态国际化资源信息
   System.out.println(getText("username") + ":" + username);
   System.out.println(getText("password1") + ":" + password1);
   System.out.println(getText("birthday") + ":" + birthday);
   return SUCCESS;
  } else {
   System.out
     .println(getText("regfaltmsg", new String[] { username }));
   return INPUT;
  }

 }

 public String getUsername() {
  return username;
 }

 public void setUsername(String username) {
  this.username = username;
 }

 public String getMymsg() {
  return mymsg;
 }

 public void setMymsg(String mymsg) {
  this.mymsg = mymsg;
 }

 public String getPassword1() {
  return password1;
 }

 public void setPassword1(String password1) {
  this.password1 = password1;
 }

 public String getPassword2() {
  return password2;
 }

 public void setPassword2(String password2) {
  this.password2 = password2;
 }

 public Date getBirthday() {
  return birthday;
 }

 public void setBirthday(Date birthday) {
  this.birthday = birthday;
 }

}

 

jsp

 

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="s" uri="/struts-tags" %>
<%@page import="java.util.Date"%>
<html>
<head>
<title>
 <s:text name="regsuccessmsg">
 <s:param><s:property  value="username" /></s:param>
 </s:text><!--使用了resuccessmsg资源文件中的key,该值存在一个占位符,所以要定义一个子元素<s:param><s:propery  value="username"/></s:param>-->
</title>
<s:head />
</head>
<body>
<table>
<% Date now=new Date(); %>
<h2>
<s:text name="welcomemsg"><!--welcomemsg在资源文件中占两个展位夫,需要定义两个子元素,分别对应{0},{1}

 

<!--初始化参数-->
<s:param><s:property  value="username" /></s:param>
<s:param><%=now%></s:param>
</s:text>
</h2>
<h2><s:text name="username"/>:<s:property  value="username" /></h2>
<h2><s:text name="password1"/>:<s:property  value="password1" /></h2>
<h2><s:text name="birthday"/>:<s:property  value="birthday" /></h2>
</table>
</body>
</html>

eg

在Action中可以调用getText(String aTextName)方法获得资源文件中的国际化信息

package ;

import java.util.Date;

import com.opensymphony.xwork2.ActionSupport;

public class Reg extends ActionSupport {

 // 定义用户名属性
 private String username;
 // 定义处理信息:注意同http中的msg不同名称
 private String mymsg;
 // 定义密码属性
 private String password1;
 // 定义确认密码
 private String password2;
 // 定义生日属性
 private Date birthday;

 public String execute() throws Exception {

  if (username != null && getPassword1().equals(getPassword2())
    && !getUsername().trim().equals("")) {
   System.out.println(getText("username") + ":" + username);
   System.out.println(getText("password1") + ":" + password1);
   System.out.println(getText("birthday") + ":" + birthday);
   return SUCCESS;
  } else {
   return INPUT;
  }

 }

 public String getUsername() {
  return username;
 }

 public void setUsername(String username) {
  this.username = username;
 }

 public String getMymsg() {
  return mymsg;
 }

 public void setMymsg(String mymsg) {
  this.mymsg = mymsg;
 }

 public String getPassword1() {
  return password1;
 }

 public void setPassword1(String password1) {
  this.password1 = password1;
 }

 public String getPassword2() {
  return password2;
 }

 public void setPassword2(String password2) {
  this.password2 = password2;
 }

 public Date getBirthday() {
  return birthday;
 }

 public void setBirthday(Date birthday) {
  this.birthday = birthday;
 }

}

 

包范围资源文件

在包的根路径下建立多个文件名位package_language_country.properties资源文件,该包所有的action都可以访问。package不是指配置文件中定义的包而是固定的名称package

username=Package Message:Your Name
password1=Package Message:Password
birthday=Package Message:Birthday
regsuccessmsg=Package Message:{0},Welcome!
regfaltmsg=Package Message:{0},Sorry!
welcomemsg=Package Message:Hello {0},Now is{1}

 

 

 

Action范围资源文件

单独为某个Action指定的国际化资源,方法:在Action类所在目录下,建立一个命名规范位ActionName_language_country.properties的资源文件。

#Action Zone
username=Action Message:Your Name
password1=Action Message:Password
password2=Action Message:Password
birthday=Action Message:Birthday

 

 

临时资源文件

在jsp中指定国际化资源的位置,需要使用<s:i18n.../>指定访问国际化资源文件的basename名称。如果<s:form.../>为<s:i18n../>的子标签,那么该<s:form.../>中的国际化信息都来自<s:i18n.../>标签所指定的临时资源文件。

 

#Temp
regpage=Temp Reg Page
username=Temp Message:Your Name
password1=Temp Message:Password
password2=Temp Message:confirm Password
birthday=Temp Message:Birthday

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="s" uri="/struts-tags" %>
<html>
<head>
<s:i18n name="ch4.temp"><!--制定临时资源文件,即在ch4包内
<title><s:text name="regpage"/></title>
</s:i18n>
<s:head />
</head>
<body>
<table>
<s:i18n name="ch4.temp">
<s:form id="id" action="Reg">
    <s:textfield name="username" key="username"/>
    <s:password name="password1" key="password1"/>
    <s:password name="password2" key="password2"/>
    <s:datetimepicker name="birthday" key="birthday" />
    <s:submit key="regbutton"/>
</s:form>
</s:i18n>
</table>
</body>
</html>

这样可以在一个jsp中使用多个资源文件来显示国际化信息。

 

加在资源文件的顺序:

业务控制器Action加载资源文件顺序

现假设有A_Action,该Action有父类B_Action,并实现接口B_Interface

public class A_Action extends B_Action implements B_Interface{

}

 

1:优先家在Action范围的,即在A_Action所在目录

2:如果在A_Action所在目录没有找到相应的key则找B_Ation的Action范围资源文件即在B_Action所在目录

 

3:如果在B_Action所在目录没有找到相应的key,则找B_Interface类的Action的,即在B_Interface所在目录

 

4:如果在B_Interface所在目录没有找到相应的key且A_Action中实现了接口ModelDriven即使用了模型驱动模式,则对于getModel()方法返回的model对象,重新按照步骤1步骤搜索。

5:如果找不到action,则搜索当前包目录下basename位package的系列文件

6:当前包找不到,就沿着当前包上溯,直到顶层包来查找basename位package的包范围

7:如包找不到,就找全局即struts.custom.i18n.resources

8:如果按上顺序还找不到,就直接输出key的字符串值

 

 jsp加载资源文件 使用<s:i18n..../>

 

动态访问国际化资源文件

eg:

建立两个国际资源文件,globalMessage_en_US.properties

dynameic.username=user name

dynameic.password1=Password

 

globaMessage_zh_CN.properties

dynameic.username=用户名

dynameic.password1=密码

 

在struts.properties文件中加入一行

struts.custom.i18n.resources=globaMessages

 

dynamic使用与Action范围资源文件或者包资源文件定义中不同的key直。

再action,在action中配置一个动态显示得jsp

<action name="DynamicAction" class="Dynamic.DynamicAction">
   <result name="success">/Dynamic/dynamic_reg.jsp
   </result>
  </action>

 

action

import com.opensymphony.xwork2.ActionSupport;

public class DynamicAction extends ActionSupport {
 // 只返回一个SUCCESS
 public String execute() throws Exception {

  return SUCCESS;
 }

}

jsp

 

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="s" uri="/struts-tags" %>
<html>
<head>
<title><s:text name="dynamic.title"/></title>
<s:head />
</head>
<body>
<table>
<s:form id="id" action="Reg">
    <s:textfield name="username" key="dynamic.username"/>
    <s:password name="password1" key="dynamic.password1"/>
    <s:password name="password2" key="dynamic.password2"/>
    <s:datetimepicker name="birthday" key="dynamic.birthday" />
    <s:submit key="dynamic.regbutton"/>
</s:form>
<ul>
           <s:url id="url" action="DynamicAction">
            <s:param name="request_locale">en_US</s:param>
        </s:url>
        <s:a href="%{url}">English</s:a>
            <s:url id="url" action="DynamicAction">
            <s:param name="request_locale">zh_CN</s:param>
        </s:url>
        <s:a href="%{url}">Chinese</s:a>
   </ul>

</table>
</body>
</html>

 

 

原创粉丝点击