18.struts2_2国际化 和 拦截器

国际化

介绍:

1、 国际化原理 ? 什么是国际化 ? 
同一款软件 可以为不同用户,提供不同语言界面  ---- 国际化软件
需要一个语言资源包(很多properties文件,每个properties文件 针对一个国家或者语言 ,
通过java程序根据来访者国家语言,自动读取不同properties文件 )

2、 资源包编写 
    properties文件命名 :  基本名称_语言(小写)_国家(大写).properties
例如 :
    messages_zh_CN.properties 中国中文
    messages_en_US.properties 美国英文
3、 ResourceBundle 根据不同Locale(地域信息),读取不同国家 properties文件
ResourceBundle bundle = ResourceBundle.getBundle("messages", Locale.US);

----------------------------

集体实现:

1. 国际化的定义
    1. 全局
        在struts.xml 中声明 一个常量(struts.custom.i18n.resources=testmessages,testmessages2)

        <constant name="struts.custom.i18n.resources" value="message"></constant>

        value 的值:
                    src下:message 
                    其他包下:com.uu.action.message

    2. 局部

        1. 针对与action
            位置:与action类在同一个包下
            名称:ActionClassName.properties
            注意:这个配置文件只对当前action 有效

        2. 针对package下所有action
            位置:在指定的包下
            名称:package.properties

        3. jsp页面临时使用某个properties配置文件
            1. 引入:  
                    <%@taglib prefix="s" uri="/struts-tags" %>
            2. 使用:
                    <s:i18n name="message">
                        <s:text name="username"/>
                    </s:i18n>
                注意: 如果配置文件不是在 src 根目录下
                    需要写全路径

2. 国际化的使用

        1. 在action类中的使用

            前提: 当前action 继承ActionSupport
            使用: this.getText("username");  获取配置文件中的内容

        2. 在validation 
            <field name="username">
                <field-validator type="requiredstring">
                    <message key="nameerror"></message>
                </field-validator>
            </field>

        3. 在jsp页面上使用

            <s:text name="名称"> 如果没有使用
            s:i18n name="">来指定,会从全局配置文件中获取。

3. 配置文件中使用动态文本

        1. action 中怎样使用
            配置文件:   msg=hello world { 0}
            action中:    this.getText("username", new String[] { "你好啊,兄弟" }

        2. jsp 页面上怎样使用
            配置文件:同上
            <s:i18n name="com.uu.action.package">
                <s:text name="username">
                    <s:param> ,天不错,来  嘿嘿嘿</s:param>
                </s:text>
            </s:i18n>

拦截器

介绍:

struts2拦截器使用的是AOP思想。
AOP的底层实现就是动态代理。(Proxy)

拦截器 采用 责任链 模式 
    *  在责任链模式里,很多对象由每一个对象对其下家的引用而连接起来形成一条链。
    *  责任链每一个节点,都可以继续调用下一个节点,也可以阻止流程继续执行

struts2中在struts-default.xml文件中声明了所有的拦截器。
而struts2框架默认使用的是defaultStack这个拦截器栈。
在这个拦截器栈中使用了18个拦截器。简单说,struts2框架
在默认情况下,加载了18个拦截器。   

使用:

1. 创建一个Interceptor,自定义一个实现了Interceptor 的类

2. 声明:
    在struts-defalult.xml文件中   (源码资源文件中的配置) 

       <interceptor-stack name="defaultStack">
            <interceptor-ref name="exception"/>
            <interceptor-ref name="alias"/>
            <interceptor-ref name="servletConfig"/>
            ..............18个
       </interceptor-stack>

    <default-interceptor-ref name="defaultStack"/>
    <default-class-ref class="com.opensymphony.xwork2.ActionSupport" />

3. 注意
    只要显示声明了一个拦截器,name默认的拦截器就不起作用了

    配置如下:
        // 在interceptors中先配置拦截器,再整个拦截器栈,把默认的拦截器(那18个)
        // 添加进栈中
        <package>
            <interceptors>
                <interceptor name="bookInterceptor" class="com.uu.interceptor.BookInterceptor">
                    <param name="includeMethods">add,update,delete</param>
                </interceptor>
                <interceptor-stack name="myStack">
                    <interceptor-ref name="bookInterceptor" />
                    <interceptor-ref name="defaultStack" />
                </interceptor-stack>
            </interceptors>

        。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
            //配置global-results ,action 
            // 重点是:在要拦截的 action 中添加interceptor-ref 的属性

            <global-results>
                <result name="login">/login.jsp</result>
            </global-results>

            <action name="login" class="com.uu.action.LoginAction">
                <result name="input">/login.jsp</result>
                <result>/book.jsp</result>
            </action>
            <action name="book_*" class="com.uu.action.BookAction" method="{1}">
                <interceptor-ref name="myStack" />
            </action>
        </package>

源码查看拦截器原理分析:

    1.在StrutsPrepareAndExecuteFilter中查找
            在doFilter方法内有一句话 execute.executeAction (request, response, mapping) 执行Action操作.

    2.在executeAction执行过程中会访问Dispatcher类中的serviceAction,在这个方法中会创建一个
        ActionProxy proxy = config.getContainer().getInstance(ActionProxyFactory.class).createActionProxy(namespace, name, method, extraContext, true, false);
        这就是我们的Action的代理对象

    3.查看ActionInvocation,查看其实现类 DefaultActionInvocation.

        在其invoke方法中
        if (interceptors.hasNext()) {//判断是否有下一个拦截器.
            final InterceptorMapping interceptor = interceptors.next(); //得到一个拦截器
            String interceptorMsg = "interceptor: " + interceptor.getName();
            UtilTimerStack.push(interceptorMsg);
            try {
                    resultCode = interceptor.getInterceptor().intercept(DefaultActionInvocation.this); 
                    //调用得到的拦截器的拦截方法.将本类对象传递到了拦截器中。
                }
            finally {
                UtilTimerStack.pop(interceptorMsg);
            }
        } 

        通过源代码分析,发现在DefaultActionInvocation中就是通过递归完成所有的拦截调用操作.

关于interceptor与Filter区别

1. 拦截器是基于java 反射机制的,过滤器是基于函数回调的
2. 过滤器依赖于servlet容器,而拦截器不依赖与servlet容器
3. 拦截器只能对ACtion起作用,而过滤器则可以对几乎所有请求起作用
4. 拦截器可以访问Aciton上下文,值栈里的对象,而过滤器不能
5. 在Action的声明周期中,拦截器可以多次调用,而过滤器只能在容器初始化的时候调用
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值