本地化
本地化全部是关于用正确的语言获得正确的文本给用户的。
本地化在
Tapestry
中支持的很好。
Tapestry
允许你很轻松的将提供给用户的文本从应用部分分离出来。。。甚至从你的
Java
代码和你的组件模板中分离。你可以用其他的语言翻译你的信息并让
Tapestry
装配起来。
组件信息目录
每一个组件类都可以拥有自己的组件信息目录。一个组件信息目录是一组有
”.properties”
扩展名的文件。这些属性文件都是使用
java.util.ResourceBundle
的同样格式。就像这行
key=value
。这些文件与组件的
HTML
模板放在一个包里。
因此一个类名为
org.example.myapp.pages.MyPage,
你就应该有一个主要的属性文件
org/example/myapp/pages/MyPage.properties
。
如果你有一个这些值的译文,你应该提供额外的属性文件,添加一个
ISO
语言代码。这样,如果你有一法语译文,你可以创建一个
MyPage_fr.properties
文件。
在多语言特定文件里的任何值将替换来自主属性文件的值。如果你有一个甚至更多的特定资源,就像法国人说法语,你因该创建
MyPage_fr_FR.properties
文件(语言代码加上国家代码,你甚至可以添加变量。。。但这未必是你需要的,这实际上超出了习惯的语言代码)。
在目录中的信息通过
key
值被访问。当访问目录信息时
Tapestry
对
key
值不区分大小写。
信息目录的继承
如果一个组件类是另一个组件类的子类,那么它继承那个基类的信息目录。他自己的信息目录扩展和替换继承自基类的值。
这样,你可以有一个组件基类包含通用信息,并且在子类中扩展或者替换这些信息(就像你扩充或替换组件基类的方法一样)。当然这要工作在很多你愿意支持的继承层上。
应用信息目录
Tapestry 4支持一个大的应用信息目录,这在Tapestry5.05中提供了。.
<o:p>如果文件WEB-INF/AppName.properties存在于上下文内,它将被作为一个全局应用的信息目录。这个AppName源自你在web.xml文件中配置的过滤器的名字。查找这个文件区分大小写。这个属性文件可以被本地化。单独的页面和组件可以覆盖定义在这个消息目录中的值。</o:p>
本地化的组件模板
同样的查找机制应用于组件模板。
Tapestry
将在每个组件模板的版本中搜索一个本地版本然后应用最匹配的。这样你就可以用
MyPage_fr.html
给法国用户,MyPage.html给其他用户。
访问本地信息
上面讨论了创建什么样的文件和把他们放到哪里,但没涉及到如何使用这些信息。
可以有两种方式访问信息:
-
在组件模板中使用
message:
绑定前缀。
-
通过注入组件信息对象。
在第一种方案里,你可以使用
message:
绑定前缀给组件参数,或使用模板表达式。
- <t:layout title="message:page-title">
-
- ${message:greeting}, ${user.name}!
-
- . . .
- t:layout>
这里,
page-title
的信息从消息目录中萃取而来并被交给
Border
组件的
title
参数。
另外,
greeting
信息被萃取和写入响应作为模板的一部分。
“prop”
照样作为默认的绑定前缀,因此,
user.name
是一个属性路径,不是信息
key
值
你可以用一组属性文件扩展这些内容。
page-title=Your Account
greeting=Welcome back
或许,一个法国版是:
page-title=Votre Compte
greeting=Bienvenue en arriere
你可以注入你的组件信息目录在你的类中,当作一个
Message
接口的实例
- @Inject
- private Messages _messages;
随后你可以
get()
信息,或者
format()
它们。
- public String getCartSummary()
- {
- if (_items.isEmpty())
- return _messages.get("no-items");
-
- return _messages.format("item-summary", _items.size());
- }
Format()
操作使用
java.text.Formatter
工作,输出你期望的漂亮的格式。
no-items=Your shopping cart is empty.
item-summary=You have %d items in your cart.
在
Tapestry
模板中做同样简单,但有时它更容易在
Java
代码中使用
.
遗失
key
值
如果你关联了一个在信息目录中没有的
key
值,
Tapestry
不会抛出异常(那样做会让刚开始开发应用非常沮丧)。当一个
key
值不能被定位,一个
”placeholder”
信息被产生,例如
"[[missing key: key-not-found]]"
。
重载
如果你在信息目录中更改了一个属性文件,你将立刻看到改变。就像组件类和组件模板一样。
Asset(
是一些
web
应用中用到的资源,如图象,视频等
)
本地化
当注入
assets
时,注入的
asset
将被很好的本地化。查找最匹配的给当前区域制造,随后最终的
Asset
将表现出来
区域选择
每个请求的区域是从
HTTP
请求的头信息中被确定的。请求的区域反映
web
浏览器的环境或是用户在客户端进行的键盘选择。这可以很明确,例如,识别英式英语和美式英语。
Tapestry
限定请求区域,将已知的内容放到请求清单内。
Tapestry
使用配置符号
tapestry.supported-locales
去选择有效的区域给每个请求。这个值是一个逗号分隔的区域名列表。
Tapestry
在列表中查找最匹配请求区域。例如,一个
"fr_FR"
请求区域将匹配
”fr”
而不是
”de”
。如果没有找到匹配的,那么在列表里的第一个区域名字被作为有效的区域(把这个当作默认的对应无匹配)。这样最根本的提供给讲法语的,就要将
”fr”
做为区域列表里的第一个。
转换区域
Tapestry目前不支持区域转换,但不久就会支持了。决心效仿Tapestry的行为:存储一个cookie在客户端在下次访问时提供默认的区域,并且在session中存储区域名(如果session存在)。
TODO:我相信这已经被Kent实现了。